aspose-words、itextpdf完美解决java将word、excel、ppt、图片转换为pdf文件

我是傲骄鹿先生,沉淀、学习、分享、成长。

如果你觉得文章内容还可以的话,希望不吝您的「一键三连」,文章里面有不足的地方希望各位在评论区补充疑惑、见解以及面试中遇到的奇葩问法

面对日常开发过程中,将各种文件转换为pdf文件的问题,总是让人头疼,这次终于完美解决了!

最好的效果无非就是在不限制文件大小、保持文件格式的情况下将文件转换为pdf格式文件,而且转换完成的文件不带水印,这样的效果应该可以满足很多需求了,之前在遇到这个问题的时候是使用spire.doc实现的,但效果很不好,每一页都是带水印的。下面将这是的方法展示给大家供大家参考。

一、集成aspose-words

实现文档转换为pdf文件需要的包是aspose-words-15.8.0,如果大家找不到包可以私信我,这里就不做链接了。

1、集成aspose-words-15.8.0

因为项目中使用的是阿里云的maven仓库,不能进行导包,就需要手动的将包导入到项目中。如图所示,将包放入到项目中。

包的位置是与src并列的位置,然后在pom文件中进行配置:

除了上面手动导入的包之外,还有其他用的包,在pom文件中添加即可。

        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi</artifactId>
            <version>4.1.2</version>
        </dependency>

        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-ooxml</artifactId>
            <version>4.1.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-scratchpad</artifactId>
            <version>4.1.2</version>
        </dependency>

        <dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itextpdf</artifactId>
            <version>5.4.3</version>
        </dependency>

        <dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itext-asian</artifactId>
            <version>5.2.0</version>
        </dependency>

        <dependency>
            <groupId>org.docx4j</groupId>
            <artifactId>docx4j</artifactId>
            <version>3.2.2</version>
        </dependency>


        <!-- 下面的依赖是为了报其他错误的 -->
        <dependency>
            <groupId>org.apache.xmlbeans</groupId>
            <artifactId>xmlbeans</artifactId>
            <version>5.0.3</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-ooxml-schemas</artifactId>
            <version>4.1.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-compress</artifactId>
            <version>1.19</version>
        </dependency>
        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-collections4</artifactId>
            <version>4.1</version>
        </dependency>

        <dependency>
            <groupId>com.zaxxer</groupId>
            <artifactId>SparseBitSet</artifactId>
            <version>1.2</version>
        </dependency>


        <!-- 修改com.aspose.cells专用包 -->
        <dependency>
            <groupId>org.javassist</groupId>
            <artifactId>javassist</artifactId>
            <version>3.26.0-GA</version>
        </dependency>

二、编写工具类

package com.dtech.common.utils.file;

import com.aspose.words.License;
import com.aspose.words.SaveFormat;
import com.itextpdf.text.Document;
import com.itextpdf.text.Image;
import com.itextpdf.text.*;
import com.itextpdf.text.pdf.*;
import org.apache.poi.hslf.usermodel.*;
import org.apache.poi.xslf.usermodel.*;

import java.awt.*;
import java.awt.Font;
import java.awt.image.BufferedImage;
import java.io.*;
import java.util.List;


/**
 * java将word、excel、ppt、图片转换为pdf文件
 */
