<dependency>
<groupId>fr.opensagres.xdocreport</groupId>
<artifactId>org.apache.poi.xwpf.converter.pdf</artifactId>
<version>1.0.6</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi</artifactId>
<version>3.9</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>3.9</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml-schemas</artifactId>
<version>3.9</version>
</dependency>
<dependency>
<groupId>org.apache.pdfbox</groupId>
<artifactId>pdfbox</artifactId>
<version>2.0.24</version>
<scope>compile</scope>
</dependency>
需要替换的参数格式——【文本】 表格【#表格】
package org.jeecg.common.util.word;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.pdfbox.io.MemoryUsageSetting;
import org.apache.pdfbox.multipdf.PDFMergerUtility;
import org.apache.poi.POIXMLDocument;
import org.apache.poi.xwpf.converter.pdf.PdfConverter;
import org.apache.poi.xwpf.converter.pdf.PdfOptions;
import org.apache.poi.xwpf.usermodel.*;
import java.io.*;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.*;
@Slf4j
public class WordConverUtils {
public static void wordTemplateReplacement(String filePath, String replaceWord,String newFilePath, HashMap<String, Object> map) {
log.info("模板路径:{},生成路径{}",filePath,newFilePath);
//有表格的word文件会增大,导致根据下表替换内容失败,分2次替换
//表格
replaceTable(map, filePath, replaceWord);
//文本
replaceText(map, replaceWord, newFilePath);
}
/**
* 生成word文档替换文本
*/
public static void replaceTable(Map<String, Object> map, String file, String wordPath) {
XWPFDocument document = null;
try {
document = new XWPFDocument(POIXMLDocument.openPackage(file));// 生成word文档并读取模板
Iterator<XWPFTable> it = document.getTablesIterator();
//表格内容替换添加
while (it.hasNext()) {
XWPFTable table = it.next();
int rcount = table.getNumberOfRows();
for (int i = 0; i < rcount; i++) {
XWPFTableRow row = table.getRow(i);
List<XWPFTableCell> cells = row.getTableCells();
for (XWPFTableCell cell : cells) {
for (Map.Entry<String, Object> e : map.entrySet()) {
if (!cell.getText().contains("【#")) {
continue;
}
Object obj = map.get(cell.getText());
if (Objects.isNull(obj)) {
continue;
}
replaceTable(table, i, obj.toString());
}
}
}
}
FileOutputStream fileOutputStream = new FileOutputStream(wordPath);
document.write(fileOutputStream);
fileOutputStream.close();
} catch (Exception e1) {
e1.printStackTrace();
}
}
/**
* 生成word文档,替换表格
*/
public static void replaceText(Map<String, Object> map, String file, String wordPath) {
XWPFDocument document = null;
//添加表格
try {
document = new XWPFDocument(POIXMLDocument.openPackage(file));// 生成word文档并读取模板
Iterator<XWPFTable> it = document.getTablesIterator();
//表格内容替换添加
while (it.hasNext()) {
XWPFTable table = it.next();
int rcount = table.getNumberOfRows();
for (int i = 0; i < rcount; i++) {
XWPFTableRow row = table.getRow(i);
List<XWPFTableCell> cells = row.getTableCells();
for (XWPFTableCell cell : cells) {
for (Map.Entry<String, Object> e : map.entrySet()) {
if (!cell.getText().contains(e.getKey()) || (cell.getText().contains("【#"))){
continue;
}
String text = cell.getText();
String v = String.valueOf(e.getValue());
String newStr = text.replace(e.getKey(), v);
//删除原来的内容
cell.removeParagraph(0);
//重新赋值替换后的内容
cell.setText(newStr);
}
}
}
}
FileOutputStream fileOutputStream = new FileOutputStream(wordPath);
document.write(fileOutputStream);
fileOutputStream.close();
} catch (Exception e1) {
e1.printStackTrace();
}
}
public static void replaceTable(XWPFTable comTable, int i, String str) {
if (StringUtils.isBlank(str)) {
XWPFTableRow row = comTable.getRow(i);
List<XWPFTableCell> tableCells = row.getTableCells();
if(CollectionUtils.isNotEmpty(tableCells)){
tableCells.forEach(item->{item.removeParagraph(0);item.setText(" ");});
}
return;
}
//对象数据
JSONArray objects = JSONArray.parseArray(str);
if (Objects.isNull(objects)) {
return;
}
int size = objects.size() - 1;
for (int a = size; a >= 0; a--) {
//表格对象,创建一行
XWPFTableRow row = comTable.getRow(i);
if (a < size) {
row = comTable.insertNewTableRow(i);
}
Map map = JSONObject.parseObject(objects.get(a).toString(), Map.class);
int b = 0;
for (Object s : map.keySet()) {
if (row.getTableCells().size() == b) {
row.addNewTableCell();
}
row.getTableCells().get(b).removeParagraph(0);
row.getTableCells().get(b).setText(String.valueOf(map.get(s)));
b++;
}
}
}
/**
* word转pdf
* @param inPath
* @param OutPath
* linux 要有对应字体,不然是乱码或不展示
*/
public static void wordTurnPdf(String inPath, String OutPath) {
XWPFDocument document = null;
try (InputStream doc = Files.newInputStream(Paths.get(inPath))) {
document = new XWPFDocument(doc);
} catch (IOException e) {
e.printStackTrace();
}
PdfOptions options = PdfOptions.create();
try (OutputStream out = Files.newOutputStream(Paths.get(OutPath))) {
PdfConverter.getInstance().convert(document, out, options);
} catch (IOException e) {
e.printStackTrace();
}
}
/**
* 合并pdf文档
* @param files
* @param newPdfPath
* @throws IOException
*/
public static void pdfMerge(List<File> files,String newPdfPath){
try {
// pdf合并工具类
PDFMergerUtility mergePdf = new PDFMergerUtility();
for (File f : files) {
if(f.exists() && f.isFile()){
// 循环添加要合并的pdf
mergePdf.addSource(f);
}
}
// 设置合并生成pdf文件名称
mergePdf.setDestinationFileName(newPdfPath);
// 合并pdf
mergePdf.mergeDocuments(MemoryUsageSetting.setupMainMemoryOnly());
new File(newPdfPath);
} catch (IOException e) {
e.printStackTrace();
}
}
/**
*
*
* @param fileName
* @return
* @throws IOException
*/
public static byte[] fileToByteArray(String fileName){
FileChannel fc = null;
byte[] result = null;
try {
fc = new RandomAccessFile(fileName, "r").getChannel();
MappedByteBuffer byteBuffer = fc.map(FileChannel.MapMode.READ_ONLY, 0,
fc.size()).load();
result = new byte[(int) fc.size()];
if (byteBuffer.remaining() > 0) {
byteBuffer.get(result, 0, byteBuffer.remaining());
}
return result;
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
fc.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return result;
}
}