H5單張、多張圖片上傳

前言

今天咱們聊一聊圖片上傳,單張Or多張 ,現在,各大圖片上傳插件數不勝數,例如:Jquery的 verupload.js,jQuery File Upload、Uploadify、jQuery.filter等等。But。上面說到的這些插件,今天咱們不談,咱們來看一看使用HTML5中的FileReader 如何實現 圖片的單張及多張預覽、刪除、上傳等功能。css

先看下實現後的效果以下:html

 

實現

前端部分

這塊是用戶點擊按鈕 其中咱們最重要的一句話是input type=file 和給了一個multiple屬性,能夠知足多張圖片上傳前端

<div class="form-group form-row">
        <label class="col-sm-2 control-label uText">俱樂部相冊</label><div class="row">
                        <div class="col-xs-10 col-sm-8 mTop5">
                            <label title="上傳俱樂部相冊" for="ClubImagesUpload" id="btnClubImg" class="col-sm-2">
                                
                                <input type="file" accept="image/*" name="ClubImagesUpload" id="ClubImagesUpload" class="hide" multiple="multiple">
                           
                                <img src="/Images/registerNewSite/btn_addimg.png" class="addImg"/>
                            </label>
                        </div>
                    </div></div>

下面這塊區域是用於圖片預覽的web

<div class="form-group form-row" id="preViewMore"><div class="row">
      <div class="col-xs-9">
         <div id="clubInputImagePreview" class="col-sm-9 img-preview img-preview-sm"></div>
       </div>
  </div></div>

 

樣式部分

什麼?連樣式你都要看,還有沒有人性(苦笑臉)數據庫

Js部分

首先咱們分析下上面的html,咱們用一個label把input和一個img標籤包起來了,咱們但願點擊效果圖那個+號圖片,就能彈出選擇相片的對話框,因此,咱們須要先給label來一個點擊事件:後端

$("#btnClubImg").click(function() {
    //TODO Something
});

接着咱們再看,由於咱們是要獲取上傳的文件,而咱們的文件主要是在input上,因此,咱們先將input標籤獲取到:瀏覽器

$("#btnClubImg").click(function() {
      var $input = $("#ClubImagesUpload");
     console.log($input);//打印當前元素
});

咱們將當前input元素標籤打印出來看看是個什麼東東app

咱們展開第一項會發現files裏面length長度是0異步

好,咱們繼續分析,由於咱們想要能當input框改變的時候,說簡單點 就是有選擇到文件的時候,咱們能獲取到當前選擇的文件,這個和獲取input框文字輸入是同樣的道理,因此,通過分析,咱們知道須要給input標籤加一個change事件:ide

 $("#btnClubImg").click(function() {
      var $input = $("#ClubImagesUpload");
      console.log($input);
      $input.on("change", function () {
         console.log(this);//打印改變後的當前元素
  });
});            

讓咱們來瞄一眼,獲取到改變後的input元素裏面有些啥東東:

這裏很清楚得能夠看到,咱們獲取到了選擇的圖片,包括有最後修改事件,圖片名稱,大小以及圖片類型(有了文件類型,咱們就能夠判斷當前用戶選擇的是不是圖片不是嗎(斜眼笑))

一樣,這是單個文件的, 若是是多個文件,就會有多個file

接着往下看,經過打印輸出咱們能夠看到,咱們再input 標籤的files元素上已經拿到了咱們想要的文件信息,咱們只須要獲取它們就好了:

 var files = this.files;
 var length = files.length;

這樣,咱們就能夠獲取到全部文件,以及文件的個數,那這裏問題來了,咱們若是是選擇多個文件,若是將其依次輸出並展現到頁面上呢?

看到上面標註的四個字,腦殼中有沒有閃現出兩個字呢?循環

 $.each(files, function (key, value) {
        //TOTO Something
  });

經過將上面獲得的files 循環,咱們能夠依次獲得每一個文件的信息。這樣,你就不只能夠將其依次輸出,若是你願意,你還能夠將其送上天~

var fileReader = new FileReader();//實例化一個FileReader對象
var file_ = files[key];//獲取當前文件
if (/^image\/\w+$/.test(file_.type)) {//將當前文件進行正則匹配,看是不是選擇的圖片
      fileReader.onload = function() {//當讀取操做完成時調用
    
       }         
}               

有必要延伸下FileReader的知識點:

FileReader主要用於將文件內容讀入內存,經過一系列異步接口,能夠在主線程中訪問本地文件。

使用FileReader對象,web應用程序能夠異步的讀取存儲在用戶計算機上的文件(或者原始數據緩衝)內容,可使用File對象或者Blob對象來指定所要處理的文件或數據。

回到主題,咱們已經可以獲得文件而且獲得返回,因此此時,咱們只須要展現返回的結果就好了

 $("#clubInputImagePreview").css("background-image", "url(" + this.result + ")");

