提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
文章目录
java导出word并动态插入多张图片
前言
`java使用加载模板导出word基本操作
java、word
一、使用步骤
1.首先使用wps等工具制作模板,设置样式、格式等(如标题,目录等);
2、在模板中需要填充数据的地方使用占位符代替如下:
3、如果模板中有图片需要使用一张图片作为占位符,不能直接使用文本占位
4、模板制作好以后另存为xml格式的文件:
5、将xml文件改为ftl格式文件,直接将文件后缀改为.ftl结尾就好;
例如(原本为:<06 管道磁粉检测报告.xml>,更名称后为<06 管道磁粉检测报告.ftl>)
6、打开保存的ftl文件,会看到有很长的二进制文件,如图:
将对应图片二进制数据全部删除,使用自定义名称替换,跟文本一样的替换方式
7、我遇到的问题主要是嵌套循环插入图片,所以这里就以图片为主,在ftl文件中插入图片主要更改3个位置,如图:
第一张图片处原本是图片对应二进制数据,这里使用 imageList2.image1 替换的,在代码中将图片转为base64编码格式,赋值给image1就可以了;
spEvaVesselCScanList是循环添加的表格数据,在每个表格中有多张图片,所以在spEvaVesselCScanList里面包含imageList2集合;
imageList2中包含多张图片信息,imageList2.index1是我在代码中自定义的索引,这个只要imageList2这个集合中每条数据的index1不重复就可以,也可以直接使用集合对应索引:imageList2_index;
imageList2.url1是图片对应路径,在ftl文件中每张图片需要替换2处,如图二;
这样模板制作基本完成
二、代码中处理
1.引入库
代码如下(示例):
<!--poi-tl word模板引擎 -->
<dependency>
<groupId>com.deepoove</groupId>
<artifactId>poi-tl</artifactId>
<version>1.8.2</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>4.1.2</version>
</dependency>
<dependency>
<groupId>e-iceblue</groupId>
<artifactId>spire.doc.free</artifactId>
<version>3.9.0</version>
</dependency>
2.代码处理
代码如下(示例):
/**
* 测试超声C扫描循环嵌套
* @return
*/
@GetMapping("/test14C")
public Map test14C(){
Configuration configuration = null;
configuration = new Configuration(Configuration.VERSION_2_3_23);
configuration.setDefaultEncoding("utf-8");
//模板文件的位置,你们的模板就是自己修改的flt文档,我的是跟代码同一个包下(确保能找到就可以)
configuration.setClassForTemplateLoading(this.getClass(), "/templates/");
Template template = null;
try {
//加载---要装载的模板文件
template = configuration.getTemplate("14 管道超声C扫描检测报告.ftl");
} catch (Exception e) {
e.printStackTrace();
}
Map map = new HashMap();
Map data = this.get14C();
//输出文档路径及名称,注意后缀一定要.doc!不然代码运行完后会打不开
String s = UUID.randomUUID().toString().replaceAll("-", "");
//String path = "D:\\file\\" + s + ".doc";
String path = "C:\\project\\upload\\word\\" + s + ".doc";
File outFile = new File(path);
Writer out = null;
try {
OutputStreamWriter outputStreamWriter = new OutputStreamWriter(new FileOutputStream(outFile), "UTF-8");
out = new BufferedWriter(outputStreamWriter);
} catch (FileNotFoundException | UnsupportedEncodingException e) {
e.printStackTrace();
}
try {
System.out.println(out);
template.process(data, out);
// System.out.println(out); 查看数据
System.out.println("word转换完成!");//查看数据
map.put("path", "/"+s + ".doc");
return map;
} catch (TemplateException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return map;
}
代码中是将数据全部封装到一个map集合中,map中的key就是ftl模板中对应的占位符,map的value就是占位符替换后的值;如果有表格等需要循环添加值的地方,map中的key对应的值应是一个list集合,在ftl模板中使用<#list **** as **** ></#list>标签包起来,如果多重循环,在list集合中再封装map集合就可以,结构如图