MUI使用H5+Api調取系統相簿多圖選擇及轉base64碼

酒醉的探戈發表於2017-12-18

偉大的哲學家曾說過
“寫程式碼,一定要翻文件”

這次我們需要用到的是調取系統相簿進行多圖上傳,
先奉上html5+api關於系統相簿的文件連結
連結:HTML5+ API Reference & gallery

首先一點,我們在使用5+Api前都需要在manifest.json檔案中進行功能模組的新增,
當然用Hbuilder的話大部分模組都已在內,這裡是關於相簿的模組

{
// ...
"permissions":{
    // ...
    "Gallery": {
        "description": "系統相簿"
    }
}
}

另外,5+Api需在plusReady事件之後

//mui封裝的方法
mui.plusReady(function(){
    // ...
});
//5+寫法
document.addEventListener( "plusready", function(){
    // ...
}, false );

進入正題,多圖上傳的核心程式碼為以下程式碼
我們可以設定多種引數,請查閱文件

// 從相簿中選擇圖片 
function galleryImg() {
    // 從相簿中選擇圖片
    console.log("從相簿中選擇圖片:");
    plus.gallery.pick( function(path){
        console.log(path);
    }, function ( e ) {
        console.log( "取消選擇圖片" );
    }, {filter:"image"} );
}

以下是多圖上傳的demo
請在包含配置檔案和mui css及js專案中開啟
iOS模擬器除錯會閃退,真機不會,具體原因未知

