template <class WndClass>
class screenhelpers : public WndClass
{
public:
typedef WndClass BaseClass;
typedef typename screenhelpers<WndClass> ThisClass;
CRect GetControlRect(CWnd *pControl) const
{
CRect rectWindow(0,0,0,0);
if (!pControl)
return rectWindow;
pControl->GetWindowRect(&rectWindow);
this->ScreenToClient(&rectWindow);
return rectWindow;
}
};
class MyDialog : public screenhelpers<CDialog>
{
public:
typedef screenhelpers<CDialog>::BaseClass MDialog;
MyDialog(int i);
MyDialog(LPCSTR lpszTemplateName, CWnd *pParentWnd);
MyDialog(int nIDTemplate, CWnd *pParentWnd);
};
MyDialog::MyDialog(int i)
{
BaseClass b;
}
MyDialog::MyDialog(LPCSTR lpszTemplateName, CWnd *pParentWnd)
: MyDialog::BaseClass(lpszTemplateName, pParentWnd)
{
}
MyDialog::MyDialog(int nIDTemplate, CWnd *pParentWnd)
: MyDialog::CDialog(nIDTemplate, pParentWnd)
{
}
我不明白为什么我似乎无法调用screenhelpers的基类。
如果MyDialog继承了屏幕截图,并且屏幕截图继承自CDialog,为什么我不能调用CDialog?
答案 0 :(得分:3)
构造函数中的初始化列表只能调用其直接父级的构造函数,而不能调用其直接构造函数。这就是为什么你不能直接初始化CDialog。
你的screenhelpers类没有定义一个带有两个参数的构造函数,所以它也不会起作用。即使您添加了这样的构造函数,我也不确定它是由typedefed名称引用它的有效语法,您可能需要使用screenhelpers<CDialog>
代替。
答案 1 :(得分:1)
如果允许MyDialog
构造函数调用CDialog
构造函数,后者将被调用两次:一次调用MyDialog
,一次调用screenhelpers
。那将是一场灾难。
如果您需要控制从CDialog
调用MyDialog
构造函数的方式,则需要使用虚拟继承:
template <class WndClass>
class screenhelpers : public virtual WndClass
然后您 (不仅仅是)能够从CDialog
调用MyDialog
构造函数。
请注意,这可能会对您的设计产生其他影响。