小编给大家分享一下H5使用反应组件实现拍的照,选择图片上传的方法,希望大家阅读完这篇文章后大所收获、下面让我们一起去探讨吧!
前段时间项目重构,改成SSR的项目,但之前用的图片选择上传组件不支持SSR (server-side-render)。遂进行了调研,发现很多的工具。但有的太大,有的使用麻烦,有的不满足使用需求。决定自己写一个代替移动端图片上传组件。图片上传是一个比较普遍的需求,PC端还好,移动端就不是特别好做了。下面将过程中一些重点的问题进行简单的记录。
<强>重点强>
1。关于输入
选择功能使用& lt; input>标签实现。属性接受=& # 39;图像/* & # 39;:捕捉表示,可以捕获到系统默认的设备,比如:照相机,照相机;摄像机——摄像机;麦克风——录音。如果设置了捕获=癱amera",那么默认使用相机,存在部分机型无法调用相机的问题,我们这里不设置。允许多选多个加上onchange事件的回调函数。最终输入大概长这个样子:
& lt;输入类型=& # 39;文件# 39; className={classes.picker} 接受=& # 39;形象/* & # 39; 多个 捕捉=癱amera"> fileToCanvas(文件、索引){//文件 让读者=new FileReader (); reader.readAsDataURL(文件); 读者。onload=(事件)=比;{ 让图像=新图像(); 的形象。src=https://www.yisu.com/zixun/event.target.result; 的形象。onload=()=> { 让imageCanvas=[“画布”+指数].getContext (2 d); 让帆布={宽度:imageCanvas.canvas。scrollWidth * 2、身高:imageCanvas.canvas。scrollHeight * 2}; 让率=形象。宽/image.height; 让canvasRatio=画布。宽/canvas.height; 让xStart=0;让yStart=0;让renderableWidth;让renderableHeight; 如果(比> canvasRatio) {//横向过大,以高为准,缩放宽度 让hRatio=形象。高度/canvas.height; renderableHeight=image.height; renderableWidth=画布。宽度* hRatio; xStart=(图片。宽度——renderableWidth)/2; } 如果(比3。文件上传的扩展名获取
部分机型拍照时文件通过onchange事件拿到的文件是<代码> blob> 代码(小米6等)此时通过<代码> blob.type 代码>手动判断扩展名。
ios 4.拍照方向获取
当ios拍照上传后发现文件被旋转了,本地文件确是正常的,这个问题的原因这里不作详细解释。有兴趣的可以搜一下,所以我们需要检测方向,并将图像旋转回正常方向。获取取向有现成的很多库如Exif。js。但是这个库有些大,为了这个小需求引入似乎不太值得.stackoverflow上有很多现成的获取图片方向的代码。
,稍微改了下:getOrientation(文件){ 返回新的承诺((解决,拒绝)=比;{ 让读者=new FileReader (); 读者。onload=function (e) {//e.target.result为base64编码的文件 让观点=new DataView (e.target.result); 如果视图。getUint16(0,假)!==0 xffd8) { 返回解决(2); } 让长度=view.byteLength; 让抵消=2; 而(抵消& lt;长度){ 让标志=视图。getUint16(偏移量,假); 抵消+=2; 如果(标志===0 xffe1) { 让tmp=视图。getUint32(抵消+=2,假); 如果(tmp !==0 x45786966) { 返回解决(1); } 让?视图。getUint16(抵消+=6,假)===0 x4949; 抵消+=视图。getUint32(抵消+ 4,小); 让标签=视图。getUint16(抵消,小); 抵消+=2; (让我=0;我& lt;标签;我+ +){ 如果视图。getUint16(抵消+ i * 12,小)===0 x0112) { 返回解决(视图。getUint16(抵消+ i * 12 + 8,小)); } } }else if(标记,0 xff00) !==0 xff00) { 打破; 其他}{ 抵消+=视图。getUint16(偏移量,假); } } 返回解决(1); }; reader.readAsArrayBuffer(文件。片(0,64 * 1024)); }); }//返回值:1——正常,2——非jpg, 1——定义
5。ios照片方向修正
正常的图像取向应该是1,于是我们将文件转为画布,使用帆布的变换方法对画布进行变换,参考。最后通过canvas.toDataURL(& # 39; & # 39;)拿到base64编码的方向正常的base64图片,再将base64转为blob进行上传;
//重置文件取向 resetOrientationToBlob(文件、取向){ 返回新的承诺((解决,拒绝)=比;{ 让读者=new FileReader (); reader.readAsDataURL(文件); 读者。onload=(事件)=比;{ 让图像=新图像(); 的形象。src=https://www.yisu.com/zixun/event.target.result; 的形象。onload=()=> { 让宽度=image.width; 让身高=image.height; 让帆布=document.createElement(“画布”); 让ctx=canvas.getContext (2 d); 如果(取向> 4 & &取向H5使用反应组件实现拍的照,选择图片上传的方法