文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

JS移动端/H5同时选择多张图片上传并使用canvas压缩图片的示例分析

2024-04-02 19:55

关注

小编给大家分享一下JS移动端/H5同时选择多张图片上传并使用canvas压缩图片的示例分析,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧!

HTML5定义了 FileReader 作为文件 API 的重要成员用于读取文件,根据 W3C 的定义,FileReader接口提供了读取文件的方法和包含读取结果的事件模型。

FileReader的实例拥有 4 个方法,其中 3 个用以读取文件,另一个用来中断读取。下面的表格列出了这些方法以及他们的参数和功能,需要注意的是 ,无论读取成功或失败,方法并不会返回读取结果,这一结果存储在 result 属性中。

方法名参数描述
abortnone中断读取
readAsBinaryStringfile将文件读取为二进制码
readAsDataURLfile将文件读取为 DataURL
readAsTextfile, [encoding]将文件读取为文本

readAsText:该方法有两个参数,其中第二个参数是文本的编码方式,默认值为 UTF-8。这个方法非常容易理解,将文件以文本方式读取,读取的结果即是这个文本文件中的内容。

readAsBinaryString:该方法将文件读取为二进制字符串,通常我们将它传送到后端,后端可以通过这段字符串存储文件。

readAsDataURL:这是例子程序中用到的方法,该方法将文件读取为一段以 data: 开头的字符串,这段字符串的实质就是 Data URL,Data URL是一种将小文件直接嵌入文档的方案。这里的小文件通常是指图像与 html 等格式的文件。

FileReader还包含了一套完整的事件模型,用于捕获读取文件时的状态,下面这个表格归纳了这些事件。

事件描述
onabort中断时触发
onerror出错时触发
onload文件读取成功完成时触发
onloadend读取完成触发,无论成功或失败
onloadstart读取开始时触发
onprogress读取中

文件一旦开始读取,无论成功或失败,实例的 result 属性都会被填充。如果读取失败,则 result 的值为 null ,否则即是读取的结果,绝大多数的程序都会在成功读取文件的时候,抓取这个值。

了解了H5提供的 FileReader 后,我们就使用 FileReader 来实现同事选择多张图片并上传。

首先,在 HTML 加入一个file表单,并设置其为 multiple(浏览器在对multiple、disabled、checked、selected等这类属性进行解析时,只要这些属性存在,默认的就会被解析成true,甭管你设置的是disabled=true或者disabled=false亦或是disabled="",如果不想这些属性起作用,唯有用js来remove掉这些属性,除非你不设置这些属性。),并设置accept="image/*"用以只能选择图片类型的文件,代码如下:

<input type="file" accept="image/*" name="upload" id="upload" multiple>
<input type="hidden" id="hiddenImgUrl" />  <!--设置这个隐藏域是为了便于存放上传至服务器后返回的图片地址-->

接下来就到了js上场了:

