2个word内容合并
package com.meritdata.ddc.common.util;
import org.apache.poi.xwpf.usermodel.*;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
/**
* @author dongxiajun
* @since 2024-11-14 15:15
*/
public class WordMerger {
/**
* 合并两个Word文档,将第二个文件合并到第一个文件中
*
* @param firstFile 第一个文件
* @param secondStream 上传的文件
* @param outputFile 输出文件
* @throws IOException IOException
*/
public static void mergeWordDocuments(String firstFile, InputStream secondStream, String outputFile) throws IOException {
// 使用 try-with-resources 自动关闭资源
try (FileInputStream fis1 = new FileInputStream(firstFile);
FileOutputStream out = new FileOutputStream(outputFile)) {
// 加载第一个文档
XWPFDocument doc1 = new XWPFDocument(fis1);
// 加载第二个文档
XWPFDocument doc2 = new XWPFDocument(secondStream);
// 合并文档
appendDocument(doc1, doc2);
// 保存合并后的文档
doc1.write(out);
}
}
/**
* 合并两个Word文档,将第二个文件合并到第一个文件中
*
* @param firstFile 第一个文件
* @param secondFile 第二个文件
* @param outputFile 输出文件
* @throws IOException IOException
*/
public static void mergeWordDocuments(String firstFile, String secondFile, String outputFile) throws IOException {
// 使用 try-with-resources 自动关闭资源
try (FileInputStream fis1 = new FileInputStream(firstFile);
FileInputStream fis2 = new FileInputStream(secondFile);
FileOutputStream out = new FileOutputStream(outputFile)) {
// 加载第一个文档
XWPFDocument doc1 = new XWPFDocument(fis1);
// 加载第二个文档
XWPFDocument doc2 = new XWPFDocument(fis2);
// 合并文档
appendDocument(doc1, doc2);
// 保存合并后的文档
doc1.write(out);
}
}
public static void appendDocument(XWPFDocument doc1, XWPFDocument doc2) {
// 获取第二个文档的所有部分,保持顺序合并
for (IBodyElement element : doc2.getBodyElements()) {
// 根据元素的类型进行不同的处理
if (element instanceof XWPFParagraph) {
XWPFParagraph paragraph = (XWPFParagraph) element;
XWPFParagraph newParagraph = doc1.createParagraph();
copyParagraph(paragraph, newParagraph);
} else if (element instanceof XWPFTable) {
XWPFTable table = (XWPFTable) element;
XWPFTable newTable = doc1.createTable();
copyTable(table, newTable);
}
}
}
private static void copyParagraph(XWPFParagraph source, XWPFParagraph target) {
// 只复制段落的布局属性(例如对齐、缩进、行距等),但不包括段落样式(避免改变标题级别)
target.getCTP().setPPr(source.getCTP().getPPr());
// 复制对齐方式、缩进、行间距等样式
target.setAlignment(source.getAlignment());
target.setVerticalAlignment(source.getVerticalAlignment());
target.setIndentationLeft(source.getIndentationLeft());
target.setIndentationRight(source.getIndentationRight());
target.setIndentationFirstLine(source.getIndentationFirstLine());
target.setSpacingBefore(source.getSpacingBefore());
target.setSpacingAfter(source.getSpacingAfter());
target.setSpacingBetween(source.getSpacingBetween());
// 复制段落中的每个run
for (XWPFRun run : source.getRuns()) {
XWPFRun newRun = target.createRun();
newRun.setText(run.text());
// 复制格式
newRun.setBold(run.isBold());
newRun.setItalic(run.isItalic());
newRun.setUnderline(run.getUnderline());
newRun.setColor(run.getColor());
newRun.setFontSize(run.getFontSize());
newRun.setFontFamily(run.getFontFamily());
}
if (source.getStyle() != null) {
target.setStyle(source.getStyle());
}
}
// 复制源表格到目标表格,包括其行和单元格的样式和内容
private static void copyTable(XWPFTable source, XWPFTable target) {
// 删除目标表格中的默认创建的第一行,确保从空状态开始复制
target.removeRow(0);
// 遍历源表格的每一行
for (XWPFTableRow sourceRow : source.getRows()) {
// 在目标表格中创建新行
XWPFTableRow newTableRow = target.createRow();
// 复制源行的样式和内容到目标新行
copyTableRow(sourceRow, newTableRow);
}
}
// 将源表格行的样式和内容复制到目标表格行
private static void copyTableRow(XWPFTableRow source, XWPFTableRow target) {
// 复制行的样式属性
target.getCtRow().setTrPr(source.getCtRow().getTrPr());
// 遍历源行的每一个单元格
for (int i = 0; i < source.getTableCells().size(); i++) {
XWPFTableCell sourceCell = source.getCell(i);
XWPFTableCell targetCell;
// 如果目标行的单元格还不够,则创建新单元格
if (i < target.getTableCells().size()) {
targetCell = target.getCell(i);
} else {
targetCell = target.addNewTableCell();
}
String text = source.getCell(0).getText();
if (text.contains("{{$fe")) {
// 复制单元格的样式属性
targetCell.getCTTc().setTcPr(sourceCell.getCTTc().getTcPr());
targetCell.setText(sourceCell.getText());
} else {
// 复制单元格的样式和内容
copyTableCell(sourceCell, targetCell);
}
}
}
// 将源单元格的样式和内容复制到目标单元格
private static void copyTableCell(XWPFTableCell source, XWPFTableCell target) {
// 复制单元格的样式属性
target.getCTTc().setTcPr(source.getCTTc().getTcPr());
// 清除目标单元格的段落
target.getParagraphs().clear();
// 复制每个段落
for (XWPFParagraph sourceParagraph : source.getParagraphs()) {
XWPFParagraph targetParagraph = target.addParagraph();
copyParagraph(sourceParagraph, targetParagraph);
}
}
}