aspose模板生成(文书工具)

动态数据

${info}

${list.id}

${list.name}

${list.address}

${list.date}

${list.danwei}

${list.number}

${list.remark}

${imgBase64}

${xw.ask}

${xw.ans}

格式

openxml

openxml

openxml

大坑:!!!!

word转xml记得转这种格式:Word XML文档(xml)

图片

存图片 先用一个照片作为占位符,然后去xml中将那一段base64 代替掉 ${imgBase64}

<pkg:part pkg:name="/word/media/image1.png" pkg:contentType="image/png">

pkg:binaryData${imgBase64}</pkg:binaryData>

</pkg:part>

但是word中保存图片文件的标签必须要连着写,不能出现换行或者空白,否则就会出现找不到图片的问题

图片的大小也是可以动态设置的 ${xxx}

遍历list

使用list遍历 (可以用来遍历生成表格,或者问答形式也可以)

只需要 在外面嵌套一层标签

<#list lists(参数) as list>

xxxxxx${list.id}xxxxxxxxxxxx${list.name}

</#list>

页脚

只在最后一页添加页脚、解决方式:

在指定位置加上一个文本框,然后给他设置为 上下环绕型、不允许重叠、然后把边框改为无边框即可





如果生成的pdf格式不对,或者多了一些字一些横线,就去xml中删除即可

删除这几个标签 endnotes 、、 footnotes 这两个是结尾多出来的横线

另一种情况:可能是因为页眉生成了横线,去xml中删除 head 标签

符号

一些特殊符号

https://www.jb51.cc/xml/541196.html

复选框

关于复选框 xxx = 1 就是选中 xxx = 0 就是未选中 这里直接传值就可以了 ${checked} (如果出现xml选中后是R或其他而不是显示√ 可以先在word中打钩先然后去xml给0)

w14:checkbox

<w14:checked w14:val= "${checked}"/>

<w14:checkedState w14:val="2612" w14:font="MS Gothic"/>

<w14:uncheckedState w14:val="2610" w14:font="MS Gothic"/>

</w14:checkbox>



集成SpringBoot中

相关依赖

<!--xml数据填充所需依赖 author: mao-->
<dependency>
<groupId>dom4j</groupId>
<artifactId>dom4j</artifactId>
<version>1.6.1</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-freemarker</artifactId>
</dependency>
<!--这里需要引入外部的包 maven仓库没有 存在resources下的lib包下-->
<dependency>
<groupId>com.aspose.words</groupId>
<artifactId>aspose-words-jdk16</artifactId>
<version>15.8.0</version>
<scope>system</scope>
<systemPath>${project.basedir}/src/main/resources/lib/aspose-words-jdk16-15.8.0.jar</systemPath>
</dependency>

Aspose Jar包下载:

蓝奏云:https://wwzv.lanzoue.com/iK7eu0t8twti

密码:1736

<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>2.1.1.RELEASE</version>
<configuration>
<fork>true</fork> <!-- 如果没有该配置,devtools不会生效 -->
<includeSystemScope>true</includeSystemScope> <!-- 引入外部的jar包 -->
</configuration>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>

true

DocToPdf

package com.nongyeservice.paper.utils;

