h5下载图片

原理:
通过 Canvas 处理图片,绘制后转成自己需要的格式进行下载

//创建Image和canvas
downloadImgH5(){
	if (!process.env.VUE_APP_PLATFORM === 'h5') return 
	let imageUrl = '/img/xxx.png'
	if (imgUrl.startsWith('/') || imgUrl.startsWith('./')) {
        imgUrl = window.location.origin + imgUrl // 本地图片转换为完整URL
    }
	// 创建Image对象处理图片
    const img = new Image()
    img.src = imageUrl // 赋值
    img.crossOrigin = "anonymous" // 处理跨域

    img.onload = () => {
        try {
          // 创建Canvas
          const canvas = document.createElement("canvas")
          const ctx = canvas.getContext("2d")
          canvas.width = img.width
          canvas.height = img.height
          ctx.drawImage(img, 0, 0, canvas.width, canvas.height)
          // 将Canvas转换为Blob
          canvas.toBlob((blob) => {
            if (!blob)  return  console.error("图片处理失败:", error)
            this.downloadFile(blob,imageUrl)
          }, "image/png")
        } catch (error) {
          console.error("保存图片失败:", error)
        }
    }

	img.onerror = (error) => {
		console.error("图片加载失败:", error)
	}
},
//下载方法
downloadFile(blob,imageUrl){
      // 创建下载链接
      const url = URL.createObjectURL(blob)
      const a = document.createElement("a")
      // 提取文件名
      let fileName = "save_image"
      const match = imageUrl.match(/[^/]+(?=\.)/)
      if (match && match[0]) {
        fileName = match[0]
      }
      a.download = `${fileName}.png`
      a.href = url
      // 模拟点击下载
      document.body.appendChild(a)
      a.click()
      // 清理
      document.body.removeChild(a)
      URL.revokeObjectURL(url)
}

以上canvas除了可以将图片转成blob流,还可以将图片转成base64进行下载

//Canvas转DataURL并下载
downloadImgH5(){
	...
	img.onload = () => {
        try {
          // 创建Canvas
          const canvas = document.createElement("canvas")
          ...
          // 将Canvas转换为Blob
          const dataURL = canvas.toDataURL('image/png')
          // 创建下载链接
		  const link = document.createElement('a')
		  link.download = filename
		  ...
        } catch (error) {
          console.error("保存图片失败:", error)
        }
    }

}
  const dataURL = canvas.toDataURL('image/png')

总合两种下载方式:
1.转DataURL并下载
2.转Blob并下载

// Canvas转DataURL并下载
function downloadCanvasAsDataURL(canvas, filename = 'canvas-image.png') {
  // 获取Base64格式的数据URL
  const dataURL = canvas.toDataURL('image/png');
  const link = document.createElement('a');
  link.download = filename;
  link.href = dataURL;
  document.body.appendChild(link);
  link.click();
  document.body.removeChild(link);
}

// Canvas转Blob并下载
function downloadCanvasAsBlob(canvas, filename = 'canvas-image.png') {
  canvas.toBlob(blob => {
    if (!blob) return;
    const url = URL.createObjectURL(blob);
    const link = document.createElement('a');
    link.download = filename;
    link.href = url;
    document.body.appendChild(link);
    link.click();
    document.body.removeChild(link);
    URL.revokeObjectURL(url); // 释放URL对象
  }, 'image/png');
}

总结:
小型图像或简单场景,使用toDataURL()更简洁,base64比原始图像大 33% 左右;
大型图像或对性能有要求的场景,推荐使用toBlob(),blob与原始图像大小相近,且内存占比更低;

若是公众号内下载,a标签下载方式会被微信浏览器默认阻止,可以引导用户去浏览器下载,或者引导用户长按图片进行保存;
也可以对接微信 JS-SDK 调用微信下载图片接口

//初始化微信sdk
const wxConfig = {
	debug: false, // 生产环境关闭debug
	appId: 'wxXXXXXXXXXXXXXXX', // 你的公众号appId
	timestamp: new Date().getTime(), // 时间戳
	nonceStr: 'xxxxxxxxxxxxxx', // 随机字符串
	signature: 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx', // 签名
	jsApiList: ['downloadImage', 'getLocalImgData'] // 需要使用的JS接口列表
}
// 配置微信JS-SDK
window.wx.config(wxConfig)
window.wx.ready(() => {
	console.log('查看微信JS-SDK是否初始化成功')
})

let imageUrl = '/img/xxx.png'
// 调用微信下载图片接口
window.wx.downloadImage({
	serverId: imgUrl, // 图片的URL
	isShowProgressTips: 1, // 显示进度提示
	success: (res) => {
		console.log('图片下载成功', res);
		// 保存到相册
		window.wx.getLocalImgData({
            localId: res.localId, // 图片的localId
            success: (result) => {
              console.log('图片已保存到相册')
            },
            fail: (err) => {
              console.error('保存图片失败:', err);
              //保存失败,请长按图片手动保存
            }
		})
	},
	fail: (err) => {
		console.error('下载图片失败', err);
	}
})
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值