onLoad function not executing - javascript

I'm trying to set up a demo page for an API I'm developing at work, but I can't get my JavaScript to work. The JavaScript should poll on my server to check if the elaboration has ended and then perform the necessary operations to get the result on the browser, but I keep getting this error:
Failed to clear temp storage: It was determined that certain files are unsafe for access within a Web application, or that too many calls are being made on file resources. SecurityError
After the first time I decided to simplify my code, cutting off calls until I got it working and the add up. Currently my function looks like this, but I still get the same error (I cleared the browser's cache, so it is not executing old versions):
function getStatus(){
window.alert("Prova");
}
It should execute when a div is loaded:
<div id="LoaderImage" onload="getStatus()">
...
</div>
Since I can see the loading gif inside the div I am sure the div is being loaded, but the function doesn't do anything anyway.
The JavaScript and jQuery code used inside my template works fine, so the main suspect for the error is this function, which is the only one which does not work.

Use onload on body instead. I would prefer to invoke it on the window object like this,
window.onload = getStatus;
or to use it on <body> .. </body> do this:
<body onload="getStatus()">
...
</body>

Related

How can I wait until a newly created Element is "ready" (all scripts downloaded)

I'm working on a piece of code that glues Sammy JS (router) and Knockout JS together.
So, this is my problem,
<script id="MyTemplate" type="text/html">
// [HTML Containing a script link (Encoded HTML)]
</script>`
I use jQuery to create an instance of this template :
var TInstance = $($("#MyTemplate").text())
Then, I want to inject the new html TInstance into my <body> or an other existing tag
$("body").html(TInstance)
All Good, now I want to do ko.applyBindings to bind the new TInstance to an ViewModel and it works.
The problem I have is: when I have an <script src="..." /> inside TInstance,
I want to wait until that script is downloaded and parsed, then do ko.applyBindings.
So I tried $(TInstance).ready(() => {ko.applyBindings(...)}), It works the first time the page loaded, but if I redo the whole process, swapping in a new TInstance the ready handler on the new TInstance won't fire.
What should I do?
Ok, this answer will not be "copy & paste and play", it will require some tweaking from you, but i think you will get the concept and you will manage.
Without adding a dependency management module, and without restructuring you code ( usually plain script tags don't get injected dynamically along with html for the same reason you have troubles right now. Its a good idea to load script tags with html for the first page load, but any content added later on, especially if some flow is required, will need programmatic handling, hence the need for module management frameworks for larger projects)
One way to do it is to stop your code execution flow and poll the enviroment to see if your script is loaded. i.e:
var demoInterval = setInterval(function(){
if(myCondition){
clearInterval(demoInterval );
functionThatStartsTheRestOfTheLogicFlow(); // this could apply bindings etc etc
}
},50);
Now for example, if you where loading jQuery with the script tag your condition could be
typeof($) !== 'undefined'
It would poll every 50 milliseconds until $ is defined, and then it would call a function to clear the polling and continue your logic flow.
In your case the condition could be the definition of a function/model, a flag-like variable that your custom js file can set and the polling would expect to read at some point etc etc.
Even better would be to remove the script tag from the html and load the script dynamically by javascript so that you can utilize the onload event of the specific script that is required, you can read an example here. Programatically controlling these cases is much easier for the developer.
Hope this helps
have resolved the problem by using a 0ms setTimeout call
setTimeout(() => { /*all new resources have been loaded and the html rendered*/ });
Help: https://eager.io/blog/how-to-decide-when-your-code-should-run/

basic javascript alert not working in Intel XDK code editor

I'm starting fresh with a new blank Intel project and I haven't even started coding yet. I'm just setting up my file tree and making sure the html and javascript pages are connected via the right anchors and script paths. My first .js file won't work though.
I've included a screen shot of test code and the errors. I know the syntax is correct because it works when I put it in <script> tags in the index.html file.
I'm getting "document not defined" and "alert not defined" errors or the js page though. I don't know what that means.
I've considered that my script tag src path in the index file is incorrect, but all the paths are relative in the commented out template script tags intel provides on the index page right out of the box, so why would I have to use an absolute path?
My path is: js/Test.js and it's the last script tag before the body.
Index.html file
*****UPDATE****
So I've tried a few things and it's still not working but I HAVE managed to get my errors down to just one inexplicable "missing semicolon", which will turn into an "unnecessary semicolon" error if I place it.
Any way as per the first screen shot you'll see that I wasn't placing the document object inside of an explicitly declared variable. Once I did that and accessed it through dot syntax instead of an equal sign then I stopped getting the error. I included this screenshot to show my work before I made the changes.
so the problem I went on to have is that unless every function or dom object was declared with "Var", I'd get an error. This includes the alert() function which I don't think I've ever seen needing to be declared that way, but I gave the code editor what it wanted and this last screenshot is the results. It's not working, BUT I'm not getting the errors I was before, except for the missing/unnecessary semicolon paradox. Removing it or including it throws an error.
JavaScript can be loaded before or after the HTML, however the way it is done is slightly different depending on how you do it.
For example if you wish to include your JavaScript files within the head of the HTML file then you must wrap your JavaScript code with either DOMContentLoaded or jQuery's $(document).ready().
The common misconception of using window.onload will not fix the issue where the elements have not loaded in correctly.
The Mozilla Developer Network states on this page:
The DOMContentLoaded event is fired when the initial HTML document has been completely loaded and parsed, without waiting for stylesheets, images, and subframes to finish loading. A very different event - load - should be used only to detect a fully-loaded page. It is an incredibly popular mistake to use load where DOMContentLoaded would be much more appropriate, so be cautious.
That quote in itself should prove that onload should not be relied on if you want the full DOM to be loaded properly before you start manipulating it. Instead you should do the following:
Vanilla
document.addEventListener("DOMContentLoaded", function (e) {
/** DOM has been fully loaded here, so manipulation can begin. **/
/** Your code here. **/
});
jQuery
$(document).ready(function () {
/** DOM has been fully loaded here, so manipulation can begin. **/
/** Your code here. **/
});
Click this link to see the difference between vanilla and jQuery.
The second way you can load JavaScript is by having all the script tags within the body but after all the HTML, that way it is guaranteed to load after the HTML.
Example
Try this working example I quickly coded up.
HTML
Replace the content within the body tag of your HTML to the following:
<button id="myJsTest">Click Me!</button>
<div id="clickCounter">Click Count: 0</div>
Replace the contents of your JavaScript with the following:
JavaScript
document.addEventListener("DOMContentLoaded", function() {
var clickCount = 0;
document.getElementById("myJsTest").addEventListener("click", function() {
clickCount++;
document.getElementById("clickCounter").innerText = "Click Count: " + clickCount;
});
});
Then use the Emulate tab in Intel XDK to test it.
Additional Information
When I use Intel XDK and I have an error, I quickly load the file in to the browser and check the console. It can be a really helpful and effective way of squashing those pesky little bugs.
Try using window.alert as alert is defined in the window object.
The reason you're seeing all those "error" messages in the editor window is because you've got the various JSLint/Hint tools loaded in the editor. They're trying to keep you honest and save you lots of time in the debugger chasing potential syntax errors.
The editor inside the XDK is Brackets, it is using standard Brackets extensions to provide those JSLint/Hint tools. You can download it and run it standalone on your system and edit directly within it, you don't have to use the editor inside the XDK (or you can use any other editor you like).
Because the Lint/Hint tools only look at one file at a time, and because your app is normally spread over multiple files, they don't know much about about what's defined in your other files. Likewise, those hint/lint tools need to be told that you're using some of the standard global methods and properties that are expected to be found in a browser (but which may not be found in other JavaScript environments, because JavaScript is no longer limited to just a browser environment -- in fact, your XDK app, aka Cordova app, runs inside a "webview" not in a browser, but that's another story...)
So, you should follow some standard practice of setting up your JSHint/Lint directives at the top of your JS files. For example, this is a good starting point:
/*jslint browser:true, devel:true, white:true, vars:true */
/*global $:false, intel:false */
See the JSHint documentation for details... and see the "Blank Cordova Starter App" in the "Start a New Project" section of the Projects tab for a better blank template to start (there is no real difference between a blank template and a demo app, they are structured identically).
For a more complete and even more instructive app, see the "Hello, Cordova" sample app. Both of those apps can also be found on the Intel XDK GitHub repo.
You are adding the js file that is <script src="js/Test.js"></script> inside header tag.
So js will be first loaded and and it will attach all events to it. But when js is loaded button id="jsTest" is not present because DOM is not loaded.
Solutions :-You can follow either of the approach
Add your js files after DOM is ready
<body>
<button id ="js/Test.js">Test JS</button>
// other HTML tags
<script src = "js/Test.js></script>
</body>
Use window.onload
The load event fires at the end of the document loading process.
window.onload = testJsFile(){
//Your code goes here
}
I will prefer to use the first approach since that also address other issues like page loading time
Try to put the line outside your JS function
document.getElementById(......
inside your html page between
<script>HERE</script>
If this is still no working. Try to add onClick attribute to the button like this:
<button id="" onClick="testJsFile()">
Its also good to use google chrome element inspection while devlopping cuse it will give you error msg for all these things.

Google Map not displaying in file called to webpage

I am working on a site which has a footer that contains a Google Map. On the homepage the footer is coded on the page and displays just fine: http://www.clickityclick.me/morehampton/index.html
However, in all the other pages I call the footer from an external file using jquery like this:
<script>
$(function(){
$('#header').load('header_contact.html')
$('#fatFooter').load('footer.html')
$('#rightNav').load('rightNav.html')
});
</script>
On the pages where the footer is loaded like this, the map does not display every time - only occasionally.
Am I missing something simple that is causing the map to not display correctly every time a page is loaded? I do not want to have to code the footer onto every page.
Any suggestions welcome.
At the moment when you call init_map() #map_canvas doesn't exist(it will be loaded later).
Call the function in the load-callback:
$('#fatFooter').load('footer.html',function(){if(!window.map){init_map();}});
additionally add this to the begin of init_map() to avoid errors:
if(!document.getElementById('map_canvas')){return;}
Usually this has to do with the CSS file not playing nice or it cannot find something and defaults to the browser's default values. When I checked this console log for your home page it contained no errors. But when i checked other pages it threw an error that stated "Uncaught TypeError: Cannot Read property 'offsetWidth' of null' which is the maps width value in short. This might be due to the 404 errors on all the pages except index.html which can be seen in your browsers Source tab.
is showing a 404. I would resolve these 404 errors and it should solve your problem.
You're setting up a race condition between the header/fatFooter/rightNav loading code and your callMap script. All those files are loaded asynchronously, so there's no guarantee which will finish first. In order to prevent your callMap script from running before the fatFooter is loaded, you'll need to use a callback instead of relying on the window's load event.
Since you're using it in two places, it might be easiest to wrap the body of init_map in a try/catch (to handle the case where the race condition doesn't go your way), and add a script block to the bottom of footer.html that calls init_map - but also wrap it in a try/catch. So either way, one try/catch block will trigger.
Another option is to create a custom event that is triggered by the loading of footer.html, and listened to by the callMap script.

loading a js file asynchronously from a js file that loads asynchronously

I had a javascript file(initial.js) on the page inserted through the script tag like so:
<script src="initial.js"></script>
This file creates dom elements(let say two links) and also loads another jQuery plugin(plugin.js) asynchronously via jQuery ajax method. Clicking on those two links brings up a module from the jQuery plugin(plugin.js).
The javascript file(initial.js) was then modified to load asynchronously on the page via jQuery ajax instead of via script tag. This has resulted in some events not getting attached to the links intermittently and this results in the plugin not being called.
I believe the browser is loading the async scripts in its own order and hence the links fail to launch the plugin intermittently. Any pointers to resolve this issue with this new set up?
At a high-level, I think you need to look into something like require.js. Alternatively, you could look into some jQuery event handling code which allows you to listen on load events of calls which may help you determine when one script loaded before loading the next one.
You have probably tried something like this in the past:
var output;
$.get('data.php',function(data){
output=data;
});
alert(output);
You will get an undefined error because Javascript doesn't wait around for the AJAX call to be returned before moving onto the next code.
Same thing goes for scripts. If you place multiple calls to multiple scripts, you will probably get the smallest one returned the quickest, and that script executed. If you load a script that is 10kb and then one that is 1kb, the 1kb script will probably return the quickest and then be executed even though it was called after the 10kb script.
To correct this, you could make a queue system and then only load each script after the previous has loaded:
var scripts=['script1.js','script2.js','script3.js'];
$(document).ready(function(){
loadScript();
});
function loadScript(){
if(sendQueue.length==0)
return;
$.getScript(scripts[0],function(){
scripts=scripts.slice(1);
loadScript();
});
}
But if you are loading scripts from within scripts from within scripts... very Inception like, then this still may not work.

Loading Javascript through an AJAX load through jQuery?

I have an javascript that I place into a page using the code below. What the code does is place an object/embed code into a webpage. Simple javascript loader to a NicoVideo movie
<script type="text/javascript" src="http://ext.nicovideo.jp/thumb_watch/sm13154955?w=640&h=395"></script>
This works great in a webpage. But what if I want to load this javascript into a page using AJAX? This no longer works for the obvious reasons, you would need to eval the script in order to get it to run. However, I have no idea how to do this. I am using jQuery on my page; so keep that in mind. I have tried the following code, but it doesn't seem to work through AJAX, or even in a normal page load environment.
<script>$.getScript("http://ext.nicovideo.jp/thumb_watch/sm13154955?w=640&h=395");</script>
Any ideas on how I would get this to work?
I think it works but its attempting to inline the write which I don't know if that would work in this case.
You would need to see if there was a way to essentially execute the '.getHTML' method and take that result and update an existing element on the page.
The issue though is that the anonymous function that is generated and executed inline might not work properly.
After reading official getScript reference, it seems you have to do something with that JS file you got a hold of, using something like this:
$.getScript("http://ext.nicovideo.jp/thumb_watch/sm13154955?w=640&h=395", function () {
// use functions from loaded file
});

Categories

Resources