I'm trying to run Adsense after the page has loaded. But inserting the Adsense script file into an element doesn't seem to run it. Here is the version without window.onload (I modeled it after the Analytics script):
<script type="text/javascript">
// adsense variables
google_ad_client = "my-pubid";
google_ad_slot = "my-adslot";
google_ad_width = 728;
google_ad_height = 90;
(function() {
var ad = document.createElement('script');
ad.async = true;
ad.src = 'http://pagead2.googlesyndication.com/pagead/show_ads.js';
var s = document.getElementById('ad_top');
s.appendChild(ad);
})();
</script>
The onload version is the same, just wrapped in window.onload. Checking Chrome dev tools, the script is inserted in the #ad_top div but no ads show. I've tried moving the variables to the very top of the page and it still doesn't display even though the script is inserted fine.
Note: I'm not interested in loading it inline at the bottom of the page and moving it (as in an answer to a related question), I don't want to start loading anything until after the page has fully loaded.
Related
I maintain some donation forms that include the GeoTrust SSL 'smart icon'. This is generated by including a script reference as so within the document where you want the seal to appear:
<script type="text/javascript" src="//smarticon.geotrust.com/si.js"></script>
Their script is obviously doing a document.write(), and if/when geotrust is being slow it blocks rendering of my donation form for up to a few seconds.
I can't use the 'async' attribute, because of the document.write(). I can't edit or rewrite GeoTrust's javascript of course. And loading the js in the footer or doing the 'append to the head' approach doesn't help either because the script needs to execute within the markup where we want the icon to appear. A further complication is that these donate pages are also part of a different third-party system full of their own javascript etc.
Here's an approach that seems to work, but I'm wondering if there's a better way:
<div id="vs_seal"></div>
<script type="text/javascript">
r(function() {
var div = document.getElementById('vs_seal');
writebackup = document.write;
document.write = function(markup) {
div.innerHTML = markup;
document.write = writebackup;
}
var script= document.createElement('script');
script.type= 'text/javascript';
script.src= '//smarticon.geotrust.com/si.js';
document.body.appendChild(script);
});
function r(f){/in/.test(document.readyState)?setTimeout('r('+f+')',9):f()}
</script>
(PS I totally stole that domready test from http://www.dustindiaz.com/smallest-domready-ever )
EDIT: If it isn't clear, what I'm doing is
writing a div
waiting for the dom to be ready (last line)
saving document.write as a variable
overriding document.write to instead insert the output into a div
loading the script dynamically via appendChild
when the script calls the overriden document.write, the last line of the override is to reset document.write to the original version (that I saved as a variable).
EDIT: After the comments below, I've simply put it into an IFRAME instead.
<style>#vs_seal iframe{border:0 none;}</style>
<div id="vs_seal"></div>
<script type="text/javascript">
r(function() {
var div = document.getElementById('vs_seal');
var iframe = document.createElement('iframe');
iframe.width = 118;
iframe.height = 55;
iframe.frameborder = 0;
iframe.scrolling = "no";
iframe.seamless = "true";
iframe.src = 'about:blank';
var content = '<!DOCTYPE html>'
+ '<head><title>Dynamic iframe</title>'
+ '<style>body{margin:0;padding:0;border:0;}</style></head>'
+ '<body><script type="text/javascript" src="//smarticon.geotrust.com/si.js">'
+ '<\/script><\/body><\/html>';
div.appendChild(iframe);
iframe.contentWindow.document.open('text/html', 'replace');
iframe.contentWindow.document.write(content);
iframe.contentWindow.document.close();
});
function r(f){/in/.test(document.readyState)?setTimeout('r('+f+')',9):f()}
</script>
I originally tried pulling in the content into a hidden IFRAME and then copying the innerHTML from the IFRAME into my div, but GeoTrust's javascript that makes their popup window all pretty needs to be executed in the context its being clicked on. The innerHTML doesn't execute the javascript, and there seemed to be no advantage to not just displaying the IFRAME.
Thanks for the comments and suggestions!
I'm trying a new ad service, and as far as I know they don't provide a functional interface to loading their ads. We want to display different ad sizes depending on the user's screen size, and this service requires you to load a different .js URL for each size.
I originally tried writing:
<script type="text/javascript"><!--
var dochead = document.getElementsByTagName('head')[0];
var newscript = document.createElement('script');
newscript.type = "text/javascript";
newscript.src = '//ads-by.madadsmedia.com/tags/22430/9194/async/' + (screen.width >= 1360 ? '160' : '120') + 'x600.js';
dochead.appendChild(newscript);
//-->
</script>
but I just got a blank page. I looked in Chrome developer tools and it seemed to be loading their script properly. Their script loads other scripts from Google, and they showed up in the DOM as well. But there was no ad image.
When I changed my script to:
<script language="JavaScript" type="text/javascript">
var prot = document.location.protocol;
var adwidth = (screen.width >= 1360 ? '160' : '120');
document.write('<script language="JavaScript" type="text/javascript"'); document.write('src="'+prot+'//ads-by.madadsmedia.com/tags/22430/9194/async/'+adwidth+'x600.js">'); document.write('<\/scr' + 'ipt>');
</script>
it worked properly. I don't generally like using document.write, I wonder why it's needed in this case? The ad service's script makes extensive use of document.write, is that why?
Because they are using document.write():
http://ads-by.madadsmedia.com/tags/22430/9194/async/160x600.js:
if (!window.ActiveXObject){
document.write("<div style=\"text-align: center; margin: 0px auto; width:160px; height:600px; position:relative;\">");
// etc.
If document.write() isn't run in-line on and actively "open" document, it'll clobber what's there. So, running their script post-load overwrites your content with theirs.
if their script uses document.write it is possible that it would cause the page to go blank, as it overwrites the stream.
document.write clears page
You could override document.write as a fix: (but I wouldn't.....)
How to deal with document.write in a script that's added after a page has loaded?
if the document is loading its ready state is interactive but the body element has not been completely parsed. You can not add a child to an element which has not been loaded. It results in an error and the script stops.
dochead.appendChild(newscript);
The quick fix is to run your function using a body.onload event. Moving the script to the bottom of the page may work but I would not consider that reliable in a world which includes Internet Explorer and badly behaving browsers.
I am loading javascript file dynamically to speed up performance of my page. The code is
<head>
<script type="text/javascript">
function includeJS(){
var scriptElement = document.createElement('script');
scriptElement.type = "text/javascript";
scriptElement.src = "script/TestScript.js";
document.getElementsByTagName('head')[0].appendChild(scriptElement);
testFunction();
}
</script>
</head>
The testFunction() is present inside the TestScript.js. So it is throwing an error like 'testFunction() is undefined' as the JavaScript file is not completely loaded. So I tried with setTimeout function to fix it. The code is
setTimeOut('testFunction()',1000);
Its working fine now. But I can not put the delay time 1000 in server as the JavaScript file loading is depends on the internet speed and file size. So is there any other way to fix it.
This is the 'script' I want before the 'body' tag:
<script type="text/javascript">
var vglnk = { api_url: '//api.viglink.com/api',
key: '89dcd0a12ff35d227eaaaff82503030b' };
(function(d, t) {
var s = d.createElement(t); s.type = 'text/javascript'; s.async = true;
s.src = ('https:' == document.location.protocol ? vglnk.api_url :
'//cdn.viglink.com/api') + '/vglnk.js';
var r = d.getElementsByTagName(t)[0]; r.parentNode.insertBefore(s, r);
}(document, 'script'));
</script>
I want this code to be where I've put "HERE"
<html>
<head>
</head>
<body>
Some HTML and stuff
HERE
</body>
</html>
How would I go about this in jQuery?
(I'm doing this from an extension. Mainly in Chrome, but also Firefox and Internet Explorer.)
You need the content script to do the insert on every page you want.
The code of the content script is really simple and doesn't need jQuery.
var code = "your script code here";
var script = document.createElement("script");
script.setAttribute("type", "text/javascript");
script.appendChild(document.createTextNode(code));
document.body.appendChild(script);
As it will only be called once you don't even need to define a function. You can debug the code using debugger on any web the content script is attaching (F12) you will see your code in the content script tab.
I had the same issue regarding the best place to add jQuery: to the header or before the body tag? The answer is that it does not matter.
The whole page (or DOM) needs to initialize or load in order to accomplish what you are doing.
And...
The more information within the body, the more reliance you need to make sure the document is loaded.
The two sentences above are redundant because:
All jQuery UI, basic syntax, widgets, etc. are triggered with:
$(document).ready( function() {
$("#some_id").click( function {
More code here
});
});`
The code above means that the the full HTML page (or 'document') needs to be loaded before jQuery can run, AKA initialized.
There is an order that jQuery needs to be loaded for a UI to work. The actual library needs to be first, then the UI. The library can be downloaded from jquery.com and uploaded to the designers web space or through a CDN (content display network) to save on bandwidth. Here is an example of how the order should be:
<script src="http://code.jquery.com/jquery-1.6.4.min.js"></script>
<script src="http://code.jquery.com/mobile/1.0/jquery.mobile-1.0.min.js"></script>
Notice the library is the first line, and then the UI. In this case I loaded jQuery Mobile.
In conclusion, it does not matter. It is a preference mostly. More in on Unclear where $(document).ready goes.
In Google DFP (DoubleClick) you are given an ad code to put in your header and another for your body. When I apply this given ad tag / code to my website, whether its asynchronous or synchronous the ad always displays within an iframe. I'm wondering how I would disable the iFrame.
Here is the generated header code via DFP:
<script type='text/javascript'>
var googletag = googletag || {};
googletag.cmd = googletag.cmd || [];
(function() {
var gads = document.createElement('script');
gads.async = true;
gads.type = 'text/javascript';
var useSSL = 'https:' == document.location.protocol;
gads.src = (useSSL ? 'https:' : 'http:') +
'//www.googletagservices.com/tag/js/gpt.js';
var node = document.getElementsByTagName('script')[0];
node.parentNode.insertBefore(gads, node);
})();
</script>
<script type='text/javascript'>
googletag.cmd.push(function() {
googletag.defineSlot('/16569348/ad-test-1', [400, 267], 'div-gpt-ad-1362958263281- 0').addService(googletag.pubads());
googletag.pubads().enableSingleRequest();
googletag.enableServices();
});
</script>
Here is the generated body code via DFP:
<!-- ad-test-1 -->
<div id='div-gpt-ad-1362958263281-0' style='width:400px; height:267px;'>
<script type='text/javascript'>
googletag.cmd.push(function() { googletag.display('div-gpt-ad-1362958263281-0'); });
</script>
</div>
Here is the jsFiddle showcasing this problem (inspect element in google chrome to see iframe):
http://jsfiddle.net/EptwH/
Again, I'd like to remove the iframe (and keep the image / ad of course)... any help would truly be appreciated. :)
From DFP's website: link
When you are using Google Publisher Tags (GPT), your ads will automatically load into iframes.
We had the same issue, as our goal was to add native ads directly to the host page DOM and not an IFRAME to gain full responsiveness. We came up with a solution, where we're posting the ad content string to the host page using messages. This way there is no more IFRAME.
For details please see http://insights.burda-studios.de/howto-run-fully-responsive-doubleclick-native-ads-without-iframes/
Please note, that we only run house ads using this approach, not any 3rd party ads where this could lead to unexpected behaviours.
I'm working for a digital advertiser and you never should disable iFrames coming from advertising.
ADS can inclusce harmfull scripts, so best would be using Safeframe (frame using src poining to foreign origin) to prevent that.
Also many ad script use document.write, and inside their iframe they can do that without problem, would they do that on main window after document.ready that would paint your page blank.
Google loads its ads into iframes purposely, this is by design.
This is done because it both allows your page to load faster and to have sand-boxed styles and scripts etc. The render of the page is faster because iframes enable asynchronous loading and rendering of the ad content.
It is possible to "bust" out of the iframe with your ad code if you want, so there is no real disadvantage to the ads being in an iframe, show us an example of what you are trying to do if you have run into a problem
Here is some more reading to do with this.
Part of your question (whether its asynchronous or synchronous) is wrong in my experience.
Not sure if this has changed or if you failed to let the GPT tags run synchronously, but since I changed to synchronous mode, iframes are no longer used.
See for yourself at belmodo.tv