移動端做圖檔上傳功能,大體上要經曆以下幾個步驟。
- 利用fileReader,讀取blob對象或者file對象,将圖檔轉為data uri的形式
- 利用canvas,在頁面上建立一個畫布,利用canvas提供的api,将圖檔畫入到這個畫布中
- 利用canvas.toDataUrl(),進行圖檔的壓縮,得到圖檔的data url值
- 上傳檔案
步驟一當中,在進行圖檔壓縮的時候,我們要先進性判斷檔案的大小,如果圖檔大小是小于200KB的時候,我們是不需要進行壓縮的,直接對圖檔進行上傳。如果圖檔是大于200KB的時候,則要先進行壓縮再上傳。
相關api相容性可以查詢 https://caniuse.com/
步驟一: 讀取檔案
var fileChooser = document.getElementById('choose');
var maxSize = 200 * 1024;
fileChooser.onchange = function () {
var file = this.files[0];
var reader = new FileReader();
reader.onload = function () {
var result = this.result;
var img = new Image();
img.src = result;
if (result.length < maxSize) {
imgUpload(result);
}
else {
var data = compress(img);
imgUpload(data);
}
}
reader.readAsDataURL(file);
}
步驟二:建立canvas
var canvas = document.createElement('canvas');
步驟三:利用canvas進行壓縮
function compress(img) {
canvas.width = img.width;
canvas.height = img.height;
var data = canvas.toDataURL('image/jpeg', 0.2); // 0.2為圖檔的品質選項
return data;
}
在利用canvas進行繪圖的過程中,ios圖檔上傳過程中,會存在這樣的情況,當手機是自拍的時候拍出來的照片是反的。這個時候如果想糾正圖檔自動旋轉的情況,将圖檔轉為二進制資料,使用(binaryajax.js),友善擷取圖檔的exif資訊,通過擷取exif的資訊來确定圖檔旋轉的角度(使用了exif.js),然後再進行圖檔的相應的旋轉處理。
<script src="https://cdn.jsdelivr.net/npm/exif-js"></script>
EXIF.getData(file, function () {
orientation = EXIF.getTag(this, 'Orientation');
console.log(orientation); // 隻有圖檔是旋轉狀态的才可以拿到值,不然就是undefined
alert(orientation);
})
根據判斷orientation的角度值來判斷是否要旋轉,
// html
<input type="file" id="choose" accept="image/*">
<canvas id="canvas"></canvas>
// javascript
var canvas = document.getElementById("canvas");
var context = canvas.getContext('2d');
function compress(img) {
if (orientation === 6) { // 左右相反
console.log(img)
document.body.appendChild(img);
canvas.width = img.width;
canvas.height = img.height;
context.rotate(180*Math.PI/180); // 進行旋轉
context.drawImage(img, 0, 0, -img.width, -img.height);
var data = canvas.toDataURL('image/jpeg', 0.2);
return data;
}
}
這樣就完成了圖檔的旋轉。