如何将变量与函数动态绑定

How to dynamically bind variable with a function?

本文关键字:函数 动态绑定 变量      更新时间:2023-11-17

问题:当image.onload事件下载并检测到新图像时,必须动态更改以前加载的图像。比如说,picture1.png下载并立即更改,picture2.png下载后立即更改,依此类推。我试过下面的方法,但没有成功:

<script type="text/javascript">
 loadImage = function(){    
     var imgs = new Array();    
     var IMG = document.getElementsByTagName('img');    
     for(var i=1;i<=IMG.length;i++)
     {
       imgs[i] = new Image();
       imgs[i].src = "picture" + i + ".png";
       imgs[i].onload = function(){
         alert('picture'+i+' loaded');
         IMG[i].setAttribute('src',imgs[i].getAttribute('src'));
       }           
     }              
 }    
</script>    
 <img src="sample.png" />
 <img src="sample.png" />
 <img src="sample.png" />
 <img src="sample.png" />
 <input type="button" value="Load Image" onclick="loadImage()"> 

事情将如何以期望的方式发生?

使用closure,因为onload事件是异步的。onload处理程序中i的值将是循环的maximum值,因为当它是invoked时,循环已经迭代。

function loadImage() {
  var temp = ['http://lorempixel.com/400/200/sports/1/', 'http://lorempixel.com/400/200/sports/2/', 'http://lorempixel.com/400/200/sports/3/'];
  var IMG = document.getElementsByTagName('img');//Get all the image tag elements from DOM
  for (var i = 0; i < IMG.length; i++) { //Loop for all elements selected
    var image = new Image();// New Image() object
    image.onload = (function(i, image) { // Closure to keep value from loop(i and image) as javascript is having function level scope and using closure, we can keep the value in the memory to be used later
      return function() { // return function as a handler of image onload and it will be getting valid(not final) value of the loop(current instance)
        alert(image.src);
        IMG[i].src = image.src;
      }
    })(i, image);
    image.src = temp[i];
  }
}
<img src="http://lorempixel.com/400/200/sports/5/" />
<img src="http://lorempixel.com/400/200/sports/6/" />
<img src="http://lorempixel.com/400/200/sports/7/" />
<input type="button" value="Load Image" onclick="loadImage()">

您可以使用javascript本机"bind"方法来执行此操作。例如:

var fn = function(index){
     alert('picture'+ index +' loaded');
     this.setAttribute('src',imgs[index].getAttribute('src'));
};
imgs[i].onload = fn.bind(IMG[i], i);