1

有没有办法撤消对 的调用AllowSetForegroundWindow(ASFW_ANY)

大图:

  • 我想要一次运行我的 exe 的单个进程。
  • 为了实现它,进程使用命名管道相互通信,如果进程已经存在,则必须将其窗口置于前面。
  • 为此,必须AllowSetForegroundWindow()使用现有的进程 ID 设置最新进程。
    • 我不想获取进程 ID(对不起我的懒惰),所以我打算做的是: 1.AllowSetForegroundWindow()使用 ASFW_ANY 调用 2. 以防万一发生错误,撤消调用,AllowSetForegroundWindow()以便其他人无法窃取焦点从我的过程中。

简而言之,我希望仅在特定时间窗口内允许其他进程从我身上窃取焦点......

任何人早些时候遇到过类似的问题,并找到任何解决方法?

另外,如果您有更好的建议/替代方案,请告诉我...

4

2 回答 2

2

根据文档,目标进程(可能包括“任何”)将在您下次调用时失去从您那里窃取焦点的能力AllowSetForegroundWindow

换句话说,听起来您一次只能激活一个这样的权限。

因此,您应该能够通过使用一些不存在的 ID 或您自己的进程 ID 调用来取消权限。这是理论,但是我没有测试过。

我个人只是通过命名管道发送目标进程 ID。

于 2012-04-04T14:58:17.903 回答
0

如果我了解您的主要要求是一次只运行一个应用程序实例。如果您描述的其他所有内容仅服从此要求,而不是某个更大计划的一部分,那么有一种更简单的方法可以实现这一目标。

您可以在应用程序启动时创建一个全局命名互斥锁。所有其他实例都会将此互斥锁视为已设置,并立即退出。这是它的快速和肮脏:

// Multiple instances detection
HANDLE my_mutex = ::CreateMutex(NULL, FALSE, "Global\\MyCuteFluffyMutex" );

int create_mutex_error = ::GetLastError();
bool already_running =
          ( my_mutex && ( create_mutex_error == ERROR_ALREADY_EXISTS ))
       || ( create_mutex_error == ERROR_ACCESS_DENIED );

if ( !already_running ) {
  // Run my application
}

::CloseHandle(my_mutex);

有关更详尽的信息CreateMutex及其参数,请参阅文档

于 2012-04-04T15:12:07.783 回答