使用 Java 更新 Word 文档中的图表数据-超详细

使用 Java 更新 Word 文档中的图表数据

在日常的工作中,尤其是在数据分析和报告自动化的场景中,可能会遇到需要定期更新 Word 文档中的图表数据的需求。比如,生成数据报告时,我们需要在图表中更新一些动态的数据值。今天,我将展示如何使用 Java 和 Apache POI 库来实现这一功能:自动读取 Word 文件中的图表,提取 Excel 数据源,修改数据并更新图表。

背景

我们要处理的是 Word 文档中的图表,而这些图表的数据源存储在嵌入的 Excel 文件中。通过操作 Excel 数据,我们可以更新图表中的数据,并且确保图表会根据新的数据重新渲染。

本篇文章的目标是:

  • 读取 Word 文件中的图表。
  • 提取和修改图表的数据源(嵌入的 Excel 文件)。
  • 更新图表数据,并将修改后的数据嵌入回 Word 文件中。

依赖库

本项目使用了 Apache POI 作为核心库,它支持读取和操作 Word 文档(.docx 文件)和 Excel 文件(.xlsx 文件)。你需要在项目中添加以下依赖:

xml 复制代码
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml</artifactId>
    <version>5.2.3</version>
</dependency>
<dependency>
    <groupId>org.apache.xmlbeans</groupId>
    <artifactId>xmlbeans</artifactId>
    <version>5.1.1</version>
</dependency>


// 或者 4.0版本

      <groupId>org.apache.poi</groupId>
      <artifactId>poi-ooxml</artifactId>
      <version>4.1.2</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.apache.poi/ooxml-schemas -->
    <dependency>
      <groupId>org.apache.poi</groupId>
      <artifactId>ooxml-schemas</artifactId>
      <version>1.4</version>
    </dependency>

    <dependency>
      <groupId>org.apache.poi</groupId>
      <artifactId>poi</artifactId>
      <version>4.1.2</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.apache.poi/poi-scratchpad -->
    <dependency>
      <groupId>org.apache.poi</groupId>
      <artifactId>poi-scratchpad</artifactId>
      <version>4.1.2</version>
    </dependency>
    <dependency>
      <groupId>org.apache.poi</groupId>
      <artifactId>poi-ooxml-schemas</artifactId>
      <version>4.1.2</version>
    </dependency>

步骤解析

  1. 读取 Word 文件 :

    使用 XWPFDocument 读取 Word 文件并获取其中的图表对象。每个图表都是一个 XWPFChart 对象,其中包含了图表的数据源,即嵌入的 Excel 文件。

  2. 提取 Excel 数据源 :

    从图表中提取嵌入的 Excel 数据源,并将其转化为 XSSFWorkbook 对象。这样我们可以访问 Excel 文件中的工作表,并对其数据进行修改。

  3. 修改 Excel 数据 :

    在修改 Excel 数据时,我们需要根据预设的规则来替换 Excel 单元格中的值。例如,在单元格中,某些值可能是动态的,需要替换为来自其他地方的数据。我们通过字符串查找和替换的方式来完成这一任务。

  4. 更新图表数据 :

    修改 Excel 数据后,我们需要将其更新回图表中。通过操作图表的底层 XML,我们可以更新图表的数据引用,并让图表基于新的数据重新绘制。

  5. 保存并覆盖原文件 :

    最后,我们将修改后的 Word 文件保存,并覆盖原有的文件,以便生成新的报告。

代码实现

以下是实现这个功能的 Java 代码:

java 复制代码
import org.apache.poi.xwpf.usermodel.*;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.apache.xmlbeans.XmlCursor;

import java.io.*;
import java.util.List;
import java.util.HashMap;
import java.util.Map;

public class WordChartUpdater {

    static Map<String,Object> cellValueMap = new HashMap<>();
    static Map<String, Object> tagDataMap = new HashMap<>();
    
    static {
        tagDataMap.put("current_branch_name","测试");
        tagDataMap.put("ZYJGZB_079","测试x");
        tagDataMap.put("ZYJGZB_091","11");
    }

