uniapp生成自定义(分享)图片并保存到相册

news2024/11/26 22:30:31

需求描述

在这里插入图片描述
在一个页面中底部有个保存图片的功能,点击能够保存一张生成的自定义表格图片。
第一眼见到这个需求 自己会出现了两个问题

  1. 如何去处理图片中的自定义内容以及样式
  2. 如何将自定义内容转化成图片
    至于保存图片,uniapp有对应的api去实现uni.saveImageToPhotosAlbum,不做赘述

实现效果展示

请添加图片描述
下面就是生成的图片在这里插入图片描述

实现步骤

大致划分成以下几个步骤
1、需要在目标页面画出图片内容的html代码,并置于于屏幕可视区域外形成隐藏的效果(不是display:none隐藏元素)
2、需要将html转成canvas的形式,再通过toDataURL方法转成base64图片形式
3、将base64转换成临时图片路径,即可展示出,并下载

已知需要用到两个插件来帮助实现
一个是html转canvas的插件 html2canvas可通过npm下载

npm install html2canvas -D

一个是将base64图片格式转本地地址的Dcloud插件image-tools

1、画需要生成图片的元素

即就是生成图片的样式 还是需要我们自己来搞出来。可以封装成一个组件形式,这里就不贴代码,因为这不是核心逻辑,况且大家需要生成图片的样式都不一样,唯一需要注意的是,这块元素是要脱离文档流,并置于屏幕外,不让用户看到

将生成图片的代码封装成一个组件,如下 需要声明一个id 为后续转canvas做准备

<KitcalculatorTable id="pagePoster"/>

并将这块区域通过固定定位置于可视区外,这样就看不到了,不能用v-if或者v-show、display:none去隐藏,这样在后续html转canvas是失败的,无法获取到该区域元素

position: fixed;
top: -999999rpx;
background-color: #fff;
padding: 30rpx;

2将html转成canvas的形式,再转成base64图片形式

<template>
	<view class="html2Canvas" id="pagePoster">
      <view class="table">
        <view class="kitCalculatorName">{{ pageData.kitCalculatorName }}</view>
        <KitcalculatorTable :tableData="tableData" :isSumData="true" />
        <view class="average-data">
          <view style="margin-right: 50rpx">件套平均价格:{{ pageData.averagePriceOneDesc }}</view>
          <view v-if="visiblePrice2">平均价格2:{{ pageData.averagePriceTwoDesc }}</view>
        </view>
      </view>
      <view class="bottom-logo">
        <img class="code" :src="codeImage" />
        <view>
          <view class="">报盘计算器,长按识别二维码使用</view>
          <img class="logo" :src="logoImage" />
        </view>
      </view>
    </view>
	<view class="muji-button" style="margin: 0 24rpx" @click="canvasImage.generateImageSave">保存图片</view>
	<view class="muji-button" @click="canvasImage.generateImageShare">分享</view>
