Zer*_*ide 3 javascript gmail javascript-events google-chrome-extension
我正在编写一个浏览器扩展,需要将处理程序附加到所有页面上的keyup和keydown事件.我可以使用以下内容脚本代码很好地工作.
document.addEventListener("keydown",keyDown, true);
document.addEventListener("keyup", keyUp, true);
Run Code Online (Sandbox Code Playgroud)
我不能让这个在Gmail中运行.具体来说,在编写新电子邮件的正文时,我无法使其工作.它将适用于我测试过的其他任何地方.我认为问题是因为Gmail正在调用stopPropagation所有键盘事件,但很难调试其最小化代码.我认为将第3个参数设置为true会导致在CAPTURE_PHASE此期间捕获事件,但这不起作用.
如何使用Google Chrome内容脚本在Gmail中编写新主体时捕获keyup和捕获keydown事件?
编辑:
通过添加"all_frames": true,到我的清单,我确保将我的内容脚本注入到DOM的所有iframe中.我甚至尝试使用以下代码:
document.addEventListener("DOMNodeInserted", function (event) {
if(event.type === "DOMNodeInserted") {
if(event.srcElement.nodeName === "IFRAME") {
console.log(event.srcElement.nodeName + " iframe detected");
event.srcElement.addEventListener("keydown", function(kevent) {
document.dispatchEvent(kevent);
}, true);
event.srcElement.addEventListener("keyup", function(kevent) {
document.dispatchEvent(kevent);
}, true);
}
}
},true);
Run Code Online (Sandbox Code Playgroud)
这仍然无法解决Gmail的问题.
您的代码不起作用,因为它event.srcElement引用了<iframe>元素,而不是其内容.要访问其内容文档,您必须等待加载(onload或轮询)frame.contentDocument帧,然后使用访问该帧.
从Chrome 37.0.1995.0开始,您还可以使用match_about_blank(with all_frames)在about:blank捕获事件的帧中插入内容脚本,并将其发送到父内容脚本.
以下是原始构思(使用轮询)的实现示例:
相关部分manifest.json:
"content_scripts": [{
"matches": ["*://mail.google.com/*"],
"js": ["contentscript.js"],
"run_at": "document_end"
}],
Run Code Online (Sandbox Code Playgroud)
contentscript.js
function keyDown(e) {console.log(e.which);}; // Test
function keyUp(e) {console.log(e.keyCode);}; // Test
(function checkForNewIframe(doc) {
if (!doc) return; // document does not exist. Cya
// Note: It is important to use "true", to bind events to the capturing
// phase. If omitted or set to false, the event listener will be bound
// to the bubbling phase, where the event is not visible any more when
// Gmail calls event.stopPropagation().
// Calling addEventListener with the same arguments multiple times bind
// the listener only once, so we don't have to set a guard for that.
doc.addEventListener('keydown', keyDown, true);
doc.addEventListener('keyup', keyUp, true);
doc.hasSeenDocument = true;
for (var i = 0, contentDocument; i<frames.length; i++) {
try {
contentDocument = iframes[i].document;
} catch (e) {
continue; // Same-origin policy violation?
}
if (contentDocument && !contentDocument.hasSeenDocument) {
// Add poller to the new iframe
checkForNewIframe(iframes[i].contentDocument);
}
}
setTimeout(checkForNewIframe, 250, doc; // <-- delay of 1/4 second
})(document); // Initiate recursive function for the document.
Run Code Online (Sandbox Code Playgroud)
请注意,我使用轮询而不是DOM突变事件,因为后者严重降低了性能.
| 归档时间: |
|
| 查看次数: |
2307 次 |
| 最近记录: |