import com.aspose.words.*;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component; import java.io.*;
import java.util.Base64;
import java.util.Map;
import java.util.regex.Pattern; /**
* @author mao
* @program paperUtil
* @description word转pdf核心代码
* @description aspose文书工具所需参数(新文书工具)
* @createDate 2023-03-23 16:50:05
**/
@Component
@Slf4j
public class DocToPdf { /**
* 模板文件存放的路径(绝对路径哈)
*/
@Value("${aspose.defaultTemplatePath}")
public String baseUrl; // private String baseUrl2 = System.getProperty("java.io.tmpdir"); @Autowired
XmlToDocx xmlToDocx; public boolean getLicense() {
boolean result = false;
try {
// aspose需要的签名文件名称
InputStream is = DocToPdf.class.getClassLoader().getResourceAsStream("license.xml");
// InputStream is = new FileInputStream(path);
License aposeLic = new License();
aposeLic.setLicense(is);
result = true;
} catch (Exception e) {
e.printStackTrace();
}
return result;
} /**
* @param params 需要填充的数据
* @param templateName 模板的文件名
* @param savePdfName 最后保存的pdf文件 可以用 文书名+文书业务id 来命名
* @return 最后生成的文书pdf文件保存路径
* @throws Exception
*/
public String doDocToPdf(Map<String, Object> params, String templateName, String savePdfName){
try {
if (!getLicense()) { // 验证License 若不验证则转化出的pdf文档会有水印产生
return null;
}
// String templateUUId = UUID.randomUUID().toString();
String xml = baseUrl + savePdfName + ".xml";
String docx = baseUrl + savePdfName + ".docx";
// XmlToDocx.toDocx(documentXmlName, docTemplatePath + documentDocName, xml, baseUrl + templateUUId + ".docx", params);
boolean b = xmlToDocx.toDocx(templateName + ".xml", baseUrl + templateName + ".docx", xml, docx, params);
if(!b) {
log.error("pdf生成失败,Method:xmlToDocx.toDocx()");
return null;
}
// 新建一个空白pdf文档
String pdf = baseUrl + savePdfName + ".pdf";
File file = new File(pdf);
FileOutputStream os = new FileOutputStream(file);
// docx是将要被转化的word文档
Document doc = new Document(docx);
String osName = isWindows();
String fonts[] = null;
/**
* 适配字体文件
*/
if (osName.equals("linux")) {
// fonts = new String[]{"/usr/share/fonts/chinese/", "/usr/share/fonts/simsun/", "/usr/share/fonts/"};
fonts = new String[]{"/usr/share/fonts/win/Fonts/"};
} else if (osName.equals("mac")) {
fonts = new String[]{"/Users/fonts/chinese/", "/Users/fonts/simsun/", "/Users/fonts/black/", "/Users/fonts/wingdings/"};
} else if (osName.equals("windows")) {
fonts = new String[]{"C:/Windows/Fonts/"};
}
FontSettings.setFontsFolders(fonts, true);
// 保存pdf
// replace(params,docx,docx);
doc.save(os, SaveFormat.PDF);
if (os != null) {
os.close();
}
delete(xml, docx);//删除文件
log.info(templateName + "文书pdf已生成至:" + pdf);
return pdf;
} catch (Exception e) {
e.printStackTrace();
return null;
}
} private String isWindows() {
String osName = System.getProperties().getProperty("os.name").toUpperCase();
if (osName.indexOf("WINDOWS") != -1) {
return "windows";
} else if (osName.indexOf("MAC") != -1) {
return "mac";
} else {
return "linux";
}
} private static String isWindowss() {
String osName = System.getProperties().getProperty("os.name").toUpperCase();
if (osName.indexOf("WINDOWS") != -1) {
return "windows";
} else if (osName.indexOf("MAC") != -1) {
return "mac";
} else {
return "linux";
}
} /**
* 删除生成的多余文件
*/
public void delete(String xmlPath, String wordPath) {
File file = new File(xmlPath);
if (file.exists()) {
file.delete();
}
File wordFile = new File(wordPath);
if (wordFile.exists()) {
wordFile.delete();
}
} /**
* aspose word 替换文字/图片。
* @param url 原文件路径
* @param saveurl 保存路径
* @param params {key:value,"$年份$":"2020","$签字1$":"$pic:d/qz1.jpg"} key 为要被替换的字符串,value 为替换为的字符串,替换为图片,则value为$pic:+图片路径
* 图片的传参: params.put("[$pic$]", "$pic:C:\\Users\\86153\\Pictures\\jackChen.jpg");
* @return
*/
public boolean replace(Map<String, Object> params, String url,String saveurl){
if(!getLicense()){
return false;
}
File file = new File(url);
if(!file.exists()){
return false;
}
try {
Document doc = new Document(url);
Range range = doc.getRange();
for(String key:params.keySet()){
if (params.get(key) == null) continue;
String value = params.get(key).toString();
if(value.startsWith("$pic:")){
value = value.substring(5);
key = key.replace("\\", "\\\\");
key = key.replace("$", "\\$");
key = key.replace("[", "\\[");
key = key.replace("]", "\\]");
key = key.replace("(", "\\(");
key = key.replace(")", "\\)");
key = key.replace("|", "\\|");
key = key.replace("+", "\\+");
key = key.replace("?", "\\?");
key = key.replace("*", "\\*");
range.replace( Pattern.compile(key),new ReplaceAndInsertImage(value) , false);
}else{
range.replace(key, value, true, false);
}
}
doc.save(saveurl); } catch (Exception e) {
e.printStackTrace();
return false;
}
return true;
} /**
* @param imgFile 文件的路径
* @return 文件转为base64 二进制流
*/
public static String fileToBase64(String imgFile) { // 将图片文件转化为二进制流
InputStream in = null;
byte[] data = null;
// 读取图片字节数组
try {
in = new FileInputStream(imgFile);
data = new byte[in.available()];
in.read(data);
in.close();
} catch (IOException e) {
e.printStackTrace();
}
// 图片头
//String imghead = "data:image/jpeg;base64,";
// return Base64.encodeBase64String(data);
// mac/linux下base64生成的base64码,换行符是\n,而word原生图片里的base64换行符是\r\n,
// return Base64.getEncoder().encodeToString(data).replace("\n", "\r\n").replace("\r\r\n", "\r\n");
return Base64.getEncoder().encodeToString(data);
} /**
* @param templateName 模板的文件名
* @param savePdfName 最后保存的pdf文件 可以用 文书名+文书业务id 来命名
* @return 最后生成的文书pdf文件保存路径
* @throws Exception
*/
public static void doDocToPdf(String templateName, String savePdfName) throws Exception {
try {
try {
// aspose需要的签名文件名称
InputStream is = DocToPdf.class.getClassLoader().getResourceAsStream("license.xml");
// InputStream is = new FileInputStream(path);
License aposeLic = new License();
aposeLic.setLicense(is);
} catch (Exception e) {
e.printStackTrace();
}
File file = new File(savePdfName);
FileOutputStream os = new FileOutputStream(file);
// docx是将要被转化的word文档
Document doc = new Document(templateName);
String osName = isWindowss();
String fonts[] = null;
/**
* 适配字体文件
*/
if (osName.equals("linux")) {
// fonts = new String[]{"/usr/share/fonts/chinese/", "/usr/share/fonts/simsun/", "/usr/share/fonts/"};
fonts = new String[]{"/usr/share/fonts/win/Fonts/"};
} else if (osName.equals("mac")) {
fonts = new String[]{"/Users/fonts/chinese/", "/Users/fonts/simsun/", "/Users/fonts/black/", "/Users/fonts/wingdings/"};
} else if (osName.equals("windows")) {
fonts = new String[]{"C:/Windows/Fonts/"};
}
FontSettings.setFontsFolders(fonts, true);
// 保存pdf
// replace(params,docx,docx);
doc.save(os, SaveFormat.PDF);
if (os != null) {
os.close();
}
// delete(null, docx);//删除文件
log.info(templateName + "文书pdf已生成");
} catch (Exception e) {
e.printStackTrace();
} }
}