</template>
<script lang="renderjs" module="canvasImage">
import html2canvas from 'html2canvas'
export default {
	mounted() {},
  methods: {
		generateImageSave(){
			this.generateImage('save')
		},
		generateImageShare(){
			this.generateImage('share')
		},
    // 生成图片需要调用的方法
    generateImage(methodType) {
	  this.$ownerInstance.callMethod('openLoading', '正在生成图片~')
      setTimeout(() => {
        const dom = document.getElementById('pagePoster') // 需要生成图片内容的 dom 节点
        html2canvas(dom, {
          width: dom.clientWidth, //dom 原始宽度
          height: dom.clientHeight,
          scrollY: 0, // html2canvas默认绘制视图内的页面,需要把scrollY,scrollX设置为0
          scrollX: 0,
          useCORS: true, //支持跨域
          // scale: 2, // 设置生成图片的像素比例,默认是1,如果生成的图片模糊的话可以开启该配置项
        }).then((canvas) => {
          // 生成成功
          // html2canvas 生成成功的图片链接需要转成 base64位的url
			this.$ownerInstance.callMethod('receiveRenderData',canvas.toDataURL('image/png'))
        }).catch(err=>{
			this.$ownerInstance.callMethod('_errAlert',`【生成图片失败,请重试】${err}`)
        })
      }, 300)
    },
  }
}
</script>
<script>
import { pathToBase64,base64ToPath} from 'image-tools';
export default {
  props: {
    pageData: {
      type: Object,
      default: () => {
        return {};
      },
    },
  },
  data() {
    return {
      temUrl: '', //生成的临时路径图片
      codeImage: '', // 件套二维码图片
      logoImage: '', // logo图片
    };
  },

  created() {
    // 处理静态图片 转为base64
    this.actionImage();
  },

  methods: {
    // 处理已知静态图片 转base64格式
    actionImage() {
      this.turnBase64Image(require('@/static/logo/down-code.png'), 'codeImage');
      this.turnBase64Image(require('@/static/logo/muji-logo.png'), 'logoImage');
    },
    // 将图片转为base 64 位url
    turnBase64Image(img, key) {
      uni.getImageInfo({
        src: img,
        success: (image) => {
          pathToBase64(image.path)
            .then((base64) => {
              this[key] = base64;
            })
            .catch((error) => {
              console.log('转换失败:', error);
            });
        },
        fail: (err) => {
          console.log('将本地图片转为base 64报错:', err);
        },
      });
    },
    /* 将base64 位的图片路径转换为 临时路径 */
    loadBase64Url(imageStr) {
      const that = this;
      base64ToPath(imageStr)
        .then((path) => {
          this.temUrl = path;
			this.closeLoading()
			this.saveImg()
        })
        .catch((error) => {
          console.error('临时路径转换出错了:', error);
        });
    },
    // 获取生成的base64 图片路径
    receiveRenderData(val) {
      const url = val.replace(/[\r\n]/g, ''); // 去除base64位中的空格
      this.loadBase64Url(url);
    },
    // 报错alert
    _errAlert(content) {
      uni.showModal({
        title: '提示',
        content: content,
      });
    },
    saveImg() {
      uni.saveImageToPhotosAlbum({
		filePath: this.temUrl,
			success: function () {
				uni.showToast('保存图片成功');
			}
	});
    },
  },
};
</script>

需要注意的两点是,这里要新建一个script节点,将语言改成renderjs的形式 在这之内做html转canvas的操作
再就是需要把生成图片中的已知静态图片 如下载二维码、企业logo转换成base64的形式

保存图片

最后就是点击保存后,调用canvasImage下的generateImage去生成图片,拿到base64格式图片通过image-tools的base64ToPath方法去转成临时路径再下载就ok了

题外话

这里涉及到renderjs的通讯知识,还是有点坑的
比如在renderjs模块调用script的方法是可以直接

this.$ownerInstance.callMethod('script内方法名',需要带的参数)

目前只了解可以在dom去调用renderjs方法,在script内貌似不能直接用。大家就要根据需求去灵活使用这个东西

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1213336.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

顶象获“直通乌镇”全球互联网大赛二等奖

11月10日&#xff0c;2023“直通乌镇”全球互联网大赛在浙江乌镇圆满落幕。本次大赛由世界互联网大会、浙江省人民政府主办&#xff0c;旨在探索互联网发展的新技术、新模式、新业态&#xff0c;推动全球互联网合作创新&#xff0c;激发互联网创业活力。 在当天的颁奖典礼上&a…

栈:括号匹配问题!

目录 题目&#xff1a; 思路分析&#xff1a; 解题思路&#xff1a; 一、配对&#xff1a; 二、数量问题&#xff1a; 三、细节问题&#xff1a; 完整代码&#xff1a; 手撕栈&#xff1a; 题目&#xff1a; 给定一个只包括 (&#xff0c;)&#xff0c;{&#xff0c;}&…

