The impossible inline Javascript delay/sleep

Yeah, the fact that javascript is single threaded really bites you here. You can use a synchronous ajax call to a purposefully slow page to emulate a sleep, but you aren't going to get the results you want. Why don't you just make sure that your IFrame is loaded before unchangeable function is called?


What you really need is an event to be fired when the iFrame content has loaded. This is actually really easy because the page inside the iFrame has its own events and it can access scripts on the parent page. You will need to be able to change the contents of the iFrame though.

In your iFrame, you'll need this piece of code

// Use whichever DOMReady function you like, or window.onload would work
window.addEventListener('DOMContentLoaded', function() {
    if (parent.window.myFunction) {
        parent.window.myFunction();
    }
}, false);

Then in your parent page, make a function called "myFunction" and put all the scripts you need to fire in there. This should work every time.

Edit: To get this to work you really need two functions. I'm assuming that's really not an option so we'll hack the one function to contain two functions and call the right part when we need it to.

function onlyThingYouCanChange(stringOrObject) {
    function createIFrame(objectToAppendIFrameTo) {
        // This comment represents all the code that appends your iFrame
    }
    function onIFrameReady() {
        // This comment represents all the stuff you want to happen when the iFrame is ready
    }

    // The bones of it
    if (stringOrObject === "iFrameLoaded") {
        onIFrameReady();
    } else {
        createIFrame(stringOrObject);
    }
}

The script in the iFrame should now be changed to something like this:

// Use whichever DOMReady function you like, or window.onload would work
window.addEventListener('DOMContentLoaded', function() {
    if (parent.window.onlyThingYouCanChange) {
        parent.window.onlyThingYouCanChange('iFrameLoaded');
    }
}, false);

I haven't tested it, but in theory that should do it


NB This is extremely hacky, and I wouldn't use it in any real-world situation. Among other potential issues, given sufficient traffic you could end up DDOSing yourself.

You could create sleep functionality by making non-asynchronous (A)JAX calls. In some older browsers this may freeze everything, but at least it won't require any kind of user response.

while (!iFrameLoaded)
{
    if (XMLHTTPRequest) {
        var request = new XMLHttpRequest();
    } else {
        var request = new ActiveXObject("Microsoft.XMLHTTP");
    }

    request.open('GET', 'anyoldfile.htm', false);
    request.send();

    // check if the iframe is loaded and set iFrameLoaded
}