easypoi模板导出word多页导出加强版

说明

上一篇文章提到多页导出,但是后边发现一个问题,如果用同一个模板导出多页内容,我们去获取多页内容的时候,会发现全部都一样,举个例子:

XWPFDocument document = WordExportUtil.exportWord07(outputUrl, maps);
List<XWPFTable> tables = document.getTables();
List<XWPFParagraph> paragraphs = document.getParagraphs();

通过上边的代码,不管获取tables 还是paragraphs,集合里边的内容都是一样的,而且表格只有一张,即使你导出的时候多页都有表格,但是代码获取的时候就只有一张表。

另一个问题,就是,到处之后会莫名多出一个空白页。

在这里插入图片描述

解决问题

因为获取不到除第一页的其他页内容,那么照这个方法就没办法了,那么只能转变思路,导出多页,那么就让多页数据在导出的时候独立起来,也就是说我们创建出多个XWPFDocument,最后把这些XWPFDocument合并起来,不再使用前一篇文章提到的官方方法exportWord07(String url, List<Map<String, Object>> list)了,这样不仅可以解决多页内容获取不到的问题,还能解决另一个问题(导出的word总是多出一页空白页)。

具体操作

创建工具类:

import org.apache.poi.xwpf.usermodel.Document;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.usermodel.XWPFPictureData;
import org.apache.xmlbeans.XmlOptions;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTBody;
import org.springframework.util.CollectionUtils;import java.util.HashMap;
import java.util.List;
import java.util.Map;/*** WordUtils** @author ZENG.XIAO.YAN* @version 1.0* @Date 2019-09-20*/
public final class WordUtils {/*** word文件合并* @param wordList* @return* @throws Exception*/public static  XWPFDocument mergeWord(List<XWPFDocument> wordList) throws Exception{if (CollectionUtils.isEmpty(wordList)) {throw  new RuntimeException("待合并的word文档list为空");}XWPFDocument doc = wordList.get(0);int size = wordList.size();if (size > 1) {//不要设置分页符,否则第二页第一行总会多出一个换行符,具体需不需要根据自己的需求来定doc.createParagraph().setPageBreak(false);for (int i = 1; i < size; i++) {// 从第二个word开始合并XWPFDocument nextPageDoc = wordList.get(i);// 最后一页不需要设置分页符if (i != (size-1)) {nextPageDoc.createParagraph().setPageBreak(false);}appendBody(doc, nextPageDoc);}}return doc;}private static void appendBody(XWPFDocument src, XWPFDocument append) throws Exception {CTBody src1Body = src.getDocument().getBody();CTBody src2Body = append.getDocument().getBody();List<XWPFPictureData> allPictures = append.getAllPictures();// 记录图片合并前及合并后的IDMap<String,String> map = new HashMap<>();for (XWPFPictureData picture : allPictures) {String before = append.getRelationId(picture);//将原文档中的图片加入到目标文档中String after = src.addPictureData(picture.getData(), Document.PICTURE_TYPE_PNG);map.put(before, after);}appendBody(src1Body, src2Body,map);}private static void appendBody(CTBody src, CTBody append,Map<String,String> map) throws Exception {XmlOptions optionsOuter = new XmlOptions();optionsOuter.setSaveOuter();String appendString = append.xmlText(optionsOuter);String srcString = src.xmlText();String prefix = srcString.substring(0,srcString.indexOf(">")+1);String mainPart = srcString.substring(srcString.indexOf(">")+1,srcString.lastIndexOf("<"));String sufix = srcString.substring( srcString.lastIndexOf("<") );String addPart = appendString.substring(appendString.indexOf(">") + 1, appendString.lastIndexOf("<"));if (map != null && !map.isEmpty()) {//对xml字符串中图片ID进行替换for (Map.Entry<String, String> set : map.entrySet()) {addPart = addPart.replace(set.getKey(), set.getValue());}}//将两个文档的xml内容进行拼接CTBody makeBody = CTBody.Factory.parse(prefix+mainPart+addPart+sufix);src.set(makeBody);}}

关键代码:

//用来装每个需要合并的XWPFDocument
List<XWPFDocument> wordList = new ArrayList<>();
XWPFDocument document = WordExportUtil.exportWord07(outputUrl, map);
XWPFTable table = document.getTables().get(0);for (int row = 4; row <= table.getNumberOfRows() - 4; row++) {// 从第二行开始,合并上一行和当前行XWPFTableRow row1 = table.getRow(row);if (row == 4) {XWPFTableCell cell = row1.getCell(6);cell.getCTTc().addNewTcPr().addNewVMerge().setVal(STMerge.RESTART);cell.setVerticalAlignment(XWPFTableCell.XWPFVertAlign.CENTER);cell.setText("根据物资的形状、性能、特点、数量、重量进行五五式合理摆放,必须做到稳固、定量、整理、方便和安全");} else if (row == table.getNumberOfRows() - 4) {XWPFTableCell cell = row1.getCell(7);CTTc ctTc = cell.getCTTc();if (ctTc != null) {CTTcPr tcPr = ctTc.getTcPr();if (tcPr == null) {tcPr = ctTc.addNewTcPr();}if (tcPr.getVMerge() == null) {tcPr.addNewVMerge();}tcPr.getVMerge().setVal(STMerge.CONTINUE);}cell.setVerticalAlignment(XWPFTableCell.XWPFVertAlign.CENTER);} else {XWPFTableCell cell = row1.getCell(10);CTTc ctTc = cell.getCTTc();if (ctTc != null) {CTTcPr tcPr = ctTc.getTcPr();if (tcPr == null) {tcPr = ctTc.addNewTcPr();}if (tcPr.getVMerge() == null) {tcPr.addNewVMerge();}tcPr.getVMerge().setVal(STMerge.CONTINUE);}cell.setVerticalAlignment(XWPFTableCell.XWPFVertAlign.CENTER);}}wordList.add(document);
}

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

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

相关文章

有限差分学习笔记

有限差分介绍 ​ 在数学中&#xff0c;有限差分法&#xff08;finite-difference methods&#xff0c;简称FDM&#xff09;&#xff0c;是一种微分方程数值方法&#xff0c;是通过有限差分来近似导数&#xff0c;从而寻求微分方程的近似解。 由泰勒展开式的推导 显式方…

【PyTorch】关于Tensorboard的简单使用

前提文章目录 【PyTorch】深度学习PyTorch环境配置及安装【详细清晰】 【PyTorch】深度学习PyTorch加载数据 文章目录 前提文章目录SummaryWriter使用add_image()的使用&#xff08;常用来观察训练结果&#xff09;利用Tensorboard观察图片 SummaryWriter使用 from torch.util…

手把手教你用vite+React18+TS+redux+prettier+eslint+Ant打造企业级前端项目

通过这篇文章你可以学到 如何使用使用 webpack 搭建项目如何在 webpack中集成 typescript如何在 webpack 中集成 React Router 和 Redux如何使用 React 的组件库 Ant Design如何在项目中集成 eslint 和 prettier 保证代码质量如何为团队开发专属的项目模板 环境依赖版本 nod…

Hive SQL语言

目录 Hive SQL之数据库与建库 create database :创建数据库 use database :选择特定的数据库 drop database :删除数据库 Hive SQL之表与建表 create table : 创建表 分隔符指定语法 Hive SQL-DML-Load加载数据 Load语法功能 语法规则之filepath 语法规则之LOCAL …

spring揭秘09-aop03-aop织入器织入横切逻辑与自动织入

文章目录 【README】【1】spring aop的织入【1.1】使用ProxyFactory 作为织入器【1.2】基于接口的代理&#xff08;JDK动态代理&#xff0c;目标类实现接口&#xff09;【补充】 【1.2】基于类的代理&#xff08;CGLIB动态代理&#xff0c;目标类没有实现接口&#xff09;【1.2…

数据缓存软件Redis推出Redis 8 这更改许可证后首个重大版本更新

2024 年 3 月流行的数据库缓存应用 Redis 宣布修改开源许可证&#xff0c;此次修改许可证的目的本质上就是避免大型云计算公司白嫖&#xff0c;例如亚马逊的 AWS 等。AWS 等云计算服务商基于 Redis 推出托管服务并向客户收费&#xff0c;作为开发商 Redis 并没有获得收益&#…

阿里云CentOs ClickHouse安装

&#x1f339;作者主页&#xff1a;青花锁 &#x1f339;简介&#xff1a;Java领域优质创作者&#x1f3c6;、Java微服务架构公号作者&#x1f604; &#x1f339;简历模板、学习资料、面试题库、技术互助 &#x1f339;文末获取联系方式 &#x1f4dd; ClickHouse安装目录 前言…

easypoi模板导出word并且合并行

导出流程 引入依赖制作模板合并导出 引入依赖 <dependency><groupId>cn.afterturn</groupId><artifactId>easypoi-base</artifactId><version>4.1.2</version> </dependency>制作模板 合并行是备注那一列&#xff0c;这一列…

YOLOv8目标检测推理流程及Python代码

在这章中将介绍目标检测推理原理,以及基于onnx模型使用Python语言进行推理。在推理原理章节中,将了解onnx模型的输入和输出,对输入的图片需要进行预处理的操作,对输出的结果需要进行后处理的操作等;在Python代码篇,将给出推理代码。 这里注意一下的是,由于在导出onnx模型…

DRF——pagination分页模块

文章目录 分页继承APIView类用法1.PageNumberPagination2.LimitOffsetPagination3.CursorPagination 继承GenericAPIView派生类用法1.PageNumberPagination2.LimitOffsetPagination3.CursorPagination 分页 在查看数据列表的API中&#xff0c;如果 数据量 比较大&#xff0c;肯…

嵌入式UI开发-lvgl+wsl2+vscode系列:9、控件(Widgets)(二)

一、前言 接下来我们总结第二部分的控件。 二、示例 1、image&#xff08;图像&#xff09; 1.1、示例1 #include "../../lv_examples.h" #if LV_USE_IMAGE && LV_BUILD_EXAMPLESvoid lv_example_image_1(void) {LV_IMAGE_DECLARE(img_cogwheel_argb);lv…

完成课题ssrf实现.SSH未创建写shell,同时完成其他漏洞复现

一、SSRF (Server-Side Request Forgery) 是一种网络安全漏洞&#xff0c;发生在服务器端应用程序中&#xff0c;允许攻击者通过服务器向任意网络资源发送请求&#xff0c;而无需用户直接参与。这种漏洞通常源于程序设计错误&#xff0c;例如当应用程序使用用户的输入作为URL请…

根据json字符串 自动生成 实体类 Model Entity .NET

①访问json2csharp的在线工具&#xff1a;http://json2csharp.com/ ②复制json字符串&#xff0c;粘贴到左边&#xff0c;按下面Convert按钮 ③右边就是 生成的 实体类 &#xff0c;直接复制到 .cs文件内就能使用 ④或者点击 Zip As File 按钮&#xff0c;直接生成 N个.cs文…

基于Springboot和BS架构的宠物健康咨询系统pf

TOC springboot509基于Springboot和BS架构的宠物健康咨询系统pf 第一章 课题背景及研究内容 1.1 课题背景 信息数据从传统到当代&#xff0c;是一直在变革当中&#xff0c;突如其来的互联网让传统的信息管理看到了革命性的曙光&#xff0c;因为传统信息管理从时效性&#x…

使用VRoid Studio二次元建模,创建专属于自己的二次元卡通人物模型,创建完全免费开源且属于自己VRM模型

最终效果 文章目录 最终效果什么是VRoid Studio官网地址下载安装VRoid Studio1、可以去它的官网下载2、steam安装 创建模型配置参数 导出模型使用别人的VRM模型这里我分享几个不错的模型&#xff0c;大家可以自行去下载 完结 什么是VRoid Studio 如果你玩过能捏脸的游戏你就能…

游戏开发设计模式之责任链模式

责任链模式&#xff08;Chain of Responsibility Pattern&#xff09;是一种行为型设计模式&#xff0c;它允许将请求沿着处理者链进行发送。每个处理者对象都有机会处理该请求&#xff0c;直到某个处理者决定处理该请求为止。 概念与定义 责任链模式的核心思想是将多个处理器…

【传输层协议】UDP协议 {端口号的范围划分;UDP数据报格式;UDP协议的特点;UDP的缓冲区;基于UDP的应用层协议}

一、再谈端口号 1.1 端口号标识网络进程 如何通过端口号找到主机上的网络进程&#xff1f; 在socket编程中bind绑定是最为重要的一步&#xff1a;他将套接字与指定的本地 IP 地址和端口号关联起来&#xff0c;这意味着指定的套接字可以接收来自指定 IP 地址和端口号的数据包…

前端宝典十:webpack性能优化最佳实践

Webpack 内置了很多功能。 通常你可用如下经验去判断如何配置 Webpack&#xff1a; 想让源文件加入到构建流程中去被 Webpack 控制&#xff0c;配置 entry&#xff1b;想自定义输出文件的位置和名称&#xff0c;配置 output&#xff1b;想自定义寻找依赖模块时的策略&#xff…

java swagger解析解决[malformed or unreadable swagger supplied]

原创不易&#xff0c;转载请注明出处&#xff1a; https://zhangxiaofan.blog.csdn.net/article/details/141498211 如果你想看完整的 利用swagger-parser解析yaml中的api请求类型、注释、接口名&#xff0c;可以参考这篇文章。 【Spring/Java项目】如何利用swagger-parser解析…

NC 最长上升子序列(三)

系列文章目录 文章目录 系列文章目录前言 前言 前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到网站&#xff0c;这篇文章男女通用&#xff0c;看懂了就去分享给你的码吧。 描述 给定数组 arr…