最近被这个向导折腾,记录一下
首先CPropertySheet做向导是个不错的东西,一个设置:
Sheet.SetWizardMode();
然后把页面AddPage进去就可以了,但是功能实在有限,尤其是如果向导页面是多分支的情况。虽然它有RemovePage和AddPage的功能,但是用起来实在是不方便,因为RemovePage会导致窗体对话框析构,这会带来很多不方便,另外,加入Sheet的对话框页面不需要自己Create出来就可以使用,这些特性都要注意。
向导页诡异特性:
1.对话框页面不需要自己Create
2.OnSetActive会自动引发页面的UpdateData(FALSE)
3.RemovePage会导致对话框资源析构
4.页面被显示的时候不引发OnInitDialog
注意第三条,这样的话我就没法在产生分支的时候随意RemovePage而保持用户已经设置的数据,造成多分支的情况无法实现。
所以自己设计一套方法来实现多分支:
1.新建MFC扩展DLL工程
2.包含头文件MsgDef.h
3.加入Dialog资源,加入对应的CPropertyPage类,如CDlgA
4.DLLMain所在文件中声明extern CDlgA *g_pDlgA;
5.DLLMain函数的DLL_PROCESS_ATTACH段g_pDlgA = new CDlgA();
6.DLLMain函数的DLL_PROCESS_DETACH段删除g_pDlgA
7.全局声明和函数
CDlgIIS *g_pDlgIIS = NULL;
CPropertyPage* GetPropertyPage()
{
return g_pDlgIIS;
}
8.def文件中声明接口GetPropertyPage
9.MsgDef.h中增加可能影响后面页变化的数据的所有排列组合,用一常量代替
10.响应消息
LRESULT CDlgA::OnWizardBack()
{
// TODO: Add your specialized code here and/or call the base class
if (!UpdateData())
{
return 0;
}
CPropertySheet * pSheet = (CPropertySheet *)AfxGetMainWnd();
pSheet->SendMessage(SOCM_BACK);
return CPropertyPage::OnWizardBack();
}
LRESULT CDlgA::OnWizardNext()
{
// TODO: Add your specialized code here and/or call the base class
if (!UpdateData())
{
return 0;
}
CWnd * pSheet = (CWnd *)AfxGetMainWnd();
pSheet->SendMessage(SOCM_NEXT,WM_USER + SOCM_DATA_*);//这里决定下个页面是谁,填写下个页面的消息ID
return CPropertyPage::OnWizardNext();
}
11.响应SOCM_SAVE消息,此消息在Finish按钮点击后由Sheet依次发送给所有的页
12.编译DLL,拷贝到主程序目录下
13.修改配置文件类似下面
<Page Text="AAA" DLL="DLLA.dll" ID="1010" />
14.OK
特性:
1.DLL和主程序耦合度低,DLL中仅提供一个接口,通讯也只通过一个Next消息实现
2.扩展页在DLL中实现,扩展性好
(待续)
首先CPropertySheet做向导是个不错的东西,一个设置:
Sheet.SetWizardMode();
然后把页面AddPage进去就可以了,但是功能实在有限,尤其是如果向导页面是多分支的情况。虽然它有RemovePage和AddPage的功能,但是用起来实在是不方便,因为RemovePage会导致窗体对话框析构,这会带来很多不方便,另外,加入Sheet的对话框页面不需要自己Create出来就可以使用,这些特性都要注意。
向导页诡异特性:
1.对话框页面不需要自己Create
2.OnSetActive会自动引发页面的UpdateData(FALSE)
3.RemovePage会导致对话框资源析构
4.页面被显示的时候不引发OnInitDialog
注意第三条,这样的话我就没法在产生分支的时候随意RemovePage而保持用户已经设置的数据,造成多分支的情况无法实现。
所以自己设计一套方法来实现多分支:
1.新建MFC扩展DLL工程
2.包含头文件MsgDef.h
3.加入Dialog资源,加入对应的CPropertyPage类,如CDlgA
4.DLLMain所在文件中声明extern CDlgA *g_pDlgA;
5.DLLMain函数的DLL_PROCESS_ATTACH段g_pDlgA = new CDlgA();
6.DLLMain函数的DLL_PROCESS_DETACH段删除g_pDlgA
7.全局声明和函数
CDlgIIS *g_pDlgIIS = NULL;
CPropertyPage* GetPropertyPage()
{
return g_pDlgIIS;
}
8.def文件中声明接口GetPropertyPage
9.MsgDef.h中增加可能影响后面页变化的数据的所有排列组合,用一常量代替
10.响应消息
LRESULT CDlgA::OnWizardBack()
{
// TODO: Add your specialized code here and/or call the base class
if (!UpdateData())
{
return 0;
}
CPropertySheet * pSheet = (CPropertySheet *)AfxGetMainWnd();
pSheet->SendMessage(SOCM_BACK);
return CPropertyPage::OnWizardBack();
}
LRESULT CDlgA::OnWizardNext()
{
// TODO: Add your specialized code here and/or call the base class
if (!UpdateData())
{
return 0;
}
CWnd * pSheet = (CWnd *)AfxGetMainWnd();
pSheet->SendMessage(SOCM_NEXT,WM_USER + SOCM_DATA_*);//这里决定下个页面是谁,填写下个页面的消息ID
return CPropertyPage::OnWizardNext();
}
11.响应SOCM_SAVE消息,此消息在Finish按钮点击后由Sheet依次发送给所有的页
12.编译DLL,拷贝到主程序目录下
13.修改配置文件类似下面
<Page Text="AAA" DLL="DLLA.dll" ID="1010" />
14.OK
特性:
1.DLL和主程序耦合度低,DLL中仅提供一个接口,通讯也只通过一个Next消息实现
2.扩展页在DLL中实现,扩展性好
(待续)
回复Comments
{commenttime}{commentauthor}
{CommentUrl}
{commentcontent}