咱們將其this.result打印出來看看是個什麼東東:

不言而喻,是將圖片轉換成了Base64的數據格式。最後,咱們調用 readAsDataURL 讀取文件內容,將其用data:url字符串表示出來

fileReader.readAsDataURL(value);

這樣,你就能夠獲得一個簡易的圖片上傳的Demo了,可是並非最終的,由於你還須要加不少業務進去。好比:獲得一張預覽圖片後,當前標籤會被佔用,若是下次循環進來,直接使用原標籤,確定會將以前的圖片替換,那這確定不是咱們想要的效果,

咱們但願是能依次展現,而不是替換展現。因此,咱們還須要作一些處理:

 $("#clubInputImagePreview").css("background-image", "url(" + this.result + ")");

//使用apend再當前元素下追加一個子節點
 $("#clubInputImagePreview") .append("<img src='/Images/registerNewSite/btn_r_del.png' class='clubsImage'  id='ImgRemove' />");

//使用after 向當前兄弟節點 追加一個同級節點                                       
$("#clubInputImagePreview").after( "<div id='clubInputImagePreview1' class='col-sm-9 img-preview img-preview-sm delImg' ></div>");

而後咱們追加的刪除圖片,也須要給其點擊事件,讓咱們的當前預覽區域消失:

$("#ImgRemove").click(function () {
          $(this).parent().remove();
});

最後,你會發現結果還不是咱們想要的,那是由於 當前ID還在,因此沒法進行下一步操做,而咱們只須要將當前元素的Id Remove掉,而後新增一個同ID的元素,這樣瀏覽器就會認爲這是一個新的元素:

 $input.removeAttr("id");
 var newInput ='<input type="file" accept="image/*" name="ClubImagesUpload" id="ClubImagesUpload" class="hide" multiple="multiple">';
 $(this).append($(newInput));

最後完整JS代碼以下:

  var intP = 0;
        $("#btnClubImg").click(function() {
            var $input = $("#ClubImagesUpload");
//            console.log($input);
            $input.on("change",
                function () {
//                    console.log(this);
                    var files = this.files;
                    var length = files.length;
                    if (intP > 8) {
                        layer.msg('圖片不能再多了~', {});
                        return;
                    }

                    $.each(files,
                        function (key, value) {
                            var fileReader = new FileReader();
                            var file_ = files[key];
                            if (/^image\/\w+$/.test(file_.type)) {
                                fileReader.onload = function() {
                                    if (intP > 8) {
                                        layer.msg('圖片不能再多了~', {});
                                        return;
                                    }
                                    if (key == 0 && intP == 0) {
                                        console.log(this.result);
                                        $("#clubInputImagePreview").css("background-image", "url(" + this.result + ")");

                                        $("#clubInputImagePreview")
                                            .append(
                                            "<img src='/Images/registerNewSite/btn_r_del.png' class='clubsImage'  id='ImgRemove' />");
                                        
                                        $("#clubInputImagePreview").after(
                                            "<div id='clubInputImagePreview1' class='col-sm-9 img-preview img-preview-sm delImg'></div>");
                                    } else {
                                        $("#clubInputImagePreview" + parseInt(intP) + "").css("background-image",
                                            "url(" + this.result + ")");

                                        $("#clubInputImagePreview" + parseInt(intP) + "").append(
                                            "<img src='/Images/registerNewSite/btn_r_del.png' class='clubsImage'  id='ImgRemove" +
                                            parseInt(parseInt(1) + parseInt(intP)) +"' />");

                                        $("#clubInputImagePreview" + parseInt(intP) + "").after(
                                            "<div id='clubInputImagePreview" +
                                            parseInt(parseInt(1) + parseInt(intP)) +
                                            "'class='col-sm-9 img-preview img-preview-sm delImg' ></div>");
                                    }
                                    if (key == 0 && intP == 0) {
                                        $("#ImgRemove").click(function () {
                                            $(this).parent().remove();
                                        });
                                    } else {
                                        $("#ImgRemove" + parseInt(parseInt(1) + parseInt(intP)) + "").click(function () {
                                            $(this).parent().remove();
                                        });
                                    }

                                    intP += parseInt(1);
                                };
                                fileReader.readAsDataURL(value);
                            } else {
                                layer.msg("格式錯誤<br/>請選擇一個圖片文件");
                            }
                        });
                

                });


            $input.removeAttr("id");
            var newInput =
                '<input type="file" accept="image/*" name="ClubImagesUpload" id="ClubImagesUpload" class="hide" multiple="multiple">';

            $(this).append($(newInput));

        });

 

下一篇,將講述 如何將前端獲得的多個File ,存入進數據庫,後端是.NET Core,敬請期待吧~

相關文章
相關標籤/搜索