Google chrome extension 自定义DevTools元素侧栏窗格如何与面板通信?

Google chrome extension 自定义DevTools元素侧栏窗格如何与面板通信?,google-chrome-extension,google-chrome-devtools,Google Chrome Extension,Google Chrome Devtools,我正在创建自定义元素侧栏窗格,如下所示: chrome.devtools.panels.elements.createSidebarPane( "MyPane", function (sidebar) { sidebar.setPage('my-pane.html'); } ); my-pane.html: <html> <head> <script src="my-pane.js"></scri

我正在创建自定义元素侧栏窗格,如下所示:

chrome.devtools.panels.elements.createSidebarPane(
    "MyPane",
    function (sidebar) {
        sidebar.setPage('my-pane.html');
    }
);
my-pane.html:

<html>
    <head>
    <script src="my-pane.js"></script>
    </head>
    <body>
    <!-- custom UI -->
    </body>
</html>
这几行失败的原因是(在)著名的:

端口错误:无法建立连接。接收端不工作 存在

sendMessage/onMessage模式是否是窗格和面板(均以.html页面表示)之间通信的正确方式

编辑

试图完全避免DevTools,并通过DOM访问页面(my-pane.html和my-panel.html似乎都位于单个父页面中的
s中):

这不起作用:

不安全的JavaScript试图使用URL访问帧 铬-extension:///devtools.html 从…起 带URL的框架 铬-extension:///devtools.html. 域、协议和端口必须匹配

编辑2

我真傻!当然,上面关于第一个
是正确的假设是完全错误的。以下内容将产生更有意义的结果:

panel.onShown.addListener(function (window) {
    for (var i = 0; i < window.top.frames.length; i++) {
        try {
            console.log(["PANEL",
                window.top.frames[i].document.getElementsByTagName('ol')
            ]);
            break;
        } catch (e) {
            console.log('BAD!', e);
        }
    }
});
panel.onShown.addListener(函数(窗口){
对于(变量i=0;i
编辑3(解决方案而非答案)

chrome.devtools.panels.create(
“我的小组”,
“icon.png”,
'my panel.html',//必须在MyPanelPage(doc){..}中定义函数callback
功能(面板){
panel.onShown.addListener(函数(窗口){
对于(变量i=0;i
奖励:我试图实现的沟通方式(绿色箭头)的形象化


根据您上次的评论


到目前为止,在将消息事件处理程序放入 background.js。但这正是我想要避免的。相反,我宁愿 更喜欢my-pane.html和my-panel.html直接对话 其他的。当不使用HTML页面作为窗格时,这当然是可能的 和面板内容

我知道发生了什么

您的面板/窗格不是扩展过程,而是内容脚本。
因此,您需要使用而不是。

您的代码缺少
onMessage
事件侦听器的定义。@RobW感谢提醒:我在两个位置尝试了通用的chrome.extension.onMessage.addListener(..):1。在my-pane.js中,就在订阅onSelectionChanged 2之后。在devtools.js内部,在窗格和面板创建之间。据我所知,这是调用的。您确定没有发生导致事件绑定失败的错误吗?您可以在devtools实例中打开另一个devtools实例以查找错误(我没有时间完全遵循代码流程;您可以使用多个
控制台.log
s,或者使用quick n dirty
警报(“somenumber”)
自己检查此错误)。到目前为止,在将消息事件处理程序放入background.js后,它仍在工作。但这正是我想要避免的。相反,我更喜欢my-pane.html和my-panel.html直接相互对话。这当然是在不使用HTML页面作为窗格和面板内容时出现的。您是否找到过这样做的方法,但避免了
edit3解决方案
??我开始做
edit3solution
作为一种方法,现在我想用
sendMessage
正确地完成它,我遇到了麻烦。我似乎在发送消息,但在
panel.html
>
panel.js
chrome.devtools.panels.create(
    'My details',
    'icon.png',
    'my-panel.html',
    function (panel) {
        panel.onShown.addListener(function (window) {
            chrome.extension.sendMessage({}, function (response) {
                console.log(response);
            });
        });
    }
);
..
panel.onShown.addListener(function (window) {
    console.log(["PANEL",
       window
           .top
           .frames[0] // Assume this is my-pane.html
           .document
           .getElementsByTagName('ol')
    ]);
});
..
panel.onShown.addListener(function (window) {
    for (var i = 0; i < window.top.frames.length; i++) {
        try {
            console.log(["PANEL",
                window.top.frames[i].document.getElementsByTagName('ol')
            ]);
            break;
        } catch (e) {
            console.log('BAD!', e);
        }
    }
});
chrome.devtools.panels.create(
    'My Panel',
    'icon.png',
    'my-panel.html', // Must define function callbackInMyPanelPage(doc) { .. }
    function (panel) {
        panel.onShown.addListener(function (window) {
            for (var i = 0; i < window.top.frames.length; i++) {
                try {
                    // Use any unique marker to identify our pane document,
                    // at worst case a security exception will be thrown..
                    var $el = window.top.frames[i].document.getElementById('myPane');

                    if ($el) {
                        try {
                            // pass pane's document to panel page
                            window.callbackInMyPanelPage(window.top.frames[i].document);
                        } catch(ex) {} // Don't interfere with a handler below 
                        break;
                    }
                } catch (e) {
                    console.warn('Cannot access <iframe/>', e);
                }
            }
        });
     }
 );