此函数读取从输入字段获取的文件并返回其dataUrls:
readAsDataURL (target) {
// target => <input type="file" id="file">
var reader = new FileReader()
return new Promise(function (resolve, reject) {
reader.onload = function (event) {
resolve(event.target.result)
}
reader.readAsDataURL(target.files[0])
})
},
如您所见,该功能仅处理单个文件。我想要返回多个文件。我尝试了reader.readAsDataURL(target.files)
,但收到了此错误:'readAsDataURL' on 'FileReader': parameter 1 is not of type 'Blob'.
如何让函数返回多个dataUrls?
答案 0 :(得分:2)
您是否尝试过使用Promise.all?您可以执行以下操作:
fileToDataURL(file) {
var reader = new FileReader()
return new Promise(function (resolve, reject) {
reader.onload = function (event) {
resolve(event.target.result)
}
reader.readAsDataURL(file)
})
}
readAsDataURL (target) {
// target => <input type="file" id="file">
var filesArray = Array.prototype.slice.call(target.files)
return Promise.all(filesArray.map(fileToDataURL))
}
这基本上与您设置的相同,但为每个创建一个承诺,只有在完成所有内容后才将结果返回到数组中。
我忘了您不能直接将target.files
视为数组,因此需要先将其转换。为此,您可以使用:Array.prototype.slice.call(target.files)
答案 1 :(得分:2)
从问题中不清楚你对这些数据库有什么用处,但大多数时候,你实际上并不需要它。
为了能够将用户文件或Blob中的媒体显示到您的文档中,最好使用将返回blobURI的URL.createObjectURL()
方法,您可以使用像任何网址一样。
blobURI优势的非详尽列表:
readAsDataURL()
相比,你应该注意后者将首先完全读取文件,将其转换为base64字符串(比原始数据大34%),最后,你将把这个大字符串存储在DOM& #39;标记,使其始终存在于内存中。从那时起,浏览器将再次读取它,将其转换为二进制文件,再次将其作为二进制文件读取,最后将其作为普通资源进行处理。
然后直接发送文件,作为多部分数据。如果你想在那里保存文件,那么前端的工作就会减少,管道中的工作量就会减少(记住~34%),而服务器端的工作就会减少。
大多数服务器端语言都有简单的内置方法来捕获POST请求中的文件,您可以使用FormData
API从前面轻松发送。
以下是您的代码示例,使用blobURIs,它会将所有文件都视为图像。
document.querySelector('input').onchange = function(){
// FileList doesn't have an forEach method yet
Array.prototype.forEach.call(this.files, function(file){
if(file.type.indexOf('image/' === 0)){
var i = new Image();
i.src = URL.createObjectURL(file); // creates a blobURI
document.body.appendChild(i);
}
});
};
&#13;
<input type="file" multiple>
&#13;
但请注意,此方法也可以缺点:
URL.revokeObject(blobURI)
时或在页面的硬刷新时。在这种情况下,您应该使用mediaElement.srcObject = MediaStream;
代替。对于您创建的Blob(不是来自<input>
),同样适用:blob将被卡在内存中,直到明确释放。在这种情况下,只需在加载资源后调用URL.revokeObjectURL(blobURI)
即可。
img.onload = URL.revokeObjectURL(img.src);
img.src = URL.createObjectURL(the_Blob_I_built);