//图片上传
var file = {
  upload: function (e) {
    var self = this;
    var files = e.target.files;
    var type = files[0].type.split('/')[0];
    if (type != 'image') {
      alertMsg('请上传图片');
      return;
    }
    //var size = Math.floor(file.size / 1024 / 1024);
    //if (size > 3) {
    //  alert('图片大小不得超过3M');
    //  return;
    //};
    for (var i = 0; i < files.length; i++) {
      var reader = new FileReader();
      reader.readAsDataURL(files[i]);
      reader.onloadstart = function () {
        //用以在上传前加入一些事件或效果,如载入中...的动画效果
      };
      reader.onloadend = function (e) {
        var dataURL = this.result;
        var imaged = new Image();
        imaged.src = dataURL;
        imaged.onload = function () {  //利用canvas对图片进行压缩
          var canvas = document.createElement('canvas');
          var ctx = canvas.getContext('2d');
          var w = 0;
          var h = 0;
          if (this.width > this.height) {
            h = 1000;
            var scale = this.width / this.height;
            h = h > this.height ? this.height : h;
            w = h * scale;
          }
          else {
            w = 1000;
            var scale = this.width / this.height;
            w = w > this.width ? this.width : w
            h = w / scale;
          }
          var anw = document.createAttribute("width");
          var anh = document.createAttribute("height");
          if (this.width > this.height) {
            anw.value = h;
            anh.value = w;
          }
          else {
            anw.value = w;
            anh.value = h;
          }
          canvas.setAttributeNode(anw);
          canvas.setAttributeNode(anh);
          if (this.width > this.height) {
            ctx.translate(h, 0);
            ctx.rotate(90 * Math.PI / 180)
            ctx.drawImage(this, 0, 0, w, h);
            ctx.restore();
          }
          else {
            ctx.drawImage(this, 0, 0, w, h);
          }
          dataURL = canvas.toDataURL('image/jpeg');
          //回调函数用以向数据库提交数据
          self.callback(dataURL);
        };
      };
    }
  },
  event: function () {
    $("#upload").change(function (e) {      
      file.upload(e);
    });
  },
  callback: function (dataURL) {
    $.ajaxSettings.async = false;  //这里必须将ajax的异步改为同步才可以把返回并保存在隐藏域中的图片地址取出同时加在地址栏中作为参数一并传入下一个页面,这样做的目的是因为返回的图片地址不是一个json数组,而是单个的json字符串,所以只能将返回的图片地址json字符串拼接在一起作为参数传到下一个页面
    $.post(url, dataURL, function (res) {  //将base64图片流的图片通过后台转换成普通的图片路径并上传至服务器
      var imgUrl = $("#hiddenImgUrl").val();
      if (res.success) {
        $(".loading").hide();
        if (imgUrl != "") {
          $("#hiddenImgUrl").val(imgUrl + "|" + res.imgUrl);  //中间加一个 | 是为了到下一个页面便于将传过去的图片地址参数转换为数组
        } else {
          $("#hiddenImgUrl").val(res.imgUrl);
        }
        var imgUrl = $("#hiddenImgUrl").val();
        window.location.href = "apply.html?imgUrl=" + imgUrl;
      } else {
        alert(res.message);
      }
    }, "json");
  },
  init: function () {
    this.event();
  }
}
file.init();

由于在通过post向服务器上传时采用了同步的方式,所以我在写项目的过程中,老是无法实现加载中的动画效果,并且把加载中的动画效果放在 reader.onloadstart方法中依旧不起作用,最后只能放在了$("#upload").change(function (e) {})方法中,代码如下:

event: function () {
    $("#upload").change(function (e) {
      $(".loading").show();     
      file.upload(e);
    });
  }

以上是同时上传多张图片并将图片传入下一个页面继续进行后续操作,那么如何在同时上传完多张图片后在本页再预览这些图片呢?其实方法也是很简单的,上边callback函数里边的$.post的返回值里就包含了上传至服务器后的图片路径,将这些路径赋给img标签的src,然后再插入到页面中就OK了,代码如下:

callback: function (dataURL) {    
    $.post(url, dataURL, function (res) {  //将base64图片流的图片通过后台转换成普通的图片路径并上传至服务器
      if (res.success) {
        $(".loading").hide();
        var result = '<div class="result"><img src="'+res.imgUrl+'" alt=""/></div>';
        var div = document.createElement('div');
        div.innerHTML = result;
        document.body.appendChild(div);        
      } else {
        alert(res.message);
      }
    }, "json");
  }

以上是“JS移动端/H5同时选择多张图片上传并使用canvas压缩图片的示例分析”这篇文章的所有内容,感谢各位的阅读!相信大家都有了一定的了解,希望分享的内容对大家有所帮助,如果还想学习更多知识,欢迎关注编程网行业资讯频道!

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     807人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     351人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     314人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     433人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     221人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-前端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