【问题标题】:Problem with a non-modal, self-closing dialog in combination with other dialogs与其他对话框结合的非模态、自动关闭对话框的问题
【发布时间】:2021-09-19 19:59:32
【问题描述】:

这是关于 MFC-MDI 应用程序的。我添加了一个弹出窗口,它应该在一段时间后关闭。因此,我创建了一个非模态对话框

CPopupDlg* pDlg = new CPopupDlg(this);
if (pDlg)
{
    pDlg->Create(IDD, this);
    pDlg->ShowWindow(SW_SHOW);
}

它将被定时器关闭并在 OnNcDestroy() 中销毁

void CPopupDlg::OnTimer(UINT_PTR nIDEvent)
{
    if (nIDEvent == m_CounterEventID)
    {
        KillTimer(nIDEvent);
        EndDialog(IDCANCEL);
        DestroyWindow();
    }
}

void CPopupDlg::OnNcDestroy()
{
    __super::OnNcDestroy();
    delete this;
}

我的问题是在打开 CPopupDlg 时可能会出现许多其他(模式)对话框和消息框。这些模式对话框通常不会在我的项目中指定父窗口(@98​​7654323@constructor 和 pParentWnd=NULL)。因此,CDialog::DoModal() 方法使用::GetLastActivePopup() 来确定其父窗口。 CPopupDlg 对话框被选为父窗口。因此,当CPopupDlg 窗口被计时器关闭时,DoModal() 崩溃。

我该如何解决这个问题?

  1. 有没有办法从::GetLastAcitvePopup() 的结果中排除CPopupDlg 对话框?

  2. 有时我看到,非模态对话框使用RunModalLoop()。这会是解决方案吗?

    popupDlg.Create(IDD, this);
    popupDlg.RunModalLoop(MLF_SHOWONIDLE);
    popupDlg.DestroyWindow();
  1. 如果弹出对话框永远不会被关闭和销毁,而只是隐藏,会发生什么情况。如果popupDlg.ShowWindow(SW_HIDE) 被调用,其他模态对话框窗口(它们是CPopupDlg wnd 的不受欢迎的子级)也会消失吗?

【问题讨论】:

  • 我猜提供实际的父指针是不可行的?我们的应用程序中有类似的情况,但我们意识到为模态对话框提供实际所需的父级的重要性(与始终使用默认 NULL 相比)。我什至调整了 CDialog 派生的 ctor 签名以将 reference 指向 CWnd 而不是指针,即要求提供父级。
  • @franji1 这不是一个选项,但谢谢。我找到了解决办法。

标签: visual-c++ mfc dialog cdialog


【解决方案1】:

我的解决方案是将弹出窗口创建为单独的桌面子窗口。它不是应用程序的子窗口,不会被::GetLastActivePopup() 选择。

CPopupDlg* pDlg = new CPopupDlg(this);
if (pDlg)
{
    pDlg->Create(IDD, GetDesktopWindow());
    pDlg->ShowWindow(SW_SHOW);
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多