MFC中如何修改非模态对话框的父窗口?能否临时变更父窗口?
MFC运行时修改非模态对话框父窗口的方案
完全可以修改已创建窗口的父窗口关系,MFC和Windows原生API都支持该操作,不需要在创建窗口时提前指定。
核心实现API
使用CWnd类内置的SetParent方法即可完成父窗口切换,函数原型如下:
CWnd* SetParent(CWnd* pWndNewParent);
该方法返回修改前的原父窗口指针,你可以提前保存该指针,用于后续恢复父窗口关系。
对应场景的操作步骤
- 弹出模态对话框C之前,先切换非模态对话框B的父窗口为C:
// 保存B的原父窗口(也就是对话框A的指针) CWnd* pBOriginalParent = pDlgB->SetParent(pDlgC);
- 正常弹出模态对话框C即可,此时B的从属关系将绑定到C:
- B的Z序会跟随C同步变化
- C最小化/移动时B会同步隐藏/跟随移动
- B不会出现在C的下层被遮挡
- 模态对话框C关闭并返回后,将B的父窗口恢复为原窗口A:
pDlgB->SetParent(pBOriginalParent);
注意事项
SetParent不会自动转换窗口的坐标体系:窗口的位置坐标默认相对于父窗口的客户区,如果你需要B在切换父窗口后保持屏幕上的原有显示位置,需要手动做坐标转换:
CRect rcDlgB; pDlgB->GetWindowRect(&rcDlgB); // 获取B的屏幕坐标 pDlgC->ScreenToClient(&rcDlgB); // 转换为C的客户区坐标 // 调整B的位置,保持大小和Z序不变 pDlgB->SetWindowPos(NULL, rcDlgB.left, rcDlgB.top, 0, 0, SWP_NOSIZE | SWP_NOZORDER);
确保模态对话框C完全销毁前完成B的父窗口恢复操作,避免出现悬空指针访问崩溃。
内容的提问来源于stack exchange,提问作者Andrew Truckle
相关产品推荐
相关产品推荐

