Javascript 检查图像加载是否完成

Javascript 检查图像加载是否完成,javascript,jquery,Javascript,Jquery,我有一个页面有太多的图像,这些图像被不平等地划分为divs哪些类是photossetc。保存所有div的主div的id为infsroll。开始时,每个divvisibility是隐藏的,位置是绝对的,每个div都有一个名为myflagc的属性,该属性的值是“notok” 我不想等待页面中的所有图像加载以显示divs,因此将加载绑定到窗口不是一个选项,而是要显示独立加载的每个div 下面是我编写的jQuery/JavasScript代码: function imagesloaded(){

我有一个页面有太多的图像,这些图像被不平等地划分为
div
s哪些类是
photossetc
。保存所有
div
的主
div
的id为
infsroll
。开始时,每个
div
visibility
隐藏的
位置
绝对的
,每个
div
都有一个名为
myflagc
属性,该属性的值是
“notok”

我不想等待页面中的所有图像加载以显示
div
s,因此将加载绑定到窗口不是一个选项,而是要显示独立加载的每个
div

下面是我编写的jQuery/JavasScript代码:

function imagesloaded(){

    var infscrolllength=jQuery('#infscroll').find('.photossetc').length;
    // gets the numbers of divs
    var completedsts = 0;
    // variable for the number of divs that completed loading (set to 0)

        jQuery('#infscroll .photossetc').each(function(){
        // loops over the divs

            if(jQuery(this).attr("myflagc")=="notok"){
                var photosetclength = jQuery(this).find('img').length;
                var totalcomplete = 0;
                jQuery(this).find('img').each(function(){
                    if(this.complete){
                        totalcomplete++;
                    }
                })
                if(totalcomplete==photosetclength){
                    sortpho(jQuery(this));
                    completedsts++;
                }
            }
            else{
                completedsts++;
            }
    })
    if(infscrolllength != completedsts){
        imagesloaded();
    }

}

function sortpho(setselector){
    setselector.css({"position":"relative"});
    setselector.css({"visibility":"visible"});
    setselector.attr({"myflagc":"ok"});
}

jQuery(document).ready(function(){
imagesloaded();

});
但是,由于未知的原因,此代码似乎不起作用。然而,我注意到,如果我在
imagesloaded()
函数的任何地方添加一个
alert
,它会正常工作,这通常意味着DOM还没有准备好,但因为我使用的是
jQuery(document)。ready
不可能是这样。我还尝试在此块末尾添加一个警报:

if(infscrolllength != completedsts){
    imagesloaded();
    alert("not completed yet");
}
我注意到它会多次触发,直到加载所有图像,这意味着代码是正确的,因此我不明白为什么没有
警报它就不能工作

我知道我可以
bind
load
事件绑定到每个
div
但是
load
与缓存的图像有问题,所以我想避免使用它

有解决办法吗?更重要的是,我想了解为什么这段代码不起作用

更新:解决方案

正如Christian Landgren提到的(见答案);JavaScript函数保持循环,防止页面呈现(即加载内容)

我找到了一种解决方法,可以实现我想要的,而不完全依赖
.load
方法。代码如下:

function imagesloaded(){
    var mysets=[];
    var setnbr=0;
    var iditer=0;
    jQuery('#infscroll .photossetc').each(function(){
        jQuery(this).attr({"id":"photosetn"+iditer});
    // giving a unique id to every div
        iditer++;
    })
    jQuery('#infscroll .photossetc').each(function(){
        var myset=[];
    // creating an array to hold the following info 0:id of div - 1: nbr of images in div - 2: nbr of images that finished loading
        myset[0]=jQuery(this).attr("id");
        myset[1]=jQuery(this).find('img').length;
        myset[2]=0;
        jQuery(this).find('img').each(function(){
            if(this.complete){  // for when the image is already cached or already loaded
                myset[2]=myset[2]+1;
            }
            else{ // for when the image isn't cached nor loaded yet
                jQuery(this).load(function(){
                    for(i=0;i<mysets.length;i++){
                        var myiset=mysets[i];
                        if(jQuery(this).parents('#infscroll .photossetc').attr("id")==myiset[0]){
                            myiset[2]=myiset[2]+1;
                            if(myiset[1]==myiset[2]){
                                jQuery('#'+myiset[0]).css({"position":"relative","visibility":"visible"});
                            }                                   
                            mysets[i]=myiset;
                        }
                    }
                })
            }
        })
        if(myset[1]==myset[2]){
            jQuery('#'+myset[0]).css({"position":"relative","visibility":"visible"});
        }
        mysets[setnbr]=myset;
        setnbr++;
    })
}
函数imagesloaded(){
var mysets=[];
var setnbr=0;
变量iditer=0;
jQuery('#infscroll.photossetc')。每个(函数(){
jQuery(this.attr({“id”:“photosetn”+iditer});
//为每个div提供唯一的id
iditer++;
})
jQuery('#infscroll.photossetc')。每个(函数(){
var myset=[];
//正在创建一个数组以保存以下信息0:div-1的id:div-2中图像的编号:已完成加载的图像的编号
myset[0]=jQuery(this.attr(“id”);
myset[1]=jQuery(this.find('img').length;
myset[2]=0;
jQuery(this).find('img').each(function(){
if(this.complete){//for当映像已缓存或已加载时
myset[2]=myset[2]+1;
}
else{//用于图像尚未缓存或加载的情况
jQuery(this.load)(函数(){

对于(i=0;iJavascript正在阻塞,这意味着您的循环将阻塞所有Javascript执行,直到满足该语句。当您添加警报时,您至少让后台布局威胁在后台加载图像,直到您按下OK,循环继续

如果要跟踪已加载的图像数量,需要在每个图像上附加一个onload事件,该事件将独立更新loadcounter

大概是这样的:

var loadCounter = 0;

function allDone(){
  // all images are loaded.
}

function imageLoaded(){
  loadCounter++;
  if (loadCounter === $('img').length){
    allDone();
  }
}

$('img').on('onload', imageLoaded)
当你说你负担不起使用onload事件时,你能详细说明一下吗?你需要跟踪load事件,以了解何时加载了所有内容。我已经成功地使用了它,并且它对缓存的图像也很有效-这些都没有任何问题

另一个(不太突出的)选项是以间隔全局检查加载计数

另一个提示是,如果您正在开发无限卷轴,则需要使用队列来处理开始加载的图像。目前无法中止单个图像请求。这意味着一旦您将图像添加到DOM树中,它将在布局引擎中排队,并且您无法从页面中删除该图像ue


解决这个问题的一个好方法是使用Async.queue机制,并将onload事件附加到Async next方法。

也许这对您有帮助,正如我所说,加载事件与缓存的图像有问题,我无法使用它。我想有一个解决方法:如果我理解正确,如果JavaScript代码正确,谢谢您的回答运行时,布局停止渲染,直到所有JavaScript代码都完成?换句话说,JavaScript代码和浏览器的布局渲染在同一线程中运行?此外,加载函数的问题是,如果缓存了图像,则不会触发。API参考:查看部分:加载的注意事项中提到了这一点t当与imagesYes一起使用时,这就是问题所在。如果您愿意,可以使用单独的工作进程-查找(我使用了load事件,它在Safari、Chrome和Firefox中运行良好,甚至在缓存的图像上也是如此)非常感谢。这解释了一切。我会检查更多的加载功能,但我找到了一个解决方法,我会用这个解决方法更新我的帖子。