微签:电子签章实力派,这19年从幕后走向台前

微签是什么&#xff1f;尽管在电子签章领域已深耕19年 &#xff0c;是国内电子签名市场的拓荒者之一&#xff0c;但因为其低调的风格&#xff0c;一直不为众人所知。不过&#xff0c;如果现在你想对目前市面上的电子签名厂商做一个专业客观的盘点的话&#xff0c;不管从哪个角度…

【论文精读2】R-MVSNet

R-MVSNet【递归多视图立体网络】&#xff0c;论文全名&#xff1a;“Recurrent MVSNet for High-resolution Multi-view Stereo Depth Inference”&#xff0c;CVPR 2019(CCF A) 在MVSNet的基础上做了一些改进&#xff0c;主要解决的问题是代价体正则化&#xff08;Cost Volume…

大语言模型概述|亚马逊这些互联网公司为什么花巨资训练自己的模型?

2023年可谓是大语言模型元年&#xff0c;OpenAI、亚马逊、谷歌等互联网公司争先恐后推出了自己的大语言模型&#xff1a;GPT-4、Titan、PaLM 2&#xff0c;还有亚马逊即将推出的第二个大语言模型Olympus等等。这一革命性技术如今已经在全球范围内引发了广泛的讨论和关注&#x…

用于部署汽车AI项目的全面自动化数据流程

如何创建、优化和扩展汽车 AI 的数据流程 想到汽车行业的人工智能 (AI) 时&#xff0c;脑海中可能会立即浮现未来的道路上遍布自动驾驶汽车的情景。虽然这一切尚未实现&#xff0c;但汽车行业已在 AI 方面取得诸多进步&#xff0c;不仅安全性提高&#xff0c;车内体验也得到改…

餐饮展示小程序的作用是什么

餐饮是市场重要的组成部分&#xff0c;尤其是我国八大菜系&#xff0c;各类细分菜数量非常多&#xff0c;并分布在全国&#xff0c;各类大小品牌餐饮商家数量也非常庞大&#xff0c;每个城市的商业街都是一个接一个餐厅&#xff0c;酒类、酒店多样。 餐饮行业经营痛点比较明显…

C++入门,详解类和对象(1)

类和对象 一&#xff0c;前言二&#xff0c;类的介绍2.1类的引入2.2类的定义 三&#xff0c;类访问限定符及其分装3.1访问限定符说明 四&#xff0c;类的作用域五&#xff0c;类的实例化六&#xff0c;类对象模型6.1类的存储方式6.2类的大小计算 七&#xff0c;this指针7.1this…

Java_static 继承

static static修饰成员变量 static修饰成员变量的应用场景 static修饰成员方法 static修饰成员方法的应用场景 static的注意事项 static的应用知识:代码块 static的应用知识:单例设计模式 饿汉式单例模式 懒汉式单例模式 面向对象三大特征之二:继承 什么是继承 继承的好处 继…

永磁材料测试系统主要应用

1. 产品特征 永磁材料测试系统装置具有独立的电参量校准功能。采用慢速减幅方式对样品退磁。超宽范围的电流连续稳定调节。磁通计的积分器零漂和霍尔探头的非线性误差影响小。系统配置连续可调双极性磁化电源&#xff0c;方便样品的磁化与退磁。测量B或J&#xff1a;采用B或J线…

【开源】基于JAVA的生活废品回收系统

目录 一、摘要1.1 项目介绍1.2 项目录屏 二、研究内容三、界面展示3.1 登录注册3.2 资源类型&资源品类模块3.3 回收机构模块3.4 资源求购/出售/交易单模块3.5 客服咨询模块 四、免责说明 一、摘要 1.1 项目介绍 生活废品回收系统是可持续发展的解决方案&#xff0c;旨在鼓…

使用 MATLAB HDL Coder 和 FPGA 快速实现自动白平衡(AWB)

