docx4j转换pdf样式问题~Java Libreoffice转换pdf

背景

本篇文章主要是介绍我在使用docx4j过程中遇到的问题,并最终如何通过Libreoffice来实现pdf的转换。

问题

在使用docx4j转换pdf过程中发现word文档中表格、加粗样式无法实现,国内、国外都找了一遍也没找到解决办法,真实把人急坏了。如果有同学通过docx4j解决了下方问题的可以留言分享。
docx4j转换pdf主要出现的问题:

  1. 表格边框显示异常,无法跟word文档中保持一致
  2. word文档字体加粗,无法展示

解决方法

在花了好几天时间,无法解决docx4j转pdf样式问题后,决定更换转换方案,于是在网上查找其他pdf转换方案,发现Java生态中开源的三方包对word转pdf样式偏差都很大,商用版本偏差小但是不考虑。针对这种情况,决定更换思路,采用非依赖包方式实现,按照这个思路,进行网上搜索,果真发现可以通过调用wps等三方office软件来实现,沿着这个路径找到了开源的【Libreoffice】,使用Java,lang包下的【Runtime】类,执行命令行命令,实现pdf转换,通过这种方式转换后,pdf样式保持了与word文档一样的样式。

使用【Libreoffice】转换pdf需要先安装该软件。官网 Windows、Linux都有对应版本。安装后建议配置环境变量。如果不配置,则需要在执行命令行时指定全路径。具体安装步骤可以网上查找。

下面是,Java代码中,通过【Libreoffice】实现word转pdf代码:

    /**
     *  通过libreoffice 转换word文档为pdf
     * @param exportWordFile        word文档
     * @param exportPdfFile          pdf文档
     */
    public static void generateClausesPdf(File exportWordFile, File exportPdfFile) throws Exception {
        String path = exportPdfFile.getAbsolutePath();
        path = path.substring(0,path.lastIndexOf(File.separator));
        try {
            String command = String.format("soffice --headless --convert-to pdf  --outdir  %s %s", path, exportWordFile.getAbsolutePath());
            log.info("libreoffice word转pdf  command命令行:{},pdf绝对路径:{}",command,exportPdfFile.getAbsolutePath());
            String redirectError = executeCommand(command);
            if (StringUtil.isNotBlank(redirectError) || redirectError.contains("writer_pdf_Export")) {
                log.error("libreoffice word转pdf失败,失败原因:{}", redirectError);
                throw new RuntimeException("libreoffice word转pdf失败,失败原因:" + redirectError);
            }
            log.info("libreoffice word转pdf成功:::{}",redirectError);
        } catch (Exception e) {
            log.error("libreoffice word转pdf异常,异常信息,::: ",e);
            throw e;
        }

    }
    /**
     *  执行linux或windows命令
     * @param command   命令
     * @return  命令行执行结果
     * @throws IOException  io异常
     * @throws InterruptedException 异常
     */
    public static String executeCommand(String command) throws IOException, InterruptedException {
        StringBuilder output = new StringBuilder();
        Process p;
        InputStreamReader inputStreamReader = null;
        BufferedReader reader = null;
        try {
            p = Runtime.getRuntime().exec(command);
            // 等待命令执行完成
            p.waitFor();
            inputStreamReader = new InputStreamReader(p.getErrorStream(), StandardCharsets.UTF_8);
            reader = new BufferedReader(inputStreamReader);
            String line = "";

            // 处理错误输出
            while ((line = reader.readLine()) != null) {
                output.append(line).append("\n");
            }
        }  finally {
            IOUtils.closeQuietly(reader);
            IOUtils.closeQuietly(inputStreamReader);
        }
        return output.toString();
    }


posted @   Easn°  阅读(419)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· AI技术革命,工作效率10个最佳AI工具
点击右上角即可分享
微信分享提示