-2

*Note: This is not concerning img tags. This is strictly a question about CSS background images.

I am trying to make a nice ajax-based template that does not refresh the page, but rather exchanges the content within a specific div. Everything is working well, except that the background images are never fully loaded by the time the newly loaded div is revealed to the user. I would expect the process to look like this:

  1. HTML content is loaded.
  2. The CSS images begin to load asynchronously.
  3. The callback function runs to completion.

For the sake of testing, I delayed the reveal just to make sure the images would have time to load before the function finished. Even with 5 extra seconds, it still displays blank boxes where images should be for a second before loading, no matter how long it's delayed. This leads me to conclude the flow must be acting more like this:

  1. HTML content is loaded.
  2. The callback function runs to completion.
  3. The CSS images begin to load asynchronously.

The "load" event does not seem to account for CSS images, and there does not seem to be any event that allows a script to wait for the CSS images to finish loading.

I even tried hacking around it by looping through every single element, checking for the presence of a background image, then creating a new Image() with a load event for each one, but that, needless to say, exceeds the call stack.

So my question is, how can I simply wait for all background images to fully display before moving forward with the script?

  • note `
    `'s don't have a `load` event, could you provide the code of your request? It sounds like you are setting the images / loading the css in your callback
    – Patrick Barr Apr 05 '17 at 20:45
  • I had no idea load events were limited like that, thanks for that bit of info. The pageDiv is located in the body, and the css link is located in the head. The css is never refreshed, but the html content inside pageDiv is unloaded and replaced by the new page's html. The css reference shouldn't be affected at all by the replacement of inner html. –  Apr 05 '17 at 20:54
  • I understand the example you gave is an attempt at a workaround for your problem, but it would never work, as you're using the callback of the outer `.load` to create a load event handler `on("load", ...`, not execute it. Also, when testing did you properly close it with parenthesis? You are aware that jQuery has 2 `.load` methods (one of them deprecated) ? – yezzz Apr 05 '17 at 21:05
  • It was a messy workaround I'm not proud of, haha. Since scripts are synchronous, I was essentially going to catch the script in a while loop until the event fired by setting var loaded = true; Regardless, it still didn't work. I am aware the event listener will not tie up the script without some extra stuff. –  Apr 05 '17 at 21:17
  • Actually, disregard the previous comment, I was thinking of a different point in time. This event listener didn't need to execute immediately, because until it fired, the div would be hidden anyway. –  Apr 05 '17 at 21:26
  • well at least you fixed that code ;) – yezzz Apr 05 '17 at 21:33

1 Answers1

1

Only once CSS is actually applied to an element does it load images and other external resources. Loading <img> tags are much easier to handle (see this question and answer). But, you COULD take advantage of caching and force the images to be loaded before that .load() call by using one of a few different approaches in HTML, CSS or JS, as follows:

HTML: Add an HTML tag to your like <link rel="prefetch" href="image.png"> for each image

CSS: Load all the images into some hidden element that exists on the initial load (see this answer).

JS: You can have JS load each image on page load (see this answer)

No matter which of these approaches you pick, you would need to specify the images to be preloaded. None of these solutions automatically pick up the image paths from the CSS.

NOTE: Each of these approaches may have varying cross-browser support. I would recommend double-checking your project requirements before using any of them.

Community
  • 1
  • 1
BCDeWitt
  • 4,540
  • 2
  • 21
  • 34
  • 2
    Some browsers may even defer loading an image until the element is actually visible. Be aware of that. http://stackoverflow.com/questions/18445663/css-based-image-preloader-doesnt-work/18445821#18445821 – yezzz Apr 05 '17 at 21:47