尝试在chrome扩展(JavaScript)中从默认脚本通信到内容脚本不起作用

尝试在chrome扩展(JavaScript)中从默认脚本通信到内容脚本不起作用,javascript,google-chrome,google-chrome-extension,communication,content-script,Javascript,Google Chrome,Google Chrome Extension,Communication,Content Script,好的,我正在通过一个扩展来改变一个网站的配色方案,这是我第一次使用内容脚本,所以是的,我是一个完全的新手,请随意对待我 问题是制表符。连接它不工作,我需要制表符id还是什么?以下是我目前掌握的情况: manifest.json: { "manifest_version": 2, "name": "ROBLOX Color Scheme", "description": "Edit the color scheme of the roblox bar! Note: Not creat

好的,我正在通过一个扩展来改变一个网站的配色方案,这是我第一次使用内容脚本,所以是的,我是一个完全的新手,请随意对待我

问题是制表符。连接它不工作,我需要制表符id还是什么?以下是我目前掌握的情况:

manifest.json:

{
  "manifest_version": 2,

  "name": "ROBLOX Color Scheme",
  "description": "Edit the color scheme of the roblox bar! Note: Not created by roblox.",
  "version": "1.0",

  "permissions": [
    "<all_urls>",
    "tabs"
  ],
  "browser_action": {
    "default_icon": "Icon.png",
    "default_popup": "Popup.html"
  },
  "content_scripts": [
    {
      "matches": ["http://www.roblox.com/*"],
      "js": ["ContentScript.js"]
    }
  ]
}
ContentScript.js:

function ChangeColor() {
  var TabId;
    chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
      TabId = tabArray[0];
    });
  var port = chrome.tabs.connect(TabId, {name: "ColorShare"});
  port.postMessage({Color: document.getElementById("Color").value});
}

document.getElementById('Color').addEventListener("click", ChangeColor);
var Color;
chrome.runtime.onConnect.addListener(function(port) {
  if (port.name == "ColorShare") then {
    port.onMessage.addListener(function(msg) {
      Color = msg.Color;
    });
  }
});

document.getElementsByClassName("header-2014 clearfix")[0].style.backgroundColor = Color;
chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    var TabId = tabArray[0].id;
    var port = chrome.tabs.connect(TabId, {name: "ColorShare"});

    function ChangeColor() {
        port.postMessage({Color: document.getElementById("Color").value});
    }
    document.getElementById('Color').addEventListener("click", ChangeColor);
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});
感谢您的帮助,感谢您抽出时间回答我的问题

编辑:由于我自己和回答者的帮助,一些文件现在已经更改,这些现在不会产生错误,但是没有任何更改,您可能提供的任何帮助都将非常好!以下是当前代码:

Script.js:

function ChangeColor() {
  var TabId;
    chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
      TabId = tabArray[0];
    });
  var port = chrome.tabs.connect(TabId, {name: "ColorShare"});
  port.postMessage({Color: document.getElementById("Color").value});
}

document.getElementById('Color').addEventListener("click", ChangeColor);
var Color;
chrome.runtime.onConnect.addListener(function(port) {
  if (port.name == "ColorShare") then {
    port.onMessage.addListener(function(msg) {
      Color = msg.Color;
    });
  }
});

document.getElementsByClassName("header-2014 clearfix")[0].style.backgroundColor = Color;
chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    var TabId = tabArray[0].id;
    var port = chrome.tabs.connect(TabId, {name: "ColorShare"});

    function ChangeColor() {
        port.postMessage({Color: document.getElementById("Color").value});
    }
    document.getElementById('Color').addEventListener("click", ChangeColor);
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});
ContentScript.js:

function ChangeColor() {
  var TabId;
    chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
      TabId = tabArray[0];
    });
  var port = chrome.tabs.connect(TabId, {name: "ColorShare"});
  port.postMessage({Color: document.getElementById("Color").value});
}

document.getElementById('Color').addEventListener("click", ChangeColor);
var Color;
chrome.runtime.onConnect.addListener(function(port) {
  if (port.name == "ColorShare") then {
    port.onMessage.addListener(function(msg) {
      Color = msg.Color;
    });
  }
});

document.getElementsByClassName("header-2014 clearfix")[0].style.backgroundColor = Color;
chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    var TabId = tabArray[0].id;
    var port = chrome.tabs.connect(TabId, {name: "ColorShare"});

    function ChangeColor() {
        port.postMessage({Color: document.getElementById("Color").value});
    }
    document.getElementById('Color').addEventListener("click", ChangeColor);
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});

编辑:这个问题已经解决了。我必须使用chrome.storage.sync.set和chrome.storage.sync.get,它们完全支持内容脚本!我会尽快发布使用的脚本

未测试,但我认为您应该这样做:

Script.js:

chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    var TabId = tabArray[0];
    var port = chrome.tabs.connect(TabId, {name: "ColorShare"});

    function ChangeColor() {
        port.postMessage({Color: document.getElementById("Color").value});
    });
    document.getElementById('Color').addEventListener("click", ChangeColor);
}
ContentScript.js:

function ChangeColor() {
  var TabId;
    chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
      TabId = tabArray[0];
    });
  var port = chrome.tabs.connect(TabId, {name: "ColorShare"});
  port.postMessage({Color: document.getElementById("Color").value});
}

document.getElementById('Color').addEventListener("click", ChangeColor);
var Color;
chrome.runtime.onConnect.addListener(function(port) {
  if (port.name == "ColorShare") then {
    port.onMessage.addListener(function(msg) {
      Color = msg.Color;
    });
  }
});

