docx4j 的使用

docx4j解析word模板-优快云博客

<dependency>
    <groupId>org.docx4j</groupId>
    <artifactId>docx4j-core</artifactId>
    <version>8.3.9</version>
</dependency>
<dependency>
    <groupId>org.docx4j</groupId>
    <artifactId>docx4j-export-fo</artifactId>
    <version>8.3.9</version>
</dependency>
<dependency>
    <groupId>org.docx4j</groupId>
    <artifactId>docx4j-JAXB-ReferenceImpl</artifactId>
    <version>8.3.9</version>
</dependency>

注意:

docx4j-core 8.3.9 jdk1.8

docx4j-core 11.4.9 jdk11

文本切分

try {

            // 读取.docx文件
            File wordFile = new File("src/main/resources/data/doc/XXXX.docx");
            WordprocessingMLPackage wordMLPackage = WordprocessingMLPackage.load(wordFile);

            // 提取文本
            List<String> paragraphs = new ArrayList<>();
            List<Object> bodyContent = wordMLPackage.getMainDocumentPart().getContent();
            for (Object content : bodyContent) {
                if (content instanceof P) { // 检查是否为段落
                    P paragraph = (P) content;
                    StringBuilder paragraphText = new StringBuilder();
                    for (Object run : paragraph.getContent()) {
                        if (run instanceof org.docx4j.wml.R) { // 检查是否为运行
                            org.docx4j.wml.R runObj = (org.docx4j.wml.R) run;
                            for (Object obj : runObj.getContent()) {
                                if (obj instanceof javax.xml.bind.JAXBElement) {
                                    javax.xml.bind.JAXBElement<?> jaxbElement = (javax.xml.bind.JAXBElement<?>) obj;
                                    if (jaxbElement.getDeclaredType() == org.docx4j.wml.Text.class) {
                                        org.docx4j.wml.Text textObj = (org.docx4j.wml.Text) jaxbElement.getValue();
                                        paragraphText.append(textObj.getValue());
                                    }
                                } else if (obj instanceof org.docx4j.wml.Text) {
                                    org.docx4j.wml.Text textObj = (org.docx4j.wml.Text) obj;
                                    paragraphText.append(textObj.getValue());
                                }
                            }
                        }
                    }
                    String trimmedParagraph = paragraphText.toString().replaceAll("[\\p{Z}\\p{C}\\u00A0]+", "");
                    if (!trimmedParagraph.isEmpty()) {
                        paragraphs.add(trimmedParagraph);
                    }
                }
            }
            String contentStr = String.join("\n", paragraphs);

            System.out.println("content: " + contentStr);

            // 文本分段
            // List<String> sentences = segmentText(content);

            // 向量化
            // List<float[]> vectors = sentences.stream().map(TextToMilvus::getVector).collect(Collectors.toList());
        } catch (Exception e) {
            e.printStackTrace();
        }

### 如何在 docx4j使用 TocGenerator 生成目录 `docx4j` 提供了一个名为 `TocGenerator` 的工具类来帮助开发者自动生成 Word 文档中的目录。以下是关于其基本原理和具体使用的详细介绍。 #### 基本概念 `TocGenerator` 是基于 Word 文档的样式层次结构工作的,它会扫描文档中具有特定样式的段落(如 Heading1, Heading2),并将其作为条目加入到目录中[^1]。 --- #### 实现步骤说明 为了生成目录,需要完成以下几个部分的工作: 1. **创建基础文档** 需要先构建一个包含多个章节标题的基础 `.docx` 文件。这些标题应设置为不同的样式(Heading1, Heading2 等)。这是目录数据源的核心。 2. **调用 TocGenerator 方法** 使用 `org.docx4j.model.structure.TocGenerator` 类的方法来自动生成 TOC(Table of Contents)字段。 3. **更新 TOC 字段** 自动生成后的 TOC 可能不会立即显示正确的内容,因此还需要通过 `WordprocessingMLPackage.updateDocProps()` 或者手动触发刷新功能。 --- #### 示例代码 以下是一个完整的 Java 示例程序,展示如何利用 `docx4j` 和 `TocGenerator` 创建带有目录的 Word 文档。 ```java import org.docx4j.Docx4J; import org.docx4j.jaxb.Context; import org.docx4j.openpackaging.packages.WordprocessingMLPackage; import org.docx4j.openpackaging.parts.WordprocessingML.MainDocumentPart; import org.docx4j.wml.ObjectFactory; import org.docx4j.wml.P; import org.docx4j.wml.R; import org.docx4j.wml.Text; import org.docx4j.model.structure.TocGenerator; public class Docx4jTocExample { public static void main(String[] args) throws Exception { // 初始化一个新的 .docx 包 WordprocessingMLPackage wordMLPackage = WordprocessingMLPackage.createPackage(); MainDocumentPart documentPart = wordMLPackage.getMainDocumentPart(); ObjectFactory factory = Context.getWmlObjectFactory(); // 添加一些带样式的段落到文档中 addStyledParagraph(documentPart, "Heading 1", "Heading1"); addStyledParagraph(documentPart, "Subheading 1.1", "Heading2"); addStyledParagraph(documentPart, "Subheading 1.2", "Heading2"); // 调用 TocGenerator 来生成目录 new TocGenerator(wordMLPackage).createTOC(); // 将最终文档保存至文件 Docx4J.save(wordMLPackage, "output_with_toc.docx", Docx4J.FLAG_SAVE_ZIP_FILE); } private static void addStyledParagraph(MainDocumentPart part, String textContent, String styleId) { P paragraph = new P(); R run = new R(); Text t = new Text(); t.setValue(textContent); run.getContent().add(t); paragraph.getContent().add(run); // 设置段落样式 paragraph.setPPr(part.getObjectFactory().createPPr()); paragraph.getPPr().setPStyle(part.getStyleDefinitionsPart() .getStyles().getStyleById(styleId)); part.addObject(paragraph); } } ``` 此代码片段展示了如何向文档中添加不同级别的标题以及如何调用 `TocGenerator` 自动化生成目录的过程。 --- #### 关键点解析 - **样式的重要性**:只有设置了适当样式的段落才会被识别为 TOC 条目。例如,“Heading1”对应于最高级标题,“Heading2”则表示次级标题。 - **动态更新机制**:虽然 `TocGenerator` 已经完成了初步工作,但在某些情况下可能仍需提醒用户打开实际生成的 Word 文件并通过 Microsoft Office 手动执行一次“Update Field”。 - **错误处理**:如果目标环境中缺少必要的字体资源或者模板定义不清晰,则可能导致异常情况发生;建议提前验证输入参数的有效性。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值