public class PdfConverUtil {
    /**
     * @param inputStream  源文件输入流
     * @param outputStream pdf文件输出流
     **/
    public static boolean imgToPdf(InputStream inputStream, OutputStream outputStream) {

        Document document = null;
        try {
            // 创建文档,设置PDF页面的大小 A2-A9, 个人觉得A3最合适
            document = new Document(PageSize.A3, 20, 20, 20, 20);
            // 新建pdf文档,具体逻辑看.getInstance方法
            PdfWriter.getInstance(document, outputStream);
            document.open();
            document.newPage();
            // 将文件流转换为字节流,便于格式转换
            BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);
            ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
            byte[] bytes = new byte[1024];
            int length = 0 ;
            while (-1 != (length = bufferedInputStream.read(bytes))) {
                byteArrayOutputStream.write(bytes, 0, length);
            }
            // 处理img图片
            Image image = Image.getInstance(byteArrayOutputStream.toByteArray());
            float height = image.getHeight();
            float width = image.getWidth();
            float percent = 0.0f;
            // 设置像素或者长宽高,将会影响图片的清晰度,因为只是对图片放大或缩小
            if (height > width) {
                // A4 - A9
                percent = PageSize.A4.getHeight() / height * 100;
            } else {
                percent = PageSize.A4.getWidth() / width * 100;
            }
            image.setAlignment(Image.MIDDLE);
            image.scalePercent(percent);
            // 将图片放入文档中,完成pdf转换
            document.add(image);
//            System.out.println("image转换完毕");
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        } finally {
            try {
                if (document != null) {
                    document.close();
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        return true;
    }

    /**
     * @param inputStream  源文件输入流
     * @param outputStream pdf文件输出流
     **/
    public static boolean wordTopdfByAspose(InputStream inputStream, OutputStream outputStream) {
        // 验证License 若不验证则转化出的pdf文档会有水印产生
        if (!getLicense()) {
            return false;
        }
        try {
            // 将源文件保存在com.aspose.words.Document中,具体的转换格式依靠里面的save方法
            com.aspose.words.Document doc = new com.aspose.words.Document(inputStream);

            // 全面支持DOC, DOCX, OOXML, RTF HTML, OpenDocument, PDF,EPUB, XPS, SWF 相互转换
            doc.save(outputStream, SaveFormat.PDF);
//            System.out.println("word转换完毕");
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }finally {
            if (outputStream != null) {
                try {
                    outputStream.flush();
                    outputStream.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
        return true;

    }

    // 官方文档的要求 无需理会
    public static boolean getLicense() {
        boolean result = false;
        try {
            String s = "<License><Data><Products><Product>Aspose.Total for Java</Product><Product>Aspose.Words for Java</Product></Products><EditionType>Enterprise</EditionType><SubscriptionExpiry>20991231</SubscriptionExpiry><LicenseExpiry>20991231</LicenseExpiry><SerialNumber>8bfe198c-7f0c-4ef8-8ff0-acc3237bf0d7</SerialNumber></Data><Signature>sNLLKGMUdF0r8O1kKilWAGdgfs2BvJb/2Xp8p5iuDVfZXmhppo+d0Ran1P9TKdjV4ABwAgKXxJ3jcQTqE/2IRfqwnPf8itN8aFZlV3TJPYeD3yWE7IT55Gz6EijUpC7aKeoohTb4w2fpox58wWoF3SNp6sK6jDfiAUGEHYJ9pjU=</Signature></License>";
            ByteArrayInputStream is = new ByteArrayInputStream(s.getBytes());
            License aposeLic = new License();
            aposeLic.setLicense(is);
            result = true;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return result;
    }

    /**
     * @param inputStream  源文件输入流
     * @param outputStream pdf文件输出流
     **/
    public static boolean excelToPdf(InputStream inputStream, OutputStream outputStream) {
        // 验证License 若不验证则转化出的pdf文档会有水印产生
        if (!getExeclLicense()) {
            return false;
        }
        try {
            com.aspose.cells.Workbook wb = new com.aspose.cells.Workbook(inputStream);// 原始excel路径
            com.aspose.cells.PdfSaveOptions pdfSaveOptions = new com.aspose.cells.PdfSaveOptions();
            pdfSaveOptions.setOnePagePerSheet(false);

            int[] autoDrawSheets={3};
            //当excel中对应的sheet页宽度太大时,在PDF中会拆断并分页。此处等比缩放。
            autoDraw(wb,autoDrawSheets);
            int[] showSheets={0};
            //隐藏workbook中不需要的sheet页。
            printSheetPage(wb,showSheets);
            wb.save(outputStream, pdfSaveOptions);
            outputStream.flush();
            outputStream.close();
            System.out.println("excel转换完毕");
        } catch (IOException e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return true;
    }


    /**
     * 设置打印的sheet 自动拉伸比例
     * @param wb
     * @param page 自动拉伸的页的sheet数组
     */
    public static void autoDraw(com.aspose.cells.Workbook wb,int[] page){
        if(null!=page&&page.length>0){
            for (int i = 0; i < page.length; i++) {
                wb.getWorksheets().get(i).getHorizontalPageBreaks().clear();
                wb.getWorksheets().get(i).getVerticalPageBreaks().clear();
            }
        }
    }

    /**
     * 隐藏workbook中不需要的sheet页。
     *
     * @param wb
     * @param page 显示页的sheet数组
     */
    public static void printSheetPage(com.aspose.cells.Workbook wb, int[] page) {
        for (int i = 1; i < wb.getWorksheets().getCount(); i++) {
            wb.getWorksheets().get(i).setVisible(false);
        }
        if (null == page || page.length == 0) {
            wb.getWorksheets().get(0).setVisible(true);
        } else {
            for (int i = 0; i < page.length; i++) {
                wb.getWorksheets().get(i).setVisible(true);
            }
        }
    }

    public static boolean getExeclLicense() {
        boolean result = false;
        try {
            String s = "<License><Data><Products><Product>Aspose.Total for Java</Product><Product>Aspose.Words for Java</Product></Products><EditionType>Enterprise</EditionType><SubscriptionExpiry>20991231</SubscriptionExpiry><LicenseExpiry>20991231</LicenseExpiry><SerialNumber>8bfe198c-7f0c-4ef8-8ff0-acc3237bf0d7</SerialNumber></Data><Signature>sNLLKGMUdF0r8O1kKilWAGdgfs2BvJb/2Xp8p5iuDVfZXmhppo+d0Ran1P9TKdjV4ABwAgKXxJ3jcQTqE/2IRfqwnPf8itN8aFZlV3TJPYeD3yWE7IT55Gz6EijUpC7aKeoohTb4w2fpox58wWoF3SNp6sK6jDfiAUGEHYJ9pjU=</Signature></License>";
            ByteArrayInputStream is = new ByteArrayInputStream(s.getBytes());
            com.aspose.cells.License aposeLic = new com.aspose.cells.License();
            aposeLic.setLicense(is);
            result = true;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return result;
    }

    /**
     * pptToPdf
     * @param inputStream
     * @param outputStream
     * @return
     */
    public static boolean pptToPdf(InputStream inputStream, OutputStream outputStream) {
        Document document = null;
        HSLFSlideShow hslfSlideShow = null;
        PdfWriter pdfWriter = null;

        try {
            hslfSlideShow = new HSLFSlideShow(inputStream);
            // 获取ppt文件页面
            Dimension dimension = hslfSlideShow.getPageSize();
            document = new Document();
            // pdfWriter实例
            pdfWriter = PdfWriter.getInstance(document, outputStream);
            document.open();
            PdfPTable pdfPTable = new PdfPTable(1);
            List<HSLFSlide> hslfSlideList = hslfSlideShow.getSlides();
            for (int i=0; i < hslfSlideList.size(); i++) {
                HSLFSlide hslfSlide = hslfSlideList.get(i);
                // 设置字体, 解决中文乱码
                for (HSLFShape shape : hslfSlide.getShapes()) {
                    HSLFTextShape textShape = (HSLFTextShape) shape;

                    for (HSLFTextParagraph textParagraph : textShape.getTextParagraphs()) {
                        for (HSLFTextRun textRun : textParagraph.getTextRuns()) {
                            textRun.setFontFamily("宋体");
                        }
                    }
                }
                BufferedImage bufferedImage = new BufferedImage((int)dimension.getWidth(), (int)dimension.getHeight(), BufferedImage.TYPE_INT_RGB);
                Graphics2D graphics2d = bufferedImage.createGraphics();
                graphics2d.setPaint(Color.white);
                graphics2d.setFont(new Font("宋体", Font.PLAIN, 12));
                hslfSlide.draw(graphics2d);
                graphics2d.dispose();

                Image image = Image.getInstance(bufferedImage, null);
                image.scalePercent(50f);
                // 写入单元格
                pdfPTable.addCell(new PdfPCell(image, true));
                document.add(image);
            }
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        } finally {
            if (document != null) {
                document.close();
            }
            if (pdfWriter != null) {
                pdfWriter.close();
            }
        }
//        System.out.println("ppt转换完毕");
        return true;
    }

    /**
     *  pptxToPdf
     * @param inputStream
     * @param outputStream
     * @return
     */
    public static boolean pptxToPdf(InputStream inputStream, OutputStream outputStream) {
        Document document = null;
        XMLSlideShow slideShow = null;
        PdfWriter pdfWriter = null;
        try {

            slideShow = new XMLSlideShow(inputStream);
            Dimension dimension = slideShow.getPageSize();
            document = new Document();
            pdfWriter = PdfWriter.getInstance(document, outputStream);
            document.open();
            PdfPTable pdfPTable = new PdfPTable(1);
            List<XSLFSlide> slideList = slideShow.getSlides();
            for (int i = 0, row = slideList.size(); i < row; i++) {
                XSLFSlide slide = slideList.get(i);
                // 设置字体, 解决中文乱码
                for (XSLFShape shape : slide.getShapes()) {
                    XSLFTextShape textShape = (XSLFTextShape) shape;
                    for (XSLFTextParagraph textParagraph : textShape.getTextParagraphs()) {
                        for (XSLFTextRun textRun : textParagraph.getTextRuns()) {
                            textRun.setFontFamily("宋体");
                        }
                    }
                }
                BufferedImage bufferedImage = new BufferedImage((int)dimension.getWidth(), (int)dimension.getHeight(), BufferedImage.TYPE_INT_RGB);
                Graphics2D graphics2d = bufferedImage.createGraphics();
                graphics2d.setPaint(Color.white);
                graphics2d.setFont(new Font("宋体", Font.PLAIN, 12));
                slide.draw(graphics2d);
                graphics2d.dispose();
                Image image = Image.getInstance(bufferedImage, null);
                image.scalePercent(50f);

                // 写入单元格
                pdfPTable.addCell(new PdfPCell(image, true));
                document.add(image);
            }
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        } finally {
            if (document != null) {
                document.close();
            }
            if (pdfWriter != null) {
                pdfWriter.close();
            }
        }
        System.out.println("pptx转换完毕");
        return true;
    }
}

 三、使用工具类进行文件转换

完成工具类编写就可以进行文件转换了,这里根据业务,将word文件进行上传服务器,然后在将服务器的word文件转换为pdf文件,访问端即可进行pdf文件预览了。

续:将代码打包上传至服务器后,转换完成的pdf文件是乱码

在window下没有问题但是在linux下有问题,说明不是代码或者输入输出流编码的问题,原因是两个平台环境的问题。说明linux环境中缺少相应的字体以供使用,可能会导致导出的文件字体乱码,或者更新域错乱问题。解决办法如下:更新字体

1、在linux环境下安装win字体,将win机器的C:\Windows\Fonts目录下的全部文件拷贝到linux服务器字体安装目录下,然后执行以下命令更新字体缓存。

2、linux服务器字体文件是在/usr/share/fonts文件夹下的,在fonts文件夹下新建一个文件夹chinese,然后把window环境中的字体上传到服务器中

3、执行命令,让字体生效

cd /usr/share/fonts 
sudo fc-cache -fv

 4、修改代码,设置字体

系列文章持续更新,微信搜一搜「傲骄鹿先生 」,回复【面试】有准备的一线大厂面试资料。

文章出处登录后可见!

已经登录?立即刷新

共计人评分,平均

到目前为止还没有投票!成为第一位评论此文章。

(0)
社会演员多的头像社会演员多普通用户
上一篇 2023年12月23日
下一篇 2023年12月23日

相关推荐

此站出售,如需请站内私信或者邮箱!