利用画布中toDataURL()将图片转为dataURL (base64)的方法详解

  

  

将图片转换为Base64编码,可以让你很方便地在没有上传文件的条件下将图片插入其它的网页,编辑器中。这对于一些小的图片是极为方便的,因为你不需要再去寻找一个保存图片的地方。

  

将图片转换成base64编码的,在web网上一般用于小图片上,不仅可以减少图片的请求数量(集合到js, css代码中),还可以防止因为一些相对路径等问题导致图片404错误。

  

  

假设一个应用场景:由于某些特殊原因从服务端请求到图片路径,要求通过该路径获取对应图片的base64 dataURL。在这个场景中,我们首先推断该图片路径是可访问的,同时还需要一种将图片转换到dataURL的方法。

  

我们如何实现它呢?

  

  

先大致回顾下正统的dataURL的语法,这有助于我们检验转换后的内容是否正确。一个完整的dataURI应该是这样的:

        数据:[& lt; mediatype>] [; base64], & lt; data>      

其中mediatype声明了文件类型,遵循MIME规则,如“图像/png”、“文本/普通”,之后是编码类型,这里我们只涉及base64;紧接着就是文件编码后的内容了。我们常常在HTML里看到img标签的src会这样写:

        src="数据:图像/gif, base64 R0lGODdhMAAwAPAAAAAAAP///ywAAAAAMAAwAAAC8IyPqcvt3wCcDkiLc7C0qwyGHhSWpjQu5yqmCYsapyuvUUlvONmOZtfzgFzByTB10QgxOR0TqBQejhRNzOfkVJ + 5 yiuqrxf5y5lkh/DeuNcP5yLWGsEbtLiOSpa TPg7JpJHxyendzWTBfX0cxOnKPjgBzi4diinWGdkF8kjdfnycQZXZeYGejmJlZeGl9i2icVqaNVailT6F5iJ90m6mvuTS4OK05M0vDk0Q4XUtwvKOzrcd3iq9uisF81M1OIcR7lEewwcLp7tuNNkM3uNna3F2JQFo97Vriy/Xl4/f1cf5VWzXyym7PHhhx4dbgYKAAA7”      

这个img引用的就是以base64编码的dataURL了,只要浏览器支持,就可以被解码成gif图片并渲染出来。

  

  

FileReader对象也有类似的方法,比如<代码> .readAsDataURL() ,然而它只接受文件或blob类型,而这两种类型一般只能通过<代码> & lt;输入(type=文件)在元素的文件属性获取,或者用blob()构造函数手工创建一个新的对象。尴尬的是我们当前只有图片路径,受制于浏览器的安全策略,<代码> & lt;输入[类型=文件]祝辞> 是可以的,并且可以被绘制到& lt; canvas>中,而& lt; canvas>正巧拥有<代码> .toDataURL() 方法。

  

万事具备,我们只需要把& lt; img>获取到的图片放到& lt; canvas>里再通过<代码> .toDataURL() 方法转化下,就可以得到以base64编码的dataURL来。看这个方法的语法:

        画布。toDataURL([类型,encoderOptions]);      

画布是DOM元素& lt; canvas>对象;参数类型指定图片类型,如果指定的类型不被支持则以默认值图像/png替代;encoderOptions可以为图像/jpeg或图像/webp类型的图片设置图片质量,取值0 - 1,超出则以默认值0.92替代。

  

在转换成dataURL前必须先确保图片成功加载到,于是<代码> .toDataURL() 方法应该写在& lt; img>的onload异步事件中。现在就来实现一个功能函数:

        函数getBase64 (url) {//通过构造函数来创建的img实例,在赋予src值后就会立刻下载图片,相比createElement()创建& lt; img>省去了append(),也就避免了文档冗余和污染   var Img=新形象(),   dataURL=";   Img.src=https://www.yisu.com/zixun/url;   Img.onload=function(){//要先确保图片完整获取到,这是个异步事件   画布var=document.createElement(“画布”),//创建帆布元素   宽度=Img。宽度,//确保画布的尺寸和图片一样   身高=Img.height;   canvas.width=宽度;   canvas.height=身高;   canvas.getContext (2 d) .drawImage (Img, 0, 0,宽度、高度);//将图片绘制到画布中   ”image/jpeg dataURL=canvas.toDataURL (');//转换图片为dataURL   };   }      

一个可供随时调用的转换函数完成了,它会在图片被加载后返回一整个dataURL字符串。

  

  

onload事件确保了转换任务在加载后执行,却又带来了新问题——dataURL只有在图片加载完成后才会返回,我们无法确定图片什么时候完成加载。如果后续要对dataURL做相关处理(比如传递到其他服务器)的话,添加一个回调是必要的,这能确保后续处理任务在成功得到dataURL之后执行,我们需要修改<代码> getBase64() :

利用画布中toDataURL()将图片转为dataURL (base64)的方法详解