XmlToDocx

package com.nongyeservice.paper.utils;

import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component; import java.io.*;
import java.util.Enumeration;
import java.util.Map;
import java.util.zip.ZipEntry;
import java.util.zip.ZipException;
import java.util.zip.ZipFile;
import java.util.zip.ZipOutputStream; /**
* @author mao
* @program paperUtil
* @description word动态填充数据核心类
* @createDate 2023-03-23 16:50:05
**/
@Component
@Slf4j
public class XmlToDocx { @Autowired
XmlTplUtil xmlTplUtil; /**
* @param xmlTemplate xml的文件名
* @param docxTemplate docx的路径和文件名
* @param xmlTemp 填充完数据的临时xml
* @param toFilePath 目标文件名
* @param map 需要动态传入的数据
* @throws IOException
*/
public boolean toDocx(String xmlTemplate, String docxTemplate, String xmlTemp, String toFilePath, Map map) {
try {
// 1.map是动态传入的数据
// 这个地方不能使用FileWriter因为需要指定编码类型否则生成的Word文档会因为有无法识别的编码而无法打开
Writer w1 = new OutputStreamWriter(new FileOutputStream(xmlTemp), "utf-8");
// 2.把map中的数据动态由freemarker传给xml
xmlTplUtil.process(xmlTemplate, map, w1);
// 3.把填充完成的xml写入到docx中
XmlToDocx xtd = new XmlToDocx();
xtd.outDocx(new File(xmlTemp), docxTemplate, toFilePath);
w1.close();
return true;
} catch (Exception e) {
e.printStackTrace();
log.error("XML to Word Failed {}" , e.getMessage());
return false;
}
} /**
* @param documentFile 动态生成数据的docunment.xml文件
* @param docxTemplate docx的模板
* @param toFilePath 需要导出的文件路径
* @throws ZipException
* @throws IOException
*/ public void outDocx(File documentFile, String docxTemplate, String toFilePath) throws ZipException, IOException {
File docxFile = new File(docxTemplate);
ZipFile zipFile = new ZipFile(docxFile);
Enumeration<? extends ZipEntry> zipEntrys = zipFile.entries();
ZipOutputStream zipout = new ZipOutputStream(new FileOutputStream(toFilePath));
int len = -1;
byte[] buffer = new byte[1024];
while (zipEntrys.hasMoreElements()) {
ZipEntry next = zipEntrys.nextElement();
InputStream is = zipFile.getInputStream(next);
// 把输入流的文件传到输出流中 如果是word/document.xml由我们输入
zipout.putNextEntry(new ZipEntry(next.toString()));
if ("word/document.xml".equals(next.toString())) {
InputStream in = new FileInputStream(documentFile);
while ((len = in.read(buffer)) != -1) {
zipout.write(buffer, 0, len);
}
in.close();
} else {
while ((len = is.read(buffer)) != -1) {
zipout.write(buffer, 0, len);
}
is.close();
}
}
zipout.close();
zipFile.close();
} }

