前端解決手機拍照旋轉問題及圖片壓縮上傳

旋轉壓縮部分因為有文件的不同類型相互轉換,所以方法調用比較多,看起來有點亂,但是實際不難理解,建議粘貼到編輯器比較方便看,希望此文章對大家有幫助

1.依賴? jquery.js


2.html部分

<input class="addImage" name="loadFile" type="file" accept="image/*" capture="camera">

//capture="camera"? ?設置手機端打開上傳文件時使用手機攝像頭拍照上傳,不寫則默認拍照或相冊


3.js部分

$('.addImage').on('change',function(){

????//開始處理圖片,此時可以做一些“圖片上傳中。。。”的提示等

????var fileObj = this.files[0];??

????var fileName = fileObj.name;

????//壓縮,先旋轉在壓縮,因為cavers從畫圖壓縮,壓縮后的圖片就沒有角度等信息了

????photoCompress(fileObj, {

? ? ? ? ? ? ? quality: 0.2? //清晰度

? ? }, function(base64Codes){

? ? ? ? //旋轉并且壓縮后傳回base64編碼,此時可以用ajax與后端傳輸圖片,此方法不做演示

? ? ? ? //模擬表單提交

? ? ? ? var form = new FormData(); // FormData 對象

????????var bl = convertBase64ToBlob(base64Codes);? //base64轉化為blob對象

? ? ? ? form.append("loadFile", bl, "file_"+Date.parse(new Date())+".jpg"); // 文件對象

? ? ? ? xhr = new XMLHttpRequest();? // XMLHttpRequest 對象

? ? ? ? xhr.open("post","<../medicalAppointment/tempImg.do", true);? ?

????????//xhr.upload.onprogress = progressFunction;//【上傳進度調用方法實現】

? ? ? ? //請求完成執行uploadComplete

? ? ? ? xhr.onload = function uploadComplete(evt){?

? ? ? ? ? ? ? ? var data = evt.target.responseText;? ? //返回的數據data

? ? ? ? ? ? ? ? console.log(data)

? ? ? ? };

? ? ? ?xhr.onerror =? function uploadFailed(){}; //請求失敗

? ? ? ?xhr.send(form); //開始上傳,發送form數據

? ? })

})

//壓縮后base64轉化為blob

var convertBase64ToBlob = function(base64){

? ? var base64Arr = base64.split(',');

? ? var imgtype = '';

? ? var base64String = '';

? ? if(base64Arr.length > 1){

? ? ? ? //如果是圖片base64,去掉頭信息

? ? ? ? base64String = base64Arr[1];

? ? ? ? imgtype = base64Arr[0].substring(base64Arr[0].indexOf(':')+1,base64Arr[0].indexOf(';'));

? ? }

? ? // 將base64解碼

? ? var bytes = atob(base64String);

? ? //var bytes = base64;

? ? var bytesCode = new ArrayBuffer(bytes.length);

? ? // 轉換為類型化數組

? ? var byteArray = new Uint8Array(bytesCode);


? ? // 將base64轉換為ascii碼

? ? for (var i = 0; i < bytes.length; i++) {

? ? ? ? byteArray[i] = bytes.charCodeAt(i);

? ? }


? ? // 生成Blob對象(文件對象)

? ? return new Blob( [bytesCode] , {type : imgtype});

};

//將base64轉換為文件

function dataURLtoFile(dataurl, filename) {

? ? ? ? var arr = dataurl.split(','), mime = arr[0].match(/:(.*?);/)[1],

? ? ? ? bstr = atob(arr[1]), n = bstr.length, u8arr = new Uint8Array(n);

? ? ? ? while(n--){

? ? ? ? ? ? u8arr[n] = bstr.charCodeAt(n);

? ? ? ? }

? ? ? ? return new File([u8arr], filename, {type:mime});

? ? }

//判斷手機類型安卓/ios

