<FormItem label="上传图片" prop="faceImg">
<div class="default-img" v-if="!formData.faceImg" @click="triggerInputFile">
<i class="iconfont icon-pic"></i>
</div>
<div class="img-box" v-else>
<Icon type="ios-close-circle-outline" @click="removeFaceImg"/>
<img :src="formData.faceImg">
</div>
</FormItem>
<input type="file" @change="getFaceImg" ref="fileInput" class="file-input" accept="image/*">
data() {
return {
formData: {
faceImg: '',
},
rules: {
faceImg: [{
required: true, validator: this.validateFaceImg }],
},
}
}
/**
* 触发 input file 上传事件
*/
triggerInputFile() {
this.$refs.fileInput && this.$refs.fileInput.click();
},
/**
* 获取上传的图片
*/
async getFaceImg(e) {
let _this = this;
let file = e.target.files[0];
// maxSize 是压缩的设置,设置图片的最大宽度和最大高度,等比缩放,level 质量,数值越小质量越低
let maxSize = {
width: 1000, height: 1000, level: 0.8 };
// 判断 文件大小 限制最大 10M
if (file.size > 10 * 1024 * 1024) {
this.$refs.fileInput && (this.$refs.fileInput.value = null); //将上传的图片清空
this.$Message.error("请大于10M的图片");
return;
}
// 压缩图片
let fileReader = new FileReader(); //读取文件内容
fileReader.onload = function() {
//onload 文件读取成功完成时触发
_this.formData.faceImg = fileReader.result.toString(); //将图片利用base64读取
let IMG = new Image(); //创建image对象,将image对象的src分别指向需加载的图片地址,图片被请求,因为Image对象没有显示在页面上,所以不会对页面布局产生影响。
IMG.src = this.result;
let imgWidth = 0,
imgHeight = 0;
IMG.onload = function() {
let w = this.naturalWidth, //这个类似于IMG.width
h = this.naturalHeight; //这个类似于IMG.height
if (w > maxSize.width || h > maxSize.height) {
// 如果图片尺寸大于最大限制,则压缩图片上传
let multiple = Math.max(w / maxSize.width, h / maxSize.height);
imgWidth = w / multiple;
imgHeight = h / multiple;
let canvas = document.createElement('canvas'),
ctx = canvas.getContext('2d');
canvas.width = imgWidth;
canvas.height = imgHeight;
ctx.drawImage(this, 0, 0, imgWidth, imgHeight);
let base64 = canvas.toDataURL('image/jpeg', maxSize.level || 1); //canvas画布转换成img图像
_this.formData.faceFile = _this.convertBlob(
window.atob(base64.split(',')[1]) //用于解码使用 base-64 编码的字符串。
);
} else {
// 如果图片尺寸小于最大限制,则不压缩直接上传
_this.formData.faceFile = file;
}
_this.$refs.fileInput && (_this.$refs.fileInput.value = null);
};
};
fileReader.readAsDataURL(file); //读取指定的 Blob 或 File 对象
},
/**
* 图片 base64 -> blob 二进制对象
*/
convertBlob(base64) {
let buffer = new ArrayBuffer(base64.length);
let ubuffer = new Uint8Array(buffer);
for (let i = 0; i < base64.length; i++) {
ubuffer[i] = base64.charCodeAt(i);
}
let blob;
try {
blob = new Blob([buffer], {
type: 'image/jpg' });
} catch (e) {
window.BlobBuilder =
window.BlobBuilder ||
window.WebKitBlobBuilder ||
window.MozBlobBuilder ||
window.MSBlobBuilder;
if (e.name === 'TypeError' && window.BlobBuilder) {
let blobBuilder = new BlobBuilder();
blobBuilder.append(buffer);
blob = blobBuilder.getBlob('image/jpg');
}
}
return blob;
},
/**
* 删除选择的图片
*/
removeFaceImg() {
this.formData.faceImg = '';
this.formData.faceFile = null;
this.$refs.formData && this.$refs.formData.validateField('faceImg');
},