Electron如何检测Mac或Windows系统是否正在被屏幕录制?
查询屏幕录制状态:Mac/Windows原生方法与Electron实现
一、Mac系统原生检测方式
- 实时状态检测:使用Core Graphics框架的
CGDisplayStreamIsRecording函数,传入显示器ID(主显示器为0)即可判断该显示器是否正在被录制,这个API是公开可用的。 - 状态监听:通过
NSWorkspace注册NSWorkspaceScreenCaptureDidStartNotification和NSWorkspaceScreenCaptureDidStopNotification通知,能在屏幕录制开始/结束时收到回调,适合实时监听场景。 - 命令行快速排查:可以通过
pgrep -x ScreenCapture检查系统自带的屏幕录制进程是否在运行,但第三方录制工具可能不会触发这个进程,仅作参考。
二、Windows系统原生检测方式
- 系统事件监听:通过
user32.dll的SetWinEventHook函数,监听EVENT_SYSTEM_CAPTURESTART(0x0014)和EVENT_SYSTEM_CAPTUREEND(0x0015)事件,这两个事件会在屏幕录制或全局截图启动/停止时触发,覆盖绝大多数录制工具。 - API调用监控:Windows 8及以上系统中,多数录制工具会调用
CreateDesktopDuplicationAPI获取桌面帧,可以通过进程钩子或系统监控工具检测该API的调用情况,但实现复杂度较高。
三、Electron框架中的实现方案
Mac平台
Electron主进程可通过ffi-napi(Node.js原生API绑定库)封装Core Graphics的CGDisplayStreamIsRecording函数,实现实时检测:
const ffi = require('ffi-napi'); const coreGraphics = ffi.Library('/System/Library/Frameworks/CoreGraphics.framework/CoreGraphics', { 'CGDisplayStreamIsRecording': ['bool', ['uint32_t']] }); // 检测主显示器录制状态 const isRecording = coreGraphics.CGDisplayStreamIsRecording(0); console.log('主显示器是否被录制:', isRecording);
注意:应用需要提前获取屏幕录制权限,否则API会返回false或抛出权限错误。
Windows平台
同样使用ffi-napi封装user32.dll的事件钩子函数,监听屏幕录制相关系统事件:
const ffi = require('ffi-napi'); const ref = require('ref-napi'); const user32 = ffi.Library('user32.dll', { 'SetWinEventHook': ['pointer', ['uint32_t', 'uint32_t', 'pointer', 'pointer', 'uint32_t', 'uint32_t', 'uint32_t']], 'UnhookWinEvent': ['bool', ['pointer']] }); const EVENT_SYSTEM_CAPTURESTART = 0x0014; const EVENT_SYSTEM_CAPTUREEND = 0x0015; // 定义事件回调 const winEventCallback = ffi.Callback('void', ['pointer', 'uint32_t', 'pointer', 'int32_t', 'int32_t', 'uint32_t', 'uint32_t'], (hookHandle, eventType) => { if (eventType === EVENT_SYSTEM_CAPTURESTART) { console.log('屏幕录制已开始'); } else if (eventType === EVENT_SYSTEM_CAPTUREEND) { console.log('屏幕录制已结束'); } } ); // 注册钩子 const hook = user32.SetWinEventHook(EVENT_SYSTEM_CAPTURESTART, EVENT_SYSTEM_CAPTUREEND, null, winEventCallback, 0, 0, 0); // 退出时清理钩子 process.on('exit', () => { user32.UnhookWinEvent(hook); });
注意:部分安全软件可能会拦截系统钩子操作,需要在应用文档中说明相关权限要求。
内容的提问来源于stack exchange,提问作者Scary Monsters
相关产品推荐
相关产品推荐

