图像在上传到服务器之前使用JavaScript调整客户端的大小

时间:2021-07-21 16:07:03

I would like to know if it is technically possible to resize an image at a client-side with JavaScript (really resize, not just change width and height). I know it's possible to do it in Flash but I would like to avoid it if possible. Is there any open source algorithm somewhere on the web?

我想知道在技术上是否可以使用JavaScript在客户端调整图像大小(实际上是调整大小,而不仅仅是更改宽度和高度)。我知道可以在Flash中完成它但我想尽可能避免它。网上某处有开源算法吗?

7 个解决方案

#1


87  

Here's a gist which does this: https://gist.github.com/dcollien/312bce1270a5f511bf4a

这是一个要点:https://gist.github.com/dcollien/312bce1270a5f511bf4a

(an es6 version, and a .js version which can be included in a script tag)

(es6版本和.js版本,可以包含在脚本标记中)

You can use it as follows:

您可以按如下方式使用它:

<input type="file" id="select">
<img id="preview">
<script>
document.getElementById('select').onchange = function(evt) {
    ImageTools.resize(this.files[0], {
        width: 320, // maximum width
        height: 240 // maximum height
    }, function(blob, didItResize) {
        // didItResize will be true if it managed to resize it, otherwise false (and will return the original file as 'blob')
        document.getElementById('preview').src = window.URL.createObjectURL(blob);
        // you can also now upload this blob using an XHR.
    });
};
</script>

It includes a bunch of support detection and polyfills to make sure it works on as many browsers as I could manage.

它包括一堆支持检测和polyfill,以确保它可以在尽可能多的浏览器上运行。

