Vue3项目实现WPS文件预览和内容回填功能

技术方案背景:根据项目需要,要实现在线查看、在线编辑文档,并且进行内容的快速回填,根据这一项目背景,最终采用WPS的API来实现,接下来我们一起来实现项目功能。

1.首先需要先准备好测试使用的文档,并且做好标签节点的标记,在要需要回填的地地方打好标记标签

打开文档 => 点击菜单栏插入 => 找到要添加书签的地方,选择工具栏的书签按钮

输入对应的命名书签

表格书签是打标记在表格内容上方,便于查找表格位置方便替换;

2. 引入WPS Web Office SDK代码示例(vue项目举例,在根目录下的index.html文件中引入)

<script src="/wps-sdk/web-office-sdk-solution-v2.0.7.umd.js"></script>

注意事项

SDK路径需要根据实际存放位置调整,若使用CDN方式可替换为完整URL

当前示例使用的是v2.0.7版本的UMD格式SDK,适用于大多数浏览器环境

建议将脚本放在<head>标签内或<body>标签末尾,避免阻塞页面渲染

初始化示例

const config = {mount: document.getElementById('office-container'),url: 'https://example.com/test.docx'
};
WebOfficeSDK.initialize(config);

版本选择建议

生产环境建议锁定具体版本号(如示例中的v2.0.7)

测试环境可使用最新版本,但需注意API兼容性

UMD格式适用于传统网页开发,若使用模块化开发可考虑ES模块版本

以上代码需配合WPS官方文档使用,确保初始化参数配置正确(WPS官方文档:快速上手 | WPS WebOffice 开放平台)

3.使用HTML代码块编写的WPS文档在线查看容器代码:

 <!-- 创建wps文档在线查看容器 -->
<div id="wps-frame" class="w-full h-[calc(100%-60px)] bg-#eee custom-mount"></div>

代码说明

该代码创建了一个具有以下特性的div容器:

  • 使用id="wps-frame"作为唯一标识
  • 通过class属性应用了多个样式:
    • w-full:宽度100%
    • h-[calc(100%-60px)]:高度为总高度减去60px
    • bg-#eee:背景色设置为浅灰色
    • custom-mount:预留的自定义挂载类名

样式补充建议

如需更精确控制样式,可以添加CSS:

#wps-frame {border: 1px solid #ddd;margin: 0 auto;overflow: hidden;
}

4. 初始化WPS容器

