Maison  >  Article  >  interface Web  >  Comment utiliser H5 pour télécharger des photos

Comment utiliser H5 pour télécharger des photos

php中世界最好的语言
php中世界最好的语言original
2018-06-04 11:20:008542parcourir

Cette fois, je vais vous montrer comment utiliser H5 pour télécharger des images et comment utiliser H5 pour télécharger des images NotesOui Lesquelles. , voici des cas pratiques, jetons un oeil.

J'ai travaillé sur un projet il y a quelques jours, et l'un des modules impliquait le téléchargement d'images sur le serveur. J'ai pris le temps de le trier aujourd'hui et j'ai découvert que plus je le triais, plus cela impliquait de points de connaissances. L'exemple suivant fait référence à la carte de recherche de Baidu.

Points de connaissances : fichier d'entrée, base64, FileReader, compression canevas, blob, encodage btoa et décodage atob, FormData.

nœud dom html :

<input type="file">

Un fichier peut être sélectionné par défaut. Plusieurs photos doivent être téléchargées. Vous pouvez ajouter l'attribut multiple="true". Utilisez généralement opacity:0; pour masquer le style par défaut, puis réécrivez son style.

1. Créer un objet

var fileReader = new FileReader();

2. Déterminez si le navigateur est compatible ---- ie8 ne prend pas en charge

if( window.FileReader )

3. Constantes d'état

常量名 描述
EMPTY 0 为开始读取文件
LOADING 1 文件读取中
DONE 2 文件读取完成
Nom de la constante

Valeur Description

VIDE 0
属性名 描述
error 读取文件时发生错误
readyState 当前fileReader对象的状态,为上述状态常量的一个
result 读取到的内容
DémarrerLecture des fichiers
CHARGEMENT 1 Lecture du fichier
TERMINÉ 2 Lecture du fichier terminée
Dans l'exemple ci-dessous, le courant le statut peut être lu séparément. 4. Attributs
Nom de l'attribut Description
Erreur Une erreur s'est produite lors de la lecture du fichier
readyState L'état de l'objet fileReader actuel est l'état ci-dessus Une constante
résultat Le contenu lu

5. Méthode

方法名 参数 描述
abort 中止读取,在非LOADING状态时调用会抛出异常
readAsArrayBuffer blob/file 读取为数组,在result中有一个ArrayBuffer对象为读取的内容
readAsBinaryString blob/file 读取为二进制,在result中有读取文件的原始二进制
readAsDataUrl blob/file 读取为dataUrl,在result中有data:url格式的字符串表示读取的内容
readAsTexx blob/file , [encoding] 读取为文本,在result中字符串表示读取的内容
Nom de la méthode

Paramètre Description
事件 描述
onabort 中断时触发
onerror 出错时触发
onload 读取成功时触发
onloadend 读取完成时触发(不论成功是否)
onloadstart 读取开始时触发
onprocess 读取中触发
abandon Aucun Abandonner la lecture, lors d'un appel dans un état non-LOADING, Lance une exception
readAsArrayBuffer blob/file Lire sous forme de tableau, dans Il y a un objet ArrayBuffer dans le résultat pour le contenu lu
readAsBinaryString blob/file Lire en binaire, il y a le binaire original du fichier lu dans le résultat
readAsDataUrl blob/file est lu en tant que dataUrl, et il y a une chaîne au format data:url dans le résultat pour représenter le contenu lu
readAsTexx blob/file , [encodage] Lire sous forme de texte, et la chaîne dans le résultat représente le contenu lu
Traitement des événements. onerror

BASE64:

我们用chrome打开一张图片,在resources里面显示的就是图片的base编码(实际上base编码比原图片稍大)

图片的base64编码也就是将一张图片编码成一个字符串,我们可以用这个字符串给img标签的src赋值,这样我们就可以看到这张图片。

如何编写:

在html中:

<span style="font-size: 14px;"><img src="data:image/gif;base64,R0lGODlhAwADAIABAL6+vv///yH5BAEAAAEALAAAAAADAAMAAAIDjA9WADs="></span>

在css中:

<span style="font-size: 14px;">background-image:url(data:image/gif;base64,R0lGODlhBAABAIABAMLBwfLx8SH5BAEAAAEALAAAAAAEAAEAAAICRF4AOw==);</span>

优缺点:

优点:1、减少了http请求;2、可以被gzip;3、没有跨域问题;4、无需考虑在更新图片时缓存问题。

