前端实现本地图片读取与简单压缩功能

2018-02-26 10:35:51 浏览数 (1)

在上一篇文章Javascript 基础夯实 —— 通过代码构建一个包含文件的 FormData 对象中提到了前端压缩图片的功能,所以本篇文章就来实现一下这个功能

前端获取本地图片文件

通过一个类型为的标签,我们可以获取到设备本地的文件,还可以声明一个的属性,这个属性用来过滤可以选择的文件,如果不声明则可以选择所有文件

在这里,的值是,这表示可以选择所有类型的图片文件,包括 png/jpg/jpeg/gif/bmp 等等,如果需要限制可以选择的文件类型,则可以改写成这样:

如果需要多选,还可以再声明一个属性

onchange 事件与获取选择的文件

我们可以通过事件监听到状态的改变,这样就能在选择完文件后,对文件进行操作

元素有一个属性,这个属性的值是一个文件对象数组,用来保存当前选择过的文件

读取文件对象内容

虽然获取到了选择的图片文件,但是我们并不能对 File 对象直接进行压缩的操作,而是需要先读取 File 对象的内容,再对读取到的内容进行操作

读取 File 对象的内容,我们可以通过 FileReader 对象来实现,此处以选择的第一张图片为例:

FileReader 对象上有以下属性及方法:

属性:

readyState:FileReader 当前的状态,有三种值,0-还未开始读取数据;1-正在读取数据;2-数据读取完成

result:在读取完成后才会存在的属性,值是读取到的文件的内容

onload:文件读取完成后触发的事件

error:读取文件时的错误信息

常用方法:

readAsDataURL:将 File 或 Blob 读取为一个 base64 编码的 URL 字符串

readAsText:读取 File 或 Blob 的文本内容,第二个参数可以指定编码类型,默认 utf-8

abort:取消读取的操作

需要注意的是, 和 都是异步的,必须监听 或者在 事件中才能获取到读取到的结果,所以出现多个文件需要遍历读取的情况时,需要特别注意

在上面的代码中,将图片文件读取为了一个 base64 编码的 URL 字符串,下面就可以通过这个字符串来创建一个 Image 对象了:

拿到图片文件生成的 image 对象,下面就可以正式进行图片的压缩了!

前端压缩图片的实现

压缩的实现又要借助到 canvas 画布元素。先来说一下原理,再来实现功能

原理简述

然后再将图片按比例缩放绘制到 canvas 上,再将 canvas 的上下文导出为一个 base64 的 url,导出的过程中我们可以设定导出的压缩比率和导出的图片格式

最终我们拿到了一个压缩后的图片的 base64 编码的 url,我们可以将这个 url 转为 Blob 对象,再通过表单的方式传输到后台。关于这一步,在开头的链接中,也就是上一篇文章已经说过了,在本文中不再赘述:

代码实现

需要注意的几点:

方法是 canvas 上下文环境的方法,而不是 canvas 元素的方法,这个方法可以接收多个参数,并且参数长度不同,作用也不同,在这里的作用是:将 image 从 (0, 0) 的位置开始截取一个宽高为 image.width, image.height 的图像(即将图像完整截取),放置在 canvas 上从 (0, 0) 开始,到 canvas.height, canvas.width 的区域中(也就是完整缩放在 canvas 中)。当传入其他数量参数时,小伙伴们可以参考这个页面:HTML DOM drawImage() 方法

导出图像方法 是 canvas 的方法,第一个参数hi导出的格式,不传或者传入错误格式的话,会默认使用 png 格式;第二个参数是导出的品质系数,范围为 0-1,默认 0.92,但是这个系数只对导出类型为 jpeg 和 webp 的图片生效

0 人点赞