You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在C++ WinApp中监听其他前台应用的关闭事件?

问题根因

你现在监听的EVENT_OBJECT_DESTROY事件会在所有UI元素(包括子控件、菜单、临时弹窗等)销毁时触发,并不是只有主窗口关闭才会触发,所以会出现无意义的回调。


修复方案

  1. 回调函数内增加多层过滤逻辑,只保留符合「前台应用主窗口关闭」的事件
  2. 搭配EVENT_SYSTEM_FOREGROUND事件记录当前前台窗口的句柄,进一步缩小触发范围

具体修改代码

首先定义全局变量存储当前前台窗口句柄:

HWND g_currentForegroundHwnd = NULL;

修改窗口事件回调逻辑:

void CALLBACK WinEventProc( 
    HWINEVENTHOOK hWinEventHook,
    DWORD         event,
    HWND          hwnd,
    LONG          idObject,
    LONG          idChild,
    DWORD         dwEventThread,
    DWORD         dwmsEventTime 
) {
    // 过滤子控件事件,只处理窗口本身的事件
    if (idObject != OBJID_CLIENT || idChild != CHILDID_SELF) {
        return;
    }
    // 过滤非顶级窗口(排除子窗口、临时弹窗等)
    if (GetParent(hwnd) != NULL) {
        return;
    }
    // 过滤自身应用的窗口
    DWORD currentPid = GetCurrentProcessId();
    DWORD winPid = 0;
    GetWindowThreadProcessId(hwnd, &winPid);
    if (winPid == currentPid) {
        return;
    }
    // 过滤不可见窗口
    if (!IsWindowVisible(hwnd)) {
        return;
    }

    if (event == EVENT_SYSTEM_FOREGROUND) {
        // 记录当前前台窗口
        g_currentForegroundHwnd = hwnd;
        return;
    }

    if (event == EVENT_OBJECT_DESTROY) {
        // 只处理当前前台窗口的销毁事件
        if (hwnd == g_currentForegroundHwnd) {
            handleProcess(hwnd);
            // 处理完成后清空前台窗口记录
            g_currentForegroundHwnd = NULL;
        }
        return;
    }
}

修改钩子注册逻辑,同时注册前台窗口切换和窗口销毁事件:

...
// 注册窗口销毁事件钩子
winDestructionHook = SetWinEventHook(EVENT_OBJECT_DESTROY, EVENT_OBJECT_DESTROY,
                     NULL, WinEventProc, 0, 0, WINEVENT_OUTOFCONTEXT);
// 注册前台窗口切换事件钩子
foregroundHook = SetWinEventHook(EVENT_SYSTEM_FOREGROUND, EVENT_SYSTEM_FOREGROUND,
                     NULL, WinEventProc, 0, 0, WINEVENT_OUTOFCONTEXT);
...

注意事项

  • 程序退出时要调用UnhookWinEvent释放两个钩子,避免资源泄漏
  • 如果需要捕获无标题栏的特殊应用窗口,可以去掉主窗口样式校验逻辑,只保留父窗口为空的判断即可
  • 该方案支持所有常规关闭操作的监听,包括右上角叉号、Ctrl+F4、任务管理器结束进程等触发主窗口销毁的场景

内容的提问来源于stack exchange,提问作者Adam

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.07 04:54:03