缺点:1、ie8以下不支持;2、不论是写在css文件还是html文件中,增加了文件的大小;3、图片大了之后,程序员编码相当困难;

应用:

根据实际需求来选择base64显示图片,或者选择css sprite,或者直接使用png等

一般使用场景:很少被更新,实际尺寸很小,在系统中大量使用。

canvas压缩:

在移动应用场景中,用户上传的图片一般很大,会导致上传时间过长而失败,既浪费时间也浪费流量,更影响用户体验。我们可以使用canvas的drawImage方法的图形裁剪功能。

1、新建image对象,给其src复制base64值,在其监听onload事件;

2、在onload事件方法中新建canvas对象,获取上下文context;

3、设置裁剪比例,调用drawImage方法填充图片。

4、通过toDataUrl方法获取裁剪之后的base64值。

详细见下例。

Blob

在传输一些比较大的图片的base64是容易出现转发错误,这里我们可以将base64转换成blob字段写到form表单中提交到后台。一般blob和base64之间的相互转换通过fileReader 的readAsDataUrl和ArrayBuffer的charCodeAt方法。下面列举几个相互转换的方法。来自(http://jsperf.com/blob-base64-conversion)

<span style="font-size: 14px;"> var blobToBase64 = function(blob, cb) {<br>      var reader = new FileReader();<br>      reader.onload = function() {<br>        var dataUrl = reader.result;<br>        var base64 = dataUrl.split(',')[1];<br>        cb(base64);<br>      };<br>      reader.readAsDataURL(blob);<br>      };<br>  var base64ToBlob = function(base64, cb) {<br>      var binary = atob(base64);<br>      var len = binary.length;<br>      var buffer = new ArrayBuffer(len);<br>      var view = new Uint8Array(buffer);<br>      for (var i = 0; i < len; i++) {<br/>        view[i] = binary.charCodeAt(i);<br/>      }<br/>      cb(new Blob([view]));<br/>      };<br/>  var base64ToBlobSync = function(base64) {<br/>      var binary = atob(base64);<br/>      var len = binary.length;<br/>      var buffer = new ArrayBuffer(len);<br/>      var view = new Uint8Array(buffer);<br/>      for (var i = 0; i < len; i++) {<br/>        view[i] = binary.charCodeAt(i);<br/>      }<br/>      var blob = new Blob([view]);<br/>      return blob;<br/>      };<br/>  var blobToBase64_2 = function(blob, cb) {<br/>      var reader = new FileReader();<br/>      reader.onload = function() {<br/>        var buffer = reader.result;<br/>        var view = new Uint8Array(buffer);<br/>        var binary = String.fromCharCode.apply(window, view);<br/>        var base64 = btoa(binary);<br/>        cb(base64);<br/>      };<br/>      reader.readAsArrayBuffer(blob);<br/>      };</span>

btoa 与 atob: ---在对base64转blob时就需要用atob对base64进行解码

btoa("javascript");     //"amF2YXNjcmlwdA=="
atob("amF2YXNjcmlwdA==") ;       //"javascript"

注意:在需要转码中文时,需要用encodeURIComponent方法对中文处理,解码时用decodeURIComponent

btoa(encodeURIComponent("我喜欢 javascript"));    //"JUU2JTg4JTkxJUU1JTk2JTlDJUU2JUFDJUEyJTIwamF2YXNjcmlwdA=="
decodeURIComponent(atob("JUU2JTg4JTkxJUU1JTk2JTlDJUU2JUFDJUEyJTIwamF2YXNjcmlwdA=="));   //"我喜欢 javascript"
FormData:

我们只需要使用new FormData()创建对象,然后append键值对,后用ajax向后台发生即可。

这里是往FormData对象添加blob字段。

注:使用Ajax将这个FormData对象提交到服务器上时,所发送的HTTP请求头中代表那个Blob对象所包含文件的文件名称的"Content-Disposition"请求头的值会是一个空字符串,这会引发某些服务器程序上的错误.从Gecko 7.0开始,这种情况下发送的文件名称改为"blob"这个字符串.

<!DOCTYPE html>
<html lang="en">
<head>
 <meta charset="UTF-8">
 <meta name="viewport" content="width=device-width,initial-scale=1.0,maximum-scale=1.0,user-scalable=0">
 <title>Document</title>
 <script src="http://apps.bdimg.com/libs/zepto/1.1.4/zepto.min.js"></script>   <!--引用baidu-->
</head>
<style>
.uploadPic{
 width: 92%;
   position: relative;
   margin: 0 auto;
   height: 2.8rem;
   line-height: 2.8rem;
   font-size: 1.3rem;
   border-radius: 4px;
   color: #fff;
   text-align: center;
   background-color: #72bcc5;
}
.uploadPic>input{
 position: absolute;
   display: block;
   width: 100%;
   height: 100%;
   right: 0;
   top: 0;
   opacity: 0;
}
.uploadPic>img{
 border:none;
}
</style>
<body>
 <p id="uploadPic" class="uploadPic">
 <span>拍摄</span>
 <input type="file" >  <!--这里可以添加multiple="true"属性,用来添加多张图片,然后对this.file[]数组操作-->
 <p style="line-height: 1rem;margin: 0.5rem 0;"><progress id="progress" value="0" max="100" style="width: 100%;"></progress></p> 
 <img src="" width="100%" style="height: 21rem;">
 </p>
</body>
<script>
 function upload(file, callBack) {
        var loading=0;
        var total=file.size;
        if(window.FileReader){
         $("#progress")[0].value=0;
         var fileReader = new FileReader();
         fileReader.onload = function() {
          console.log(fileReader.readyState);  //读取完成
             compressPic(this.result,callBack)
         };
         fileReader.onerror = function() {
          console.log(fileReader.error);
         };
         fileReader.onprogress = function (e){
          console.log(fileReader.readyState);  //读取中
          loading += e.loaded;
          $("#progress")[0].value=(loading / total) * 100; 
         }
         console.log(fileReader.readyState);  //未读取
         fileReader.readAsDataURL(file)
        }else{
         alert("您的浏览器不支持FileReader");
        }
    }
    function base64ConvertToBlob(picData, type, size) {
            type = type || "";
            size = size || 512;
            var decodeFileData = atob(picData);  //此处用atob解码,转码函数btoa。在使用方法时注意操作中文时,需对中文decodeURIComponent转换
            var dataArray = [];
            var len = decodeFileData.length;
            for (var i = 0; i < len; i += size) {
                var pieceData = decodeFileData.slice(i, i + size);   //这里做了一个512的分组
                var arr = new Array(pieceData.length);
                for (var j = 0; j < pieceData.length; j++) {
                    arr[j] = pieceData.charCodeAt(j)
                }
                var u8a = new Uint8Array(arr);
                dataArray.push(u8a)
            }
            return new Blob(dataArray, {type: type})
    }
    function compressPic(picData,callBack) {
        var img=new Image();
        img.onload = function(){
         var width = img.width;
         var height = img.height;
         var standard=800;  //以800为基准压缩
         if (width > standard || height > standard) {
             var rate = Math.max(width / standard, height / standard);
             width /= rate;
             height /= rate
         }
      var canvas = document.createElement("canvas");
         canvas.width = width;
         canvas.height = height;
         var context = canvas.getContext("2d");
         context.fillRect(0, 0, canvas.width, canvas.height);
         context.drawImage(img, 0, 0, width, height);
         var data = canvas.toDataURL("image/jpeg", 1);
         //var blobData=base64ConvertToBlob(data.replace(/^.*?,/, ""), "image/jpeg")  //-----需要去掉符号,不然使用atob方法报错
         //doAjax(new FormData().append('image',data));   //后续可以这样做,转换成Blob字段,组装FormData,发送至后台
         console.log("the after canvas compress size : " + data.length);
         callBack(data)
        };
        img.src=picData;
        console.log("the before canvas conpress size : "+picData.length);
    }
 $("#uploadPic input").change(function() {
 var file=this.files[0];
 upload(file, function(picData){
             $("#uploadPic img")[0].src = picData;    //预览
            }
        );
    });
</script>
</html></span>

相信看了本文案例你已经掌握了方法,更多精彩请关注php中文网其它相关文章!

推荐阅读:

JS中特性与UA检测

Ajax的工作原理核心以及对象

Événement Description
onabort Déclenché sur interruption
Déclenché lorsqu'une erreur se produit
onload td> Déclenché lorsque la lecture est réussie
onloadend Déclenché lors de la lecture est terminé (indépendamment du succès ou non)
onloadstart Déclenché lorsque la lecture commence
onprocess Déclenché lors de la lecture

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn