I am new to javascript and struggling with this basic problem - I want to load jQuery only if the window size is below a certain threshold (i.e., the mobile version doesn't require it). For the desktop version, jQuery must load in the <head> and not the <body>, as the content above the fold requires it.
I've tested the loop, and I'm getting the screen width printed on the page, but jQuery isn't loading. I'm sure it's a basic syntax problem but I just can't see it! Any help would be most appreciated. :)
<script type="text/javascript">
function loadjsfile(filename){
var fileref=document.createElement('script');
fileref.setAttribute("type","text/javascript");
fileref.setAttribute("src", filename);
}
var w=window.innerWidth
|| document.documentElement.clientWidth
|| document.body.clientWidth;
if (w > 899){
document.write("screen Width: " + w);
loadjsfile("http://ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js");
}
</script>
you've created the fileref variable that contains your script tag object but you never add it to the DOM, thus it never loads.
function loadjsfile(filename){
var fileref = document.createElement('script');
fileref.setAttribute("type","text/javascript");
fileref.setAttribute("src", filename);
//add this line
document.getElementsByTagName('head')[0].appendChild(fileref);
}
Related
I have went through a ton of answers, and I can not get anything to work for me. Please be patient and specific as I am a newbie when it comes to using JavaScript.
I am attempting to get an external JavaScript file to load on Desktop only. Below is the code I am currently using, but it is not working. Can someone please help me achieve this.
<script>
(function() {
if( window.innerWidth > 600 ) {
var theScript = document.createElement('script');
theScript.type = 'text/javascript';
theScript.src = 'www.siteminds.net/m/1.6/mind_loader.php?pid=y2w6z8B3N31&cast_id=v1532315&autoplay=1&avname=jackie&wc=1&avnum=15&band_type=av';
var s = document.getElementsByTagName('script')[0];
s.parentNode.insertBefore(theScript, s);
}
})();
</script>
I am placing this code in the head section, however, the script is not running.
The website is responsive using respond.js. I also added enquire.js in an attempt to use that method (which I also couldn't get to work)
Probably, the main issue is that you must include the protocol on the URL so:
'www.siteminds.net/m/1.6/mind_loader.php?pid=y2w6z8B3N31&cast_id=v1532315&autoplay=1&avname=jackie&wc=1&avnum=15&band_type=av'
needs to be:
'http://www.siteminds.net/m/1.6/mind_loader.php?pid=y2w6z8B3N31&cast_id=v1532315&autoplay=1&avname=jackie&wc=1&avnum=15&band_type=av'
Your code could also fail if there were not already some script tags. This version is not vulnerable to that:
<script>
(function() {
if( window.innerWidth > 600 ) {
var theScript = document.createElement('script');
theScript.type = 'text/javascript';
theScript.src = 'http://www.siteminds.net/m/1.6/mind_loader.php?pid=y2w6z8B3N31&cast_id=v1532315&autoplay=1&avname=jackie&wc=1&avnum=15&band_type=av';
var head = document.getElementsByTagName('head')[0];
head.appendChild(theScript);
}
})();
</script>
Note: a test for innerWidth > 600 is not even close to a fail-proof way to detect a desktop installation as even a tablet in landscape mode will pass that test.
This is what ended up working for me.
<script>
var width = window.innerWidth
|| document.documentElement.clientWidth
|| document.body.clientWidth;
if ( width > 600) {
document.write('<script src="//www.siteminds.net/m/1.6/mind_loader.php?pid=y2w6z8B3N31&cast_id=v1532315&autoplay=1&avname=jackie&wc=1&avnum=15&band_type=av" async><\/script>');
}
</script>
I've been working hard to achieve 100/100 on Google Pagespeed (https://developers.google.com/speed/pagespeed/insights/) but I keep getting hungup when trying to use Javascript to download CDN based files. I get 'CAUTION: Provisional headers are shown.' and I assume it's blocking this kind of call for security reasons but I'm stuck.
I can call script files asycn like this, which Google likes:
<script src="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js" async></script>
But what am I to do about the CSS files? If I call it the normal way:
<link href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css" rel="stylesheet">
Google complains and says I have a 'blocking CSS resources'.
Here's a copy of the code I've been trying to use so far:
var headID = document.getElementsByTagName("head")[0];
var cssNode = document.createElement('link');
cssNode.type = 'text/css';
cssNode.rel = 'stylesheet';
cssNode.href = '//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css';
headID.appendChild(cssNode);
Anyone have any suggestions?
Here is the code I ended up creating to handle loading both css and js files async at the same time. Just put this at the bottom of your HTML before you closing tag and edit the loadjscssfile() calls as necessary.
<script>
/* Beginning of async download code. */
window.onload = function(){
function loadjscssfile(filename, filetype) {
if(filetype == "js") {
var cssNode = document.createElement('script');
cssNode.setAttribute("type", "text/javascript");
cssNode.setAttribute("src", filename);
} else if(filetype == "css") {
var cssNode = document.createElement("link");
cssNode.setAttribute("rel", "stylesheet");
cssNode.setAttribute("type", "text/css");
cssNode.setAttribute("href", filename);
}
if(typeof cssNode != "undefined")
document.getElementsByTagName("head")[0].appendChild(cssNode);
}
loadjscssfile("//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css", "css");
loadjscssfile("//fonts.googleapis.com/css?family=Open+Sans:300&subset=latin,cyrillic-ext,latin-ext,cyrillic,greek-ext,greek,vietnamese", "css");
loadjscssfile("/css/style.css", "css");
loadjscssfile("//ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js", "js");
loadjscssfile("//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js", "js");
};
/* End of async download code. */
</script>
Google provides a good explanation of this here:
https://developers.google.com/speed/docs/insights/OptimizeCSSDelivery
It seems like they want you to inline CSS that is crucial to the page's initial display. Then load secondary CSS after. Since the bootstrap CSS is one large mix, I think it'll be non-trivial to separate crucial/non-crucial for your page.
Perhaps you can inline some duplicate CSS that exists in bootstrap.css
I'd suggest you to inline the styles for the critical path (above the fold):
https://github.com/addyosmani/above-the-fold-css-tools
https://github.com/addyosmani/critical
Then load the other css async:
https://github.com/filamentgroup/loadCSS/
I'm new to php. I have a doubt, don't know if this can be done, or if it should be done in another way or what.
I want to load a JS only if the screen size is higher than x size.
I wrote this but the JS is not being loaded (in fact I want to load a couple of JS):
<script language="javascript">
if (screen.width > 549) {
<script src='js/jquery-1.8.1.min.js' type='text/javascript'></script>
}
best regards!
php cannot detect a clients screen width/height, that all would have to be done client side.
function addScript(src){
var script = document.createElement("script");
script.type = "text/javascript";
script.src = src;
document.head.appendChild(script);
}
if(screen.width > 549){
addScript("js/jquery-1.8.1.min.js");
addScript("js/someOtherScript.js");
}
It's cleaner to detect the screen width in JavaScript. Also remember the screensize can change in a session. For example when a user resizes his screen.
Use this in your JavaScript file:
var width = document.body.clientWidth;
if(width > 549) {
} else if(width < 300) {
} else {
}
You cannot determine a clients' browser window size before a client has received a page with PHP.
Technically you could load a page, get javascript to send back the window size and then store it in the session for that user, but I don't really see the point. You're better off either always including the javascript file, or using a javascript library to conditionally add other scripts to the DOM.
I'm working within a platform that I do not have server side access to. That means I can't load javascript files directly into the head, only the body.
Here's how I'm doing my loads:
function loadjscssfile(filename, filetype){
//http://www.javascriptkit.com/javatutors/loadjavascriptcss.shtml
if (filetype=="js"){ //if filename is a external JavaScript file
var fileref=document.createElement('script')
fileref.setAttribute("type","text/javascript")
fileref.setAttribute("src", filename)
}
else if (filetype=="css"){ //if filename is an external CSS file
var fileref=document.createElement("link")
fileref.setAttribute("rel", "stylesheet")
fileref.setAttribute("type", "text/css")
fileref.setAttribute("href", filename)
}
if (typeof fileref!="undefined")
document.getElementsByTagName("head")[0].appendChild(fileref)
}
}
loadjscssfile('https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js','js');
loadjscssfile('http://redacted.com/data.php?rand='+Math.random(),'js');
However, the third javascript file (a jQuery plugin) I load requires jQuery.
When I load the page I get this error (in Chrome)
Uncaught ReferenceError: jQuery is not defined
My inclination is that my plugin is loading before jQuery. Because if I refresh the page (when jQuery is cached) the error disappears. However, I need this to work even when jQuery is not cached. Thoughts?
This is not an elegant solution but it works always for me: copy/paste the content of jquery.min.js file directly to your html page
<script> ... </script>
What I do is this
if (typeof $ === 'undefined') {
document.write("<script src='//ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js'><\/script>");
var timeout = 0;
while (typeof $ === 'undefined' && timeout++ < 100);
}
This will wait until jquery is loaded before it moved on to do anything else. Then load your plugin.
As you're trying you have to load jQuery and run the other scripts after it loads. To do that you can use a loader library, like yepnope or headjs, remembering that as you cannot put scripts on your head you have to put the loader code along to the script.
Your code will be something like this:
yepnope( // or head.js
'https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js',
'http://redacted.com/data.php?rand='+Math.random(),
'https://raw.github.com/aakilfernandes/jquery.inject/master/jquery.inject.js?rand='+Math.random()
);
Another thing you can do is just put the jquery script on the body and load the other scripts after it:
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script>
$.getScript('http://redacted.com/data.php?rand='+Math.random());
$.getScript('https://raw.github.com/aakilfernandes/jquery.inject/master/jquery.inject.js?rand='+Math.random());
</script>
I have the following file:
<html>
<head>
<title></title>
<link rel="css" type="text/css" href="/empty.css" title="css" />
<script type="text/javascript" src="/Prototype"></script>
<script type="text/javascript">
function load_content()
{
var d = new Date();
new Ajax.PeriodicalUpdater('content', '/DOC?'+d.getTime(),
{
method: 'post',
frequency: 5,
onSuccess: function(transport) {
for(i=0; (a = document.getElementsByTagName('link')[i]); i++)
{
if(a.getAttribute('rel') == 'css' && a.getAttribute("type") == 'text/css')
{
a.href = '/CSS?'+d.getTime();
}
}
}
});
}
</script>
</head>
<body>
<div id="content"></div>
<script type="text/javascript">
load_content();
</script>
</body>
</html>
Note: Ignore the d.getTime() calls...these are just to get around an issue with IE not loading a new page from an AJAX call because it's caching scheme is too aggressive.
Basically, when it reloads the file at /DOC, it is supposed to be setting the current stylesheet to the file at /CSS... both DOC and CSS and constantly changing.
What's weird is that in Chrome it works great. DOC loads up in the "content" div and the stylesheet gets set to CSS and that css is applied to the page. I can change with CSS page and withing 5 seconds, when the page is refreshed, the CSS will be refreshed as well.
But in IE and Firefox, the HTML will load and I can see that the href attribute of the stylesheet link IS getting changed to "/CSS + getTime()" but, while the HTML loads, the css is never applied to the page. I can even change the content of DOC and it updates, but the css is never even applied. It just stays a style-free page.
Does Firefox and IE not support changing the style sheet reference in this way?
Is there a better way to do this?
Rather than changing the sheet in a single link, try using alternate style sheets. See this link on using alternate style sheets:
http://www.alistapart.com/articles/alternate/
The best way to include files via javascript is to insert a new dom element.
var a = document.createElement('link');
a.href="inset.css";
a.rel="stylesheet";
document.getElementsByTagName("head")[0].appendChild(a);
However, obviously the problem you're going to run into though is that firefox and ie will not repaint the canvas once the document is finished loading (and you're using ajax). The way you get around that is by taking the contents of the stylesheets and including them in a style element. This sample code will change the color on the page dynamically.
function onLoadFunction() {
var a = document.createElement('style');
a.appendChild(document.createTextNode('body {color: blue;}'));
document.getElementsByTagName("body")[0].appendChild(a);
}
When you load a new sheet, just destroy the css inside the style element and replace it.
maybe this will help you ...
http://www.javascriptkit.com/javatutors/loadjavascriptcss.shtml
function loadjscssfile(filename, filetype){
if (filetype=="js"){ //if filename is a external JavaScript file
var fileref=document.createElement('script')
fileref.setAttribute("type","text/javascript")
fileref.setAttribute("src", filename)
}
else if (filetype=="css"){ //if filename is an external CSS file
var fileref=document.createElement("link")
fileref.setAttribute("rel", "stylesheet")
fileref.setAttribute("type", "text/css")
fileref.setAttribute("href", filename)
}
if (typeof fileref!="undefined")
document.getElementsByTagName("head")[0].appendChild(fileref)
}
It looks like you are simply reloading the existing page every time. Why not just use the refresh tag in your header to force the document to reload each time and put in the CSS and content server-side. A lot simpler and it works even with javascript disabled.
<meta http-equiv="refresh" content="5;url=http://example.com/DOC" />
It might be a caching issue. If you do a hard refresh (Ctrl+R in FF, Ctrl+F5 in IE) does it display the style properly? If that does fix it, you may want to look at removing the Last-Modified header from the CSS file or adding a cache control header telling the browser not to cache it.