FineUploader:运行中的客户端缩略图

FineUploader: Thumbnails on the fly clientside

本文关键字:客户端 略图 运行 FineUploader      更新时间:2023-09-26

我正在进行FineUploader实现。特殊要求是在客户端动态创建缩略图,然后上传带有原始图像上传的缩略图

我有一个对FF有效的实现,但似乎对iOs无效。看起来是这样的:

var uploader = new qq.FineUploaderBasic({
  button: document.getElementById(buttonID),
  request: {
    endpoint: '/up/load/a/' + $('section#ajax-viewport').data('albumid')
  },
  callbacks: {
    onSubmit: function(id, fileName) {
            // getFile obtains the file being uploaded
        file = this.getFile(id); 
            // create a thumbnail & upload it:
        ThumbDown(file, id, 200, fileName);
    },
  }
}) 

此代码调用一个函数:

function ThumbDown(file, id, dimension, fileName) {
var reader = new FileReader();  
reader.onload = function(e) {
    var img = document.createElement("img");
    img.onload = function (ev) {
        var thumbnailDimensions; // object holding width & height of thumbnail
        var c=document.getElementById("canvas-for-thumbnails"); // must be a <canvas> element
        var ctx=c.getContext("2d");
            // set thumbnail dimensions of canvas:
        thumbnailDimensions = calcThumbnailDimension (img.width, img.height, dimension )
        c.width = thumbnailDimensions.width;
        c.height = thumbnailDimensions.height;
        var ctx = c.getContext("2d");
        ctx.drawImage(img, 0, 0, c.width, c.height);
        uploadThumbnail(c.toDataURL('image/jpeg'), //a base64 encoded representation of the image
                        id,               
                        fileName);       // we need filename to combine with mother-image on the server
    };
    img.src = e.target.result;
}
reader.readAsDataURL(file);
} // end function

最后,缩略图上传了一个愚蠢的ajax调用:

function uploadThumbnail (base64encodedString, id, fileName) {
  $.post('/up/thumb',
  {
    img : base64encodedString,
    id: id,
    fileName: fileName
  },
  function(data) {});
}

我的问题:

1) 目前我有两个上传:一个是母亲的图像,另一个是缩略图。我想将此合并到一个FineUploader调用中。然而,由于缩略图创建的异步性,我看不到这样做的方法。

我是不是错过了什么?这是否可以将其减少为一个FineUploader调用?

2) 此代码将缩略图上载为base64编码的字符串。我想将缩略图作为图像上传(或作为blob?)。也许是按照Jeremy Banks的配方。这适用于FineUploader吗?

3) 我是否错过了FineUploader的其他选项/方法,但我应该使用?

任何帮助,一如既往,不胜感激。

因此,上传原始图像已经很简单了。Fine Uploader会帮你处理好的。如果我理解正确,您还需要上传图像的缩放版本(您已经生成)。我建议您将绘制的图像放到画布上,并将其转换为Blob。然后,您可以将此Blob直接提交到Fine Uploader,它将为您上传。

例如,将uploadThumbnail的值更改为:

function uploadThumbnail(thumbnailDataUri, id, filename) {
    var imageBlob = getImageBlob(thumbnailDataUri, "image/jpeg"),
        blobData = {
            name: filename,
            blob: imageBlob
        };
    // This will instruct Fine Uploader to upload the scaled image
    uploader.addBlobs(blobData);
}  
function getImageBlob(dataUri, type) {
    var binary = atob(dataUri.split(',')[1]), 
        array = [];
    for(var i = 0; i < binary.length; i++) {
        array.push(binary.charCodeAt(i));
    }
    return new Blob([new Uint8Array(array)], {type: type});
}

注意:getImageBlob函数是根据这个堆栈溢出答案改编的。如果这对你有效,一定要对我链接的答案投赞成票。

服务器侧注释

Blob相当于没有name属性的File。服务器端代码处理Blob的上传方式与处理包含<input type="file">表单字段的File或表单提交的方式大致相同。与服务器唯一明显的区别是包含文件的多部分边界的Content-Disposition标头中的filename参数值。换句话说,由于大多数浏览器生成包含Blob对象的多部分编码请求的方式,您的服务器可能会认为图像被命名为"blob"或其他通用名称。Fine Uploader应该能够通过显式指定浏览器的文件名来绕过这一点,该文件名将包含在blob的Content-Disposition标头中,但这种功能没有广泛的浏览器支持。Fine Uploader在一定程度上绕过了这一限制,在包含Blob实际名称的请求中包含了一个"qqfilename"参数。

未来对缩略图生成的原生支持&缩放

计划是在Fine Uploader中添加对缩略图预览的本地支持。这包含在功能请求#868和#896中。还有其他相关的功能请求打开,例如图像旋转和与图像相关的验证。这些功能和其他与图像相关的功能可能会在不久的将来添加到Fine Uploader中。请务必对现有的功能请求发表评论,或者如果您愿意,请添加其他请求。

正如Ray Nichollus指出的那样,从FineUploader的4.4版本开始,这个功能已经被移植到了他们的框架中。

以下是创建FineUploader实例时设置上传大小的示例:

var uploader = new qq.FineUploader({
...
scaling: {
    sizes: [
        {name: "small", maxSize: 100},
        {name: "medium", maxSize: 300}
    ]
}
});

查看他们上传缩放图像的页面。