0

I have the following simple JavaScript that loads a bunch of images and places them on HTML canvas (canvasCTX is the 2D canvas context):

for (var i=0 ;i<10; i++) {   
  var placementX = i*25;
  var imageObj = new Image();
  imageObj.src = 'assets/png/' + i + '.png';
  imageObj.onload = function() {
    canvasCtx.drawImage(imageObj,placementX,0);
  };
}

Now the problem I find is that all the images are placed at the same place - the last variable created by the loop. I think that's because the for loop continues to run whilst images are being loaded, as the onload is an asynchronous event.

How do I make sure each image gets the correct placementX from it's turn in the for loop?

benRollag
  • 1,219
  • 4
  • 16
  • 21
CaribouCode
  • 13,998
  • 28
  • 102
  • 174

3 Answers3

1

try this code .

function draw(placementX , imagePath)
{

  var image = document.createElement("img");
  image.src=imagePath;        
  console.log(placementX , "before loading");//to ensure that x befor image loading is the same after loading

  image.onload=(function()
  { 
                canvas.drawImage(image , placementX  , 0);
                console.log(placementX , " after loading");//to ensure that x befor image loading is the same after loading

  });
}

var placementX =0;

for (var i=0 ;i<10; i++) 
{   
     placementX = i*25;
     draw('assets/png/' + i + '.png' , placementX );

}
Mo Haidar
  • 3,748
  • 6
  • 37
  • 76
0

Use a closure.

for (var i=0 ;i < 10; i++) {   
    (function(x){
        var placementX = x*25;
        var imageObj = new Image();
        imageObj.src = 'assets/png/' + x + '.png';
        imageObj.onload = function() {
        canvasCtx.drawImage(imageObj,placementX,0);
        };
    })(i);

}
user3152069
  • 408
  • 3
  • 9
  • couldn't get this method to work for some reason although I did find a solution by putting the onload in a separate function and calling that in the for loop, whilst sending the relevant variable to it at the time. I'm wondering if this method tries to achieve the same thing. – CaribouCode May 17 '14 at 01:21
  • This suggested method can work, but is less efficient than defining a single function outside the loop and calling it as needed from within. – JAAulde May 17 '14 at 01:26
0
    var i=0
    function update_image()
    { if(i<10)
    {   
          var placementX = i*25;
          var imageObj = new Image();
          imageObj.src = 'assets/png/' + i + '.png';
          imageObj.onload = function() {
            canvasCtx.drawImage(imageObj,placementX,0);
           i++;
    update_image();
          }
        }
update_image();
ProllyGeek
  • 15,517
  • 9
  • 53
  • 72