const init = async () => {window.fileurlType = props.fileObj.fileurl.split('.').pop().toLowerCase();instance = WebOfficeSDK.init({//文档类型officeType: window.fileurlType === 'xlsx' || window.fileurlType === 'xls' ? WebOfficeSDK.OfficeType.Spreadsheet : window.fileurlType === 'docx' || window.fileurlType === 'doc' ? WebOfficeSDK.OfficeType.Writer : WebOfficeSDK.OfficeType.Otl,appId: "你申请的预览服务的appid",fileId: props.fileObj.fileid,token: token,mount: document.getElementById('wps-frame'),mode: props.submitType === true ? 'nomal' : 'simple',});//如果props.submitType为true,则设置为可以编辑 否则设置为只读if (props.submitType == false) {await instance.ready();const app = instance.Application;await app.ActiveDocument.SetReadOnly({Value: true});} else {await instance.ready();//根据接口返回信息对文档进行回填getInformationBackfilling();}
}

5. 容器初始化后我们拿到需要回填的数据就可以进行数据回填操作

//根据接口返回信息对文档进行回填
const getInformationBackfilling = () => {detailObj(props.fileObj?.projectid || props.projectid ).then(res => {const { data } = res//解析JSON格式的回填数据const recruitcontent = JSON.parse(data.recruitcontent)//保存预设的书签内容的回填信息,字段需要对应在文档中打的标记书签allData.value = {projectname: data.projectname,projectcode: data.projectcode,recrunit: data.recrunit,abbreviation: data.projectname,}// 执行书签回显业务setBookmarks()// 获取表格回显内容const list = recruitcontent.map((item, index) => {item.indexNumber = index + 1item.projectName = data.projectnameitem.subProjectDl = ""return item})// 执行表格回显业务addTable(list, 1)})
}

6. 书签回显业务

//书签赋值
const setBookmarks = async () => {const app = instance.Application;// 书签对象const bookmarks = await app.ActiveDocument.Bookmarks;let replaceArr = [];needSet.forEach((item) => {let { key } = getKey(item.name);replaceArr.push({name: item.name,type: 'text',value: allDataInfo.value[key]?.toString(),});});// 替换书签内容const isReplaceSuccess = await bookmarks.ReplaceBookmark(replaceArr);
}

7. 表格回显业务

//插入表格(标的物)
const addTable = async (list, type) => {if (!list && list?.length == 0) return;const app = instance.Application;let tabelHeade = [{title: '序号',key: 'indexNumber',},{title: '项目名称',key: 'projectName',},{title: '子目名称',key: 'subProjectName',},{title: '技术服务内容',key: 'techServiceContent',},{title: '单位',key: 'unit',},{title: '数量',key: 'quantity',},{title: '备注',key: 'remark',},];const tables = await app.ActiveDocument.Tables;// 等待表格创建完成await new Promise(resolve => {const interval = setInterval(async () => {const currentCount = await tables.Count;if (currentCount >= 10) {clearInterval(interval);resolve();}}, 300);});setTimeout(async () => {// 获取页面中总表格数量const count = await tables.Count;const Bookmark = await app.ActiveDocument.Bookmarks.Item('定义的表格书签名');// 插入表格await tables.Add(Bookmark.Range, // 位置信息list.length + 1, // 新增表格的行数tabelHeade.length, // 新增表格的列数1,2,);const tableOne = await tables.Item(Bookmark);for (let i = 0; i < list.length + 1; i++) {for (let j = 0; j < tabelHeade.length; j++) {const curCell = await tableOne.Rows.Item(i + 1).Cells.Item(j + 1);const rowText = await curCell.Range;// 设置单元格内容的字号const font = await rowText.Font;font.Size = 12; // 设置字号为 12rowText.Text = i == 0 ? tabelHeade[j].title : list[i - 1][tabelHeade[j].key] ? list[i - 1][tabelHeade[j].key].toString() : "";}}}, 1000 * 1.5);};

8. 扩展内容合并单元格

// 合并行表格单元格 instance:WebOfficeSDK初始化的文档容器,tableIndex:表格编号, rowIndex:开始行,startColIndex:结束行  , value: 替换值)
async function mergeTableCells(instance, tableIndex, rowIndex, startColIndex, endColIndex, value) {const app = instance.Application;const doc = app.ActiveDocument;const tables = await doc.Tables;// 获取指定表格const table = await tables.Item(tableIndex);// 获取指定行const row = await table.Rows.Item(rowIndex);// 获取起始单元格和结束单元格const startCell = await row.Cells.Item(startColIndex);const endCell = await row.Cells.Item(endColIndex);// 合并单元格await startCell.Merge(endCell);// 设置合并后单元格的值const mergedCell = await row.Cells.Item(startColIndex);const mergedCellRange = await mergedCell.Range;mergedCellRange.Text = value;
}// 合并列表格单元格(instance:WebOfficeSDK初始化的文档容器,tableIndex:表格编号, startRowIndex:开始列,endRowIndex:结束列, value: 替换值 )
async function mergeFirstColumnRows(instance, tableIndex, startRowIndex, endRowIndex, value) {const app = instance.Application;const doc = app.ActiveDocument;const tables = await doc.Tables;// 获取指定表格const table = await tables.Item(tableIndex);// 获取起始行和结束行const startRow = await table.Rows.Item(startRowIndex);const endRow = await table.Rows.Item(endRowIndex);// 获取第一列的起始单元格和结束单元格const startCell = await startRow.Cells.Item(1);const endCell = await endRow.Cells.Item(1);// 合并单元格await startCell.Merge(endCell);// 设置合并后单元格的值const mergedCell = await table.Rows.Item(startRowIndex).Cells.Item(1);const mergedCellRange = await mergedCell.Range;mergedCellRange.Text = value;
}

小结:

1. 根据业务需求,首先初始化时,实现了文档在线查看的功能,根据是否需要编辑的状态设置文档只读模式或者编辑模式;

2. 实现回填功能中,根据拿到的需要回填的数据做处理对应给需要回填的书签内容区域

3. 回填表格功能,根据表头配置好对应回显字段,进行业务回填,增加扩展功能对表格中部分地方单元格合并的方法;

功能代码是已实现的业务逻辑,中间也踩坑不少,最终实现文档在线查看,在线编辑以及文本和表格回填功能,欢迎大家多多交流沟通,提出建议,指出错误,我们一起成长,最后希望大家在踩坑路上继续成长。

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

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

相关文章

汇编语言学习(三)——DoxBox中debug的使用

目录 一、安装DoxBox&#xff0c;并下载汇编工具&#xff08;MASM文件&#xff09; 二、debug是什么 三、debug中的命令 一、安装DoxBox&#xff0c;并下载汇编工具&#xff08;MASM文件&#xff09; 链接&#xff1a; https://pan.baidu.com/s/1IbyJj-JIkl_oMOJmkKiaGQ?pw…

关于DDOS

DDOS是一门没什么技术含量的东西&#xff0c;其本质而言是通过大量数据报文&#xff0c;发送到目标受害主机IP地址上&#xff0c;导致目标主机无法继续服务&#xff08;俗称&#xff1a;拒绝服务&#xff09; DDOS灰产人期望达成的预期目标&#xff0c;几乎都是只要把对面打到 …

Modbus转Ethernet IP网关助力罗克韦尔PLC数据交互

在工业自动化领域&#xff0c;Modbus协议是一种广泛应用的串行通信协议&#xff0c;它定义了主站和从站之间的通信规则和数据格式。罗克韦尔PLC是一种可编程的逻辑控制器&#xff0c;通过Modbus协议实现与其他设备之间的数据交互。然而&#xff0c;随着以太网技术的普及和发展&…

C# winform教程(二)----button

一、button的使用方法 主要使用方法几乎都在属性内&#xff0c;我们操作也在这个界面 二、作用 用户点击时触发事件&#xff0c;事件有很多种&#xff0c;可以根据需要选择。 三、常用属性 虽然属性很多&#xff0c;但是常用的并不多 3.常用属性 名称内容含义AutoSize自动调…

【 java 基础问题 第二篇 】

目录 1.深拷贝和浅拷贝 1.1.区别 定义 定义 1.2.实现深拷贝的方式 2.泛型 2.1.定义 2.2.作用 3.对象 3.1.创建对象的方式 3.2.对象回收 3.3. 获取私有成员 4.反射 4.1.定义 4.2.特性 4.3.原理 5.异常 5.1.异常的种类 5.2.处理异常的方法 6.Object 6.1.等于与…

Kafka 入门指南与一键部署

Kafka 介绍 想象一下你正在运营一个大型电商平台&#xff0c;每秒都有成千上万的用户浏览商品、下单、支付&#xff0c;同时后台系统还在记录用户行为、更新库存、处理物流信息。这些海量、持续产生的数据就像奔腾不息的河流&#xff0c;你需要一个强大、可靠且实时的系统来接…

湖北理元理律师事务所:企业债务重组的风险控制方法论

一、担保链破解&#xff1a;阻断债务传染的核心技术 2023年武汉某建材公司案例&#xff1a; 原始债务结构&#xff1a; A公司&#xff08;主债务人&#xff09;欠款200万 ↓ B公司&#xff08;担保人&#xff09;←连带责任触发执行 ↓ C公司&#xff08;B公司担…

如何在CloudCompare中打开pcd文件

你只需要将pcd文件的路径改在全英文路径下&#xff0c;CloudCompare就可以打开。若含中文&#xff0c;就会报错&#xff1a;

中医的十问歌和脉象分类

中医核心理论框架如下 诊断技术如下 本文主要介绍问诊和切诊。 十问歌的“十”是虚指&#xff0c;实际包含12个核心问题&#xff0c;脉象28种中常见仅10余种&#xff0c;重点解释脉诊的物理本质&#xff08;血流动力学触觉感知&#xff09; 以下是中医十问歌的完整内容及脉…

基于智能代理人工智能(Agentic AI)对冲基金模拟系统:模范巴菲特、凯西·伍德的投资策略

股票市场涉及众多统计数据和模式。股票交易基于研究和数据驱动的决策。人工智能的使用可以实现流程自动化&#xff0c;让投资者在研究上花费更少的时间&#xff0c;同时提高准确性。这使他们能够更加专注于监督实际交易和服务客户。 顶尖对冲基金经理发挥着至关重要的作用&…

大二下期末

一.Numpy&#xff08;Numerical Python&#xff09; Numpy库是Python用于科学计算的基础包&#xff0c;也是大量Python数学和科学计算包的基础。不少数据处理和分析包都是在Numpy的基础上开发的&#xff0c;如后面介绍的Pandas包。 Numpy的核心基础是ndarray&#xff08;N-di…

D3ctf-web-d3invitation单题wp

#注入 #用kali构造凭证访问MinIO服务器 #用mc带临时凭证访问远程Minion的储存桶 还有一个 minio 服务的api&#xff0c;我们后面要用 /static/js/tools.js function generateInvitation(user_id, avatarFile) {if (avatarFile) {object_name avatarFile.name;genSTSCreds(ob…

基于 Vue 和 Spring Boot 实现滑块验证码的机器验证

基于 Vue 和 Spring Boot 实现滑块验证码的机器验证 需求概述技术选型前端实现1. 引入组件2. 修改后端请求URL3. 新增机器验证页面4.首页调用验证组件 后端实现流程梳理具体实现1. 引入依赖2. 增加yml配置3. 代码实现4.跨域配置&#xff08;可选&#xff09; 实现效果二次验证的…

[Java恶补day13] 53. 最大子数组和

休息了一天&#xff0c;开始补上&#xff01; 给你一个整数数组 nums &#xff0c;请你找出一个具有最大和的连续子数组&#xff08;子数组最少包含一个元素&#xff09;&#xff0c;返回其最大和。 子数组是数组中的一个连续部分。 示例 1&#xff1a; 输入&#xff1a;nums …

sql server如何创建表导入excel的数据

在 SQL Server 中&#xff0c;可以通过几种方式将 Excel 数据导入到数据库表中。下面是一个完整的流程&#xff0c;包括如何创建表&#xff0c;以及将 Excel 数据导入该表的方法&#xff1a; ✅ 方法一&#xff1a;使用 SQL Server Management Studio (SSMS) 的导入向导&#x…

C++单例模式教学指南

C单例模式完整教学指南 &#x1f4da; 目录 [单例模式基础概念][经典单例实现及问题][现代C推荐实现][高级话题&#xff1a;双重检查锁][实战应用与最佳实践][总结与选择指南] 1. 单例模式基础概念 1.1 什么是单例模式&#xff1f; 单例模式&#xff08;Singleton Pattern&…

使用xdocreport导出word

之前java总用freemaker进行导出&#xff0c;但是改xml实在是太繁琐了&#xff0c;这次找了另一个工具进行体验. 一、简单导出 pom引入 <dependency><groupId>fr.opensagres.xdocreport</groupId><artifactId>fr.opensagres.xdocreport.core</arti…

vscode里如何用git

打开vs终端执行如下&#xff1a; 1 初始化 Git 仓库&#xff08;如果尚未初始化&#xff09; git init 2 添加文件到 Git 仓库 git add . 3 使用 git commit 命令来提交你的更改。确保在提交时加上一个有用的消息。 git commit -m "备注信息" 4 …

C++.OpenGL (2/64)你好,三角形(Hello Triangle)

你好,三角形(Hello Triangle) 绘制流程概览 #mermaid-svg-MvIGIovxiuKVfzy8 {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-MvIGIovxiuKVfzy8 .error-icon{fill:#552222;}#mermaid-svg-MvIGIovxiuKVfzy8 .error…

汽车安全体系:FuSa、SOTIF、Cybersecurity 从理论到实战

汽车安全&#xff1a;功能安全&#xff08;FuSa&#xff09;、预期功能安全&#xff08;SOTIF&#xff09;与网络安全(Cybersecurity) 从理论到实战的安全体系 引言&#xff1a;自动驾驶浪潮下的安全挑战 随着自动驾驶技术从L2向L4快速演进&#xff0c;汽车安全正从“机械可靠…