Skip to content

Commit

Permalink
Merge pull request #643 from chinapandaman/PPF-641
Browse files Browse the repository at this point in the history
PPF-641: implement Adobe mode
  • Loading branch information
chinapandaman authored Jun 9, 2024
2 parents 7cc7120 + 30e256d commit c60ffad
Show file tree
Hide file tree
Showing 5 changed files with 64 additions and 3 deletions.
5 changes: 5 additions & 0 deletions PyPDFForm/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,11 @@
Yes = "/Yes"
Off = "/Off"

# For Adobe Acrobat
AcroForm = "/AcroForm"
Root = "/Root"
NeedAppearances = "/NeedAppearances"

# Field flag bits
READ_ONLY = 1 << 0
MULTILINE = 1 << 12
Expand Down
12 changes: 10 additions & 2 deletions PyPDFForm/filler.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,10 @@
from typing import Dict, Tuple, Union, cast

from pypdf import PdfReader, PdfWriter
from pypdf.generic import DictionaryObject
from pypdf.generic import (BooleanObject, DictionaryObject,
NameObject)

from .constants import WIDGET_TYPES, Annots
from .constants import WIDGET_TYPES, AcroForm, Annots, NeedAppearances, Root
from .coordinate import (get_draw_checkbox_radio_coordinates,
get_draw_image_coordinates_resolutions,
get_draw_text_coordinates,
Expand Down Expand Up @@ -164,10 +165,17 @@ def simple_fill(
template: bytes,
widgets: Dict[str, WIDGET_TYPES],
flatten: bool = False,
adobe_mode: bool = False,
) -> bytes:
"""Fills a PDF form in place."""

# pylint: disable=too-many-branches
pdf = PdfReader(stream_to_io(template))
if adobe_mode and AcroForm in pdf.trailer[Root]:
pdf.trailer[Root][AcroForm].update(
{NameObject(NeedAppearances): BooleanObject(True)}
)

out = PdfWriter()
out.append(pdf)

Expand Down
5 changes: 4 additions & 1 deletion PyPDFForm/wrapper.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,10 @@ def fill(
widgets[key].value = value

self.stream = simple_fill(
self.read(), widgets, flatten=kwargs.get("flatten", False)
self.read(),
widgets,
flatten=kwargs.get("flatten", False),
adobe_mode=kwargs.get("adobe_mode", False),
)

return self
Expand Down
Binary file not shown.
45 changes: 45 additions & 0 deletions tests/test_adobe_mode.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
# -*- coding: utf-8 -*-

import os

from PyPDFForm import FormWrapper


def test_fill_sejda_complex(sejda_template_complex, pdf_samples, request):
expected_path = os.path.join(
pdf_samples, "adobe_mode", "paragraph", "sample_filled_sejda_complex.pdf"
)
with open(expected_path, "rb+") as f:
obj = FormWrapper(sejda_template_complex).fill(
{
"checkbox": True,
"radio": 0,
"dropdown_font_auto_left": 0,
"dropdown_font_auto_center": 1,
"dropdown_font_auto_right": 2,
"dropdown_font_ten_left": 0,
"dropdown_font_ten_center": 1,
"dropdown_font_ten_right": 2,
"paragraph_font_auto_left": "paragraph_font_auto_left",
"paragraph_font_auto_center": "paragraph_font_auto_center",
"paragraph_font_auto_right": "paragraph_font_auto_right",
"paragraph_font_ten_left": "paragraph_font_ten_left",
"paragraph_font_ten_center": "paragraph_font_ten_center",
"paragraph_font_ten_right": "paragraph_font_ten_right",
"text__font_auto_left": "test text",
"text_font_auto_center": "test text",
"text_font_auto_right": "test text",
"text_font_ten_left": "text_font_ten_left",
"text_font_ten_center": "text_font_ten_center",
"text_font_ten_right": "text_font_ten_right",
},
adobe_mode=True,
)

request.config.results["expected_path"] = expected_path
request.config.results["stream"] = obj.read()

expected = f.read()

assert len(obj.read()) == len(expected)
assert obj.stream == expected

0 comments on commit c60ffad

Please sign in to comment.