document.getElementsByClassName("header-2014 clearfix")[0].style.backgroundColor = Color;
chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    var TabId = tabArray[0].id;
    var port = chrome.tabs.connect(TabId, {name: "ColorShare"});

    function ChangeColor() {
        port.postMessage({Color: document.getElementById("Color").value});
    }
    document.getElementById('Color').addEventListener("click", ChangeColor);
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});
chrome.runtime.onConnect.addListener(function(port) {
    if (port.name == "ColorShare") {
        port.onMessage.addListener(function(msg) {
            document.querySelector("header-2014 clearfix").style.backgroundColor = msg.Color;
        });
    }
});

您应该使用chrome.tabs.sendMessage而不是chrome.tabs.connect

Script.js

function ChangeColor() {
  var tabId;
  chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    tabId = tabArray[0].id;
    chrome.tabs.sendMessage(tabId,{color: document.getElementById("Color").value});
  });
}

document.getElementById('Color').addEventListener("click", ChangeColor);
chrome.runtime.onMessage.addListener(function(msg, sender, sendResponse) {
  document.getElementsByClassName("header-2014 clearfix")[0].style.backgroundColor = msg.color;
});
ContentScript.js

function ChangeColor() {
  var tabId;
  chrome.tabs.query({currentWindow: true, active: true}, function(tabArray) {
    tabId = tabArray[0].id;
    chrome.tabs.sendMessage(tabId,{color: document.getElementById("Color").value});
  });
}

document.getElementById('Color').addEventListener("click", ChangeColor);
chrome.runtime.onMessage.addListener(function(msg, sender, sendResponse) {
  document.getElementsByClassName("header-2014 clearfix")[0].style.backgroundColor = msg.color;
});
这将解决异步问题,并切换到单个消息,而不是长期连接。除非您来回发送大量信息,否则单个消息可能比打开端口要好。您也可以以附加字段的形式向消息中添加某种描述,例如:

chrome.tabs.sendMessage(tabId,{type: 'setColor', color: stuff});

然后,您可以检查侦听器中的类型,并将其像那样分开。

我认为您误解了端口的概念。一个端口用于会话中的多条消息。但是当会话结束时(例如,当选项卡关闭时),端口将被销毁。无论如何,您不应该在每次单击时重新创建端口

您的一条评论提到刷新页面,这让我认为您希望此颜色在页面重新加载时保持不变。从用户界面的角度来看,这是有意义的,但您真的应该在一开始就提到这一点

正如我所说,当选项卡关闭(或重新加载)时,端口会被破坏。如果希望值持久化,则需要一种存储机制,例如(也可以使用本地存储,但前面的链接给出了不使用本地存储的几个原因)

manifest.json只需要
“权限”:[“activeTab”,“storage”],
。您可能还需要一个页面操作,而不是浏览器操作(或者两者都不需要,我来讨论一下)

ContentScript.js:

我将参数更改为
querySelector
,因为在索引页上找不到您要查找的元素

Popup.html:

如果有先前设置的背景色,我们希望使用
ContentScript.js
onload message
Script.js
。不幸的是,
Script.js
仅在我们单击操作图标时才存在。因此,我们为当前颜色(如果已设置)设置了
Script.js
ask
ContentScript.js


正如Ruwanka Madhushan所注意到的,您的原始脚本失败(部分原因是),因为您假设异步
chrome.tabs.query将在继续下一行代码之前完成。异步javascript非常强大,但它让您承担了不假设代码已完成的责任。您需要使用嵌套函数调用,可以是匿名调用(如
Script.js
的onclick),也可以是命名实用函数调用(如
setCurColor
)。(还有一些javascript库可以帮助实现异步函数,但我不知道它们。)

一切正常,但有一个小问题:-在这种情况下,当您单击颜色选择器输入时。(非常糟糕的)解决方法是打开弹出窗口,右键单击并选择“检查元素”。这将打开弹出窗口的控制台,并防止在您选择颜色时关闭弹出窗口。另一个选项可能是将颜色选择器嵌入弹出窗口中的iframe中(我不知道这是否可行)


但既然我们讨论的是您的扩展选项,那么最好的选择可能是使用。这也将为html提供更多的空间。例如,您可能需要考虑一个按钮来删除LoalSaltAg.MyBGCuffe,以便获得默认的后退。或者其他定制网站的选项,因为我希望你不会为了改变颜色而麻烦。而且它会隐藏操作图标,因为您可能要设置选项,然后想忘记现有的扩展。

我认为出于您的目的,不需要长时间的连接,只需使用。顺便说一句,由于您使用的是长寿命连接,所以我将坚持这一点

首先,您有一个id为
button
的按钮,但您正在为颜色输入
document.getElementById('color').addEventListener(“单击”,更改颜色)附加click事件处理程序您必须更改,这是我的popup.html代码

popup.html

<!DOCTYPE html>
<html>
    <head>
        <p>Choose a color:</p>
        <input type="color" id="ColorVal">
        <button type="button" id="color">Change Color!</button>
    </head>
    <body>
        <script src="script.js"></script>
    </body>

</html>

选择一种颜色:

换颜色!

在Script.js中相应地更改id。除此之外,您编辑的Script.js和ContentScript.js都很好。您的第一个代码失败,因为查询选项卡需要很多时间。因为tabid不存在,所以端口声明失败。希望这将对您有所帮助。

好的,您正在尝试通过消息传递来实现这一点。我知道你可能认为长寿命是一条出路,但事实并非如此。您必须使用存储系统,尤其是与内容脚本完全兼容的chrome.storage

您不必使用浏览器操作,只需创建一个选项页面,将颜色保存到chrome.storage,然后内容脚本就可以在其中检索颜色。