案列:图片压缩 canvas高级应用:图片压缩算法实现
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<input type="file" id="upload">
<script>
const ACCEPT = ['image/jpg','image/png','image/jpeg']
const MAXSIZE = 800*800
const MAXSIZE_STR = '1MB'
function convertImageToBase64(file,callback){
let reader = new FileReader(); // 读取文件的内容
reader.addEventListener('load',function(e) {
// console.log(e.target.result);
// console.log(reader.result);
const base64Image = e.target.result
callback && callback(base64Image)
reader = null // 让内存去回收reader对象
})
reader.readAsDataURL(file) //blob对象,是浏览器前端给我们提供的一个对象,主要是用来标记文件的
}
function compress(base64Image, callback) {
console.log(base64Image);
let maxW = 600; // 要求图片的最大宽高
let maxH = 600;
const image = new Image() // 浏览器内置的Image对象
image.addEventListener('load',function(e) {
let ratio; // 图片的压缩比
let needCompress = false // 图片是否进行压缩
console.log(image.naturalWidth,image.naturalHeight);
if(maxW < image.naturalWidth){
needCompress = true
ratio = image.naturalWidth / maxW
console.log(ratio);
maxH = image.naturalHeight / ratio
console.log(maxH);
}
if(maxH < image.naturalHeight){
needCompress = true
ratio = image.naturalHeight / maxH
maxW = image.naturalWidth / ratio
}
if(!needCompress){
maxH = image.naturalHeight
maxW = image.naturalWidth
} // 如果不需要压缩 则获取图片的实际宽高
const canvas = document.createElement('canvas')
canvas.setAttribute('id','__compress__')
canvas.width = maxW
canvas.height = maxH
canvas.style.visibility = 'hidden'
document.body.appendChild(canvas)
const ctx = canvas.getContext('2d')
ctx.clearRect(0,0,maxW,maxH)
ctx.drawImage(image, 0,0,maxW,maxH)
const compressImage = canvas.toDataURL('image/jpeg',0.8)
console.log(compressImage);
callback && callback(compressImage)
const _image = new Image()
_image.src = compressImage
document.body.appendChild(_image)
canvas.remove()
console.log('压缩比:'+image.src.length / _image.src.length);
})
image.src = base64Image
document.body.appendChild(image) // 将image挂载到body下面
}
function uploadToServer(compressImage) {
console.log('upload to server...', compressImage);
}
const upload = document.getElementById('upload')
upload.addEventListener('change',function(e){
console.log(e.target.files);
const [file] = e.target.files
if(!file){
return
}
const {type:fileType, size:fileSize} = file
// if(ACCEPT.indexOf(fileType)<0){
// 图片类型检查
if(!ACCEPT.includes(fileType)){
alert(`不支持[${fileType}]这种文件类型!`)
upload.value = ''
return
}
// 图片的类型检查
if(fileSize > MAXSIZE){
alert(`文件超出${MAXSIZE_STR}`)
upload.value = ''
return
}
// 压缩图片
// 将图片转成base64
convertImageToBase64(file,(base64Image)=>compress(base64Image,uploadToServer))
})
</script>
</body>
</html>