(it also ignores gif images - in case they're animated)

(它也忽略了gif图像 - 如果它们是动画的)

#2


55  

The answer to this is yes - in HTML 5 you can resize images client-side using the canvas element. You can also take the new data and send it to a server. See this tutorial:

答案是肯定的 - 在HTML 5中,您可以使用canvas元素调整客户端图像的大小。您还可以获取新数据并将其发送到服务器。看本教程:

http://hacks.mozilla.org/2011/01/how-to-develop-a-html5-image-uploader/

http://hacks.mozilla.org/2011/01/how-to-develop-a-html5-image-uploader/

#3


12  

If you were resizing before uploading I just found out this http://www.plupload.com/

如果你在上传之前调整大小我刚刚发现这个http://www.plupload.com/

It does all the magic for you in any imaginable method.

它以任何可以想象的方式为您提供所有魔力。

Unfortunately HTML5 resize only is supported with Mozilla browser, but you can redirect other browsers to Flash and Silverlight.

不幸的是,Mozilla浏览器仅支持HTML5调整大小,但您可以将其他浏览器重定向到Flash和Silverlight。

I just tried it and it worked with my android!

我刚尝试过,它与我的机器人一起工作!

I was using http://swfupload.org/ in flash, it does the job very well, but the resize size is very small. (cannot remember the limit) and does not go back to html4 when flash is not available.

我在flash中使用http://swfupload.org/,它可以很好地完成工作,但调整大小非常小。 (不记得限制)并且当flash不可用时不会返回到html4。

#4


7  

http://nodeca.github.io/pica/demo/

http://nodeca.github.io/pica/demo/

In modern browser you can use canvas to load/save image data. But you should keep in mind several things if you resize image on the client:

在现代浏览器中,您可以使用画布来加载/保存图像数据。但是,如果在客户端上调整图像大小,则应记住几件事:

  1. You will have only 8bits per channel (jpeg can have better dynamic range, about 12 bits). If you don't upload professional photos, that should not be a problem.
  2. 每个通道只有8位(jpeg可以有更好的动态范围,大约12位)。如果您不上传专业照片,那应该不是问题。
  3. Be careful about resize algorithm. The most of client side resizers use trivial math, and result is worse than it could be.
  4. 关于调整大小算法要小心。大多数客户端调整器使用琐碎的数学,结果比它可能更糟。
  5. You may need to sharpen downscaled image.
  6. 您可能需要锐化缩小的图像。
  7. If you wish do reuse metadata (exif and other) from original - don't forget to strip color profile info. Because it's applied when you load image to canvas.
  8. 如果您希望重用原始元数据(exif和其他),请不要忘记删除颜色配置文件信息。因为它是在将图像加载到画布时应用的。

#5


6  

Perhaps with the canvas tag (though it's not portable). There's a blog about how to rotate an image with canvas here, I suppose if you can rotate it, you can resize it. Maybe it can be a starting point.

也许使用canvas标签(尽管它不可​​移植)。有一篇关于如何在这里使用画布旋转图像的博客,我想如果你可以旋转它,你可以调整它的大小。也许它可以成为一个起点。

See there also.

也见。

#6


2  

Yes, with modern browsers this is totally doable. Even doable to the point of uploading the file specifically as a binary file having done any number of canvas alterations.

是的,使用现代浏览器,这是完全可行的。甚至可以将文件专门上传为具有任意数量的画布改变的二进制文件。

http://jsfiddle.net/bo40drmv/

http://jsfiddle.net/bo40drmv/

(this answer is a improvement of the accepted answer here)

(这个答案是对这里接受的答案的改进)

Keeping in mind to catch process the result submission in the PHP with something akin to:

请记住在PHP中捕获处理结果提交的内容类似于:

//File destination
$destination = "/folder/cropped_image.png";
//Get uploaded image file it's temporary name
$image_tmp_name = $_FILES["cropped_image"]["tmp_name"][0];
//Move temporary file to final destination
move_uploaded_file($image_tmp_name, $destination);

If one worries about Vitaly's point, you can try some of the cropping and resizing on the working jfiddle.

如果一个人担心维塔利的观点,你可以尝试一些裁剪和调整工作的jfiddle。

#7


0  

You can use a javascript image processing framework for client-side image processing before uploading the image to the server.

在将图像上载到服务器之前,您可以使用javascript图像处理框架进行客户端图像处理。

Below I used MarvinJ to create a runnable code based on the example in the following page: "Processing images in client-side before uploading it to a server"

下面我使用MarvinJ根据以下页面中的示例创建一个可运行的代码:“在将图像上传到服务器之前在客户端处理图像”

Basically I use the method Marvin.scale(...) to resize the image. Then, I upload the image as a blob (using the method image.toBlob()). The server answers back providing a URL of the received image.

基本上我使用方法Marvin.scale(...)来调整图像大小。然后,我将图像上传为blob(使用方法image.toBlob())。服务器回答提供所接收图像的URL。

/***********************************************
 * GLOBAL VARS
 **********************************************/
var image = new MarvinImage();

/***********************************************
 * FILE CHOOSER AND UPLOAD
 **********************************************/
 $('#fileUpload').change(function (event) {
	form = new FormData();
	form.append('name', event.target.files[0].name);
	
	reader = new FileReader();
	reader.readAsDataURL(event.target.files[0]);
	
	reader.onload = function(){
		image.load(reader.result, imageLoaded);
	};
	
});

function resizeAndSendToServer(){
  $("#divServerResponse").html("uploading...");
	$.ajax({
		method: 'POST',
		url: 'https://www.marvinj.org/backoffice/imageUpload.php',
		data: form,
		enctype: 'multipart/form-data',
		contentType: false,
		processData: false,
		
	   
		success: function (resp) {
       $("#divServerResponse").html("SERVER RESPONSE (NEW IMAGE):<br/><img src='"+resp+"' style='max-width:400px'></img>");
		},
		error: function (data) {
			console.log("error:"+error);
			console.log(data);
		},
		
	});
};

/***********************************************
 * IMAGE MANIPULATION
 **********************************************/
function imageLoaded(){
  Marvin.scale(image.clone(), image, 120);
  form.append("blob", image.toBlob());
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://www.marvinj.org/releases/marvinj-0.8.js"></script>
<form id="form" action='/backoffice/imageUpload.php' style='margin:auto;' method='post' enctype='multipart/form-data'>
				<input type='file' id='fileUpload' class='upload' name='userfile'/>
</form><br/>
<button type="button" onclick="resizeAndSendToServer()">Resize and Send to Server</button><br/><br/>
<div id="divServerResponse">
</div>

#1


87  

Here's a gist which does this: https://gist.github.com/dcollien/312bce1270a5f511bf4a

这是一个要点:https://gist.github.com/dcollien/312bce1270a5f511bf4a

(an es6 version, and a .js version which can be included in a script tag)

(es6版本和.js版本,可以包含在脚本标记中)

You can use it as follows:

您可以按如下方式使用它:

<input type="file" id="select">
<img id="preview">
<script>
document.getElementById('select').onchange = function(evt) {
    ImageTools.resize(this.files[0], {
        width: 320, // maximum width
        height: 240 // maximum height
    }, function(blob, didItResize) {
        // didItResize will be true if it managed to resize it, otherwise false (and will return the original file as 'blob')
        document.getElementById('preview').src = window.URL.createObjectURL(blob);
        // you can also now upload this blob using an XHR.
    });
};
</script>

It includes a bunch of support detection and polyfills to make sure it works on as many browsers as I could manage.

它包括一堆支持检测和polyfill,以确保它可以在尽可能多的浏览器上运行。

(it also ignores gif images - in case they're animated)

(它也忽略了gif图像 - 如果它们是动画的)

#2


55  

The answer to this is yes - in HTML 5 you can resize images client-side using the canvas element. You can also take the new data and send it to a server. See this tutorial:

答案是肯定的 - 在HTML 5中,您可以使用canvas元素调整客户端图像的大小。您还可以获取新数据并将其发送到服务器。看本教程:

http://hacks.mozilla.org/2011/01/how-to-develop-a-html5-image-uploader/

http://hacks.mozilla.org/2011/01/how-to-develop-a-html5-image-uploader/

#3


12  

If you were resizing before uploading I just found out this http://www.plupload.com/

如果你在上传之前调整大小我刚刚发现这个http://www.plupload.com/

It does all the magic for you in any imaginable method.

它以任何可以想象的方式为您提供所有魔力。

Unfortunately HTML5 resize only is supported with Mozilla browser, but you can redirect other browsers to Flash and Silverlight.

不幸的是,Mozilla浏览器仅支持HTML5调整大小,但您可以将其他浏览器重定向到Flash和Silverlight。

I just tried it and it worked with my android!

我刚尝试过,它与我的机器人一起工作!

I was using http://swfupload.org/ in flash, it does the job very well, but the resize size is very small. (cannot remember the limit) and does not go back to html4 when flash is not available.

我在flash中使用http://swfupload.org/,它可以很好地完成工作,但调整大小非常小。 (不记得限制)并且当flash不可用时不会返回到html4。

#4


7  

http://nodeca.github.io/pica/demo/

http://nodeca.github.io/pica/demo/

In modern browser you can use canvas to load/save image data. But you should keep in mind several things if you resize image on the client:

在现代浏览器中,您可以使用画布来加载/保存图像数据。但是,如果在客户端上调整图像大小,则应记住几件事:

  1. You will have only 8bits per channel (jpeg can have better dynamic range, about 12 bits). If you don't upload professional photos, that should not be a problem.
  2. 每个通道只有8位(jpeg可以有更好的动态范围,大约12位)。如果您不上传专业照片,那应该不是问题。
  3. Be careful about resize algorithm. The most of client side resizers use trivial math, and result is worse than it could be.
  4. 关于调整大小算法要小心。大多数客户端调整器使用琐碎的数学,结果比它可能更糟。
  5. You may need to sharpen downscaled image.
  6. 您可能需要锐化缩小的图像。
  7. If you wish do reuse metadata (exif and other) from original - don't forget to strip color profile info. Because it's applied when you load image to canvas.
  8. 如果您希望重用原始元数据(exif和其他),请不要忘记删除颜色配置文件信息。因为它是在将图像加载到画布时应用的。

#5


6  

Perhaps with the canvas tag (though it's not portable). There's a blog about how to rotate an image with canvas here, I suppose if you can rotate it, you can resize it. Maybe it can be a starting point.

也许使用canvas标签(尽管它不可​​移植)。有一篇关于如何在这里使用画布旋转图像的博客,我想如果你可以旋转它,你可以调整它的大小。也许它可以成为一个起点。

See there also.

也见。

#6


2  

Yes, with modern browsers this is totally doable. Even doable to the point of uploading the file specifically as a binary file having done any number of canvas alterations.

是的,使用现代浏览器,这是完全可行的。甚至可以将文件专门上传为具有任意数量的画布改变的二进制文件。

http://jsfiddle.net/bo40drmv/

http://jsfiddle.net/bo40drmv/

(this answer is a improvement of the accepted answer here)

(这个答案是对这里接受的答案的改进)

Keeping in mind to catch process the result submission in the PHP with something akin to:

请记住在PHP中捕获处理结果提交的内容类似于:

//File destination
$destination = "/folder/cropped_image.png";
//Get uploaded image file it's temporary name
$image_tmp_name = $_FILES["cropped_image"]["tmp_name"][0];
//Move temporary file to final destination
move_uploaded_file($image_tmp_name, $destination);

If one worries about Vitaly's point, you can try some of the cropping and resizing on the working jfiddle.

如果一个人担心维塔利的观点,你可以尝试一些裁剪和调整工作的jfiddle。

#7


0  

You can use a javascript image processing framework for client-side image processing before uploading the image to the server.

在将图像上载到服务器之前,您可以使用javascript图像处理框架进行客户端图像处理。

Below I used MarvinJ to create a runnable code based on the example in the following page: "Processing images in client-side before uploading it to a server"

下面我使用MarvinJ根据以下页面中的示例创建一个可运行的代码:“在将图像上传到服务器之前在客户端处理图像”

Basically I use the method Marvin.scale(...) to resize the image. Then, I upload the image as a blob (using the method image.toBlob()). The server answers back providing a URL of the received image.

基本上我使用方法Marvin.scale(...)来调整图像大小。然后,我将图像上传为blob(使用方法image.toBlob())。服务器回答提供所接收图像的URL。

/***********************************************
 * GLOBAL VARS
 **********************************************/
var image = new MarvinImage();

/***********************************************
 * FILE CHOOSER AND UPLOAD
 **********************************************/
 $('#fileUpload').change(function (event) {
	form = new FormData();
	form.append('name', event.target.files[0].name);
	
	reader = new FileReader();
	reader.readAsDataURL(event.target.files[0]);
	
	reader.onload = function(){
		image.load(reader.result, imageLoaded);
	};
	
});

function resizeAndSendToServer(){
  $("#divServerResponse").html("uploading...");
	$.ajax({
		method: 'POST',
		url: 'https://www.marvinj.org/backoffice/imageUpload.php',
		data: form,
		enctype: 'multipart/form-data',
		contentType: false,
		processData: false,
		
	   
		success: function (resp) {
       $("#divServerResponse").html("SERVER RESPONSE (NEW IMAGE):<br/><img src='"+resp+"' style='max-width:400px'></img>");
		},
		error: function (data) {
			console.log("error:"+error);
			console.log(data);
		},
		
	});
};

/***********************************************
 * IMAGE MANIPULATION
 **********************************************/
function imageLoaded(){
  Marvin.scale(image.clone(), image, 120);
  form.append("blob", image.toBlob());
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://www.marvinj.org/releases/marvinj-0.8.js"></script>
<form id="form" action='/backoffice/imageUpload.php' style='margin:auto;' method='post' enctype='multipart/form-data'>
				<input type='file' id='fileUpload' class='upload' name='userfile'/>
</form><br/>
<button type="button" onclick="resizeAndSendToServer()">Resize and Send to Server</button><br/><br/>
<div id="divServerResponse">
</div>