如何在Javascript/Node/Electron中监听耳机/头戴式耳机按键事件?
浏览器端 JavaScript 解决方案
- 确保媒体上下文存在:
navigator.mediaSession需要页面关联活跃的媒体播放上下文,仅绑定事件但无媒体元素时,部分系统(尤其是移动端)不会响应耳机按键。示例:
// 创建媒体元素并关联到 mediaSession const audio = new Audio(); audio.src = 'your-audio-source.mp3'; // 添加媒体元数据(部分系统需要此步骤识别活跃媒体) navigator.mediaSession.metadata = new MediaMetadata({ title: '示例音频', artist: '示例作者', album: '示例专辑', }); // 绑定你的原有事件(现在有媒体上下文支撑) navigator.mediaSession.setActionHandler('play', () => { console.log('play'); audio.play(); }); navigator.mediaSession.setActionHandler('pause', () => { console.log('pause'); audio.pause(); }); navigator.mediaSession.setActionHandler('previoustrack', () => { console.log('previoustrack') }); navigator.mediaSession.setActionHandler('nexttrack', () => { console.log('nexttrack') });
- 降级方案:监听键盘事件:部分耳机按键会触发系统级键盘事件,可直接捕获:
document.addEventListener('keydown', (e) => { switch(e.code) { case 'MediaPlayPause': console.log('耳机播放/暂停'); break; case 'MediaNextTrack': console.log('耳机下一曲'); break; case 'MediaPreviousTrack': console.log('耳机上一曲'); break; } });
注意:浏览器需处于 HTTPS 环境(localhost 除外),移动端浏览器需用户主动交互后才能绑定媒体事件。
Node.js 解决方案
Node.js 无原生媒体键监听 API,需借助第三方库监听 HID 设备(耳机属于 HID 外设),推荐使用 node-hid:
- 安装依赖:
npm install node-hid
- 扫描并监听耳机设备:
const HID = require('node-hid'); // 列出所有 HID 设备,筛选你的耳机(可通过产品名称或 ID 定位) const devices = HID.devices(); const headphoneDevice = devices.find(d => d.product.includes('耳机') || d.productId === 你的设备ID); if (headphoneDevice) { const hid = new HID.HID(headphoneDevice.path); hid.on('data', (data) => { // 不同耳机的按键数据格式不同,需自行抓包解析字节值 switch(data[2]) { case 0x01: // 示例:播放/暂停对应字节 console.log('耳机播放/暂停'); break; case 0x02: // 示例:下一曲对应字节 console.log('耳机下一曲'); break; case 0x03: // 示例:上一曲对应字节 console.log('耳机上一曲'); break; } }); hid.on('error', (err) => { console.error('HID设备错误:', err); }); } else { console.log('未找到耳机设备'); }
Electron 解决方案
Electron 支持两种主流方案,结合主进程与渲染进程实现:
1. 主进程用 globalShortcut 监听系统级媒体键
// main.js 主进程代码 const { app, globalShortcut, BrowserWindow } = require('electron'); let mainWindow; app.whenReady().then(() => { mainWindow = new BrowserWindow({ width: 800, height: 600 }); mainWindow.loadFile('index.html'); // 注册媒体键快捷键 globalShortcut.register('MediaPlayPause', () => { console.log('耳机播放/暂停'); // 向渲染进程发送事件同步状态 mainWindow.webContents.send('media-key', 'play-pause'); }); globalShortcut.register('MediaNextTrack', () => { console.log('耳机下一曲'); mainWindow.webContents.send('media-key', 'next'); }); globalShortcut.register('MediaPreviousTrack', () => { console.log('耳机上一曲'); mainWindow.webContents.send('media-key', 'previous'); }); }); app.on('will-quit', () => { // 退出前注销所有快捷键 globalShortcut.unregisterAll(); });
2. 渲染进程结合 mediaSession
与浏览器端方案一致,确保渲染进程中有活跃的媒体元素,再绑定 mediaSession 事件,Electron 渲染进程支持完整的 navigator.mediaSession API。
内容的提问来源于stack exchange,提问作者Christian
相关产品推荐
相关产品推荐

