600字范文,内容丰富有趣,生活中的好帮手!
600字范文 > vue2移动端上传 预览 压缩图片 解决拍照旋转问题

vue2移动端上传 预览 压缩图片 解决拍照旋转问题

时间:2020-03-10 23:20:24

相关推荐

vue2移动端上传 预览 压缩图片 解决拍照旋转问题

/exif-js/exif-js

/javascript/exif-js/demo/

因为最近遇到个移动端上传头像的需求,上传到后台的数据是base64位,其中为了提高用户体验,把比较大的图片用canvas进行压缩之后再进行上传。在移动端调用拍照功能时,会发生图片旋转,为了解决这个问题引入了exif去判断拍照时的信息再去处理图片,这是个很好的插件。关于exif.js可以去他的GitHub上了解,这边直接npm install exif-js --save 安装,然后import一下就可以使用了。以下就是源码,可以直接使用。

[html]view plaincopy<template> <div> <divstyle="padding:20px;"> <divclass="show"> <divclass="picture":style="'backgroundImage:url('+headerImage+')'"></div> </div> <divstyle="margin-top:20px;"> <inputtype="file"id="upload"accept="image"@change="upload"> <labelfor="upload"></label> </div> </div> </div> </template> <script> importExiffrom'exif-js' exportdefault{ data(){ return{ headerImage:'',picValue:'' } }, mounted(){ }, methods:{ upload(e){ letfiles=e.target.files||e.dataTransfer.files; if(!files.length)return; this.picValue=files[0]; this.imgPreview(this.picValue); }, imgPreview(file){ letself=this; letOrientation; //去获取拍照时的信息,解决拍出来的照片旋转问题 Exif.getData(file,function(){ Orientation=Exif.getTag(this,'Orientation'); }); //看支持不支持FileReader if(!file||!window.FileReader)return; if(/^image/.test(file.type)){ //创建一个reader letreader=newFileReader(); //将图片2将转成base64格式 reader.readAsDataURL(file); //读取成功后的回调 reader.onloadend=function(){ letresult=this.result; letimg=newImage(); img.src=result; //判断图片是否大于100K,是就直接上传,反之压缩图片 if(this.result.length<=(100*1024)){ self.headerImage=this.result; self.postImg(); }else{ img.onload=function(){ letdata=press(img,Orientation); self.headerImage=data; self.postImg(); } } } } }, postImg(){ //这里写接口 }, rotateImg(img,direction,canvas){ //最小与最大旋转方向,图片旋转4次后回到原方向 constmin_step=0; constmax_step=3; if(img==null)return; //img的高度和宽度不能在img元素隐藏后获取,否则会出错 letheight=img.height; letwidth=img.width; letstep=2; if(step==null){ step=min_step; } if(direction=='right'){ step++; //旋转到原位置,即超过最大值 step>max_step&&(step=min_step); }else{ step--; step<min_step&&(step=max_step); } //旋转角度以弧度值为参数 letdegree=step*90*Math.PI/180; letctx=canvas.getContext('2d'); switch(step){ case0: canvas.width=width; canvas.height=height; ctx.drawImage(img,0,0); break; case1: canvas.width=height; canvas.height=width; ctx.rotate(degree); ctx.drawImage(img,0,-height); break; case2: canvas.width=width; canvas.height=height; ctx.rotate(degree); ctx.drawImage(img,-width,-height); break; case3: canvas.width=height; canvas.height=width; ctx.rotate(degree); ctx.drawImage(img,-width,0); break; } }, compress(img,Orientation){ letcanvas=document.createElement("canvas"); letctx=canvas.getContext('2d'); //瓦片canvas lettCanvas=document.createElement("canvas"); lettctx=tCanvas.getContext("2d"); letinitSize=img.src.length; letwidth=img.width; letheight=img.height; //如果图片大于四百万像素,计算压缩比并将大小压至400万以下 letratio; if((ratio=width*height/4000000)>1){ console.log("大于400万像素") ratio=Math.sqrt(ratio); width/=ratio; height/=ratio; }else{ ratio=1; } canvas.width=width; canvas.height=height; //铺底色 ctx.fillStyle="#fff"; ctx.fillRect(0,0,canvas.width,canvas.height); //如果图片像素大于100万则使用瓦片绘制 letcount; if((count=width*height/1000000)>1){ console.log("超过100W像素"); count=~~(Math.sqrt(count)+1);//计算要分成多少块瓦片 //计算每块瓦片的宽和高 letnw=~~(width/count); letnh=~~(height/count); tCanvas.width=nw; tCanvas.height=nh; for(leti=0;i<count;i++){ for(letj=0;j<count;j++){ tctx.drawImage(img,i*nw*ratio,j*nh*ratio,nw*ratio,nh*ratio,0,0,nw,nh); ctx.drawImage(tCanvas,i*nw,j*nh,nw,nh); } } }else{ ctx.drawImage(img,0,0,width,height); } //修复ios上传图片的时候被旋转的问题 if(Orientation!=""&&Orientation!=1){ switch(Orientation){ case6://需要顺时针(向左)90度旋转 this.rotateImg(img,'left',canvas); break; case8://需要逆时针(向右)90度旋转 this.rotateImg(img,'right',canvas); break; case3://需要180度旋转 this.rotateImg(img,'right',canvas);//转两次 this.rotateImg(img,'right',canvas); break; } } //进行最小压缩 letndata=canvas.toDataURL('image/jpeg',0.1); console.log('压缩前:'+initSize); console.log('压缩后:'+ndata.length); console.log('压缩率:'+~~(100*(initSize-ndata.length)/initSize)+"%"); tCanvas.width=tCanvas.height=canvas.width=canvas.height=0; returnndata; }, } } </script> <style> *{ margin:0; padding:0; } .show{ width:100px; height:100px; overflow:hidden; position:relative; border-radius:50%; border:1pxsolid#d5d5d5; } .picture{ width:100%; height:100%; overflow:hidden; background-position:centercenter; background-repeat:no-repeat; background-size:cover; } </style>

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。