关于这些年做的 图片上传下载做的处理总结(including根据图片url上传文件)

2 篇文章 0 订阅
2 篇文章 0 订阅

下载文档

我们查柜的认知是后端给前端传一个链接地址,将地址放在a标签上,点击链接下载文件。
可有时候往往不是这样的,后端给前端返回了一个文档流,这就需要我们自己转换为Blob格式的数据,再使用这个数据转化成一个url地址,模拟一个a标签,将地址放进去。

	//创建一个blob是excel格式的
 		let blob = new Blob([res.data], {
          type: 'application/vnd.ms-excel'
        });
        let contentDisposition = res.headers['content-disposition'];
        //国际化默认名称
        let fileName = langUtil.t(
                  defineMessages({
                    v: { id: 'dynamicForm.export.excelName', defaultMessage: '表格数据' }
                  })
                )+"_"+moment(new Date()).format("YYYY-MM-DD");
               
        //根据后端返回res.headers['content-disposition'];格式,取文件名
        if (contentDisposition) {
          fileName = window.decodeURI(
            (contentDisposition.split(';')[1] || '').split('=')[1],
            'UTF-8'
          );
        }
        //createObjectURL创建一个地址
        let downloadUrl = URL.createObjectURL(blob);
        //创建a标签,赋值地址
        let downloadLink = document.createElement('a');
        downloadLink.style.display = 'none';
        downloadLink.href = downloadUrl;
        //设置下载的属性
        downloadLink.setAttribute('download', fileName);
        document.body.appendChild(downloadLink);
        //模拟点击
        downloadLink.click();

如何在只有图片url的情况下,上传文件

下面是前两年有个需求,当时写了下相关说明文档
https://shimo.im/docs/wRrcpkTJkqcqpqX6/ 《记图片地址转文件并上传的一次操作》,可复制链接后用石墨文档 App 或小程序打开

简单概括一下我们的需求:我们要在点击图片之后,调用另一个接口,把该张图片文件上传上去。
点击这张图片,我们只能拿到一个url

//这是我们能拿到的图片地址
var img =
  "http://dumbo-daily.oss-cn-shanghai.aliyuncs.com/images/80146/29968540-2d52-11ea-9da8-9d82bfa55a03.png?OSSAccessKeyId=LTAI4FuYJmVdizPfGGW3TjnH&Expires=15779641503600&Signature=E0oIN1zu0%2Ff%2B%2BsA1p2G2jvrjRiI%3D"; 

//我们创建一个图片,将图片地址赋给图片
var image = new Image();
image.src = img;
image.setAttribute("crossOrigin", "Anonymous");
image.onload = function() {
//等到图片加载完成之后,将图片转成base64
  var base64 = getBase64Image(image);
  console.log(base64);

  //将base64转换成file
  var file = btof(base64, "test");
  //拿到file,用file上传文件
  };

//下面是分别使用的两个方法

//将图片转换成base64
function getBase64Image(img) {
 //先将图片转换成canvas,并绘制canvas
  var canvas = document.createElement("canvas");
  canvas.width = img.width;
  canvas.height = img.height;
  var ctx = canvas.getContext("2d");
  ctx.drawImage(img, 0, 0, img.width, img.height);
  var ext = img.src.substring(img.src.lastIndexOf(".") + 1).toLowerCase();
  //使用canvas的toDataUrl,将canvas转换成base64数据
  var dataURL = canvas.toDataURL("image/" + ext);
  return dataURL;
}

//转换成file
function btof(data, fileName) {
  const dataArr = data.split(",");
  //处理base64 数据
  //因为图片的base64大概是这样的  :base64,R0lGODlhHAAmAKIHAKqqqsvLy0hISObm5vf394uLiwAAAP///yH5B…EoqQqJKAIBaQOVKHAXr3t7txgBjboSvB8EpLoFZywOAo3LFE5lYs/QW9LT1TRk1V7S2xYJADs=
  //所以要将数据截取一下
  const byteString = atob(dataArr[1]);
  const options = {
    type: "image/jpeg",
    endings: "native"
  };
 // 创建一个8位无符号整型数组,将byteString的每个字节转换成unicode变化后,放进这个整型数组
  const u8Arr = new Uint8Array(byteString.length);
  for (let i = 0; i < byteString.length; i++) {
    u8Arr[i] = byteString.charCodeAt(i);
  }
 //然后就可以根据数组创建文件了
  return new File([u8Arr], fileName + ".jpg", options);
}

关于btoa和atob
btoa从String 对象中创建一个 base-64 编码的 ASCII 字符串,其中字符串中的每个字符都被视为一个二进制数据字节
atob 将base64解码,还原成编码前的数据
其实这两个方法特别好记,拆开看就是 b to a ,以及 a to b
const encodedData = btoa(‘Hello, world’); // encode a string
const decodedData = atob(encodedData); // decode the string
在这里插入图片描述

Uint8Array 数组类型表示一个8位无符号整型数组,创建时内容被初始化为0。创建完后,可以以对象的方式或使用数组下标索引的方式引用数组中的元素。
new Uint8Array(); // ES2017 最新语法
new Uint8Array(length); // 创建初始化为0的,包含length个元素的无符号整型数组
new Uint8Array(typedArray);
new Uint8Array(object);
new Uint8Array(buffer [, byteOffset [, length]]);

str.charCodeAt(index) 是将这个字符串的某一位,转化成Unicode 16位整数
而charAt([index])是直接返回该字符串index处的字符

关于unicode,看看他人的文章 https://blog.csdn.net/hezh1994/article/details/78899683

方法二
getBase64(imgUrl,_this) {
    window.URL = window.URL || window.webkitURL;
    const xhr = new XMLHttpRequest();
    xhr.open("get", imgUrl, true);
    // 至关重要
    xhr.responseType = "blob";
    xhr.onload =function() {
        if (this.status == 200) {
            // 得到一个blob对象
            const blob1 = this.response;
           // const file = new File([blob], 'test.png', {type: 'image/png'});
            //  至关重要
            const oFileReader = new FileReader();
            oFileReader.onloadend = (e)=> {
                const base64 = e.target.result;
               //拿到base64
                console.log(blob,file)
             
            };
            oFileReader.readAsDataURL(blob1);
             //====为了在页面显示图片,可以删除==== 
            var img = document.createElement("img"); 
             img.onload = function (e) {   
             window.URL.revokeObjectURL(img.src); // 清除释放 };
              // 创建DOMString
             let src = window.URL.createObjectURL(blob); 
             img.src = src 
             document.getElementById("container1").appendChild(img);   
             //====为了在页面显示图片,可以删除====


        }
    }
    xhr.send();
}

粘贴上传

主要原理是监听粘贴parse事件

document.addEventListener('paste', function (event) {
    var items = event.clipboardData && event.clipboardData.items;
    var file = null;
    if (items && items.length) {
        // 检索剪切板items
        for (var i = 0; i < items.length; i++) {
            if (items[i].type.indexOf('image') !== -1) {
                file = items[i].getAsFile();
                break;
            }
        }
    }
    // 此时file就是剪切板中的图片文件
});

预览上传的图片

var reader = new FileReader()
reader.onload = function(event) {
    // event.target.result就是图片的Base64地址啦
}
reader.readAsDataURL(file);

上面代码中的event.target.result就是图片的Base64地址,然后页面对应DOM元素位置插入如下HTML就可以看到图片效果了:

< img src="’ + event.target.result + '"/>

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值