XmlTplUtil

package com.nongyeservice.paper.utils;

import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component; import java.io.File;
import java.io.IOException;
import java.io.Writer;
import java.util.Map; /**
* @author mao
* @program paperUtil
* @description word动态填充工具类
* @createDate 2023-03-23 16:50:05
**/
@Component
public class XmlTplUtil { @Value("${aspose.defaultTemplatePath}")
public String baseUrl; private XmlTplUtil tplm = null;
private Configuration cfg = null; private XmlTplUtil() {
// cfg = new Configuration();
// try {
// cfg.setDirectoryForTemplateLoading(new File(baseUrl));
// } catch (Exception e) {
// e.printStackTrace();
// }
} private Template getTemplate(String name) throws IOException {
if (tplm == null) {
// tplm = new XmlTplUtil();
cfg = new Configuration();
try {
cfg.setDirectoryForTemplateLoading(new File(baseUrl));
} catch (Exception e) {
e.printStackTrace();
}
}
Template template = cfg.getTemplate(name,"utf-8");
return template;
} /**
* @param templatefile 模板文件
* @param param 需要填充的内容
* @param out 填充完成输出的文件
* @throws IOException
* @throws TemplateException
*/
public void process(String templatefile, Map param, Writer out) throws IOException, TemplateException {
// 获取模板
Template template = getTemplate(templatefile);
template.setOutputEncoding("utf-8");
// 合并数据
template.process(param, out);
if (out != null) {
out.close();
}
} }

ReplaceAndInsertImage 只需要改word即可

DocToPdf中有一个replace()方法,需要用到这个类

package com.nongyeservice.paper.utils;

import com.aspose.words.*;

public class ReplaceAndInsertImage implements IReplacingCallback{
public String url;
public ReplaceAndInsertImage(String url){
this.url = url;
}
@Override
public int replacing(ReplacingArgs e) throws Exception {
//获取当前节点
Node node = e.getMatchNode();
//获取当前文档
Document document = (Document) node.getDocument();
DocumentBuilder builder = new DocumentBuilder(document);
// //将光标移动到指定节点
builder.moveTo(node);
// //插入图片
builder.insertImage(url);
return ReplaceAction.REPLACE;
}
}

license.xml aspose所需要的证书

<License>
<Data>
<Products>
<Product>Aspose.Total for Java</Product>
<Product>Aspose.Words for Java</Product>
</Products>
<EditionType>Enterprise</EditionType>
<SubscriptionExpiry>20991231</SubscriptionExpiry>
<LicenseExpiry>20991231</LicenseExpiry>
<SerialNumber>8bfe198c-7f0c-4ef8-8ff0-acc3237bf0d7</SerialNumber>
</Data>
<Signature>sNLLKGMUdF0r8O1kKilWAGdgfs2BvJb/2Xp8p5iuDVfZXmhppo+d0Ran1P9TKdjV4ABwAgKXxJ3jcQTqE/2IRfqwnPf8itN8aFZlV3TJPYeD3yWE7IT55Gz6EijUpC7aKeoohTb4w2fpox58wWoF3SNp6sK6jDfiAUGEHYJ9pjU=</Signature>
</License>