<!doctype html>
<html>

    <head>
        <meta charset="UTF-8">
        <title></title>
        <meta name="viewport" content="width=device-width,initial-scale=1,minimum-scale=1,maximum-scale=1,user-scalable=no" />
        <link href="../css/mui.min.css" rel="stylesheet" />
        <style type="text/css">
            .mui-bar{
                height: 64px;
                padding-top: 20px;
            }
            .mui-content{
                padding-top: 64px !important;
            }
            .width{
                position: absolute;
                width: 100%;
                min-height: 100%;
                top: 50%;
                transform: translateY(-50%);
                -ms-transform: translateY(-50%);
                -moz-transform: translateY(-50%);
                -webkit-transform: translateY(-50%);
                -o-transform: translateY(-50%);
            }
            .height{
                position: absolute;
                height: 100%;
                min-width: 100%;
                left: 50%;
                transform: translateX(-50%);
                -ms-transform: translateX(-50%);
                -moz-transform: translateX(-50%);
                -webkit-transform: translateX(-50%);
                -o-transform: translateX(-50%);
            }
            .tips{
                padding: 12px;
            }
            .tips p{
                margin: 0;
                line-height: 1.5
            }
            .photo-list{
                background-color: #fff;
                padding: 6px;
            }
            .photo-list .photo-box , .add-btn{
                position: relative;
                float: left;
                margin: 1%;
                width: 23%;
                height: 0;
                padding-bottom: 23%;
                border-radius: 3px;
                overflow: hidden;
            }
            .add-btn{
                border: dashed 1px #DDD;
                font-size: 30px;
            }
            .delete{
                font-size: 20px;
            }
            .add-btn , .delete{
                position: relative;
                font-family: Muiicons;
                font-weight: 400;
                font-style: normal;
                line-height: 1;
                display: inline-block;
                text-decoration: none;
                -webkit-font-smoothing: antialiased;
            }
            .add-btn:after{
                content: `e468`;
                position: absolute;
                left: 50%;
                top: 35%;
                transform: translateX(-50%);
                color: #aaa;
            }
            .delete:after{
                content: `e401`;
                position: absolute;
                left: 50%;
                transform: translateX(-50%);
                color: #fff;
            }
            .photo-box .delete{
                position: absolute;
                bottom: 0;
                left: 0;
                width: 100%;
                height: 24px;
                background-color: rgba(0,0,0,.4);
            }
        </style>
        
    </head>

    <body>
        
        <header class="mui-bar mui-bar-nav">
            <h1 class="mui-title">從相簿上傳圖片</h1>
        </header>
        
        <div class="mui-content">
            <div class="tips">
                    <p>上傳照片</p>
            </div>
            <div class="photo-list mui-clearfix" id="list">
                    <div class="photo-box">
                        <img src="../images/activity1.png" />
                        <div class="delete"></div>
                    </div>
                <div class="add-btn" id="btn"></div>
            </div>
        </div>
        
        <script src="../js/mui.min.js"></script>
        <script type="text/javascript">
            mui.init();
            
            //DOM獲取及變數
            var list = document.getElementById(`list`);
            var btn  = document.getElementById(`btn`);
            var setNum = 9 ;  //圖片最大選擇數量
            
            /* *
             * 調取系統相簿需在API載入完成後發生
             */
            mui.plusReady(function(){
                //新增圖片按鈕點選
                btn.addEventListener(`tap`,function(){
                    var num = setNum;
                    if( list.querySelector(`.photo-box`) ){
                        var box = list.getElementsByClassName(`photo-box`);
                        num -= box.length;
                    }
                    galleryImgs( num );
                });
                
            },false);
            
            // 從相簿中選擇多張圖片 
            function galleryImgs( num ){
                // 從相簿中選擇圖片
                console.log("從相簿中選擇多張圖片:");
                plus.gallery.pick( function(e){
                        for(var i in e.files){
                            console.log( e.files[i] );
                            insertPhoto( e.files[i] ); //將圖片放在頁面上
                        }
                }, function ( e ) {
                        console.log( "取消選擇圖片" );
                },{ 
                        filter   : "image",     //系統相簿選擇器中可選擇的檔案型別 "image" , "video" , "none"
                        multiple : true,        //是否支援多選
                        maximum  : num,         //最多選擇的檔案數量,上面設定了全域性變數
                        system   : false,       //是否使用系統檔案選擇介面,iOS下無效
                        onmaxed  : function(){  //超出選擇最大檔案數時觸發
                        mui.toast( `最多選擇` + num + `張圖片` )
                    }
                });
            }
            
            //將選擇的圖片轉base64並加入到頁面中
            function insertPhoto ( data ){
                var imgClass ;  //img的class名
                //建立image物件並轉換base64碼
                var img = new Image();
                    img.src = data ;
                    img.onload = function(){
                        //建立canvas畫布
                        var canvas = document.createElement("canvas"); 
                        //在css中不要直接給img設定寬高,否則此處會獲取到css設定的值
                        var width  = img.width;
                        var height = img.height;
                        //比較圖片寬高設定圖片顯示和canvas畫布尺寸
                        if (width > height) { 
                                imgClass = `height`;
                            if (width > 500) { 
                                height = Math.round(height *= 500 / width); 
                                width = 500; 
                            } 
                        } else { 
                                imgClass = `width`;
                            if (height > 500) { 
                                width = Math.round(width *= 500 / height); 
                                height = 500; 
                            } 
                        } 
                        canvas.width  = width;                               //設定新的圖片的寬度
                        canvas.height = height;                              //設定新的圖片的長度
                        var ctx = canvas.getContext("2d"); 
                        ctx.drawImage(img, 0, 0, width, height);             //繪圖
                        var dataURL = canvas.toDataURL("image/png", 0.8);    //供img標籤使用的src路徑
                        //將最後拿到的圖片類名和src放入頁面中
                        var div = document.createElement(`div`);
                            div.setAttribute(`class`,`photo-box`);
                            div.innerHTML = `<img class="` + imgClass + `" src="` + dataURL + `"/>
                                            <div class="delete"></div>`;
                        list.insertBefore( div , btn );
                        btnHidden();  //顯示或隱藏新增按鈕
                    }
            }
            
            //刪除
            mui(`#list`).on(`tap`,`.delete`,function(){
                this.parentNode.remove();
                btnHidden();  //顯示或隱藏新增按鈕
            })
            
            // 在5+文件中關於多圖選擇引數中 maximum 的解釋是
            // 取值範圍為1到Infinity,預設值為Infinity,即不限制選擇的圖片數。 如果設定的值非法則使用預設值Infinity。
            // 我們在點選是會使用 -= 來出來 pNum ,會得到負值而導致使用預設值
            // 故在每次新增圖片時進行判斷,是否隱藏新增按鈕
            function btnHidden(){
                if ( list.querySelector(`.photo-box`) ) {
                    var box = list.getElementsByClassName(`photo-box`);
                    if( box.length > setNum - 1 ){
                        btn.classList.add(`mui-hidden`);
                    } else {
                        btn.classList.remove(`mui-hidden`);
                    }
                } else {
                    btn.classList.remove(`mui-hidden`);
                }
            }
        </script>
    </body>

</html>

相關文章