• File API


    ES5 推出了一系列的 API:

    • BLOB (二进制大对象)
    • File (文件接口,基于 BLOB,但是增加了文件相关的方法,比如路径,大小)
    • FileList (借助 <input type="file">,来获取硬盘文件的一个接口)
    • FileReader
    • URL

    1 Simple APIs

    // 第一步,获取 input
    var fileInput = document.getElementById("myfile");
    
    // 第二步,通过 input 获取 FileList
    var fileList = fileInput.files;
    
    // 第三步,通过 FileList 获取某个文件的对象
    var file = fileList[0];
    
    // 简单来说,获取 File 对象就是:
    file = document.getElementById('myfile').files[0];

    一个图片 <img src="" > 的 src 可以使下面三个之一:

    1. 文件在操作系统中的路径
    2. DataURL 数据,用 Base64 编码,将二进制文件进行加密的过程,然后就可以使用这字符串来表示二进制文件了
    3. ObjectURL,它是我们需要使用的文件的一个引用字符串而已,格式为 blob:http://localhsot:8080/a3b05b0e-bd18-4b53-b6b8-0b345e9aebdb

    2 Preview Demo

    使用 ObjectURL:

    myfile.onchange = function () {
        var imgUrl = URL.createObjectURL(myfile.files[0]);
        myimg.src = imgUrl;
        myimg.onload = () => URL.revokeObjectURL(imgUrl);
    };

    3 Compress and Upload with AJAX

    function shangchuantupian() {
        // 1. 获取图片的数据
        // 2. 校验大小,如果超过尺寸,那么对其进行压缩
        // 3. 加上你的水印
        // 4. 调用 ajax 方式,将其发送到服务器
    
        var canvas = document.createElement("canvas");
    
        var image = new Image();
        var imgUrl = URL.createObjectURL(myfile.files[0]);
        image.src = imgUrl;
    
        image.onload = () => {
            URL.revokeObjectURL(imgUrl);
    
            canvas.width = image.width / 2;
            canvas.height = image.height / 2;
    
            var ctx = canvas.getContext('2d');
            ctx.drawImage(image, 0, 0, image.width / 2, image.height / 2);
            ctx.fillText("nf147", image.width / 2 - 20, image.height / 2 - 20);
    
            canvas.toBlob(function (b) {
                var fd = new FormData();
                fd.append("fff", b);
    
                fetch("/myupload", {
                    method: 'post',
                    body: fd
                }).then(resp => resp.body);
            }, "image/jpeg");
        };
    }

    4 Compress and Upload [version 2]

    HTML:

    <style>
     #myimg {
         border: 3px solid gray;
         border-radius: 5px;
         position: absolute;
         top: 0;
         left: 0;
     }
    
     #mymask {
         position: absolute;
         top: 0;
         left: 0;
     }
    </style>
    
    
    
    <div class="container">
        <div style="margin-top: 2em;">
            <input type="file" id="myfile" style="display: none"> <!-- 选择文件后,要预览 -->
            <button class="btn btn-primary" onclick="myfile.click()">选择图片</button>
            <button class="btn btn-primary" onclick="clickMe()">上传图片</button>
        </div>
    
        <div style="position: relative">
            <img src="" id="myimg" title="暂时没有上传" width="200" height="200"/>
            <canvas id="mymask" width="200" height="200">不支持canvas</canvas>
        </div>
    </div>

    JS:

    var ctx;
    
    myfile.onchange = () => { // 预览图片
        var imgUrl = URL.createObjectURL(event.target.files[0]);
        myimg.src = imgUrl;
        myimg.onload = () => URL.revokeObjectURL(imgUrl);
    };
    
    function clickMe() {
        compressImgWithCanvas(myfile.files[0], uploadWithAJAX);
        // uploadWithAJAX(myfile.files[0]);
    
    }
    
    /**
     * 压缩图片,然后执行某些任务
     */
    function compressImgWithCanvas(blob, taskCallback) {
        console.log("bbb");
        var rat = 2;
        var w = myimg.naturalWidth / rat, h = myimg.naturalHeight / rat;
    
        var canvas = document.createElement("canvas");
        canvas.width = w;
        canvas.height = h;
    
        var ctx = canvas.getContext('2d');
        ctx.drawImage(myimg, 0, 0, w, h);
        ctx.fillText("nf147", w - 20, h - 20);
    
        canvas.toBlob(taskCallback, "image/jpeg");
    }
    
    /**
     * 更新预览进度
     */
    function refreshProgress(r) {
        if (!ctx) ctx = mymask.getContext('2d');
        ctx.save();
        ctx.clearRect(0, 0, 200, 200);
        ctx.globalAlpha = 0.6;
        ctx.fillRect(0, (1 - r) * 200, 200, 200);
        ctx.globalAlpha = 1;
        ctx.fillStyle = "white";
        ctx.font = "20px 微软雅黑";
        ctx.fillText(r * 100 + '%', 80, 180);
        ctx.restore();
    }
    
    /**
     * 通过 AJAX 上传 blob 类型的文件
     * @param blob
     */
    function uploadWithAJAX(blob) {
        var fd = new FormData();
        fd.append("fff", blob);
    
        $.ajax({
            method: 'post',
            url: "/myupload",
            cache: false,
            contentType: false,
            data: fd,
            processData: false,
            xhr: () => {
                var xhr = $.ajaxSettings.xhr();
                xhr.upload.onprogress = (ev) => {
                    refreshProgress(ev.loaded / ev.total);
                };
                return xhr;
            }
        }).done(console.log)
            .fail((xhr, staus, err) => console.error(xhr, staus, err));
    }
  • 相关阅读:
    Redis
    双向绑定篇
    Vue篇1
    css篇-页面布局-三栏布局
    css篇-简化版
    Promise篇
    几道JS代码手写面试题
    安全篇
    Vue篇
    跨域篇--JSONP原理
  • 原文地址:https://www.cnblogs.com/guapishuo/p/10098834.html
Copyright © 2020-2023  润新知