如果您接受一条建议,请不要这样做。这里的优先级是内容,图像是次要的。不要因为图像而让用户等待内容。这会让人头疼,尤其是在连接速度较慢的情况下。
最好的办法是使用一些占位符/指示符图像来提供有关加载组件的反馈,并且可能对<img> 标签中的图像使用一些不错的淡入淡出效果。
注意:对于小图像,您可以尝试Data: URIs,它允许您将图像嵌入到 HTML 或 CSS 文件中。
更新
永远不要说不。 :) 这是您可以使用的原型。它在 FF 3+ 和 IE 5.5+ 中对我来说很好,但由于某种原因,Chrome 显示 cssRules 为空。我必须弄清楚为什么。另一个 TODO 是在 IE 中合并 @import-ed 规则,因为它不能与标准规则集一起使用。
无论如何,如您所见,您需要传递一个document、一个callback 并且有一个可选 timeout 参数(默认为10 秒)。
callback 将在文档中的每个图像加载后执行。 (请注意,如果它因 404 失败,脚本会处理它)。在这里你可以做你的fadeIn或show之类的。
timeout 是作为备用的,如果出现任何问题,它会在一定时间后调用回调。
// this function will execute a callback after all
// images has been loaded in a document
function imageLoader(document, callback, timeout) {
timeout = timeout || 10000; // 10s default
var i, j, remaining = 0; // number of loading images
// hash table to ensure uniqueness
// url => image object
var imgs = {};
function handler(el, event) {
remaining -= 1;
if (remaining == 0 && !callback.done
&& typeof callback === "function") {
callback.done = true;
callback();
}
}
// adds the image to the hash table
function addImage(src, img) {
if (!imgs[src]) {
remaining++;
img = img || new Image();
img.onload = handler;
img.onerror = handler;
img.src = img.src || src;
// add to the hash table
imgs[src] = img;
}
}
// now gather all those images
var sheets = document.styleSheets;
for (i=0; i<sheets.length; i++) {
// HTML <img> tags
var els = document.getElementsByTagName("IMG");
for (i=0; i<els.length; i++) {
var el = els[i].src;
addImage(el.src, el);
}
// CSS background images
var css = sheets[i];
var pos = css.href.lastIndexOf("/");
var cssDir = (pos != -1) ? css.href.substring(0, pos + 1) : "";
var rules = css.cssRules || css.rules;
for (j=0; j<rules.length; j++) {
var style = rules[j].style;
var img = style.backgroundImage;
if (img == "none") img = "";
var filename = img.substring(4, img.length - 1).replace(/['"]/g,"");
if (filename) {
if (filename.indexOf("http://") != 0
&& filename.indexOf("/") != 0) {
filename = cssDir + filename;
}
addImage(filename);
}
}
}
// correct the start time
var start = +new Date();
var timer = setInterval(function(){
var elapsed = +new Date() - start;
// if timout reached and callback
// hasn't been not called yet
if (elapsed > timeout && !callback.done) {
callback();
callback.done = true;
clearInterval(timer);
}
}, 50);
}