    public static void updateChartInWord(File wordFile, ChartData chartData) throws IOException {
        // 1. 读取 Word 文件
        FileInputStream fis = new FileInputStream(wordFile);
        XWPFDocument document = new XWPFDocument(fis);

        // 2. 获取文档中的所有图表
        List<XWPFChart> charts = document.getCharts();
        if (charts.isEmpty()) {
            System.out.println("No charts found in the Word document.");
            return;
        }

        // 3. 获取图表的数据源
        for (XWPFChart chart : charts) {
            XSSFWorkbook workbook = getChartDataAsWorkbook(chart);
            if (workbook == null || workbook.getNumberOfSheets() == 0) {
                System.out.println("The chart does not have a valid data source.");
                continue;
            }

            // 4. 修改 Excel 数据
            modifyChartData(workbook, chartData);

            // 5. 将修改后的 Excel 数据嵌入到 Word 图表中
            updateChartWithNewData(chart, workbook);
        }

        // 6. 保存更新后的 Word 文件(覆盖原文件)
        FileOutputStream fos = new FileOutputStream(wordFile);
        document.write(fos);
        fos.close();
        fis.close();
    }

    private static XSSFWorkbook getChartDataAsWorkbook(XWPFChart chart) throws IOException {
        try {
            return chart.getWorkbook();
        } catch (InvalidFormatException e) {
            throw new IOException("Failed to extract workbook from chart", e);
        }
    }

    private static void modifyChartData(XSSFWorkbook workbook, ChartData chartData) {
        XSSFSheet sheetAt = workbook.getSheetAt(0);
        for (int i = 0; i < 20; i++) {  // 20列20行数据
            XSSFRow row = sheetAt.getRow(i);
            if (row == null) {
                break;
            }
            for (int j = 0; j < 20; j++) {
                XSSFCell cell = row.getCell(j);
                if (cell == null) {
                    break;
                }
                if (CellType.NUMERIC != cell.getCellType() && cell.getStringCellValue().contains("$")) {
                    String key = cell.getStringCellValue();
                    String substring = key.substring(key.lastIndexOf("$"), key.lastIndexOf("}") + 1);
                    if (tagDataMap.get(substring) != null) {
                        String s = key.replace(substring, (String) tagDataMap.get(substring));
                        cell.setCellValue(s);
                        cellValueMap.put(cell.getAddress().toString(), s);
                    } else {
                        cell.setCellValue(0);
                        cellValueMap.put(cell.getAddress().toString(), 0);
                    }
                }
            }
        }
    }

    private static void updateChartWithNewData(XWPFChart chart, XSSFWorkbook updatedWorkbook) throws IOException {
        // 图表数据更新的逻辑...
        // 评论或者私信即可领取
    }

    public static void main(String[] args) throws IOException {
        // 创建一个示例对象,填充数据
        ChartData chartData = new ChartData("value_079", "Branch A", "value_091");

        // 修改 Word 文件
        File wordFile = new File("D:\\Desktop\\GZRC_ceshi.docx");  // 修改为你的 Word 文件路径
        updateChartInWord(wordFile, chartData);
    }
}

代码详解

  • 读取 Word 文件 :首先,我们使用 XWPFDocument 从 Word 文件中读取数据。

  • 提取 Excel 数据源 :通过 getChartDataAsWorkbook 获取图表数据源,即嵌入在图表中的 Excel 文件。

  • 修改数据 :modifyChartData 方法根据需求修改 Excel 中的单元格数据,使用 tagDataMap 中的数据进行替换。

  • 更新图表 :在 updateChartWithNewData 方法中,我们将修改后的数据更新回图表。

  • 保存更新的 Word 文件 :最后,通过 document.write(fos) 将修改后的文件保存回磁盘。

总结

使用 Apache POI 处理 Word 文件中的图表更新是一项非常有用的技能,尤其是在自动化报告生成的过程中。通过对图表数据源(嵌入的 Excel 文件)进行修改,我们可以实现动态更新图表数据并更新 Word 文档,从而大大提高工作效率。

如果你有任何问题,或者遇到困难,欢迎在评论区留言。希望这篇文章能对你有所帮助!


相关推荐
小羊没烦恼!4 天前
微服务化的基石——持续集成
java·大数据·word·powerpoint·.net
俊昭喜喜里4 天前
java中的继承和多态的区别
java
小羊没烦恼!4 天前
初探性能优化——2个月到4小时的性能提升
java·开发语言·windows·算法·c#
譕痕4 天前
JSONObject与JSONArray封装数据格式区别
java·json
胡写代码4 天前
别再前后端各写一套表单校验了
java·后端
小鱼能吃糖4 天前
缺陷修复总览 · mall电商项目:5类缺陷,1个病根,4个业务域
java·电商
此时不提桶,更待何时4 天前
01-06-A-JVM排查实战详解
java·jvm
伞伞悦读4 天前
【第38期】Python 模块与包详解:import、from、模块搜索路径、包结构和 __init__
开发语言·python
vipxieliang4 天前
ValidX 在 DDD 领域驱动设计中的实践
java·spring boot
C语言小火车4 天前
C/C++ 为什么需要编译器?
开发语言·c++