You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用pypdf调整PDF页面尺寸后输出文件在Acrobat中显示异常

问题:PDF适配A4尺寸后Adobe Acrobat显示/打印异常

我用以下Python代码将PDF页面调整为适配A4尺寸:

from pypdf import PdfReader, PdfWriter, Transformation, PageObject, PaperSize
from pypdf.generic import RectangleObject

reader = PdfReader("input.pdf")
writer = PdfWriter()
for page in reader.pages:
  

  A4_w = PaperSize.A4.width
  A4_h = PaperSize.A4.height

  # resize page to fit *inside* A4
  h = float(page.mediabox.height)
  w = float(page.mediabox.width)
  scale_factor = min(A4_h/h, A4_w/w)

  transform = Transformation().scale(scale_factor,scale_factor).translate(0, A4_h/2 - h*scale_factor/2)
  page.add_transformation(transform)

  page.cropbox = RectangleObject((0, 0, A4_w, A4_h))

  # merge the pages to fit inside A4

  # prepare A4 blank page
  page_A4 = PageObject.create_blank_page(width = A4_w, height = A4_h)
  page.mediabox = page_A4.mediabox
  page_A4.merge_page(page)

  writer.add_page(page_A4)
writer.write('output.pdf')

该代码对多数文件有效,但部分输入文件处理后出现异常:输出PDF在Adobe Acrobat中打开或打印时,图像缺失、背景颜色异常,首页纯文本仅显示第一行;但在MacOS Preview或Chrome浏览器中显示正常。

涉事输入PDF是通过MacOS Preview混合不同PDF页面并拖入图片制作的,输入文件可被Adobe Acrobat正常读取。请问这是pypdf的bug还是操作有误?如何让输出PDF在Adobe Acrobat及打印机中正常显示?


分析与解决方案

可能原因

  • PDF结构兼容性差异:MacOS Preview生成的PDF可能包含图层、透明对象或非标准内容流等结构,pypdf转换时未完全兼容这些Adobe Acrobat严格遵循的格式规范,导致渲染异常。
  • 页面边界设置冲突:代码中先后设置cropbox和修改mediabox的操作,可能让Acrobat对页面边界的解析逻辑混乱,进而影响内容渲染。
  • 变换与合并的优先级问题:原页面添加变换后直接合并到空白页,Acrobat可能未正确将变换应用到所有嵌套内容(如图片、文本块)。

修复方案

方案1:调整页面边界与变换的处理逻辑

移除单独设置cropbox的步骤,通过变换和媒体盒统一控制页面尺寸,避免边界冲突,同时补充水平居中逻辑:

from pypdf import PdfReader, PdfWriter, Transformation, PageObject, PaperSize

reader = PdfReader("input.pdf")
writer = PdfWriter()
A4_w = PaperSize.A4.width
A4_h = PaperSize.A4.height

for page in reader.pages:
    h = float(page.mediabox.height)
    w = float(page.mediabox.width)
    scale_factor = min(A4_h/h, A4_w/w)
    
    # 计算水平+垂直居中偏移
    offset_x = (A4_w - w * scale_factor) / 2
    offset_y = (A4_h - h * scale_factor) / 2
    
    # 应用缩放和平移变换
    transform = Transformation().scale(scale_factor, scale_factor).translate(offset_x, offset_y)
    page.add_transformation(transform)
    
    # 创建空白A4页并合并变换后的页面
    page_A4 = PageObject.create_blank_page(width=A4_w, height=A4_h)
    page_A4.merge_page(page)
    
    writer.add_page(page_A4)

writer.write('output.pdf')

方案2:禁用pypdf的压缩优化

如果方案1无效,尝试在写入PDF时禁用压缩,保留原始内容结构,避免Acrobat解析出错:

# 在writer.write前添加以下设置
writer.set_compression_mode(False)
writer.write('output.pdf')

方案3:用Ghostscript标准化输入PDF

先通过Ghostscript将MacOS Preview生成的非标准PDF转为标准化格式,再用pypdf处理:

# 命令行执行,生成标准化后的PDF
gs -sDEVICE=pdfwrite -dCompatibilityLevel=1.7 -dNOPAUSE -dBATCH -sOutputFile=standardized.pdf input.pdf

之后以standardized.pdf作为pypdf的输入文件。

方案4:替换为PyMuPDF(fitz)库处理

若pypdf兼容性问题无法解决,改用对复杂PDF支持更好的PyMuPDF:

import fitz  # PyMuPDF

doc = fitz.open("input.pdf")
output = fitz.open()
A4_rect = fitz.Rect(0, 0, fitz.paper_size("a4")[0], fitz.paper_size("a4")[1])

for page in doc:
    # 创建新A4页面
    new_page = output.new_page(width=A4_rect.width, height=A4_rect.height)
    # 计算缩放比例
    src_rect = page.rect
    scale = min(A4_rect.width / src_rect.width, A4_rect.height / src_rect.height)
    scaled_rect = src_rect * scale
    # 计算居中偏移
    offset = (A4_rect - scaled_rect) / 2
    # 将原页面内容绘制到新A4页
    new_page.show_pdf_page(offset + scaled_rect, doc, page.number)

output.save("output.pdf")
output.close()
doc.close()

内容的提问来源于stack exchange,提问作者Zain Khaishagi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.02 08:10:23