2017-06-06 556 views
0

我目前正在构建一个应用程序,用户可以在其中同时上传多个图像并使用它们。由于一些进程由于大图像文件而表现不佳,我想在用户获得它们之前调整它们的大小。如何使用img.onload返回函数?

在我的resizer()函数中,我尝试使用画布调整大小。它可以工作,但由于'canvas.toDataURL()'在img.onload函数中,所以我不知道如何返回值并将其解析为handleFiles()函数。

而且......我尝试了一些案件中,我从handleFiles()一些代码 - 这样的:

var preview = document.getElementById("img"+count); 
var surface = document.getElementById("cubface"+count); 
var count = counterImg(); 
preview.src = resizer(e.target.result, count); 
surface.src = resizer(e.target.result, count); 

,并把它们在img.onload函数的最后像

var preview = document.getElementById("img"+number); 
var surface = document.getElementById("cubface"+number); 
preview.src = canvas.toDataURL; 
surface.src = canvas.toDataURL; 

我获得了调整大小,但是我只获取了要处理的循环中的最后一幅图像。

所以问题是:

  1. resizer()功能,如何返回canvas.toDataURL值是img.onload

  2. 为什么循环仅覆盖最后一个实例而不是每个图像以及如何解决这个问题?

全码:

的JavaScript:

function resizer(base64, number){ 

    // Max size for thumbnail 
    if(typeof(maxWidth) === 'undefined') maxWidth = 1200; 
    if(typeof(maxHeight) === 'undefined') maxHeight = 1200; 

    var img = new Image(); 
    img.src = base64; 

    // Create and initialize two canvas 
    var canvas = document.createElement("canvas"); 
    var ctx = canvas.getContext("2d"); 
    var canvasCopy = document.createElement("canvas"); 
    var copyContext = canvasCopy.getContext("2d"); 

    img.onload = function() { 

     // Determine new ratio based on max size 
     var ratio = 1; 
     if (img.width > maxWidth) 
      ratio = maxWidth/img.width; 
     else if (img.height > maxHeight) 
      ratio = maxHeight/img.height; 

     // Draw original image in second canvas 
     canvasCopy.width = img.width; 
     canvasCopy.height = img.height; 
     copyContext.drawImage(img, 0, 0); 

     // Copy and resize second canvas to first canvas 
     canvas.width = img.width * ratio; 
     canvas.height = img.height * ratio; 
     ctx.drawImage(canvasCopy, 0, 0, canvasCopy.width, canvasCopy.height, 0, 0, canvas.width, canvas.height); 

     return canvas.toDataURL(); 

    }; 

    return img.onload; 

} 


function handleFiles(files) { 
    for (var i = 0; i < files.length; i++) { 
     var file = files[i]; 
     var count = counterImg(); 
     var preview = document.getElementById("img"+count); 
     var surface = document.getElementById("cubface"+count); 

     var reader = new FileReader(); 
     reader.onload = (function (preview, surface) { 
      return function (e) { 
       var newimage = resizer(e.target.result, count); 
       preview.src = newimage; 
       surface.src = newimage; 
       $('#image-cropper'+count).cropit('imageSrc', e.target.result); 
      } 
     })(preview, surface); 
     reader.readAsDataURL(file); 
    } 
} 
+0

你肯定在$('#图像栽跟头'+ count)变量数的范围是否正确?您可能想将其添加到您的功能(预览,表面)。 – user3220633

+0

它只是这个功能: 'var j = 0; function counterImg(){ j ++; return j; }' – PLAYCUBE

回答

1

变量count不能正常范围的。

从声明函数的时间到使用它的时间之间存在延迟,因此每次执行都以相同的值结束。所以jquery选择器将始终返回相同的元素。这就解释了为什么只有最后一张图像被修改。

下面是一个演示执行的jsfiddle。

https://jsfiddle.net/Lc6bngv5/1/

为了解决这个问题,简单地传递数到封装的预览和表面的功能:

reader.onload = (function (preview, surface, count) { 
     return function (e) { 
      var newimage = resizer(e.target.result, count); 
      preview.src = newimage; 
      surface.src = newimage; 
      $('#image-cropper'+count).cropit('imageSrc', e.target.result); 
     } 
    })(preview, surface, count); 

对于第二个问题:

调整大小函数返回的功能。它不会返回该函数的结果。要正确地获得url,我会用一个回调函数:

reader.onload = (function (preview, surface, count) { 
    return function (e) { 
     var newimage = resizer(e.target.result, count, function(url){ 
      preview.src = url; 
      surface.src = url; 
      $('#image-cropper'+count).cropit('imageSrc', e.target.result); 
     }); 
    } 
})(preview, surface, count); 

而且你必须做调整大小以下变化:

function resizer(base64, number, cb){ 
    ... 
    img.onload = function() { 
     ... 
     // return canvas.toDataURL(); 
     cb(canvas.toDataURL()); 
    }; 
} 
+0

哇,谢谢你的建议!这解决了第二个问题。任何想法如何在'img.onload'中返回,所以我可以将'canvas.toDataURL();'解析为'handeFiles()'? – PLAYCUBE

+1

我添加了一个编辑,你可以使用回调函数,这将允许你正确地得到结果。 – user3220633

+0

谢谢!这太棒了! – PLAYCUBE

相关问题