如何将类从chrome扩展名应用于活动标签页

时间:2014-10-28 05:17:59

标签: javascript google-chrome-extension

我正在开发一个chrome extension,其中一个可以从弹出窗口中给出的列表中选择颜色方案,并将其应用于打开(突出显示)选项卡。从代码片段之一我开始知道在chrome.tabs.executeScript中使用code : "document.body.style.backgroundColor='red'"会更改背景颜色。但code只有一行。

我的步骤

  • 从弹出窗口中选择颜色方案
  • 获取所选li
  • 的班级名称
  • 将该类应用于DOM文档

请参阅以下代码

popup.js

document.addEventListener('DOMContentLoaded', function () {
  var li = document.querySelectorAll('li');
  for (var i = 0; i < li.length; i++) {
    li[i].addEventListener('click', click);
  }
});

function click(e) {
  // console.log(e.target.className); // gives correct value
  chrome.tabs.executeScript(null, {       
     code : "var scriptOptions = { param1: e.target.className} ;"}, function(e){
      console.log('clicked class');
      console.info(param1);  // gives nothing
      document.body.setAttribute('class', e.target.className);
    });
   window.close();
}
  • 如何在函数(e)中获取e.target.className

再次如果我使用jquery。它只更改了弹出的背景颜色,请参阅代码

    $(function(){
      console.log('jQuery added');
      $(document).on ('click', 'li', function(){
       var cl = this.className;
       $('body').removeClass().addClass(cl);
     });
 });

请告诉我

  • 在javascript和jQuery中实现此目的的正确方法是什么

2 个答案:

答案 0 :(得分:2)

  
      
  • 如何在函数(e)中获取e.target.className?
  •   

让我们看一下以下示例代码:

var a = 1;

function f(a) {
  alert(a);
}

f(2);

这是您问题的简化版本。全局范围中有一个变量a,但是通过命名函数参数a,您实际上是在创建一个同名的局部变量。

在您的代码中:

function click(e) {
  // e is now from click(e)
  chrome.tabs.executeScript(null, {       
    code : "var scriptOptions = { param1: e.target.className} ;"}, function(e){
      // e is now from function(e)
  });
}

解决方案很简单:您没有使用executeScript回调的参数,因此只需使用function() { /* ... */ }作为回调。


  

如果我使用jQuery,它只会改变弹出背景颜色

您的代码在弹出窗口的上下文中运行; $('body')指的是popup的正文。与document.body相同 - executeScript的回调在弹出窗口中执行。

要更改活动选项卡,需要从该选项卡中的内容脚本完成此操作。


  

实现此目的的正确方法是什么

虽然您可以注入代码,但最好制作一个等待命令的内容脚本。

// content.js
if(!injected) { // Make sure it's only executed once
  injected = true;
  chrome.runtime.onMessage.addListener(function(message, sender, sendResponse) {
    if(message.action == "bodyClass") {
      document.body.setAttribute('class', message.class);
    }
  });
}

然后从弹出窗口中注入此脚本,然后向其发送消息:

chrome.tabs.query({active: true, currentWindow: true}, function(tabs){
  // requires only activeTab permission
  chrome.tabs.executeScript(tabs[0].id, {file: "content.js"}, function() {
    // This code executes in the popup after the content script code executes
    //   so it is ready for the message
    chrome.tabs.sendMessage(tabs[0].id, {action: "bodyClass", class: "example"});
  });
});

如果你需要jQuery,你需要先注入它:

chrome.tabs.executeScript(tabs[0].id, {file: "jquery.js"}, function() {
  chrome.tabs.executeScript(tabs[0].id, {file: "content.js"}, function() {
    /* content script ready */
  }
}

或者,你可以在清单中定义脚本而不是每次都注入它,但这可能会耗尽内存,因为它是在不需要它的标签中注入的。

答案 1 :(得分:0)

铬和铬中存在错误我需要使用JSON.stringify ( e.target.className )之前通过{{1}发送}

code

来自chorme.sendMessage documentation

  

从扩展程序向内容脚本发送请求看起来非常好   类似的,除了您需要指定将其发送到哪个标签

 code : "var scriptOptions = { selectedClass: "  +  JSON.stringify(cl) + " }"