t-houssian / fillpdf Goto Github PK
View Code? Open in Web Editor NEWA python library to make filling pdfs much easier
License: MIT License
A python library to make filling pdfs much easier
License: MIT License
I have fields for the same thing on different pages, but the program seems to crash when the program tries to read the PDF during the read/write dictionary to PDF command. When I rename one field it works again.
When I do:
fillpdfs.write_fillable_pdf('blankpdf.pdf', 'completed.pdf', data_dict, flatten=False)
I get:
Traceback (most recent call last): File "<string>", line 1, in <module> File "C:\Users\micha\AppData\Roaming\Python\Python38\site-packages\fillpdf\fillpdfs.py", line 211, in write_fillable_pdf key = target['/Parent'][ANNOT_FIELD_KEY][1:-1] + '.' + key TypeError: 'NoneType' object is not subscriptable
and in VS code in the coding window itself during debugging:
Exception has occurred: TypeError 'NoneType' object is not subscriptable File "C:\Users\micha\DANVA2\main_program\testpdfoutput2.py", line 6, in <module> fillpdfs.write_fillable_pdf('blankpdf.pdf', 'completed.pdf', data_dict, flatten=False)
All I have to do is rename one field to have a different name, however, I want multiple fields with the same name! Help!
It didn't work for me when my dictionary contained floats instead of strings:
values_dict = {'field': 7.2}
fillpdfs.write_fillable_pdf(input_filename, output_filename, values_dict)
But if I just wrap all dictionary values in a str()
call then it works.
Hi,
Great work. I am trying to design a PDF form to use with your script. However whenever i try to run the same, i am not able to get some of the fields to show up. Its skipping certain fields e.g name and MRD no. Can you pls help. I have attached both my python file and PDF form for reference.
import fillpdf
from fillpdf import fillpdfs
fillpdfs.get_form_fields(pdf, sort=True, page_number=1)
fillpdfs.print_form_fields(pdf, sort=False, page_number=1)
# data_dict = {
# "name": "Swapnil",
# "mrd": "1234",
# "age": "45",
# "sex": "Female",
# }
fill text2 form fields with text
fillpdfs.write_fillable_pdf(pdf,pdf2, data_dict )
If you want it flattened:
fillpdfs.flatten_pdf(pdf2, 'newflat.pdf')
Running this gives -
Values From Page 1
Values From Page 1
{'Text4': '03-Aug-2022',
'Print': None,
'complaints': '',
'addmed': '5. Enfenac eye drops - 1 drop Two times per day - ',
'Text10': '04-Aug-2022',
'Text11': '06-Aug-2022',
'Text13': '24-Aug-2022',
'Text21': '10-Aug-2022',
'Text22': '11-Aug-2022',
'Text23': '17-Aug-2022',
'Text24': '18-Aug-2022',
'Text25': '24-Aug-2022',
'Text26': '25-Aug-2022',
'Text27': '01-Sep-2022',
'Text31': '01-Sep-2022',
'Text28': '07-Sep-2022',
'Text29': '08-Sep-2022',
'Text30': '14-Sep-2022',
'Text5': '01-Nov-2022'}
I've tried to use this lib to read and write pdf with AES 128 encryption, the file doesn't have password, even though I can open the file fine without a password, it doesn't work when using this lib. Searching around shows it's because PyPDF2 doesn't support.
Stacktrace:
PdfReadError Traceback (most recent call last)
<ipython-input-29-c3346d48ed79> in <module>()
----> 1 fillpdfs.get_form_fields("imm5483e.pdf")
4 frames
/usr/local/lib/python3.7/dist-packages/PyPDF2/pdf.py in getObject(self, indirectReference)
1615 # if we don't have the encryption key:
1616 if not hasattr(self, '_decryption_key'):
-> 1617 raise utils.PdfReadError("file has not been decrypted")
1618 # otherwise, decrypt here...
1619 import struct
PdfReadError: file has not been decrypted
Can you switch to use pdfrw
for consistency and I believe that should fix this issue
So I have a PDF which is an information form, using named fields and populated.
I have defined data_dict = {} at the start of code
When I run fillpdfs.print_form_fields('data.pdf'), I get the list of fields along with the data
Then I run fillpdfs.get_form_fields('data.pdf')
If I do a print(data_dict), there is nothing entered
and fillpdfs.write_fillable_pdf('blank.pdf', 'output.pdf', data_dict) produces a blank document as I would expect.
Complete code below;
import fillpdf
from fillpdf import fillpdfs
data_dict = {}
fillpdfs.print_form_fields('data.pdf')
fillpdfs.get_form_fields('data.pdf')
print(data_dict)
fillpdfs.write_fillable_pdf('blank.pdf', 'output.pdf', data_dict)
Help is appreciated!
Hi I can read the PDF from AWS S3 like this.
bucket = "advance-directive"
key = "assets/CA.test.pdf"
key2 = "assets/CA.test.2.pdf"
s3 = boto3.client('s3',
region_name='....',
aws_access_key_id='...',
aws_secret_access_key="....")
bytes_buffer = io.BytesIO()
s3.download_fileobj(Bucket=bucket, Key=key, Fileobj=bytes_buffer)
byte_value = bytes_buffer.getvalue()
# reader = PdfReader(BytesIO(byte_value))
fillpdfs.get_form_fields(BytesIO(byte_value), sort=False, page_number=None)
For some apps, I save to S3 like this.
with BytesIO() as bytes_stream:
writer.write(bytes_stream)
bytes_stream.seek(0)
s3.put_object(Body=bytes_stream, Bucket=bucket, Key=key2, ContentType='application/pdf')
How do I get to output byte data that I can put on AWS?
fillpdfs.write_fillable_pdf(BytesIO(byte_value), output_pdf_path, {'name': 'my name'}, flatten=False)
The get_form_fields()
function raises an error when launched on a pdf with pages without annotations
The error is :
Traceback (most recent call last):
File "[python script]", line 48, in <module>
fillpdf.fillpdfs.get_form_fields("form.pdf")
File "[root]\venv\lib\site-packages\fillpdf\fillpdfs.py", line 34, in get_form_fields
for annotation in annotations:
TypeError: 'NoneType' object is not iterable
I just took a look to the code of the function and the bug could be fixed by adding: if annotations:
before the for annotation in annotations:
loop.
the new code would be:
def get_form_fields(input_pdf_path):
"""
Retrieves the form fields from a pdf to then be stored as a dictionary and
passed to the write_fillable_pdf() function. Uses pdfrw.
Parameters
---------
input_pdf_path: str
Path to the pdf you want the fields from.
Returns
---------
"""
data_dict = {}
pdf = pdfrw.PdfReader(input_pdf_path)
for page in pdf.pages:
annotations = page[ANNOT_KEY]
if annotations:
for annotation in annotations:
if annotation[SUBTYPE_KEY] == WIDGET_SUBTYPE_KEY:
if annotation[ANNOT_FIELD_KEY]:
key = annotation[ANNOT_FIELD_KEY][1:-1]
data_dict[key] = ''
if annotation[ANNOT_VAL_KEY]:
value = annotation[ANNOT_VAL_KEY]
data_dict[key] = annotation[ANNOT_VAL_KEY]
try:
if type(annotation[ANNOT_VAL_KEY]) == pdfrw.objects.pdfstring.PdfString:
data_dict[key] = pdfrw.objects.PdfString.decode(annotation[ANNOT_VAL_KEY])
except:
pass
print("{" + ",\n".join("{!r}: {!r}".format(k, v) for k, v in data_dict.items()) + "}")
I had some pdf (1.4) that didn't work with your code and I made the following changes to your write function to make it work:
def write_fillable_pdf_mine(input_pdf_path, output_pdf_path, data_dict):
ANNOT_KEY = '/Annots' # key for all annotations within a page
ANNOT_FIELD_KEY = '/T' # Name of field. i.e. given ID of field
ANNOT_FORM_type = '/FT' # Form type (e.g. text/button)
ANNOT_FORM_button = '/Btn' # ID for buttons, i.e. a checkbox
ANNOT_FORM_text = '/Tx' # ID for textbox
SUBTYPE_KEY = '/Subtype'
WIDGET_SUBTYPE_KEY = '/Widget'
ANNOT_FIELD_PARENT_KEY = '/Parent' # Parent key for older pdf versions
ANNOT_FIELD_KIDS_KEY = '/Kids' # Kids key for older pdf versions
template_pdf = pdfrw.PdfReader(input_pdf_path)
for Page in template_pdf.pages:
if Page[ANNOT_KEY]:
for annotation in Page[ANNOT_KEY]:
target = annotation if annotation[ANNOT_FIELD_KEY] else annotation[ANNOT_FIELD_PARENT_KEY]
if target and annotation[SUBTYPE_KEY] == WIDGET_SUBTYPE_KEY:
key = target[ANNOT_FIELD_KEY][1:-1] # Remove parentheses
if key in data_dict.keys():
if target[ANNOT_FORM_type] == ANNOT_FORM_button:
# button field i.e. a checkbox
target.update( pdfrw.PdfDict( V=pdfrw.PdfName(data_dict[key]) , AS=pdfrw.PdfName(data_dict[key]) ))
if target[ANNOT_FIELD_KIDS_KEY]:
target[ANNOT_FIELD_KIDS_KEY][0].update( pdfrw.PdfDict( V=pdfrw.PdfName(data_dict[key]) , AS=pdfrw.PdfName(data_dict[key]) ))
elif target[ANNOT_FORM_type] == ANNOT_FORM_text:
# regular text field
target.update( pdfrw.PdfDict( V=data_dict[key], AP=data_dict[key]) )
if target[ANNOT_FIELD_KIDS_KEY]:
target[ANNOT_FIELD_KIDS_KEY][0].update( pdfrw.PdfDict( V=data_dict[key], AP=data_dict[key]) )
template_pdf.Root.AcroForm.update(pdfrw.PdfDict(NeedAppearances=pdfrw.PdfObject('true')))
pdfrw.PdfWriter().write(output_pdf_path, template_pdf)
Hello together,
I really like fillpdf, but I have a problem when it comes to scripts inside the Adobe Acrobat document. I have multiple PDFs that I want to fill out automatically. These documents have some Fields(column sum and column average) that are filled by an Adobe Acrobat scripts. If I fill the lines by fillpdf, the script doesn't notice any change and does not calculate the new result of the sum and average. An ugly workaround is to open after fillpdf every single document, make some random changes, and let the script calculate the sum and the average. Another bad workaround would be to calculate the sum and the average on my own, and then just put the result inside the sum and average fields of the PDF.
How can this be done in a better way? Can I somehow "touch" the PDF to make him clear that I have changed something, and force him to recalculate the fields?
Thank you.
Unfortunally this Tool does generate Documents not conform to PDF/A.
Hey,
thanks for this gem. Is there a way to place some picture in the PDF with your fillpdf?
I've got some PDF where an area opens an "select image file" dialoge. but i don't figured it out how to do it correctly with your lib
'Radio Button 1': None,
None is the default option,
When I change it to '1'
'Radio Button 1': 1,
or
'Radio Button 1': '1',
no matter the value is int or string,
all of them can not be fill,
the PDF that generated for this field is still empty.
Do I set wrong?
Thank you
Hello
I have some problem with your excellent lib. May be you can help me with this.
bc_farm_.pdf - blank pdf file
bc_farm.pdf - example of filled rdiocheckbox and child checkbox by adobe reader
bc_farm.json - extracted fields with values from example filled file
And now, the command insertfillpdf -j bc_farm.json -o bc_farm_filled.pdf bc_farm_.pdf
does not populate the first radio flag correctly with child flags.
Can you help me fix this?
Thanks
Hello after the update I have this error TypeError: 'NoneType' object is not subscriptable when i use "write_fillable_pdf" method at line:
key = target['/Parent'][ANNOT_FIELD_KEY][1:-1] + '.' + key
Hello - i try to read an edit the attached pdf using the module -
Reading with
workPDF = fillpdfs.get_form_fields(fn)
and writing with
fillpdfs.write_fillable_pdf(fn, fnOut, workPDF, flatten=False)
works generally fine when i have changed the fnOut-Dict.
But for whatever reason the first entry in the pdf (field "Renter(s) Name") is not updated in the final pdf.
Is it possible that this special field i non-editable?
Can i somehow check if a field is non-editable when i have read the dictionary using fillpdf?
Hey there, bacially i am trying to flatten my pdf using poppler method aka
fillpdfs.flatten_pdf(file_name, file_name, as_images=True)
now issue with the pdf has some bar code images as well issue is it reducses the resoloution which breaks the barcode
it bascially makes the barcode lines blurry which makes it unscanable..
is there a way to flatten because the as_images=False method isn't working..
top image is after flatten and bottom is before
There might be an issue with in regards to pathing to a PDF file from a file-share server. I tried to let it read the pdf form field with fillpdfs.get_form_fields(r'//ExampleServer/Server-Drive-Name/Folder1/Folder2/Folder3/Folder4/Folder5/Folder6/Folder7/Folder8/PDFFILE.pdf')
and i get this error..
PdfParseError('Could not read PDF file %s' % pdfrw.errors.PdfParseError: Could not read PDF file PDFFILE.pdf
Is it possible that the server im trying to get to might have more security or is it a bug within this module?
The code/pathing works with a local PDF file on my desktop but otherwise it display's this error when trying to grab it from another directory.
I apologize if this is a silly question/issue, just cant come up with a fix or at least find one?
Loving this non the less as it has saved me a ton of typing!
Thanks! :)
fillpdfs.write_fillable_pdf('input.pdf', 'new.pdf', data_dict)
File "/opt/homebrew/lib/python3.11/site-packages/fillpdf/fillpdfs.py", line 295, in write_fillable_pdf
template_pdf.Root.AcroForm.update(pdfrw.PdfDict(NeedAppearances=pdfrw.PdfObject('true')))
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
AttributeError: 'NoneType' object has no attribute 'update'
Not sure where it's going wrong.
Just using a standard tax document
data_dict = {
'f1_1[0]': 'Wakka',
}
fillpdfs.write_fillable_pdf('input.pdf', 'new.pdf', data_dict)
Hi there,
I'm using fillpdf to fill a PDF with generated form fields, which so far works great. I can see the fields filled in my OS PDF viewer. Then trying to print them via CUPS though, the text inserted in the form fields gets removed and is not printed.
The CUPS logs say something like:
W [15/Feb/2022:11:10:39 +0000] [Job 7] /var/spool/cups/d00007-001, object 46 0 at offset 67385: operation for dictionary attempted on object of type string: ignoring key replacement request
D [15/Feb/2022:11:10:39 +0000] cupsdMarkDirty(---J-)
D [15/Feb/2022:11:10:39 +0000] cupsdSetBusyState: newbusy="Printing jobs and dirty files", busy="Printing jobs and dirty files"
D [15/Feb/2022:11:10:39 +0000] [Job 7] Set job-printer-state-message to "/var/spool/cups/d00007-001, object 46 0 at offset 67385: operation for dictionary attempted on object of type string: ignoring key replacement request", current level=WARN
W [15/Feb/2022:11:10:39 +0000] [Job 7] /var/spool/cups/d00007-001, object 47 0 at offset 67599: operation for dictionary attempted on object of type string: ignoring key replacement request
D [15/Feb/2022:11:10:39 +0000] cupsdMarkDirty(---J-)
D [15/Feb/2022:11:10:39 +0000] cupsdSetBusyState: newbusy="Printing jobs and dirty files", busy="Printing jobs and dirty files"
D [15/Feb/2022:11:10:39 +0000] [Job 7] Set job-printer-state-message to "/var/spool/cups/d00007-001, object 47 0 at offset 67599: operation for dictionary attempted on object of type string: ignoring key replacement request", current level=WARN
W [15/Feb/2022:11:10:39 +0000] [Job 7] /var/spool/cups/d00007-001, object 48 0 at offset 67844: operation for dictionary attempted on object of type string: ignoring key replacement request
D [15/Feb/2022:11:10:39 +0000] cupsdMarkDirty(---J-)
D [15/Feb/2022:11:10:39 +0000] cupsdSetBusyState: newbusy="Printing jobs and dirty files", busy="Printing jobs and dirty files"
D [15/Feb/2022:11:10:39 +0000] [Job 7] Set job-printer-state-message to "/var/spool/cups/d00007-001, object 48 0 at offset 67844: operation for dictionary attempted on object of type string: ignoring key replacement request", current level=WARN
This is when using fillpdf on Ubuntu Server 20.04 LTS, mupdf installed from the package repository. On my Mac OSX based system though (mupdf installed via brew), the generated PDF works fine with CUPS, which makes me think its a dependency problem somehow, although I'm lacking the expertise to find out what exactly is being used.
Could you help me pointing into the right direction?
Hi,
I have a PDF form example that I would like to fill and everything is working fine besides the list boxes are not changing their values.
For example I have a list box for Gender and I can't change it's value, even the default value from the template is not displayed.
Thank you!
Hello, thanks for the wonderful library!!
Is there any way I can use a different font style to fill my pdf?
Characters that are represented in section D2 of PDF manual version 1.7 (starting on page 1001) work fine.
However, other unicode characters such as ■ (U+25A0) disappear when I flatten the page. These unicode characters do appear if I leave the PDF un-flattened. Flattening the PDF, however, causes them to disappear.
I've tried flattening the PDF in two separate ways:
In 1, special characters appear
In 2, special characters do NOT appear.
Although option 2 is generally "better" in terms of rendering text consistently and correctly sized, it fails to render special characters.
Basically if the pdfrw.PdfString.to_bytes() value looks like "(\x81)" it will flatten correctly. However, if the pdfrw.PdfString.to_bytes() looks like "" it will vanish during the flattening process.
EDIT: My question originally implied that 1 and 2 both failed to show special characters. In fact, it only fails when using flatten_pdf(as_image=True)
Dear author,
Thank you for your software.
We have some issues with presenting filled PDF's with RTL languages in the browser.
It comes up reversed.
The solution is to save the file.
We do flatten the file but still - upon exiting the file it asks if we would like to save it.
Why does it happen?
How can we automate saving?
Does fillpdf support saving the file?
Best,
I'm trying to autofill an i-9 right now I'm just using random data. But when I print the fields with fillpdfs.print_form_fields('i-9-paper-version.pdf')
I get this
{',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+^$xí\\020\\025X\\006\x9dÜYúAmkÇr>íÖâ=\\002\\010*çÎ6í?L\x96Õ1ò¤\x94ìD\x99\x93\\012\x85Éi\x9d\x92Ø\x93ý\x98\\017Ë¢N&Î2\x87%lk\\000\x9e': ',…·\x00‚å{›“\x0cä«1´:+&„Œ[õ˛„Y¼€ÑqïËÎ\x17', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\010øóQ\x80\xad\x80Ï\\0167\\015<bB\x9cÜ"4bbT\x80ê©\x8aî\\037Âõè\\010^\x8b&jÕÙ±r\x92õ\x9d,\\036\\000¦C\\024$tnã+.ï\\016B%é
Ô0Õõ': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+Eõ3EÎ¥\x85\x93B\001k\x8aP\022¨¤MöËBY\x9b\x87Ï6x3TëfÏ\x9a\x96âÇxOt÷\x9eý5\030}\x8c\x85âÄ': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+líhç\x9e¼ûlïälI¥_öwÀQ\x82\003.\022\x944ø\010ýѮ߯ÁNÕ0¦Z\x8bÓ9¦ÈzJöá\x9a\x89ð$ÑÓËïâºpÆ\x81\025<W\003': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+«P¢\014w\x85\x94ÍÊÈú\x80p\(mãzôUµÉ\033\016ÿ\003\037ò\031]q\013<1\x92Ó\001iþº\x91\x91W¤\002-ê\x9a\016u\007Ü\010su\002¦=¿¿\015Rßb': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\x99m>6Nlnq\017¤\x9d\x8d¾pTZókÀv©Nº/Ç\x8d¸¹øÖ\024pQÕ\x9c©\\034³l·\\034L\x9f\x98&SÐ': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x99$4æ\x8d\\024ÌÀ\x9f\\033àÔÎ\\037\\003WOäÈÞ\\036¦bi\\017\x91\\032Æp\\005w\x98#\\013\\005¼\\024K\x9f>ôQõá7-Do': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x9aÿª¨O\\003{WËû\x80¾ JQ ²Ék{©\x9b\\010øc«®¿vLÈ\\007¶£3z\x83A1\x9b\x8eb\\025\\001ãSé]': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+·¥ûT¾\x98\\023M[AÐ[þÂ}ÎQR}ï\x86\x80\x9f\\0215ÆÙ»w\\011.¢\x9aoã¹\\025MV<ÓìnhX\x8f\xa0ý\\002úË.ê\x86\\027\\001\x81g\x95jlNõÏ': ",…·\x00‚å{›“\x0cä«1´:+$:›þ\x01#Ü\x11‰ÎÀ¹B'¹ƒ", ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+1U¢\\014\x98\\035CÆÃx¡ÙuZp\x8fºQ\x90j{µÎ\\032\\024ß\x83{\\031\\017N}¾\\011RDN4=\\031M%Ú:\\\\ÐK9\\0210»a\\022-~\x8cã3üçë~rèÕ{°\x99D\\036\\020\\014FßdËÝl7»': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+:°j6Ît\x7f̨U|Þ\\027/s¦\x9bcÑd:1Ý\'KpÂ\x85$ÌJ\x89\\015\x8c0Ëþ?·8vx\\030»\\000\\023ÏUÙ°_\\003\\005\x90Iáp\\03426\\017\x9c\x84J\x83*\x7fõ¨\\001$Î\x97i"¨\x85ð\\(º': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+*2=H\x96<\\000I;d\x9b\x8bcè$¯©°\x91x\x8eMØ\\021\xad\x9cRAt\\005\x9d\\006\x9aÊ\x86é±¼éd"\x90\\003\\003ÚÕ\x9cî_eØvK\\027XG\\021¢ù\\007GM\x90ùx]\x90\\032\\001ç\\015r\\011X\x9c9gíÜÏ': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+8\x8eÄ\x9e\\)ãt\\000,¢|\x90ÕR\\021T\\006ÄÀë{\\022Æ;f\\007\\020\\037.W\x8d±éÏÎ$\x9c&F\x919VÞãÀÐ\\030}ù[ékB\x86\\014Ì\\000¼L«ù¨â\\023': '', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x80E\\037\\000\x88¾®q2²fº7º5í®a=ÍÍ\\021:á¿ãL\x8ed{h§¢t>ù=\\013q\\010\\023´,ë´'ÁÒÔ\x90\x9ckà\x8e\x91 ÞñÃ%mlËb": '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\011\\001\x81Û\\\\Ïg\\011¿ÿ\\001@ý\xa0¶3\\021mÎĪm¨ÿ&,úI¨H·\xa0Ó\\030\x9fÊ_\x90%´JDlüdl\x91<<õ\\005Tm/É\\021¨¸\\002ì\xa0hÂ2\x8f\x810!\'"U\x90ðyÝÃ\x97\\022MË': 'Off', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x8f\x7fð1 æ\\015c\\027Á5M6\\031ÜÕÁà\x9fz'_r£\\034\x81c
\\^weÖAlu\003úa«\031\x91T\021þMÎLo\x89,ºGîÙ\x85ã²d3?\004ÄáÀj½åÚ\0150>Î$V\x9aD\x9e>^\x87p}\)1¬\x85\x82tø\023ä+Æ\x86\013\007\011Ôìt¼÷\x9b\033\x85L\)ýÌì<": 'Off',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+νF\x9d\011\xa0ýü\015a,¡\x9c\x85\026lÉ÷°\x98ÉÓ\x88¢Í¶3¿\031ç"%ZXã#<YoÒi\017E\(\x90²\0310\020\x99iD\005-\x8aD\x82X\007\033|v\006P\x81m\011®C\x9f\011ÜÒ9\x991Q Q\036\011\011\032lk÷;#{2\xa0\x9aá1Ây_HAV\x91¯2Ñö\021\x9b?\x96\x8f:': 'Off',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+Æ|Ã\022º&VGü}Të¿\011çù\007¥\030i\005\026\\%z*\010îáiGB\x8e¨;\x81\x83\020\x8d\x7f\x8cB\x87Úë;\020\016÷\x9f@{1ÝU,\026eÔþ\007áñÖtÂ\001\x99Þè\x87\x81\002N¸±\x86FËÏ': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\024È8±\012\x8c\x98Ü\015\x82K\x91\017fB\006ª¡¸¡\x847Jóû¶©\x97¼sÃËgRõ\x81\x9e3v\024£E6ð³\000Qɬe\011\x9b\003ôl³\010¨¯\x9fì\035Uè\036A\x81\xa0·\x93\x8e¶\x88©|·\x9aM\x8e÷\x81b.¢\x95ÈÉ6\x86úµ\025\x8cóø¯\015ÛèlÎ\024SS,F6ä\013\032\x94\x84<{\x93,ßõà¡\(\024\032\x80ÿè¸': 'Off',
",\x83·\000\x91å{\x89\x8d\014ä«1´:+Ðdr§-Ü\x8d÷'C«2£\004å«S8йªA\011ps7Õ\026³\032Qç\004ÐC©ú\013\x8c\x9eâ塼\x8cí\000\031É\xadÁ2\x9c1»1!ÏÁÌ\034ù\026 ï\037öê\034w,å,L\x95\x83N\000¥": '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+"µ.{Ù\034\x89¤¨Õösþ·¯\x9a®ô°ºÂ\)\036F\007·0\x96\x96\020kæ\x8e¤W»\x979ð9õç\\003nàö\\036\x82\x81\\013\\014&BòÞµÖn4«^\\033áÃê\\004\x91&:6¥\x9cTç²<õód': '', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+i5Ú§;\x8f«§äw\x9f]\x8bø[\\003\x7f\x9d£\x8cï\xa0S\x8aíÕªävç Õ´gL\x92Æg\\023©{\\03459À4\x98luhB\x86l®Áx\\011Í«\\006¦'*": '', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x91^æ¯Hã8[«d\x932²¸öø%ä.÷]Køp\\000:Ù\x90k\\001jÑD\\033\x80³·ýbÝÙ\\033¤\x8eâÜ¥']\\021\x88T$\x94\\016°²ÑNÊÎ_¨¶": '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+þ<×:nÇ5û·\x8b\\005ª8l\x8dØ\\020°¤\\014èU\x94Ïhß<YÍJ=G[yh+Å\\031\x83¢\\)úî\x8dõTU\\003\\025}Ò\x8d]\x8c@ÌO\\021~²Zl³©': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+ÿJYKtºä\\026¥\\004\x8fRÙDÄKùǸFB+Ý\'Z\x8d\x98øݧýr]ÔA_ÛJP¸ßçͪ~AÆ\x98\x96+£\\004>üT\\002z[\\027g¦\x8d\\012ð\x80¶\'\x81FiÆ6oÉ0LoD\\025"': 'Off', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+¡Pwx\x99ÇÔgÒº
\x83c%c¬g°Ù³Ñ\007Ö®!Ö^vaõ%ÝÊŲ1!\007¡ò\x80¤\022Û1øf26|Ä\032\022LôÍ\004§ê\\Ú\014,ö«ä8\005VmâL²}S\x93µíOhS÷¸3\x83\004\x96«°x;=bð«ð^r\x8b+ðÔX\031\015\x85½ÿaAìº': 'Off',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\000tõ\037|mçF\x7fdPÝMk\x8a\027ç\x86W\x9cp$\x9bà\x86SR8\x87\020J\007â½F\014üÄ\x8f×hXuµQ\(>>\x84k¯×\025!û\x9eB\000ð\x98ó;â\007': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+O\001Ø\x9eU©\023\007\027\016âí\014¸ìw«+Qé@¶y@?ª=\037\035¸\036Áoån\x898\037lï¹\010r\031\x91Ì\023yÁ\x80ËË\x91úÕÜr\030ý2¡Áñ': '',÷>\016K\x81Z´ð>¾pMê\013ªa¼6\017§y1=·ß¥¥\x91Òé\x85¦\011\010\x88": '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+rMÌÛH\001!C|&4âÊ®ýë\014´¦æ¿\016Í=ú¤ð±Ç\033\030m\x8a\032¯\034Í\x9aàÞyOß\021.\x93áº\005GÇ\x80Ý\xa0\\[NeÀ®\x82\012xé': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+¯:ey\x9f/\x8b!O\x85\032Ä\x85·\x8bWãóX\014â96\x99wèò\x8eb\x87Øü·:¬Û\x99ú\x96\006ãóV\017N¡\003': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+*1¦ØÊzz\x9cÊ÷ë°VeCÑpâöÄ&;æS\x88\x87\\K©ý\015\x94ä|\x80×±Á\x96\x91\x87?\x8d\\027zÀ\\015': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+C\\020\x8bÖϱ\\031Öw\\007\\024,±If¦\\025¼\x8a%\x98³\x9cS÷¹A²êSùB;¢\x7fÍí\x87Ì\x85
ÈSÊaÈ\x95\x94': ',…·\x00‚å{›“\x0cä«1´:+5xóÞÛ\x15†m#,b²ÇÀ¬Ö',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+,¯\007F·\016«\x96b\031ع\035\003\x96°ØøÆ\025\034¬\000,[Ú\x81õ\016qðñ¤\004Æ\013&\x90!\x83o\003"HDwHÛ': ',…·\x00‚å{›“\x0cä«1´:+ˇ\x11yÂ/0£&‚÷¹¾b\x0c:À',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\x8a{\005ÙÞNk\x9dv\x8d#Q·¡\x87^\035õ¦ðfnêÉ´Å¥\000\x98ÛçÏw¤&vÌÄxØk}ÈRX\012Ì.-5¯ìU¯\012Ùï\x82\000\x85hYôÀ': '',
",\x83·\000\x91å{\x89\x8d\014ä«1´:+Ó\x87\004\x98Äb\x7fw'Á¹À^9kWù\017ÿ\x9bÆ9øi&t3\x96
',\x83·\000\x91å{\x89\x8d\014ä«1´:+zZa\001\x7fÌXÃ\003×\x99Ò\x98\020\\´\003\x9b\xa0\032P=â\x88\x7fÑR\x91Ï\x97\x8e\015EKà&g\033Àe¢¡ò÷¬\x96\x9b': '',\007$\x93&83Ü": '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\x98\025Öø·\x9e.\x8e]«ô#¯h\x7f@¶\x90æÒ¢Xå\x97\002¢ä÷RókÀ\x9cíÉV\015\x92è¥+*R\x84¢\020\x82\x83\x9bÍ\\024iB1,\\020\x9cØ¢2FY\\037': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+/é
õ8°\003D\x91\004R\004ctÜØ0\x94s\015±U_h\x84Æ\032ª\x9d¿R#\x98ÂÞ\x8béL\006j\030£\x87ãã]u$Ní\x8dz§\014»3\026.ÿ\x7fä%\x97ô': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\022ó\026uTSÂül@\021²ðS\x83\(¾B®\034\x94ú³\x8f઩y,ÀR¯ë¨\025cNÌAºã\025¨0\015\037³ÞFù->#\024qn©,æ!\x8d®\x8e<': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\034'¤Îy\x90\x82\x8aá|\x94IûH±Ë\023\x89¨SJ_®S\xa0"e6¼¨\011\x84\xadve«q\0110h"\x86ýU\024\001"\025akºa\026¤\xa0C\x8a5m@÷á[¦': '',
",\x83·\000\x91å{\x89\x8d\014ä«1´:+'\x81ë¾\x80>#¯E³ÀȾL Ó\x90¨Ì]5eqÚ¤idñð=\xadC\034\x83Uµ>L\032j\x88£\021µ\011\021sræ\036êî+\016ã
',\x83·\000\x91å{\x89\x8d\014ä«1´:+è\000£GI\xadþÔÈ\(\x9aÓ9ÅVé\(ó¸\x9b\\011b\\030\x92Ì»\\034\x9b\\031ËØôfÄ©½\x8dmLÖ@\x8d\\033;´É\\025%\\021ä÷ïÁi5É\\004Ó£ü¶o\x8a': '', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+ç¹*\\011{¿\x98\\022\x8feÜú|°]·ÏÞ½<\\022²þcÜÈÖò¤'ã\\000=\x9b\\000\\031\\026n\x945~\x8c§M\x88YmIÐLÔ\\032\x9cñ\x8a·éÔYÓò;sÇ": '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\030>ÝPç´ýÚ\x9c\x8a\\036ú\x8a\\023¹½è\\035\\030^\x9a[Øv\x98+\x8aX\x7f\\0221ck\\033Åf-˽7\x910¬\\033S\\002»å\x86$¼\\030]\xa0\x96-µ×ÚÂÝß&Ê': '', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+¢R7\xa02U'{¦äP?\\032Gú©9¸Ò³Aü\x9a\\024¾·]M\x9d J0Ì\x97s/\\005ª\x9btx\x8f?°ãl\x9e½7r
rEo&Ñ\x972\)\036^ò·y": '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+/:Ùu\x84|_Ý\034g\x85\x9f\x9fm¥a\x85Nü\012iÑ÷W\036g\x90}ÑódÄ¡\x81Ùÿ»Ã¼\001½%¦û©¸\016\\D]\020\x8c\033G\x84ÂþùBMTTOm': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\x9c\x8cÖ.ØéÇ»Ü\x95À³DA\)\x9a0\034\x99ºZ½\026ÏL\x87GíA\\004\xadÁð\xadG¹\x8aíWÌfq¡\\022±Ï\x83\x8d»2öBÝ\\003v\\016I´K\x84 ¢\x8c\\025\\027\\022þ\x8e7\x9b¼¢sÑÄså+\\020': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+vVà\x92W\\027Á\x99c\\031\\005µË\\007Åï3±\\034\\003~å4\\027\\020Ú\x94co\x91×\\)¸\\\\#j¬[C$ç³Ôï\\036\\004WG\\0076sü¢,T@àj]\\024=ÿ05\\017Çß\x9fiæ\x92òiö¸ÖuøÅ&': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+ëôËög\x81\\022eÌu\\007æÓÂFD\\036\x85ÌÐñØz©Å\\031ý\\006\\030çµÖ\\015èǧ\\036¾a/"\x91\x9f\\033ä²£¸Ò\\012+.Ñ\\005\x98I\x9ejWÛ\x93\'?Ù¨sôÆT\\035\x98\\027NìW\x80\\002&\\021°': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+ãÒGû\\022kkU9\\023}{6\\033«\x875àRã\x8e&þ\\022V\\005\x8fP2àù\\023ùf®Í\\\\Ý×ɹ+ºBµ\x81p!Ü\\021ç¨f<\\037?v~8¾#i¡M': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x7f#"3Q¸,\x92\x8dõ\\035\\001ê¨÷é@ll¥XÅ Ó#Ìû\\\\|\x93ÉCt]´f\\031ð>\\022YÄO\\020À\x8eL9E\\002w$ø@_Ë{¤\x89\x89k¿ò\\006': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\013ò-\x9eÉ@ºúI×\\000\\001Æ\x957Gü\x86ÿ\\011¥\x91´kÉs8\\016\x92.zÚpJØxµÛ@\x85ÔjhÃ?M\\033\x9f^\\025¢mÿªf»í6®"5Rÿ\\020': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\017cII´\x85JJL/zºq\\004ÃØ\x93m%ÏÚ\x81\xa0C*\x8b\x83D¸àÓq0\x8cEEú\x9a\\002\x8aóF>\\0157\\017\\003·À\\003RÍ\\015Î@YuÒe\\030}ßeâðZÂýÐFܤM¹\x8dLØ!Ìc': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\015ë\\010h\x98\x8e>\\016øê}GÃ\\023ðº\\016\xa0\\)Í\x9f\x8a©kÙjèÕ\x81h470Bò@ßRÛoT2\\024¶Á~\x8bu\\025\\025\x89¬\\030HñhcÇ¥¶·\\020\\012ü': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\001\x88Õls\\034ö\x99èÊø\x7fÕ\x9d\x89\\025ÿ \\027\x81hJì! \x85\\002¬\\014b\x99mÇÂÝßZµË;N:\x86´\x8b\x8dÛ}¤§ðwkSpeN\x8c\x89¥;Nå\x97': '', ",\x83·\\000\x91å{\x89\x8d\\014ä«1´:+£\\036é\x9b¬\x8e4ê\x94Lb\\0004êï]\\015A@ºyi¥Î'\\011~x²òT¸ Í\x87_\x8eÐ\\007´\x94\x91üG\\034k\\0374xµZ%©ª@®7\\003eÅ¥\\003\\000o": '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+R\x9eòÒD\xad\\026\x92¢7BUNÝ\x8eÖXªÄÊñ_#7\\035w@Xú\\004Âi\x7fü\\016ó¬\x96\x87Ë#\x9a,àyÈD\x9f\x90ðàoih\\023OÎ\\025\x88\\000\x91òõÚ¦tèU]\\032\x81Ú\\006«\\012B\x88\x9eµ\\015': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\014×\\030\\011|\x92Bm@¦GÅÍæU\\013ÒûM\\014ü¥\\000kûÔ\x96\x9b¨ú"NÏ-5t\\030îó\x9c©\x88äße8Ú4\\020\x95¯§\x9a\\020þ«\\032ó~07\x98\x86\\006': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\x91ïÃQ:1\x97\x83\\013\x97\x7f~D¦\x83Í\x9a\\033¿\\030¤Þû¤±\\010áWþÖd\\004ÂE\\013Ï\x85\x8f\\035\x9e\x99±µ°1{Kq@\x80\\034ë\x8bÜüÊ¥§ý\x88\\037ÈÆc;\\(U\\000z\\006\x88W\\)$Å\x8d\x8a\\015v\xa0:÷Ër\\005\\017Ý4\xad±h´\\0328»Û': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+C\x91_4ø\x9b©Õ}Òz½-L\\002\\034Æ\\)\x98\\(ÝI\x8cßÊ\\033\\035®Ì¿\x89ÂÅ\\011Cü\\014\x81\\0010\\016A\x90\x9eÔ0È\\022¡\x94Ë:¿×>R\\000Y\x9aZ\\002\\013"P\x82¼Â\x89ób\x95[Ðl\x8dYåMÃJz´OGËó8²Xù÷\x97\x89ÆÍD': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\005\xa0\x89:â®\\002ÝÞ£ì\x8ep÷\\003á\\035Ynð\x9d\\024¡\x85[P\x9aÒIFùÕ\x8bzß;\x85\\034\x84Up=L1\x94㱿;ýæª*\\035@lC@ö·3\x7fEºÁ\x93à\\031\x99\x99åRðó\x9b¥¥\x9a\x99o': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\006ïÚ[D8\x9aç"\x90å\x8ezàä!Ã\x8b©y\x9dü\\017\\016\\030\\(g4?«<¹¸uë\x86¤nD\\024\x86SàÉ{uG©:FÑ\\021\x98x0K¿ôëZá·L»\\007q\\001\\014\x8b\x96w£\x9clÐ\x85\\010\\014\x9e°\\032³z\\0050È\\\\毹\x85÷\\001%Lú': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+¢\\026B\x97eÊeh
\x92\021å=\x89½j\012Â\x8cJkJIKm+×ÓÎa1/?\022T½\002©×uÒý¨¼ä\004«âÃj\017\024Âz¨8ÔÛ6lòGãUS8v°È"R\017ª\026<aâ\x9fIwµÓ\026\x81\035³â\007\023ü\x91ã\020weo': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+6Ó]\)±\\wn¹^È.-K{öj\032ÁQb\011¥\030\x8d@\007®\\035\\000vS0·\\023\\016¨Ü\\012Ã1$\\024k\x83<\xadMÅÐ$ê.:Jr\x81t«Ê.ºq': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+AÉí\\015ª\x8cV\\037{ôµ½<\\001\x814j¬\x9an\\020-Ñç¦vqÂ\\012Zq\\022m\xadyd\\0258\x7f¿]ô«Ý\\010\\)6÷TÐi¤¸e>5ßð¦\x91_\x82ð}': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+\\026,VÑ
BÚð§\x81i\x90Â¥\016;ÿ_6="ðÚ\x85\036Å \0173M\x86\x83z\x85P\005®&^\x88\010@löy^U': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+Z÷\x8eþ:£/ªFZ\001C[\000BEIÉò\x87E«$çM\x84afä\032\013®c\x91«þ\006\030KK¦:ðâ\012\x8d^\026': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+\020ÀQX3XUÉäN\x94Êóê#\x96;Ðqß\015¼a\036\007Ó\x8b¦1ÉÐ\x8c®ÄÐ\x920\024x+ê~g2µÜên': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+X\x8dÔaµ\x94§H \030Ê!&ñ{\032Ûùg,ôüÜC\002ª\x92\013\(zO\x91+nî\x9dÈǹ\001Ò7\x8c·½Yås': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+yé\x8a"\x95¨Á/Ð>\x95\001&¼:ÊiÄNWT\x92ðHF.ÃýÜ¥ò@k\003ù\004hÓæ\035õ¼4Â\020h\\027F\\026lWæ\x8d\\031\x9a<xÚE\x83ZÈw': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+l" e\x84åÎ&%ùw\x9fÓöbf1Q$\x9c©\x88$8Èù<\x7f\x7f\x89F7BÒÂ}º\\015\\)NÌ´·1Ù«\x99ÀùWÊíü»ó¬x?¬ ¦!ð\x90©}Ö7\\021\\011¡¶\\032\\015¨f ±¡\x8e': '', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+òa\\007Ö²´wáÂ>ª=h!põ\\037
âÅ\024\x94ûW\x92A=\005«vsEøZèÍW\x9dÁ\037\003Ee\x94¥¯A\027#ãÓ88\x93°«Â\024\x93ð¼R\021': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+!ãÌ#T7\x8fåI\001BO¸ï\(\x87©ÚÙ\(ÒW³\025©r{\000.+\x98\x9bJP\x91Y<±PuZ£\x98BG\013¶aâ\x9e5J\0302\(Ú1ãÜ¡|\036Ç\x89': '',
',\x83·\000\x91å{\x89\x8d\014ä«1´:+çüÕàLsx\x82\x84\x8b\x9bqwpÚð\x98×fÞí6\037Ϥ1[ÿ·ú\012i¿1E¿\030¦Ni%tÈèNU': ',…·\x00‚å{›“\x0cä«1´:+}<ŠŁ \x15¨“lNägÊœ•˙', ',\x83·\\000\x91å{\x89\x8d\\014ä«1´:+Ó«7© s\\\\bF\\004r×®Þ\x8bY\\030%Udȼ0Â%Ä\x94Ô\\036h\\021ÎA\x89£Q\x9de²\x99C\\020î6<²ös\\035M]¤1\\023LÄ\\017aàk¸=\\003¼2\x85lëÚQWù\x9eË-Oâ¥FYF\x91ñ_á$üÛ\x9cdm\\021.|·Ü': ''}
If I generate a dict off of these fields and put a random value in I get this
Traceback (most recent call last): File "pdf.py", line 14, in <module> fillpdfs.write_fillable_pdf('i-9-paper-version.pdf', 'new.pdf', d, flatten=True) File "/Users/bogden/Library/Python/3.8/lib/python/site-packages/fillpdf/fillpdfs.py", line 256, in write_fillable_pdf options = [pdfrw.objects.pdfstring.PdfString.decode(x[0]) for x in options] File "/Users/bogden/Library/Python/3.8/lib/python/site-packages/fillpdf/fillpdfs.py", line 256, in <listcomp> options = [pdfrw.objects.pdfstring.PdfString.decode(x[0]) for x in options] File "/Users/bogden/Library/Python/3.8/lib/python/site-packages/pdfrw/objects/pdfstring.py", line 431, in to_unicode return raw.decode('pdfdocencoding') File "/Users/bogden/Library/Python/3.8/lib/python/site-packages/pdfrw/objects/pdfstring.py", line 316, in decode return codecs.charmap_decode(input, errors, decoding_map) UnicodeDecodeError: 'charmap' codec can't decode byte 0xad in position 25: character maps to <undefined>
It seems like there's an error decoding. Is there something I'm missing?
Thank you for this library. I am delighted to have found it. Overall, it is working really well. Did I mention I'm delighted to have found it?
The only issue I have noticed is when using text fields with a "comb" in an Adobe Acrobat-generated PDF. US Government SS5 and DS11 forms both utilize combs. When flatten=False
, combed text fields work correctly and spread the text over the comb. When flatten=True
, the combed text fields are no longer spread out over the comb and instead are left justified.
The flattened PDF file produced by flatten_pdf() is in an unfortunately low resolution. Can this be adjusted?
Maybe it could be better if it either threw custom exception or skipped this part and gracefully finished the rest of flattening?
/usr/local/lib/python3.8/site-packages/fillpdf/fillpdfs.py in flatten_pdf(input_pdf_path, output_pdf_path, as_images)
100 for annotation in Page[ANNOT_KEY]:
101 annotation.update(pdfrw.PdfDict(Ff=1))
--> 102 template_pdf.Root.AcroForm.update(pdfrw.PdfDict(NeedAppearances=pdfrw.PdfObject('true')))
103 pdfrw.PdfWriter().write(output_pdf_path, template_pdf)
104
AttributeError: 'NoneType' object has no attribute 'update'
I wanted to check to see if this is a known issue - I otherwise might dig in myself and volunteer a solution.
It looks like if you copy and paste a checkbox field while designing a PDF Form using Acrobat (as of 2024.002), it creates a significantly different structure than if you create a fresh checkbox.
The write_fillable_pdf function seems to get tripped up by this, as it fails this check:
# button field i.e. a radiobuttons
**if not annotation['/T']:**
Is this a known issue with Acrobat/PDF Forms and this library? I'm tempted to dig in and try to understand the structure of c&p fields a little better.
Checkboxes work correctly when as_images is not set to true however in order to ensure that my pdfs are printable from iOS and iPADOS I need to flatten them using the as_images flag. When the as_images flag is set to true all of my checkboxes are automatically filled even if they were not filled by the write_fillable_pdf function.
I have tried a basic function to check out the output by following these links...
https://stackoverflow.com/a/66809578
https://fillpdf.readthedocs.io/en/latest/
My findings so far...
First of all, thanks for the library. Really helpful.
I think it may be really useful (at least it is for me) a command line interface.
I have done some simple wrappers for your library: cli_fillpdf
If you think is useful, you could add the code to the library, if not, I will keep it public and made if available through pip.
I used "NameOfField": "Yes" to check a Checkbox, but it doesn't check it, it only makes it a lighter gray.
I also tried True, didn't work either.
Mietzuschuss nach dem Wohngeldgesetz BUND bf v2.3.pdf
# Without umlauts, name are extracted OK
MZ1.3-DA_PersAngGeburtsdatum
# With umlauts, not OK
þÿ\000M\000Z\0001\000.\0003\000-\000E\000T\000_\000P\000e\000r\000s\000A\000n\000g\000S\000t\000a\000a\000t\000s\000a\000n\000g\000e\000h\000ö\000r\000i\000g\000k\000e\000i\000t
I have a fillable pdf with few check boxes for language. So i need to check the language by fitting the data into data_dict. I have tried but it's not updating for different languages. I have seen in the pypi check box is in queue for future work. So is it implemented? If yes can you please let me know how can i select different check box by giving the value in data_dict
For my use case, I am listing course credits in a PDF with only 13 rows in the table. If a user has more than 13 credits, I would like to add another page to continue filling in there. Is it possible to add another page to the PDF using the same template as the first page?
Hi there, wondering if with this library I can rename fields in a PDF. If so is there any docs? Thanks!
Add ability to fill drop downs.
How do I set the font-size of the text I enter into a PDF when using the write_fillable_pdf function? I tried setting the fields in the template PDF to font-size 8, but I think the function resets the font-size to "Auto". So what happens then is there are different font sizes in each field because the various words and numbers are different sizes. So large numbers should up small and small numbers show up large. It looks messy.
Hi,
starting on line 207, the code currently reads:
if target and annotation[SUBTYPE_KEY] == WIDGET_SUBTYPE_KEY:
key = target[ANNOT_FIELD_KEY][1:-1] # Remove parentheses
target_aux = target
while target_aux['/Parent']:
key = target['/Parent'][ANNOT_FIELD_KEY][1:-1] + '.' + key
target_aux = target_aux['/Parent']
Line 211 should be:
key = target_aux['/Parent'][ANNOT_FIELD_KEY][1:-1] + '.' + key
As currently implemented, the code will fail to find fields in the corresponding data_dict if their parents have parents (no proper loop up the ladder of parents).
Apart from that, thank you for your very helpful library!
Kind regards,
Johannes Bergmann
Hello,
I am trying to place a text that contains greek characters, but it always puts '.....' in the pdf no matter what. I tried multiple things with .encode
and .decode
but nothing seems to work. I also experimented with different fonts because I read that some font families might not support greek.
If I add all my data to a dictionary and use write_fillable_pdf
it works. But unfortunately I want to create a black pdf with text in specific positions to print on pre-printed forms.
Any suggestions?
SOLUTION: Instead of 'Yes', it is 'On'. PLEASE UPDATE THE DOCUMENTATION.
The docs on checking off boxes are shown below. 'Yes' did not work to check boxes within my PDF. Purely by accident, I found the solution is actually 'On'. Now the appropriate check box in my PDF is checked off.
data_dict = {'Address 1 Text Box': '500 West Main Street',
'Driving License Check Box': 'On',
'Language 1 Check Box': 'On',}
fillpdfs.write_fillable_pdf('blank.pdf', 'new.pdf', data_dict)
I have a form in which there are some checkboxes. I am reading field names. All names are correctly retrieved except for the check boxes.
Here is the code.
import fillpdf
from fillpdf import fillpdfs
pdf_path = "C:\\Users\\PycharmProjects\\GenForm\\1003.pdf"
fields = fillpdfs.get_form_fields(pdf_path)#, sort=False, page_number=None)
print(fields)
The output looks like this:
{'Check Box1': '', 'Check Box4': 'Yes', 'CB-1-1': 'On', 'CB-1-2': '', 'CB-1-3': '', 'CB-1-4': '', 'CB-1-5': 'On', 'Agency Case Number': 'asdasd', 'Lender Case Number': 'sadsadsa'}
I do not want the keys like 'CB-1-1' instead it should give me its lable like for which check box is being maked as yes or empty.
Is there a way to do this?
When I use the library as a standalone it works fine and all. But when I use it in Django, it saves weirdly.
This is my code:
def _fill_form(self, application):
import requests
from fillpdf import fillpdfs
from django.core.files import File
from io import BytesIO
from django.forms.models import model_to_dict
ctx = model_to_dict(application)
response = requests.get("http://localhost:8000/static/document/form.pdf")
if not response.ok:
log.error("couldn't get form")
in_stream = BytesIO(response.content)
out_stream = BytesIO()
fillpdfs.write_fillable_pdf(
in_stream,
out_stream,
ctx,
flatten=True
)
application.arabic_document.save("Some fillpdf file.pdf", File(out_stream))
Hi!
I have a problem when I try to fill an empty pdf file (with the function "write_fillable_pdf").
The fields are filled correctly, but when I open the file (with a pdf reader, like Adobe Acrobat Reader DC) and then try to close it, the window to save the pdf file appears.
If I don't save the file there, and then check the form fields values (obtained with the function "get_form_fields"), the fields inside the dictionary are empty.
To retrieve successfully the fields after filling the pdf, I have to manually save the pdf.
Is there any way to programatically "save" the pdf after the filling of the fields is complete?
Hey
fillpdfs.flatten_pdf('new.pdf', 'newflat.pdf') does nothing
when i add as_image=True it works but quality is poor
Windows, latest version
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.