【问题标题】:Hide an MFC dialog window隐藏 MFC 对话窗口
【发布时间】:2012-10-12 10:16:40
【问题描述】:

我编写了一个基于 MFC 对话框的应用程序,该应用程序由另一个应用程序启动。目前,我还没有添加任何代码。这只是我得到的默认文件。其他应用程序可以成功启动我的应用程序。

我试图在其他应用程序启动时隐藏我的应用程序的窗口。

BOOL CMyApp::InitInstance()
{
    CMyAppDlg dlg;
    m_pMainWnd = &dlg;        

    INT_PTR nResponse = dlg.DoModal();

    if (nResponse == IDOK)
    {
    }
    else if (nResponse == IDCANCEL)
    { 
    }

    return FALSE;
}

我尝试使用:

dlg.ShowWindow(SW_HIDE) 

但它仍然没有隐藏窗口。

我怎样才能完成这项任务?

【问题讨论】:

  • 您的CMyAppDlg 是否继承自CDialog
  • 谢谢。它继承自CDialogEx
  • 你的对话是无模式的吗? CMyAppDlg 不会显示任何内容。如果你调用 dlg.DoModal(),那么代码将不会在它之后到达 ShowWindow。
  • @ixe013,感谢您的回复。我打电话给dlg.DoModal()。请查看更新后的代码。
  • 这不是Hiding an MFC dialog box的复制品吗?

标签: winapi visual-c++ mfc


【解决方案1】:

我建议你在某个地方遇到另一个问题。

如果您创建一个全新的空白 MFC 应用程序 (Visual Studio 2010),那么在 App::InitInstance 中,设置 SW_HIDE 而不是 SW_SHOW确实会导致结果窗口被隐藏。

BOOL CProj1App::InitInstance()
{

// boilerplate code
      . . . 

// The one and only window has been initialized, so show and update it
m_pMainWnd->ShowWindow(SW_HIDE);   // WORKS!
m_pMainWnd->UpdateWindow();

return TRUE;
}

【讨论】:

  • 我尝试了你的解决方案,它构建完美,但是当我运行它时,它在m_pMainWnd->ShowWindow(SW_HIDE); 执行后中断。
  • ShowWindow() 中,它在ASSERT(::IsWindow(m_hWnd) || (m_pCtrlSite != NULL)); 之后中断
  • @chintan,我同意,我可以复制你说的话。上面的代码在您使用向导创建“单文档”应用程序时有效,但在您创建“对话”应用程序时无效。我建议创建一个“单一文档”应用程序并查看 InitInstance 的样板实现有何不同。
  • 非常感谢您的回复。我将尝试创建一个“Signle Document”应用程序并回复。再次感谢。
  • @chintan - 我再说一遍......看看 InitInstance 的样板实现有何不同。我建议您使用 SingleDocument 作为您的灵魂。我建议您查看为 SingleDocument 生成的代码,以找出您的解决方案不起作用的原因。
【解决方案2】:

一旦您致电DoModal,您的对话就注定会显示出来。只有一种解决方法可以成功避免焦点/闪烁问题。在这里查看我的答案:Hiding an MFC dialog box

因此,您的代码应如下所示:

BOOL CMyApp::InitInstance() 
{ 
    CMyAppDlg dlg;
    dlg.SetVisible(FALSE); // Sets m_visible flag to FALSE.

    m_pMainWnd = &dlg;         

    INT_PTR nResponse = dlg.DoModal(); 

    if (nResponse == IDOK) 
    { 
    } 
    else if (nResponse == IDCANCEL) 
    {  
    } 

    return FALSE; 
} 

【讨论】:

  • 此方法在 Windows 10 中按 Alt + Tab 时不会隐藏应用程序。
【解决方案3】:

解决上述问题。 InitInstance 代码应该如下:

BOOL CMyApp::InitInstance()
{
    CWinApp::InitInstance();
    AfxEnableControlContainer();

    CMyAppDlg dlg;
    dlg.Create(IDD_MyAppUI_DIALOG,NULL);
    dlg.ShowWindow(SW_HIDE);
    dlg.UpdateWindow();
    m_pMainWnd = &dlg;

    return TRUE;
}

【讨论】:

  • 在离开 InitInstance 作用域时不会销毁 dlg 吗?
  • 是的,它将被销毁。所以这段代码最终会崩溃。如果在堆上创建对话框,@chintan 提出的解决方案将起作用。
  • 你是不是简单地尝试了 dlg.ShowWindow(SW_MINIMIZED); ?
  • 这没有回答原始问题。显然,隐藏 非模态 对话框是轻而易举的事。问题在于DoModal() 的逻辑。因此,解决方法找到了here
【解决方案4】:

首先让我解决之前解决方案的一些问题。

chintan s: 当函数超出范围时,确实对话框将被终止。如果将对话框声明为应用类的成员变量,这将是一个有效的解决方案。

维基: 不需要调用 Windows API,因为对话框是从 CWnd 派生的,它继承了 ShowWindow 成员,只接受一个参数:show 命令。

ixe013: 此解决方案将起作用,但是,在对话框隐藏之前,它会闪烁,因为在调用 OnInitDialog 之前调用了 ShowWindow。

皮特: 这不起作用,因为模态对话框在 m_pMainWnd 分配任何值之前启动。

解决方案由ixe013指出。

这是目前唯一可行的解​​决方案,但您必须在对话框类中声明 member 变量,如文章中所述。

【讨论】:

    【解决方案5】:

    您必须从内部隐藏对话框。

    1. 重载 OnInitDialog
    2. 调用 CDialogEx::OnInitDialog()
    3. 隐藏窗口并返回

    这里是代码

    BOOL CMyAppDlg::OnInitDialog()
    {
        BOOL result = CDialogEx::OnInitDialog();
    
        this->ShowWindow(SW_HIDE);
    
        return result;  // return TRUE  unless you set the focus to a control
    }
    

    another method with a sentinel value,YMMV。

    【讨论】:

      【解决方案6】:

      showWindow 方法有 2 个变量。

      • 窗口句柄
      • nCmdShow(控制窗口的显示方式)

        BOOL WINAPI 显示窗口( HWND hWnd, int nCmdShow );

        HWND hWnd = GetSafeHwnd();

        显示窗口(hWnd,SW_HIDE);

      HERE

      【讨论】:

      • 感谢您的回复。但它说m_visible 未定义。
      • 再次感谢,但现在它说 GetSafeHwnd() 未定义。
      • 是否包含 Afxwin.h 头文件
      • 不需要调用GLOBAL函数::ShowWindow(...)。使用 this->ShowWindow(...) 只是它的一个包装器。
      猜你喜欢
      • 2012-01-05
      • 1970-01-01
      • 1970-01-01
      • 2012-04-16
      • 1970-01-01
      • 1970-01-01
      • 2010-12-04
      • 1970-01-01
      • 2017-01-02
      相关资源
      最近更新 更多