使用 MATLAB HDL Coder 和 FPGA 快速实现自动白平衡&#xff08;AWB&#xff09; 在此项目中&#xff0c;我们将使用 MATLAB Simulink 和 HDL 编码器创建自定义 IP -- AWB。 MATLAB 设计 自动白平衡模块的设计是使用 HDL Coder 在 MATLAB 和 Simulink 中创建的。HDL Coder能够生…

Vim + YCM + clangd

目录 1. Vim的安装 1.1 Vim安装vim-plug2. 安装YCM3. 进行语言补全配置 3.1 测试效果 1. 目的&#xff1a;让 Vim 像 C/C IDE 一样具备自动补全代码等功能 2. YCM&#xff1a;YouCompleteMe GitHub - ycm-core/YouCompleteMe: A code-completion engine for Vi…

[数据结构]—带头双向循环链表——超详解

&#x1f493;作者简介&#x1f389;&#xff1a;在校大二迷茫大学生 &#x1f496;个人主页&#x1f389;&#xff1a;小李很执着 &#x1f497;系列专栏&#x1f389;&#xff1a;数据结构 每日分享✨&#xff1a;旅行是为了迷路&#xff0c;迷路是为了遇上美好❣️❣️❣️ …

2年博士后|心外医生赴美国耶鲁大学开展研究

G医生决定放弃申报CSC&#xff0c;改为自费出国&#xff0c;并在美国密歇根大学安娜堡分校和耶鲁大学两所名校中选择了更为出名的后者。因为不是CSC出资&#xff0c;G医生得以通过签证&#xff0c;顺利出国&#xff0c;实现了在世界知名高校从事2年博士后的个人职业规划目标。 …

11月15日星期三今日早报简报微语报早读

1、2023胡润女企业家榜出炉&#xff1a;郭得胜夫人邝肖卿首次成为中国女首富&#xff0c;龙湖吴亚军蝉联中国白手起家女首富&#xff1b; 2、叶剑英元帅夫人吴博逝世&#xff0c;享年106岁&#xff1b; 3、外交部&#xff1a;所谓“联合国军”是冷战产物&#xff0c;于法无据…

低代码JNPF,发挥软件定制的威力

目录 1.介绍 2.可视化逻辑编排工具 提供自动化的解决方案 3.功能特色展示 4.结语 近几年&#xff0c;随着低代码与无代码相关话题的火热&#xff0c;逻辑编排作为其重要构成部分也备受关注&#xff0c;集团内外不乏优秀的实践。之前在做技术调研时发现了不少业内逻辑编排相关的…

智能导诊的开发技术有哪些?

智能导诊源码 智能导诊是医疗领域中一项重要的应用&#xff0c;它可以帮助医生和患者更快速、更准确地诊断疾病&#xff0c;提高医疗效率和精度。以下是智能导诊开发技术的几个方面: 1.数据收集整合 智能导诊系统需要收集大量的医疗数据&#xff0c;包括患者症状、病史、检查结…

jenkins+centos7上传发布net6+gitlab

工作中实践了一下jenkins的操作&#xff0c;所以记录一下这次经验 首先安装好jenkins并注册自己的jenkins账号 因为我们的项目代码管理使用的是gitlab&#xff0c;在开始之前先在jenkins上安装gitlab的插件&#xff0c;安装之后应该是要重启jenkins的服务&#xff0c;后续jen…

python+django+mysql个人博客项目部署(VMware部署)

目录 一、Vmware新建win7虚拟机 二、组件/软件安装 2.1 安装python3 2.2 更新pip 2.3 安装pycharm 2.4 安装django 2.5 win安装mysql 三、配置数据库 3.1 安装sqlite客户端 3.2 db.sqlite3导出为myblog.sql 3.3 Heidisql连接本地sql 四、部署项目 4.1 安装模块 4.2 尝试运行 …