最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - How to wait for loading images in canvas - Stack Overflow

programmeradmin0浏览0评论

My test needs to interact with the image loaded in canvas.

But I have no idea how to implement the wait of loading the image. If I expect only canvas tests are beginning to interact with it, while the image is still loaded.

I have to use driver.sleep(), but this is a bad and unreliable solution. There are a part of page code with canvas:

<canvas class='ol-unselectable' width='816' height='400' style='width: 100%; height: 100%;'></canvas>

Also, the application is written in Angular.

The Network tab in the developer console in the browser shows that at the time of loading images is Img request.

I think, it is possible to write some code to check the load the image into canvas in the browser and use it via js executor.

But I have not idea how do it. Help me please.

UPD. I try build custom waiting condition:

exports.isAllImageLoad = function isAllImageLoad(driver) {
    return new Condition('image loading', function(driver) {
        return driver.executeScript(
            'var img = new Image();' +
            'img.onload = function() { return true; };' +
            'img.onload()'
        ).then(function(result) {
            console.log('image loading: ' + result);
            return result;
        });
    });
};

and use it with:

return driver.wait(isAllImageLoad(driver), waitTimeOut);

But console show me thah result of img.onload() is null.

UPD.i try use this code:

exports.isAllImageLoad = function isAllImageLoad(driver) {
    return new Condition('image loading', function(driver) {
        return driver.executeScript(
            'var image = new Image();' +
            'function mainLoop(){' +
                'if(imageplete){' +
                    'return true;' +
                '}else{' +
                    'return false;' +
                '}' +
            '}' +
            'mainLoop();'
        ).then(function(result) {
            console.log('image loading: ' + result);
            return result;
        });
    });
};

But the same returns null.

My test needs to interact with the image loaded in canvas.

But I have no idea how to implement the wait of loading the image. If I expect only canvas tests are beginning to interact with it, while the image is still loaded.

I have to use driver.sleep(), but this is a bad and unreliable solution. There are a part of page code with canvas:

<canvas class='ol-unselectable' width='816' height='400' style='width: 100%; height: 100%;'></canvas>

Also, the application is written in Angular.

The Network tab in the developer console in the browser shows that at the time of loading images is Img request.

I think, it is possible to write some code to check the load the image into canvas in the browser and use it via js executor.

But I have not idea how do it. Help me please.

UPD. I try build custom waiting condition:

exports.isAllImageLoad = function isAllImageLoad(driver) {
    return new Condition('image loading', function(driver) {
        return driver.executeScript(
            'var img = new Image();' +
            'img.onload = function() { return true; };' +
            'img.onload()'
        ).then(function(result) {
            console.log('image loading: ' + result);
            return result;
        });
    });
};

and use it with:

return driver.wait(isAllImageLoad(driver), waitTimeOut);

But console show me thah result of img.onload() is null.

UPD.i try use this code:

exports.isAllImageLoad = function isAllImageLoad(driver) {
    return new Condition('image loading', function(driver) {
        return driver.executeScript(
            'var image = new Image();' +
            'function mainLoop(){' +
                'if(image.plete){' +
                    'return true;' +
                '}else{' +
                    'return false;' +
                '}' +
            '}' +
            'mainLoop();'
        ).then(function(result) {
            console.log('image loading: ' + result);
            return result;
        });
    });
};

But the same returns null.

Share Improve this question edited Mar 1, 2017 at 3:29 Valentina asked Feb 28, 2017 at 18:02 ValentinaValentina 6542 gold badges11 silver badges25 bronze badges 2
  • Thanks for the replies. All solutions propose to use the image url, but the fact is that the images load is different, depending on the previous actions of the user. – Valentina Commented Mar 1, 2017 at 2:55
  • I try build custom waiting condition: exports.isAllImageLoad = function isAllImageLoad(driver) { return new Condition('image loading', function(driver) { return driver.executeScript( 'var img = new Image();' + 'img.onload = function() { return true; };' + 'img.onload()' ).then(function(result) { console.log('image loading: ' + result); return result; }); }); }; and use it with: return driver.wait(isAllImageLoad(driver), waitTimeOut); But console show me thah result is null. – Valentina Commented Mar 1, 2017 at 2:57
Add a ment  | 

2 Answers 2

Reset to default 1

The is an alternative approch to waiting for the onload.

When the DOM has done all it can with the image and it has loaded, or the image has failed to load it sets the semaphore image.plete to true.

You can use that semaphore to determine whether or not it is safe to render the image.

var image = new Image();
image.src = "imageURI";
function mainLoop(){
     if(image.plete){
          ctx.drawImage(image,0,0,100,100);
     }else{
          ctx.fillRect(0,0,100,100); // image placeholder
     }
     requestAnimationFrame(mainLoop);
}
mainLoop();

This allows you to continue rendering while images are loading.

Though you can not tell directly if the image has loaded or there is an error.

An alternative is to attach your own semaphore.

var image = new Image();
image.src = "imageURI";
image.onload =  function(){this.ready=true}

And use the ready semaphore to indicate that the image is ready to render.

You can place all your code inside the image onload event that you wanna process after the image has been successfully loaded.

DEMO (drawing an image on canvas after its been loaded successfully)

var ctx = document.getElementById('canvas').getContext('2d');
ctx.fillStyle = 'black';
ctx.font="50px Arial";
ctx.fillText('Loading...', 300, 200);
var image = new Image();
image.src = 'https://s-media-cache-ak0.pinimg./originals/e9/dc/10/e9dc10141d0b4e5c9e360cc5669e65ed.jpg';
image.onload = function() {
  ctx.clearRect(0, 0, 816, 480)
  ctx.drawImage(image, 0, 0);
}
#canvas {
  background-color: lightgrey;
}
<canvas id="canvas" class="ol-unselectable" width="816" height="400" style="width: 100%; height: 100%;"></canvas>

发布评论

评论列表(0)

  1. 暂无评论