I'm making an extension to customize Google' homepage background.So I write some match rules in manifest like this:
"content_scripts": [
{
"matches": ["https://www.google.com/", "http://www.google.com/"],
"js": ["static/js/jquery.js", "static/js/contentscript.js"]
}
],
and some scripts in contentscript.js
:
var imgURL = chrome.extension.getURL("static/images/bg.jpg");
$('body').css('background-image', 'url(' + imgURL + ')');
The script works fine for https://www.google.com, but when I try to search something ,the page jumps to https://www.google.com/#newwindow=1&sclient=psy-ab&q=Google&oq=Google&gs_l=hp.3..35i39l2j0i20l2j0l6.4788.5717.2.5939.5.3.2.0.0.0.142.397.0j3.3.0....0.0..1c.1.20.hp.xCFVga8gVZU&bav=on.2,or.r_cp.r_qf.&bvm=bv.49784469%2Cd.dGI%2Cpv.xjs.s.en_US.MpiVkF51mpA.O&fp=806ba48f5b2ed550&biw=1920&bih=963
But the script is still working after the jumping! And if I paste the long url in a new tab directly, it won't work!
I think it should be related with iframe or Ajax or something else. Could someone give some more details? And how can I prevent scripts from running after the url changed?
If you want to apply a style to Google's home page, just use a selector which is very specific to Google's homepage. With the Inspector, I quickly discovered that the <body>
tag at the homepage has a class "hp". This class does not show up in search results.
Drop your JavaScript code, and use
manifest.json
"content_scripts": [
{
"matches": ["*://www.google.com/*"],
"css": ["my-google-style.css"]
}
],
"web_accessible_resources": [
"static/images/bg.jpg"
],
*
, means "http" and "https"."web_accessible_resources"
key is necessary if you want to display the image in an external (=non-extension) page.my-google-style.css
body.hp {
background-image: url("chrome-extension://__MSG_@@extension_id__/static/images/bg.jpg");
}
The first part of my answer is the recommendation for your case. In general, if you want to catch every (scripted and user-initiated) URL change, including but not limited to:
history.pushState
/ history.replaceState
location.hash = '...';
... then you need to use the chrome.webNavigation
API in the background/event page, in particular the onHistoryStateUpdated
and/or onReferenceFragmentUpdated
events. In response to these events, you'll either send a message or execute a content script.
If you only expect rewrites of the reference fragment (aka location hash), then there's no need for the webNavigation
API. The implementation will be simplier, as you only need to listen to the global hashchange
event in the content script.