Java使用PDFBox实现调整PDF每页格式

 更新时间:2024年03月24日 08:08:33   作者:zoeil  
这篇文章主要为大家详细介绍了Java如何使用PDFBox实现调整PDF每页格式,文中的示例代码讲解详细,具有一定的借鉴价值,有需要的小伙伴可以参考下

maven依赖,这里使用的是pdfbox的2.0.30版本

        <dependency>
            <groupId>org.apache.pdfbox</groupId>
            <artifactId>pdfbox</artifactId>
            <version>2.0.30</version>
        </dependency>
 
        <dependency>
            <groupId>org.apache.pdfbox</groupId>
            <artifactId>pdfbox-tools</artifactId>
            <version>2.0.30</version>
        </dependency>

一、内容没有图片

如果内容没有图片,可以直接将纸张改为A4大小

import java.io.File;
import java.io.IOException;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
 
public class AdjustPdfPageWidthToA4 {
    public static void main(String[] args) {
        // 输入的PDF文件路径
        String inputFilePath = "input.pdf";
        // 输出的PDF文件路径
        String outputFilePath = "output.pdf";
        
        try {
            // 加载PDF文件
            PDDocument document = PDDocument.load(new File(inputFilePath));
            
            // 遍历每一页
            for (PDPage page : document.getPages()) {
                // 将页面宽度调整为A4尺寸
                page.setMediaBox(PDRectangle.A4);
            }
            
            // 保存修改后的PDF文件
            document.save(outputFilePath);
            document.close();
            
            System.out.println("PDF页面宽度已调整为A4尺寸,并保存为新的PDF文件。");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

但是如果有图片的话,会出现图片被截断,显示不全的情况出现,所以我们需要对图片元素按比例缩放

二、内容有图片

首先要对页面内容进行判断,如果页面是图片的话,对图片进行比例缩放,比如A4,就缩放到可以放进A4

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
 
import org.apache.pdfbox.cos.COSName;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.PDResources;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
import org.apache.pdfbox.pdmodel.graphics.PDXObject;
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject;
import org.apache.pdfbox.text.PDFTextStripper;
 
import javax.imageio.ImageIO;
 
/**
 * @author zjy
 * @describe 调整PDF每页为A4格式
 */
public class AdjustPdfPageWidthToA4Util {
    static String inputFilePath = "C:\\xxx\\xxx\\xx.pdf";
    // 输出的PDF文件路径
    static String outputFilePath = "D:\\result.pdf";
 
    public static void main(String[] args) {
 
        try {
            // 加载PDF文件
            PDDocument document = PDDocument.load(new File(inputFilePath));
 
            // 遍历每一页
            int totalPages = document.getNumberOfPages();
 
            for (int i = 0; i < totalPages; i++) {
                // 获取当前Page页面
                PDPage page = document.getPage(i);
                // 获取对应页面的资源对象
                PDResources resources = page.getResources();
                // 遍历当前页面所有内容,找出图片对象
                for (COSName cosName : resources.getXObjectNames()) {
                    PDXObject pdxObject = resources.getXObject(cosName);
                    // 判断是不是图片对象
                    if (pdxObject instanceof PDImageXObject) {
                        // 获取图片对象
                        PDImageXObject pdxObject1 = (PDImageXObject) pdxObject;
                        BufferedImage image = pdxObject1.getImage();
                        // 4、创建页面内容流,指定操作哪个文档中的哪个页面
                        PDPageContentStream stream = new PDPageContentStream(document, page);
                        float[] imageWH = getImageWH(image, PDRectangle.A4);
                        stream.drawImage(pdxObject1, imageWH[0], imageWH[1], imageWH[2], imageWH[3]); // 绘制图片到PDF页面里面
                        stream.close(); // 关闭页面内容流
                        page.setMediaBox(PDRectangle.A4);
 
                    } else {
                        page.setMediaBox(PDRectangle.A4);
                    }
                }
 
            }
 
            // 保存修改后的PDF文件
            document.save(outputFilePath);
            document.close();
 
            System.out.println("PDF页面宽度已调整为A4尺寸,并保存为新的PDF文件。");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
 
    /**
     * 获取图片的宽度、高度,单位是【pt】
     *
     * @param box PDF文档页面矩形区域对象,可以获取到矩形区域的宽高
     * @return 返回缩放之后的图片宽高
     */
    public static float[] getImageWH(BufferedImage img, PDRectangle box) {
        try {
            // px 转换成 pt 单位
            float xAxis;
            float yAxis;
            int w = img.getWidth();
            int h = img.getHeight();
            float width = (float) (w * 3.0 / 4); // 这里是因为 1pt = 3/4 px,pt和px单位转换
            float height = (float) (h * 3.0 / 4);
            float pw = box.getWidth() - 60; // 设置图片与文档边缘的空白间距
            float ph = box.getHeight() - 60; // 设置图片与文档边缘的空白间距
            if (width > pw) {
                float scale = pw / width;  // 缩放比列
                width = pw; // 宽度等于页面宽度
                height = height * scale; // 高度自动缩放
            } else {
                float scale = ph / height;  // 缩放比列
                height = ph; // 高度等于页面高度
                width = width * scale;  // 宽度自动缩放
            }
            // 计算图片在X、Y轴上的显示位置
            xAxis = (box.getWidth() - width) / 2; // X轴居中对齐
//            yAxis = box.getHeight() - height - 10; // 距离页面顶部10个pt
            yAxis = (box.getHeight() - height) / 2; // Y轴垂直居中对齐
            return new float[]{xAxis, yAxis, width, height};
        } catch (Exception e) {
            e.printStackTrace();
        }
        return new float[]{0, 0, 0, 0};
    }
}

运行完如下图所示,图片缩小至能放入A4,放在正中间

三、改进

上面的代码是将图片等比例缩小到A4能够放得下,也就是上下或者左右可能有很大的空白,图片比较小,难以看清,因此改进

import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
 
import org.apache.pdfbox.cos.COSName;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.PDResources;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
import org.apache.pdfbox.pdmodel.graphics.PDXObject;
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject;
import org.apache.pdfbox.text.PDFTextStripper;
 
import javax.imageio.ImageIO;
 
/**
 * @author zjy
 * @describe 调整PDF每页为A4格式
 */
public class AdjustPdfPageWidthToA4Util {
    static String inputFilePath = "C:\\xxx\\xxx\\xx.pdf";
    // 输出的PDF文件路径
    static String outputFilePath = "D:\\result.pdf";
 
    public static void main(String[] args) {
 
        try {
            // 加载PDF文件
            PDDocument document = PDDocument.load(new File(inputFilePath));
 
            // 遍历每一页
            int totalPages = document.getNumberOfPages();
 
            for (int i = 0; i < totalPages; i++) {
                // 获取当前Page页面
                PDPage page = document.getPage(i);
                // 获取对应页面的资源对象
                PDResources resources = page.getResources();
                // 遍历当前页面所有内容,找出图片对象
                for (COSName cosName : resources.getXObjectNames()) {
                    PDXObject pdxObject = resources.getXObject(cosName);
                    // 判断是不是图片对象
                    if (pdxObject instanceof PDImageXObject) {
                        // 获取图片对象
                        PDImageXObject pdxObject1 = (PDImageXObject) pdxObject;
                        BufferedImage image = pdxObject1.getImage();
                        // 4、创建页面内容流,指定操作哪个文档中的哪个页面
                        PDPageContentStream stream = new PDPageContentStream(document, page);
                        float[] imageWH = getImageWH(image, PDRectangle.A4);
                        stream.drawImage(pdxObject1, 0, 0, imageWH[0], imageWH[1]); // 绘制图片到PDF页面里面
                        stream.close(); // 关闭页面内容流
//                        page.setMediaBox(PDRectangle.A4);
                        page.setMediaBox(new PDRectangle(imageWH[0], imageWH[1]));
 
                    } else {
                        page.setMediaBox(PDRectangle.A4);
                    }
                }
 
            }
 
            // 保存修改后的PDF文件
            document.save(outputFilePath);
            document.close();
 
            System.out.println("PDF页面宽度已调整为A4尺寸,并保存为新的PDF文件。");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
 
    /**
     * 获取图片的宽度、高度,单位是【pt】
     *
     * @param box PDF文档页面矩形区域对象,可以获取到矩形区域的宽高
     * @return 返回缩放之后的图片宽高
     */
    public static float[] getImageWH(BufferedImage img, PDRectangle box) {
        try {
            // px 转换成 pt 单位
            float xAxis;
            float yAxis;
            int w = img.getWidth();
            int h = img.getHeight();
            float width = (float) (w * 3.0 / 4); // 这里是因为 1pt = 3/4 px,pt和px单位转换
            float height = (float) (h * 3.0 / 4);
            float pw = box.getWidth() ;
            float ph = box.getHeight() ;
            if (width > pw) {
                float scale = pw / width;  // 缩放比列
                width = pw; // 宽度等于页面宽度
                height = height * scale; // 高度自动缩放
            } else {
                float scale = ph / height;  // 缩放比列
                height = ph; // 高度等于页面高度
                width = width * scale;  // 宽度自动缩放
            }
            // 计算图片在X、Y轴上的显示位置
            return new float[]{width, height};
        } catch (Exception e) {
            e.printStackTrace();
        }
        return new float[]{0, 0};
    }
}

这样子图片的宽度是A4的,长度就是原图片的长度了

以上内容参考:Java使用PDFBox实现操作PDF文档

到此这篇关于Java使用PDFBox实现调整PDF每页格式的文章就介绍到这了,更多相关Java PDFBox调整PDF格式内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Java使用策略模式解决商场促销商品问题示例

    Java使用策略模式解决商场促销商品问题示例

    这篇文章主要介绍了Java使用策略模式解决商场促销商品问题,简单描述了策略模式的概念、原理,并结合实例形式分析了Java基于策略模式解决商品促销问题的相关操作技巧,需要的朋友可以参考下
    2018-05-05
  • Spring Security 自动踢掉前一个登录用户的实现代码

    Spring Security 自动踢掉前一个登录用户的实现代码

    这篇文章主要介绍了Spring Security 自动踢掉前一个登录用户的实现代码,本文通过实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-05-05
  • 讲解Java中的基础类库和语言包的使用

    讲解Java中的基础类库和语言包的使用

    这篇文章主要介绍了Java中的基础类库和语言包的使用,是Java入门学习中的基础知识,需要的朋友可以参考下
    2015-09-09
  • SpringBoot详解实现自定义异常处理页面方法

    SpringBoot详解实现自定义异常处理页面方法

    SpringBoot是Spring全家桶的成员之一,是一种整合Spring技术栈的方式(或者说是框架),同时也是简化Spring的一种快速开发的脚手架
    2022-06-06
  • Spring中的@Lazy注解用法实例

    Spring中的@Lazy注解用法实例

    这篇文章主要介绍了Spring中的@Lazy注解用法实例,在Spring中常用于单实例Bean对象的创建和使用,单实例Bean懒加载容器启动后不创建对象,而是在第一次获取Bean创建对象时,初始化,需要的朋友可以参考下
    2023-08-08
  • SpringBoot实现动态插拔的AOP的完整案例

    SpringBoot实现动态插拔的AOP的完整案例

    在现代软件开发中,面向切面编程(AOP) 是一种非常重要的技术,能够有效实现日志记录、安全控制、性能监控等横切关注点的分离,在传统的 AOP 实现中,切面逻辑往往是固定的,难以动态调整,本文将详细探讨如何利用 Spring Boot 实现动态插拔的 AOP,需要的朋友可以参考下
    2025-01-01
  • Java简单实现两个Word文档的差异比对

    Java简单实现两个Word文档的差异比对

    在文档管理与版本控制场景中,比较两个 Word 文档之间的差异是一个常见需求,本文将介绍如何使用 Java 语言,借助 Spire.Doc for Java 库,实现两个 Word 文档的内容比较功能,希望对大家有所帮助
    2026-05-05
  • SpringBoot3.x集成nacos并实现多环境配置的操作步骤

    SpringBoot3.x集成nacos并实现多环境配置的操作步骤

    本文详细介绍了如何在Springboot3.x中集成Nacos2.x版本,包括nacos的安装、配置更改,以及在集成过程中遇到的问题,如端口设置、依赖版本调整等,文中通过图文介绍的非常详细,需要的朋友可以参考下
    2024-10-10
  • Java中String性能优化

    Java中String性能优化

    本文给大家分享的是如何在java中对String进行性能优化,使用String的时候需要有哪些注意事项呢,这就是今天我们要给大家总结分析的,有需要的小伙伴可以参考下。
    2015-03-03
  • Java压缩文件为ZIP并加密的详细步骤

    Java压缩文件为ZIP并加密的详细步骤

    Zip是一种常用的文件压缩格式,下面这篇文章主要给大家介绍了关于Java压缩文件为ZIP并加密的详细步骤,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2023-11-11

最新评论