尽管使用了setwindowpos,为什么窗户没有达到顶峰?

时间:2016-06-30 09:40:51

标签: c++ mfc mfc-feature-pack

 m_pMainWnd->SetForegroundWindow(); 
m_pMainWnd->SetWindowPos(&CWnd::wndTop, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE);

我使用上面的线条将我的一个窗户顶到顶部。但令我失望的是,一切都没有发生。 虽然使用<& CWnd :: wndTopMost>是最重要的窗口,但没有关注它。 VS15,mfc

2 个答案:

答案 0 :(得分:5)

对不起,但你要问的不是(琐碎​​)可能的。您的窗口没有出现的原因是因为您的应用程序不是前台应用程序(即负责前台窗口的应用程序)。

来自manual page

  

使用SetWindowPos将窗口置于顶部,即进程   拥有该窗口必须具有SetForegroundWindow权限。

当然,你做到了。但是,您没有检查其返回代码。以下是man page所说的内容:

  

系统限制哪些进程可以设置前景窗口。一个   只有在以下情况之一时,进程才能设置前台窗口   条件是真的:

     
      
  • 该过程是前台过程。
  •   
  • 该过程由前台进程启动。
  •   
  • 该过程收到了最后一个输入事件。
  •   
  • 没有前台进程。
  •   
  • 正在调试该过程。
  •   
  • 前台进程不是现代应用程序或开始屏幕。
  •   
  • 未锁定前景(请参阅LockSetForegroundWindow)。
  •   
  • 前台锁定超时已过期(请参阅SystemParametersInfo中的SPI_GETFOREGROUNDLOCKTIMEOUT)。
  •   
  • 没有菜单处于活动状态。
  •   

这些限制的总和是,您很可能无法将窗口变成前景窗口,而且无法将其置于前面。

有办法解决这个问题。您可以确保前台进程调用SetForegroundWindow。不幸的是,这并没有运行你的代码。

有一次我必须这样做,我使用hooks将我的代码注入前台窗口的过程。这不是初学者的伎俩。如果你不愿意这样做,那就没有办法做你想做的事。

编辑添加: Windows试图阻止您执行您尝试执行的操作。从另一个应用程序窃取焦点会给用户带来非常差的UI体验。请重新考虑您是否希望做您想做的事情。

答案 1 :(得分:-2)

您应该使用CWnd :: wndTopMost而不是CWnd :: wndTop。 即使停用,CWnd :: wndTopMost也会使窗口保持最顶层。

参见文档: https://msdn.microsoft.com/en-us/library/a1yzfz6d.aspx

关于两者之间差异的一篇新旧文章: https://blogs.msdn.microsoft.com/oldnewthing/20051121-10/?p=33263