【转】JS手机端图片上传前压缩

上一篇文章有一个压缩的代码,这几天在网上看到了一个移动端兼容的代码,原文地址:https://blog.csdn.net/catastrophe_zy/article/details/81234140,作者写的比较简略,我按照自己的理解弄了一下,请用手机测试代码。

compress.js

class Compress{
		
	constructor(file, option){
		this.file = file;
		this.config = Object.assign({
			quality : 0.9
		},option);
		
		return this.process();
	}
	
	//支持压缩的格式
	get mimeTypes()  {
		return {
			PNG : "image/png",
			JPEG : "image/jpeg",
			WEBP : "image/webp",
			BMP : "image/bmp"	
		}
	};
	
	get supportTypes(){
		return Object.keys(this.mimeTypes).map(type => this.mimeTypes[type]);
	}
	
	//判断格式是否支持
	isSupportedType (type){
		return this.supportTypes.includes(type);
	}
	
	process(){
		this.outputType = this.file.type;
		if(this.isSupportedType(this.file.type) == false){
			return Promise.reject(new Error("不支持该文件类型"));
		}
		
		return this.getOriginImage().then(img => {
			return this.getCanvas(img);
		}).then(canvas => {
			let scale = 1;
			
			if(this.config.maxWidth){
				scale = Math.min(1, this.config.maxWidth / canvas.width);
			}
			if(this.config.maxHeight){
				scale = Math.min(1, scale, this.config.maxHeight / canvas.height);
			}
			
			
			return this.doScale(canvas, scale);
		}).then(result => {
			return new Promise((resolve, reject) => {
				resolve(this.toBlob(result));
			})
		})
	}
	
	//通过file 初始化 image
	getOriginImage() {
		return new Promise((resolve, reject) => {
			let img = new Image();
			img.onload = () => {
				resolve(img);
			};
			img.onerror = () => {
				reject("图片加载失败");
			};
			
			img.src = URL.createObjectURL(this.file);
		})
	}
	
	getCanvas(img) {
		return new Promise((resolve, reject) => {
			// 通过得到图片的信息来调整显示方向以正确显示图片,主要解决 ios 系统上的图片会有旋转的问题
			EXIF.getData(img, () => {
				let orientation = EXIF.getTag(img, "Orientation") || 1;
				
				let canvas = document.createElement("canvas");
				
				
				let ctx = canvas.getContext("2d");
				
				if(orientation == 6){
					canvas.width = img.height;
					canvas.height = img.width;
					ctx.rotate(90 * Math.PI / 180);
					ctx.drawImage(img, 0 , 0 , img.width, img.height, 0, -img.height ,canvas.height,canvas.width);
					
				}else{
					canvas.width = img.width;
					canvas.height = img.height;
					ctx.drawImage(img, 0, 0);
				}
				
				resolve(canvas);
			});
		})
	}
	
	doScale(source, scale){
		if(scale == 1){
			return Promise.resolve(source);
		}
		
		let mirror = document.createElement("canvas");
		mirror.width = Math.ceil(source.width * scale);
		mirror.height = Math.ceil(source.height * scale);
		
		let mctx = mirror.getContext("2d");
		
		mctx.drawImage(source, 0, 0, source.width, source.height, 0, 0, mirror.width, mirror.height);
		
		
		return Promise.resolve(mirror);
	}
	
	// 这里把 base64 字符串转为 blob 对象
	toBlob(result) {
		let dataURL = result.toDataURL(this.outputType, this.config.quality);
		let buffer = atob(dataURL.split(",")[1]).split("").map(char => char.charCodeAt(0));
		let blob = new Blob([ new Uint8Array(buffer) ], {
			type : this.outputType
		});
		return {
			blob: blob,
			url: dataURL
		};
	}
	
}// JavaScript Document

upload.js:

var formdata = new FormData();

//点击按钮上传图片,
function upload(file,imgID){
	new Compress(file,{maxWidth:1024, maxHeight:1024, quality: 0.7}).then(function(data){
		//这里写回调函数,data会传入两个属性,url:压缩后图片url,blob:压缩后图片blob值		
		formdata.append(imgID, data.blob, "file_"+Date.parse(new Date())+".jpg"); 
		document.getElementById("show"+imgID).src = data.url;
	},function(err){
		//这里写异常处理
		alert(err);
	})	
}

//统一提交数据
function sublitForm()
{
    //开始上传文件
	var uploadurl="uploadFile.jsp";
	var xhr= new XMLHttpRequest();  // XMLHttpRequest 对象
	xhr.open("post", uploadurl, true); //post方式,url为服务器请求地址,true 该参数规定请求是否异步处理。
	
	//上传成功
	xhr.onload = function(evt) {
		//服务断接收完文件返回的结果
		var data = JSON.parse(evt.target.responseText);
		if(data.success) 
		{			
			window.location.href="step5.jsp";
		}
		else
		{
			alert("上传失败:"+data.error);
		}
	
	}
	
	//上传失败的话
	xhr.onerror=function(evt) {
		alert("上传失败!");
	}
	
	//开始上传文件
	xhr.send(formdata); //开始上传,发送form数据	
}

upload.htm

...
<script language="javascript" type="text/javascript" src="js/exif.js"></script>
<script language="javascript" type="text/javascript" src="js/compress.js"></script>
<div class="itemline">
            <label for="img">一寸免冠照片或扫描件:</label>
            <input type="file" id="img" name="img" vlaue="" onchange="javascript:upload(this.files[0],'img');"/>
            <div style=" text-align:center"><img src="" id="showimg"/></div>         
        </div>
        <div class="itemline">           
            <label for="img">身份证照片或扫描件:</label>
            <input type="file" id="cardimg" name="cardimg" vlaue="" onchange="javascript:upload(this.files[0],'cardimg');"/>
            <div style=" text-align:center"><img src="" id="showcardimg"/></div>
        </div>
...

 

Guess you like

Origin blog.csdn.net/qq_42213965/article/details/98660616