function isAndroid_ios(){?

????var u = navigator.userAgent, app = navigator.appVersion;?

????var isAndroid = u.indexOf('Android') > -1 || u.indexOf('Linux') > -1; //android終端或者uc瀏覽器?

????var isiOS = !!u.match(/\(i[^;]+;( U;)? CPU.+Mac OS X/); //ios終端?

????return isAndroid==true?true:false;?

}

//壓縮圖片

function photoCompress(file,w,objDiv){

? ? ? ? var ready=new FileReader();

? ? ? ? /*開始讀取指定的Blob對象或File對象中的內容. 當讀取操作完成時,readyState屬性的值會成為DONE,如果設置了onloadend事件處理程序,則調用之.同時,result屬性中將包含一個data: URL格式的字符串以表示所讀取文件的內容.*/

? ? ? ? ready.readAsDataURL(file);

? ? ? ? ready.onload=function(){

? ? ? ? ? ? ? var re=this.result;

? ? ? ? ? ? ? var imageSize = e.total;//圖片大小

? ? ? ? ? ? ? if(isAndroid_ios()){?

? ? ? ? ? ? ? ? ? ?//安卓? //不旋轉圖片

? ? ? ? ? ? ? ? ? ? canvasDataURL(re,w,objDiv)

? ? ? ? ? ? ?}else{

????????????????//旋轉圖片

????????????????var image = new Image();

? ? ? ???????? image.src = re;

????????????????image.onload = function () {

? ? ? ? ? ? ? ? //開始旋轉圖片

? ? ? ? ? ???? var newImage = rotateImage(image);

? ? ? ? ????? var newImageSrc = newImage.src;

? ? ? ? ? ? ? canvasDataURL(newImageSrc,w,objDiv);

? ? ? }

}

? ? ? ? }

? ? }

? ? function canvasDataURL(path, obj, callback){

? ? ? ? var img = new Image();

? ? ? ? img.src = path;

? ? ? ? img.onload = function(){

? ? ? ? ? ? var that = this;

? ? ? ? ? ? // 圖片原始尺寸

? ? ? ? ? ? var originWidth = that.width;

? ? ? ? ? ? var originHeight = that.height;

? ? ? ? ? ? // 最大尺寸限制,可通過設置寬高來實現圖片壓縮程度

? ? ? ? ? ? var maxWidth = 1000,

? ? ? ? ? ? ? ? maxHeight = 2000;

? ? ? ? ? ? // 目標尺寸

? ? ? ? ? ? var w = originWidth || obj.width,

? ? ? ? ? ? ? ? h = originHeight || obj.height;

? ? ? ? ? ? // 圖片尺寸超過1000x2000的限制

? ? ? ? ? ? if(originWidth > maxWidth || originHeight > maxHeight) {

? ? ? ? ? ? ? ? if(originWidth / originHeight > maxWidth / maxHeight) {

? ? ? ? ? ? ? ? ? ? // 更寬,按照寬度限定尺寸

? ? ? ? ? ? ? ? ? ? w = maxWidth;

? ? ? ? ? ? ? ? ? ? h = Math.round(maxWidth * (originHeight / originWidth));

? ? ? ? ? ? ? ? } else {

? ? ? ? ? ? ? ? ? ? h = maxHeight;

? ? ? ? ? ? ? ? ? ? w = Math.round(maxHeight * (originWidth / originHeight));

? ? ? ? ? ? ? ? }

? ? ? ? ? ? }

? ? ? ? ? ? // 默認按比例壓縮

? ? ? ? ? /* var w = that.width,

? ? ? ? ? ? ? ? h = that.height,

? ? ? ? ? ? ? ? scale = w / h;

? ? ? ? ? ? w = obj.width || w;

? ? ? ? ? ? h = obj.height || (w / scale);*/

? ? ? ? ? ? var quality = 0.7;? // 默認圖片質量為0.7

? ? ? ? ? ? //生成canvas

? ? ? ? ? ? var canvas = document.createElement('canvas');

? ? ? ? ? ? var ctx = canvas.getContext('2d');

? ? ? ? ? ? // 創建屬性節點

? ? ? ? ? ? var anw = document.createAttribute("width");

? ? ? ? ? ? anw.nodeValue = w;

? ? ? ? ? ? var anh = document.createAttribute("height");

? ? ? ? ? ? anh.nodeValue = h;

? ? ? ? ? ? canvas.setAttributeNode(anw);

? ? ? ? ? ? canvas.setAttributeNode(anh);

? ? ? ? ? ? ctx.drawImage(that, 0, 0, w, h);

? ? ? ? ? ? // 圖像質量

? ? ? ? ? ? if(obj.quality && obj.quality <= 1 && obj.quality > 0){

? ? ? ? ? ? ? ? quality = obj.quality;

? ? ? ? ? ? }

? ? ? ? ? ? // quality值越小,所繪制出的圖像越模糊

? ? ? ? ? ? var base64 = canvas.toDataURL('image/jpeg', quality);

? ? ? ? ? ? // 回調函數返回base64的值

? ? ? ? ? ? callback(base64);

? ? ? ? }

? ? }

//旋轉圖片,手機拍照上傳圖片旋轉問題

function rotateImage(image) {

? ? //console.log('rotateImage');

? ? var width = image.width;

? ? var height = image.height;

? ? var canvas = document.createElement("canvas")

? ? var ctx = canvas.getContext('2d');

? ? var newImage = new Image();


? ? //旋轉圖片操作

? ? EXIF.getData(image,function () {

? ? ? ? ? ? var orientation = EXIF.getTag(this,'Orientation');

? ? ? ? ? ? // orientation = 6;//測試數據

? ? ? ? ? ? //alert('orientation:'+orientation);

? ? ? ? ? ? switch (orientation){

? ? ? ? ? ? ? ? //正常狀態

? ? ? ? ? ? ? ? case 1:

? ? ? ? ? ? ? ? ? ? console.log('旋轉0°');

? ? ? ? ? ? ? ? ? ? // canvas.height = height;

? ? ? ? ? ? ? ? ? ? // canvas.width = width;

? ? ? ? ? ? ? ? ? ? newImage = image;

? ? ? ? ? ? ? ? ? ? break;

? ? ? ? ? ? ? ? //旋轉90度

? ? ? ? ? ? ? ? case 6:

? ? ? ? ? ? ? ? ? ? console.log('旋轉90°');

? ? ? ? ? ? ? ? ? ? canvas.height = width;

? ? ? ? ? ? ? ? ? ? canvas.width = height;

? ? ? ? ? ? ? ? ? ? ctx.rotate(Math.PI/2);

? ? ? ? ? ? ? ? ? ? ctx.translate(0,-height);

? ? ? ? ? ? ? ? ? ? ctx.drawImage(image,0,0);

? ? ? ? ? ? ? ? ? ? imageDate = canvas.toDataURL('Image/jpeg',1)

? ? ? ? ? ? ? ? ? ? newImage.src = imageDate;

? ? ? ? ? ? ? ? ? ? break;

? ? ? ? ? ? ? ? //旋轉180°

? ? ? ? ? ? ? ? case 3:

? ? ? ? ? ? ? ? ? ? console.log('旋轉180°');

? ? ? ? ? ? ? ? ? ? canvas.height = height;

? ? ? ? ? ? ? ? ? ? canvas.width = width;

? ? ? ? ? ? ? ? ? ? ctx.rotate(Math.PI);

? ? ? ? ? ? ? ? ? ? ctx.translate(-width,-height);

? ? ? ? ? ? ? ? ? ? ctx.drawImage(image,0,0);

? ? ? ? ? ? ? ? ? ? imageDate = canvas.toDataURL('Image/jpeg',1)

? ? ? ? ? ? ? ? ? ? newImage.src = imageDate;

? ? ? ? ? ? ? ? ? ? break;

? ? ? ? ? ? ? ? //旋轉270°

? ? ? ? ? ? ? ? case 8:

? ? ? ? ? ? ? ? ? ? console.log('旋轉270°');

? ? ? ? ? ? ? ? ? ? canvas.height = width;

? ? ? ? ? ? ? ? ? ? canvas.width = height;

? ? ? ? ? ? ? ? ? ? ctx.rotate(-Math.PI/2);

? ? ? ? ? ? ? ? ? ? ctx.translate(-height,0);

? ? ? ? ? ? ? ? ? ? ctx.drawImage(image,0,0);

? ? ? ? ? ? ? ? ? ? imageDate = canvas.toDataURL('Image/jpeg',1)

? ? ? ? ? ? ? ? ? ? newImage.src = imageDate;

? ? ? ? ? ? ? ? ? ? break;

? ? ? ? ? ? ? ? //undefined時不旋轉

? ? ? ? ? ? ? ? case undefined:

? ? ? ? ? ? ? ? ? ? console.log('undefined? 不旋轉');

? ? ? ? ? ? ? ? ? ? newImage = image;

? ? ? ? ? ? ? ? ? ? break;

? ? ? ? ? ? }

? ? ? ? }

? ? );

? ? return newImage;

}

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容