openxml文书工具 Aspose 工具 word to pdf的更多相关文章

  1. aspose将word转pdf时乱码,或者出现小方框问题

    通常来讲,出现这种问题一般是因为Linux服务器没有安装中文字体  查看Linux目前的所有字体 fc-list #查看Linux目前的所有中文字体 fc-list :lang=zh #将window ...

  2. Aspose 强大的服务器端 excel word ppt pdf 处理工具

    Aspose 强大的服务器端 excel word ppt pdf 处理工具 http://www.aspose.com/java/word-component.aspx

  3. 【产品对比】Word开发工具Aspose.Words和Spire.Doc性能和优劣对比一览

    转:evget.com/article/2018/4/3/27885.html 概述:Microsoft Office Word是微软公司的一个文字处理器应用程序,作为办公软件必不可少的神器之一,Wo ...

  4. Jacob工具类使用文件互转服务 word转html html转excel word转pdf excel转pdf ppt转pdf

    前提条件  必须安装MS office 1.jdk使用jdk1.8 2.jacob.dll放在..\jdk1.8\jre\bin目录下 3.eclipse的jre版本要和jdk一致,window-&g ...

  5. java word转pdf 工具类

    package com.elitel.hljhr.comm.web.main.controller; import java.io.File; import java.io.FileOutputStr ...

  6. java实现word转pdf在线预览(前端使用PDF.js;后端使用openoffice、aspose)

    背景 之前一直是用户点击下载word文件到本地,然后使用office或者wps打开.需求优化,要实现可以直接在线预览,无需下载到本地然后再打开. 随后开始上网找资料,网上资料一大堆,方案也各有不同,大 ...

  7. JAVA使用aspose实现word文档转pdf文件

    引入jar包 下载地址:https://yvioo.lanzous.com/iezpdno3mob 然后打开下载的目录打开cmd执行 mvn install:install-file -Dfile=a ...

  8. Aspose.Words操作word生成PDF文档

    Aspose.Words操作word生成PDF文档 using Aspose.Words; using System; using System.Collections.Generic; using ...

  9. OpenXMl倒出word、PDF

    OpenXMl倒出word.PDF @using MarkdownSharp @{     ViewBag.Title = "预览";     Layout = "~/V ...

  10. 哪些工具可以在word中快速绘制图形

    在数学试卷.论文.电子教案等编写过程中,我们经常要作出数学图形或图像,若用Word自身携带的绘图工具绘制,多有不便.比如一些曲线的形状很难画得像,画到位,作图时修修改改,颇为费力,所以需要借助一些辅助 ...

随机推荐

  1. 分享一个我遇到过的“量子力学”级别的BUG。

    你好呀,我是歪歪. 前几天在网上冲浪的时候,看到知乎上的这个话题: 一瞬间,一次历史悠久但是记忆深刻的代码调试经历,"刷"的一下,就在我的脑海中蹦出来了. 虽然最终定位到的原因令人 ...

  2. Oracle12c 数据库 警告日志

    目录 一:查看警告日志文件的位置 二:警告日志内容 三:告警日志监控: 方案1: 方案2: 方案3: 正文 回到顶部 一:查看警告日志文件的位置 Oracle 12c环境下查询,alert日志并不在b ...

  3. linux下expdp和impdp命令

    一.查看管理理员目录(同时查看操作系统是否存在,因为Oracle并不关心该目录是否存在,如果不存在,则出错) >select * from dba_directories; 删除定义目录 > ...

  4. javascript 判断浏览器

    navigator.userAgent 通常我们可以通过navigator.userAgent只读属性来获取浏览器的一些信息,算是原生方法吧. jquery -jquery1.9 版本可以通过$.br ...

  5. Docker中的Gitlab数据迁移

    一.选择版本 GitLab 12.2或更高版本:   docker exec -t gitlab-backup create GitLab 12.1和更早版本:   gitlab-rake gitla ...

  6. 使用Python解决氢原子问题

    引言 大家好!今天我们将讨论一个非常经典的物理问题-氢原子问题,并使用 Python 来进行求解.氢原子问题是量子力学中的基础问题,它帮助我们理解原子内部的电子结构及其能量水平.通过这篇文章,大家将学 ...

  7. nginx禁止IP访问,仅供域名访问(域名访问限制不严格漏洞)

    域名访问限制不严格漏洞解决 nginx添加相关配置 通过default_server,在http中最前面加上该配置 server { listen 80 default_server; server_ ...

  8. WPF静态资源StaticResource和动态资源DynamicResource有什么区别,x:Static又是什么意思?

    什么叫WPF的资源(Resource) 资源是保存在可执行文件中的一种不可执行数据.WPF中资源用ResourceDictionary类表示,这个类就是一个字典,字典的key和value都是objec ...

  9. Windows系统设置开机自启动+分块压缩+文件共享

    开机自启动+分块压缩+文件共享 一.设置开机自启动 win+R 打开运行窗口,输入 shell:startup 此时桌面会弹出一个目录文件夹,只需要将需要启动的软件放入该文件夹即可开机自启. C:\U ...

  10. RMQ学习笔记

    RMQ学习笔记 前言:这个算法无论是从适配性还是长度来说都很有实力... 关于 RMQ RMQ 是英文 Range Maximum/Minimum Query 的缩写,表示区间最大(最小)值. 详细信 ...