说我有两个主要的类,Application
和ApplicationGUI
。 Application
做很多事情,可以在不知道ApplicationGUI
存在的情况下愉快地运行。 ApplicationGUI
通过许多方式链接到Application
,它可能具有50或100个不同的旋钮,可以改变Application
的行为。ApplicationGUI
是一个分层结构,因此它具有许多ControlGroup
实例,每个实例包含任意数量的Button
和Knob
,甚至包含另一个ControlGroup
。
当前设计:实例化ApplicationGUI
(Application
已经使用一组默认参数运行)后,我将Application
参数的指针传递给GUI的各个组件。例如:
my_gui.sound_controlgroup.knob.link_to_param(&(my_application.volume));
如果我需要做一些更复杂的事情,说调用
Application
,my_application.update_something()
的成员函数,这是怎么做的?简单的答案是将指向my_application的指针传递给
my_gui.sound_controlgroup.knob
,但是如果我只需要调用my_application的功能之一,就好像我在给我的旋钮一个选项来更改它甚至应该了解的所有内容(my_application.update_something_unrelated()
, 例如)。在这种情况下,最干净的方法是什么?另外,这要么要求公开
ApplicationGUI
的所有子组件,要么要求在层次结构的每个阶段都具有一个功能,以将该指针转发到底层。这导致了很多功能。这是带有大量旋钮的UI的必然结果吗? 最佳答案
快速简短答案
为了实现您的非GUI相关的Application
对象和GUIApplication
对象之间的交互,我建议应用“属性,方法和事件处理程序”范例。
扩展复杂答案
G.U.I.开发是O.O.P.最实用的实现之一理论。
什么是“属性,方法和事件处理程序”范例?
这意味着非GUI类和GUI类的构建都应具有:
“事件”(处理程序)也称为“信号”,并通过函数指针实现。不确定,但是,我认为您的“旋钮”就像事件处理程序。
这是一种应用
my_application.update_something_unrelated()
的技术,您可以在问题中使用它。由于C++与Java一样没有属性语法,因此可以使用“getter”和“setter”方法,也可以使用“属性”模板。
例如,如果您的应用程序具有
Close
方法,则可以声明类似以下示例的内容。注意:它们不是完整的程序,只是一个想法:
// Applications.hpp
public class BaseApplicationClass
{
// ...
};
public class BaseApplicationClientClass
{
// ...
};
typedef
void (BaseApplicationClientClass::*CloseFunctor)
(BaseApplicationClass App);
public class ApplicationClass: public BaseApplicationClass
{
// ...
public:
Vector<BaseApplicationClientClass::CloseFunctor>
BeforeCloseEventHandlers;
Vector<BaseApplicationClientClass::CloseFunctor>
AfterCloseEventHandlers;
protected:
void ConfirmedClose();
public:
virtual void Close();
} Application;
// Applications.cpp
void ApplicationClass::ConfirmedClose()
{
// do close app. without releasing from memory yet.
} // void ApplicationClass::ConfirmedClose()
void ApplicationClass::Close()
{
// Execute all handlers in "BeforeCloseEventaHandlers"
this.ConfirmedClose();
// Execute all handlers in "AfterCloseEventaHandlers"
} // void ApplicationClass::Close()
// AppShells.cpp
public class AppShell: public BaseApplicationClientClass
{
// ...
};
void AppShell::CloseHandler(ApplicationClass App)
{
// close GUI
} // void AppShell.CloseHandler(ApplicationClass App)
void AppShell::setApp(ApplicationClass App)
{
App->BeforeCloseEventHandlers->add(&this.CloseHandler);
} // void AppShell.setApp(ApplicationClass App)
void main (...)
{
ApplicationClass* AppKernel = new ApplicationClass();
ApplicationGUIClass* AppShell = new ApplicationGUIClass();
AppShell.setApp(App);
// this executes "App->Run();"
AppShell->Run();
free AppShell();
free AppKernel();
}
更新:修复了从全局函数指针(也称为“全局函子”)到对象函数指针(也称为“方法函子”)的类型声明。
干杯。
关于c++ - 制作GUI时干净的OOP设计,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/29580090/