<input
type="file"
accept="image/*"
@change="select">
iOS下会唤起选择照片或者拍照面板
Android直接进入选择照片,添加capture="camera"后直接唤起拍照
所以Android需要自己实现一个拍照或者选择照片面板来适应iOS,所以让APP实现去吧,整个统一的UI
select(event) {
// eslint-disable-next-line no-console
console.log('select', event, event.target);
const file = event.target.files[0];
// eslint-disable-next-line no-console
console.log('start', file);
const fileReader = new FileReader();
fileReader.onload = async (e) => {
// eslint-disable-next-line no-console
console.log('filereader.onload', file, file.type, e.target);
const base64Str = e.target.result;
if (!base64Str) {
Toast.show('选择文件有误,请重试');
return;
}
const img = new Image();
img.onload = async () => {
try {
// eslint-disable-next-line no-console
console.log('img.onload');
// 获取横屏竖屏
const Orientation = await this.getOrientation(img);
let n = 0;
if (Orientation === 6) {
n = 1;
}
// iphone拍照上传图片横屏的问题
const canvas = this.rotateAndCompressImg(img, n, 700);
// eslint-disable-next-line no-console
console.log('canvas压缩旋转后的canvas');
// 导出base64文件
const imgData = canvas.toDataURL('image/jpeg');
// eslint-disable-next-line no-console
console.log('canvas压缩旋转后的base64', imgData.length);
// 获取被canvas压缩后的图片对象,从而获取base64字符串字节大小
const blob = await Tools.base64ToBlob(imgData.split(',')[1], 'image/png');
// eslint-disable-next-line no-console
console.log('压缩后的img', blob, blob.size);
// 限制 15M 以内
if (blob.size > 1048576 * 15) {
Toast.show('选择文件太大,请重选');
return;
}
this.uploadImg({
file: imgData.slice(imgData.indexOf(',') + 1),
type: 'image/jpeg'
});
// change事件监听的是input的value的改变,不清空,就不能选择同一个文件
// eslint-disable-next-line no-console
console.log(event.target);
if (event.target && event.target.value) {
event.target.value = '';
}
} catch (err) {
// eslint-disable-next-line no-console
console.log('外层', err);
}
};
img.src = base64Str;
};
fileReader.readAsDataURL(file);
},
getOrientation(img) {
return new Promise(((resolve) => {
EXIF.getData(img, function _cb() {
try {
EXIF.getAllTags(this);
const Orientation = EXIF.getTag(this, 'Orientation');
resolve(Orientation);
} catch (e) {
// eslint-disable-next-line no-console
console.log('getOrientation', e);
// reject(e);
// 即便获取图片宽高失败也不阻止后续图片上传显示,只是不能旋转
resolve(0);
}
});
}));
},
rotateAndCompressImg(img, n, maxWidth = 700) {
const canvas = document.createElement('canvas');
const anw = document.createAttribute('width');
const anh = document.createAttribute('height');
let w;
let h;
const isLandscape = n % 2 !== 0;
// eslint-disable-next-line no-console
console.log('img原始宽高', img.width, img.height);
if (isLandscape) {
w = img.height;
h = img.width;
} else {
w = img.width;
h = img.height;
}
if (w > maxWidth) {
h *= (maxWidth / w);
w = maxWidth;
}
anw.nodeValue = w;
anh.nodeValue = h;
canvas.setAttributeNode(anw);
canvas.setAttributeNode(anh);
const ctx = canvas.getContext('2d');
ctx.translate(w / 2, h / 2);
ctx.rotate(n * 0.5 * Math.PI);
ctx.drawImage(img, -w / 2, -h / 2, w, h);
return canvas;
},
async uploadImg({ file, type }) {
// eslint-disable-next-line no-console
console.log('uploadImg');
Indicator.open({
text: '图片上传中...',
});
try {
const { url: src } = await recruitApi.uploadImage({
file: file || '',
image: 40,
type: this.getPlatform()
});
Indicator.close();
this.urls.push({
type,
src
});
} catch (error) {
if (error.name === 'CustomError') {
Toast.show(error.response && error.response.data && error.response.data.msg);
return;
}
Toast.show(error.message);
} finally {
Indicator.close();
}
},
网友评论