1

我遇到了画布问题。不返回任何错误。我正在尝试制作一个加载器,在应用程序启动之前加载所有资源,如图片、声音、视频等。加载器必须绘制动态加载的资源数。但是此时,我的加载器的结果是冻结浏览器,直到它绘制加载的资源总数。

如果我不清楚,请告诉我:) 这是代码:

function SimpleLoader(){
    var ressources ;
    var canvas;
    var ctx; 

    this.getRessources = function(){
        return ressources;
    };

    this.setAllRessources = function(newRessources){
        ressources = newRessources;
    };

    this.getCanvas = function(){
        return canvas;
    };

    this.setCanvas = function(newCanvas){
        canvas = newCanvas;
    };

    this.getCtx = function(){
        return ctx;
    };

    this.setCtx = function(newCtx){
        ctx = newCtx;
    };
};

SimpleLoader.prototype.init = function (ressources, canvas, ctx){
    this.setAllRessources(ressources);
    this.setCanvas(canvas);
    this.setCtx(ctx);
};

SimpleLoader.prototype.draw = function (){
    var that = this;
    this.getCtx().clearRect(0, 0, this.getCanvas().width, this.getCanvas().height);
    this.getCtx().fillStyle = "black";
    this.getCtx().fillRect(0,0,this.getCanvas().width, this.getCanvas().height)
    for(var i = 0; i < this.getRessources().length; i++){
        var data = this.getRessources()[i];
        if(data instanceof Picture){
            var drawLoader = function(nbLoad){
                that.getCtx().clearRect(0, 0, that.getCanvas().width, that.getCanvas().height);
                that.getCtx().fillStyle = "black";
                that.getCtx().fillRect(0,0, that.getCanvas().width, that.getCanvas().height);
                that.getCtx().fillStyle = "white";
                that.getCtx().fillText("Chargement en cours ... " + Number(nbLoad) +"/"+ Number(100), that.getCanvas().width/2, 100 );
            }
            data.img = new Image();
            data.img.src = data.src;
            data.img.onload = drawLoader(Number(i)+1); //Update loader to reflect picture loading progress
        } else if(data instanceof Animation){
            /* Load animation */
        } else if(data instanceof Video){
            /* Load video */
        } else if(data instanceof Sound){
            /* Load sound */
        }else {

        }
    }
};

因此,使用此代码,所有资源都已加载,但我想显示加载进度。对我错过了什么的一些想法?

4

1 回答 1

1

您在加载程序中“忙于循环”,因此浏览器没有机会重绘/更新画布。

您可以在循环中实现setTimeout(getNext, 0)或将绘制函数放在轮询当前状态之外。requestAnimationFrame在这种情况下,我会推荐前者。

在伪代码中,这是使其工作的一种方法:

//Global:
    currentItem = 0
    total = numberOfItems

//The loop:
    function getNextItem() {
        getItem(currentItem++);
        drawProgressToCanvas();

        if (currentItem < total)
            setTimeout(getNextItem(), 0);
        else
            isReady();
    }
    getNextItem(); //start the loader

根据需要采用。

值为 0的setTimeout将在下次有可用时间时提示调用(即在重绘、清空事件堆栈等之后)。isReady()这只是加载所有内容后进入下一步的一种方法。(如果您发现使用 0 有任何问题,请尝试使用例如 16。)

使用requestAnimationFrame是一种更底层和更有效的方式。目前并非所有浏览器都支持它,但有一些 polyfills 可以帮助你解决这个问题 - 对于这种用法,它并不那么重要,但只是为了让你也知道这个选项(如果你没有'已经)。

于 2013-05-14T08:13:25.703 回答