前端实现根据模版导出word【docxtemplater】

场景

有的时候我们需要根据后端提供的数据,然后结合word模版来生成word。我们可以使用第三方库docxtemplater

效果

代码

App.vue

<template><div class="app"><el-divider content-position="center">1.基本使用</el-divider><el-button type="primary" @click="exportWord_1">导出word</el-button><el-divider content-position="center">2.带有表格的导出</el-divider><el-button type="primary" @click="exportWord_2">导出word</el-button><el-divider content-position="center">3.带有图片的导出</el-divider><el-button type="primary" @click="exportWord_3">导出word</el-button></div>
</template><script>
import Docxtemplater from 'docxtemplater'
import PizZip from 'pizzip'
import PizZipUtils from 'pizzip/utils/index.js'
import { saveAs } from 'file-saver'
// import ImageModule from 'docxtemplater-image-module/build/imagemodule'
import ImageModule from 'docxtemplater-image-module-free'import logo from '@/assets/1.png'export default {data() {return {}},methods: {exportWord_1() {PizZipUtils.getBinaryContent('/word/template.docx', (err, content) => {if (err) {throw err}const zip = new PizZip(content)const doc = new Docxtemplater(zip, {paragraphLoop: true,linebreaks: true,})doc.render({title: '邮件标题',name: 'Coder',content: '这是一封测试邮件',signer: 'Me',sign_time: '2024/07/02',})const out = doc.getZip().generate({type: 'blob',mimeType:'application/vnd.openxmlformats-officedocument.wordprocessingml.document',})saveAs(out, 'Test.docx')})},exportWord_2() {PizZipUtils.getBinaryContent('/word/template.docx', (err, content) => {if (err) {throw err}const zip = new PizZip(content)const doc = new Docxtemplater(zip, {paragraphLoop: true,linebreaks: true,})doc.render({title: '邮件标题',name: 'Coder',content: '这是一封测试邮件',signer: 'Me',sign_time: '2024/07/02',movie_list: [{name: '盗梦空间',price: 56,release_date: '2013-06-03',},{name: '斗破苍穹',price: 46,release_date: '2024-01-03',},{name: '疯狂的麦克斯*狂暴女神',price: 76,release_date: '2024-07-02',},],})const out = doc.getZip().generate({type: 'blob',mimeType:'application/vnd.openxmlformats-officedocument.wordprocessingml.document',})saveAs(out, 'Test.docx')})},exportWord_3() {// 官方示例,尝试不成功/*const imageOptions = {getImage(url) {return new Promise(function (resolve, reject) {PizZipUtils.getBinaryContent(url, function (error, content) {if (error) {return reject(error)}return resolve(content)})})},getSize(img, url, tagName) {return new Promise(function (resolve, reject) {const image = new Image()image.src = urlimage.onload = function () {resolve([image.width, image.height])}image.onerror = function (e) {console.log('img, url, tagName : ', img, url, tagName)alert('An error occured while loading ' + url)reject(e)}})},}PizZipUtils.getBinaryContent('/word/template.docx', (err, content) => {if (err) {throw err}const zip = new PizZip(content)const doc = new Docxtemplater(zip, {paragraphLoop: true,linebreaks: true,modules: [new ImageModule(imageOptions)],})doc.renderAsync({logo: logo,title: '邮件标题',name: 'Coder',content: '这是一封测试邮件',signer: 'Me',sign_time: '2024/07/02',movie_list: [{name: '盗梦空间',price: 56,release_date: '2013-06-03',},{name: '斗破苍穹',price: 46,release_date: '2024-01-03',},{name: '疯狂的麦克斯*狂暴女神',price: 76,release_date: '2024-07-02',},],}).then(function () {const out = doc.getZip().generate({type: 'blob',mimeType:'application/vnd.openxmlformats-officedocument.wordprocessingml.document',})saveAs(out, 'Test.docx')})})*/PizZipUtils.getBinaryContent('/word/template.docx', (err, content) => {if (err) {throw err}var opts = {}opts.centered = falseopts.getImage = function (tagValue, tagName) {return new Promise(function (resolve, reject) {PizZipUtils.getBinaryContent(tagValue, function (error, content) {if (error) {return reject(error)}return resolve(content)})})}opts.getSize = function (img, tagValue, tagName) {// FOR FIXED SIZE IMAGE :return [150, 150]// FOR IMAGE COMING FROM A URL (IF TAGVALUE IS AN ADRESS) :// To use this feature, you have to be using docxtemplater async// (if you are calling setData(), you are not using async).return new Promise(function (resolve, reject) {var image = new Image()image.src = urlimage.onload = function () {resolve([image.width, image.height])}image.onerror = function (e) {console.log('img, tagValue, tagName : ', img, tagValue, tagName)alert('An error occured while loading ' + tagValue)reject(e)}})}var imageModule = new ImageModule(opts)const zip = new PizZip(content)const doc = new Docxtemplater().loadZip(zip).attachModule(imageModule).compile()doc.resolveData({logo: logo,title: '邮件标题',name: 'Coder',content: '这是一封测试邮件',signer: 'Me',sign_time: '2024/07/02',movie_list: [{name: '盗梦空间',price: 56,release_date: '2013-06-03',},{name: '斗破苍穹',price: 46,release_date: '2024-01-03',},{name: '疯狂的麦克斯*狂暴女神',price: 76,release_date: '2024-07-02',},],}).then(function () {doc.render()var out = doc.getZip().generate({type: 'blob',mimeType:'application/vnd.openxmlformats-officedocument.wordprocessingml.document',})saveAs(out, 'test-image.docx')})})},},
}
</script><style lang="less" scoped>
.app {padding: 40px;
}
</style>

public/word/template.docx

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Mysql MVCC多版本解析

1.首先各行数据,都有一个trx_id(事务ID)和回滚指针,形成一个链表数据结构的数据。其实这便是undo.log(回滚日志) 2.当select查询数据的时候,还会生成视图数据。 其中包含未提交的最小事务、未提交事务ID数组、应该分配下一个的事务ID、创建视图的事务ID 首先会生成read …

Linux的访问权限详解

题目解读访问权限 rw-r--r--分别代表什么东西 r:代表可读 w:可写 e:可执行 方便起见进行拆分rw- 代表文件所属用户的权限 r-- 代表同组用户的权限 r-- 代表其他用户的权限同时我们可以用2进制来表示: r:4 w:2 e:1 也即是3位二进制数则可以表示 chmod 命令 更改对应的文件的权…

Linux统计日志中有多少个不同的IP登录

题目解析 知识点: 1、awk -F {print $3} 指定空格是分隔符进行分割,取第三个。(不指定默认分隔符也是空格) 2、uniq -c(uniq命令可以去除排序过的文件中的重复行,因此uniq经常和sort合用。也就是说,为了使uniq起作用,所有的重复行必须是相邻的。参数 - c :进行计…

WebAPI项目框架仓储模式+导入SqlSuag

仓储(Respository)是对数据库访问的一个封装 解决方案新建Respository文件夹,新建类库Web.Core.IRepository,Web.Core.Repository 解决方案新建Services文件夹,新建类库Web.Core.IServices,Web.Core.Services 在类库Web.Core.Model下面新建Entity文件夹SqlSugar是国人开发者…

操作系统内存管理学前补充知识

操作系统内存管理学前补充知识 目录操作系统内存管理学前补充知识什么是内存,有什么作用数据的数量单位指令的工作原理3种装入的方式(逻辑地址—>物理地址)绝对装入静态重定位动态重定位从写程序到程序的运行链接的三种方式 什么是内存,有什么作用 手机有内存,电脑中也…

Nginx proxy manager反向代理docker hub

1.域名解析 用作反向代理的域名要提前解析,如果使用外国的DNS域名提供商的话,最好提前一天解析好。 2.配置NPM 2.1.Details选项卡2.2.SSL选项卡2.3.Advanced选项卡 location / {# Docker hub 的官方镜像仓库proxy_pass https://registry-1.docker.io; proxy_set_header Host…

cJSON:构建JSON

使用cJSON库构建比较简单的JSON类型: create_json.c #include <stdio.h> #include <string.h> #include <stdlib.h>#include "cJSON.h"static int create_json_type_1(void) {char *json_str = NULL;cJSON *root = NULL;root = cJSON_CreateObjec…

【esp32 学习笔记】将lvgl融入esp-idf项目中

lvgl科普 lvgl 主要特点:Github库整体了解版本号编排原则屏幕兼容性LVGL 问题处理: lvgl 与 FreeRTOS 由于esp-idf本身带了 FreeRTOS系统,因此需要关注一下操作系统相关的内容:void lvgl_thread(void) {while(1) {uint32_t time_till_next;time_till_next = lv_timer_hand…

QT6 CMake项目配置 (Visual Studio)

QT6 CMake项目配置 (Visual Studio) 上一节已经编译好了动态和静态的QT库,接下来在CMake中引入。 这边主要介绍使用Visual Studio的配置方法 测试环境 首先使用VS创建一个项目来测试CMake能否正常使用。 如果是首次打开VS会有个配置主题的界面,自己选一下就好了 首先我们来创…

ssrf+结合redis 写入crontab或者公钥(两种环境)

REDIS redis作为一种数据库 其实是会真的将数据写入到内存中的 我们利用ssrf请求 请求redis 实现服务器对自己的公钥或任务计划写入 实现无密码登录 或反弹bashredis监听所有地址时 才能被外部访问 否则只能127.0.0.1 本地访问 而且开启保护模式后会导致目标端口只能本地访问 这…

ffmpeg常用命令汇总

最近在学习ffmpeg,将基础命令做一次汇总,便于自己以后查阅: 1. ffmpeg 常用命令 ffmpeg 帮助信息查看 // 查看 ffmpeg 的基础信息。 ffmpeg --help// 查看高级参数部分。 ffmpeg --help long// 查看全部的帮助信息。 ffmpeg --help full转封装 // -hide_banner: 隐去 ffmpeg …

麻烦问一下xpath标签定位的这个索引是做什么用的?

大家好,我是Python进阶者。 一、前言 前几天在Python最强王者交流群【杨又串🍻】问了一个Python网络爬虫的问题,问题如下:老师,麻烦问一下xpath标签定位的这个索引是做什么用的,我听网课把这个知识点跳过了? 二、实现过程 后来【隔壁😼山楂】给了一个指导:这个过去出…

李沐动手学深度学习V2-chap_preliminaries

李沐动手学深度学习V2 文章内容说明 本文主要是自己学习过程中的随手笔记,需要自取 课程参考B站:https://space.bilibili.com/1567748478?spm_id_from=333.788.0.0 课件等信息原视频简介中有CSV文件修改读取成张量tensor 数据预处理 首先(创建一个人工数据集,并存储在CSV(…

C语言打印倒三角形,底边长n作为参数输入,从键盘输入

打印倒三角形,底边长n作为参数输入,从键盘输入。#include <stdio.h> int main(int argc, char const *argv[]) {int i, j, k, l, n;printf("请输入底边长: \n");scanf("%d", &n);while (getchar() != \n);printf("输出图形如下:\n"…

WebAPI项目框架JWT权限验证

JWT是什么?校验逻辑?授权过程?这里就不过多的阐述了,直接上代码 在appsettings.json中配置jwt参数的值 SecretKey必须大于16个字符1 {2 "Logging": {3 "LogLevel": {4 "Default": "Information",5 "Micros…

2.SpringBoot快速上手

2.SpringBoot快速上手 SpringBoot介绍javaEE的开发经常会涉及到3个框架Spring ,SpringMVC,MyBatis.但是这三个框架配置极其繁琐,有大量的xml文件,spring Boot对之前的配置进行极大的简化Spring Boot 是由Pivotal团队提供的基于Spring的全新框架,简化Spring应用的初始搭建和…

RTMP协议

RTMP(Real-Time Messaging Protocol)是一个综合性的协议,不仅可以传输音视频数据,还可以传输信令控制指令。RTMP 使用 TCP 作为传输协议,可以直接在 TCP 连接上传输音视频数据,也可以传输控制指令,实现了音视频流的实时传输和控制。 与RTSP 不同,RTSP(Real-Time S…

yarn install 时显示 node_modules\esbuild: Command failed

可以找一找你的nodejs安装路径是不是中文的,如果是中文的换成英文应该就可以了(记得系统变量里也要改掉)

阿里云个人账号 创建docker仓库

1、创建阿里云账号 2、搜索“容器镜像服务”,进入,点击“管理控制台” 3、选择个人实例,这一步可能会让你创建registry密码(如果没有创建过的话),后面登录需要 4、创建命名空间5、创建镜像仓库 输入信息,点击下一步,选择本地仓库 6、进入管理页面 执行相关命令

Django3在网页上生成二维码

1.安装依赖包pip install django-qr-code2.在django,你项目的settings中,安装app 打开你项目的setting,找到INSTALLED_APPS ,在这里新加一条qr_code INSTALLED_APPS = [...,rest_framework,qr_code,... ] 3.在你打算渲染的html文档中,导入模板 {% load qr_code %}ps:如果…