2
1
mirror of https://github.com/qpdf/qpdf.git synced 2024-12-22 10:58:58 +00:00

Annotation flattening including form fields

Flatten annotations by integrating their appearance streams into the
content stream of the containing page. In the case of form fields,
only flatten if /NeedAppearance is false (or equivalently absent). If
flattening form fields, also remove /AcroForm from the document
catalog.
This commit is contained in:
Jay Berkenbilt 2018-12-31 23:08:57 -05:00
parent 95d6b17a89
commit 3b8ce4f12a
20 changed files with 19540 additions and 5 deletions

View File

@ -1,5 +1,22 @@
2018-12-31 Jay Berkenbilt <ejb@ql.org> 2018-12-31 Jay Berkenbilt <ejb@ql.org>
* Add several methods for flattening form fields and annotations:
- QPDFPageDocumentHelper::flattenAnnotations - integrate
annotation appearance streams into page contents with special
handling for form fields: if appearance streams are up to date
(/NeedAppearances is false in /AcroForm), the /AcroForm key of
the document catalog is removed. Otherwise, a warning is
issued, and form fields are ignored. Non-form-field
annotations are always flattened if an appearance stream can
be found.
- QPDFAnnotationObjectHelper::getPageContentForAppearance -
generate the content stream fragment to render an appearance
stream in a page's content stream. Called by flattenAnnotations.
- QPDFAnnotationObjectHelper::getAnnotationAppearanceMatrix -
calculate the matrix that will transform from the appearance
stream coordinates to the page coordinates. Called by
getPageContentForAppearance.
* Add method QPDFObjectHandle::mergeDictionary(), which * Add method QPDFObjectHandle::mergeDictionary(), which
recursively merges dictionaries with semantics designed for recursively merges dictionaries with semantics designed for
merging resource dictionaries. See detailed description in merging resource dictionaries. See detailed description in

View File

@ -31,6 +31,8 @@
#include <qpdf/QPDF.hh> #include <qpdf/QPDF.hh>
class QPDFAcroFormDocumentHelper;
class QPDFPageDocumentHelper: public QPDFDocumentHelper class QPDFPageDocumentHelper: public QPDFDocumentHelper
{ {
public: public:
@ -84,7 +86,21 @@ class QPDFPageDocumentHelper: public QPDFDocumentHelper
QPDF_DLL QPDF_DLL
void removePage(QPDFPageObjectHelper page); void removePage(QPDFPageObjectHelper page);
// For every annotation, integrate the annotation's appearance
// stream into the containing page's content streams, merge the
// annotation's resources with the page's resources, and remove
// the annotation from the page. Handles widget annotations
// associated with interactive form fields as a special case,
// including removing the /AcroForm key from the document catalog.
QPDF_DLL
void flattenAnnotations();
private: private:
void flattenAnnotationsForPage(
QPDFPageObjectHelper& page,
QPDFObjectHandle& resources,
QPDFAcroFormDocumentHelper& afdh);
class Members class Members
{ {
friend class QPDFPageDocumentHelper; friend class QPDFPageDocumentHelper;

View File

@ -149,12 +149,12 @@ QPDFAnnotationObjectHelper::getAnnotationAppearanceMatrix(int rotate)
QPDFMatrix matrix; QPDFMatrix matrix;
if (matrix_obj.isMatrix()) if (matrix_obj.isMatrix())
{ {
/// QTC::TC("qpdf", "QPDFAnnotationObjectHelper explicit matrix"); QTC::TC("qpdf", "QPDFAnnotationObjectHelper explicit matrix");
matrix = QPDFMatrix(matrix_obj.getArrayAsMatrix()); matrix = QPDFMatrix(matrix_obj.getArrayAsMatrix());
} }
else else
{ {
/// QTC::TC("qpdf", "QPDFAnnotationObjectHelper default matrix"); QTC::TC("qpdf", "QPDFAnnotationObjectHelper default matrix");
} }
QPDFObjectHandle::Rectangle rect = rect_obj.getArrayAsRectangle(); QPDFObjectHandle::Rectangle rect = rect_obj.getArrayAsRectangle();
if (rotate && flags.isInteger() && (flags.getIntValue() & 16)) if (rotate && flags.isInteger() && (flags.getIntValue() & 16))
@ -176,7 +176,7 @@ QPDFAnnotationObjectHelper::getAnnotationAppearanceMatrix(int rotate)
switch (rotate) switch (rotate)
{ {
case 90: case 90:
/// QTC::TC("qpdf", "QPDFAnnotationObjectHelper rotate 90"); QTC::TC("qpdf", "QPDFAnnotationObjectHelper rotate 90");
rect = QPDFObjectHandle::Rectangle( rect = QPDFObjectHandle::Rectangle(
rect.llx, rect.llx,
rect.ury, rect.ury,
@ -184,7 +184,7 @@ QPDFAnnotationObjectHelper::getAnnotationAppearanceMatrix(int rotate)
rect.ury + rect_w); rect.ury + rect_w);
break; break;
case 180: case 180:
/// QTC::TC("qpdf", "QPDFAnnotationObjectHelper rotate 180"); QTC::TC("qpdf", "QPDFAnnotationObjectHelper rotate 180");
rect = QPDFObjectHandle::Rectangle( rect = QPDFObjectHandle::Rectangle(
rect.llx - rect_w, rect.llx - rect_w,
rect.ury, rect.ury,
@ -192,7 +192,7 @@ QPDFAnnotationObjectHelper::getAnnotationAppearanceMatrix(int rotate)
rect.ury + rect_h); rect.ury + rect_h);
break; break;
case 270: case 270:
/// QTC::TC("qpdf", "QPDFAnnotationObjectHelper rotate 270"); QTC::TC("qpdf", "QPDFAnnotationObjectHelper rotate 270");
rect = QPDFObjectHandle::Rectangle( rect = QPDFObjectHandle::Rectangle(
rect.llx - rect_h, rect.llx - rect_h,
rect.ury - rect_w, rect.ury - rect_w,

View File

@ -1,4 +1,6 @@
#include <qpdf/QPDFPageDocumentHelper.hh> #include <qpdf/QPDFPageDocumentHelper.hh>
#include <qpdf/QPDFAcroFormDocumentHelper.hh>
#include <qpdf/QTC.hh>
QPDFPageDocumentHelper::Members::~Members() QPDFPageDocumentHelper::Members::~Members()
{ {
@ -62,3 +64,128 @@ QPDFPageDocumentHelper::removePage(QPDFPageObjectHelper page)
{ {
this->qpdf.removePage(page.getObjectHandle()); this->qpdf.removePage(page.getObjectHandle());
} }
void
QPDFPageDocumentHelper::flattenAnnotations()
{
QPDFAcroFormDocumentHelper afdh(this->qpdf);
if (afdh.getNeedAppearances())
{
this->qpdf.getRoot().getKey("/AcroForm").warnIfPossible(
"document does not have updated appearance streams,"
" so form fields will not be flattened");
}
pushInheritedAttributesToPage();
std::vector<QPDFPageObjectHelper> pages = getAllPages();
for (std::vector<QPDFPageObjectHelper>::iterator iter = pages.begin();
iter != pages.end(); ++iter)
{
QPDFPageObjectHelper ph(*iter);
QPDFObjectHandle page_oh = ph.getObjectHandle();
if (page_oh.getKey("/Resources").isIndirect())
{
QTC::TC("qpdf", "QPDFPageDocumentHelper indirect resources");
page_oh.replaceKey("/Resources",
page_oh.getKey("/Resources").shallowCopy());
}
QPDFObjectHandle resources = ph.getObjectHandle().getKey("/Resources");
if (! resources.isDictionary())
{
// This should never happen and is not exercised in the
// test suite
resources = QPDFObjectHandle::newDictionary();
}
flattenAnnotationsForPage(ph, resources, afdh);
}
if (! afdh.getNeedAppearances())
{
this->qpdf.getRoot().removeKey("/AcroForm");
}
}
void
QPDFPageDocumentHelper::flattenAnnotationsForPage(
QPDFPageObjectHelper& page,
QPDFObjectHandle& resources,
QPDFAcroFormDocumentHelper& afdh)
{
bool need_appearances = afdh.getNeedAppearances();
std::vector<QPDFAnnotationObjectHelper> annots = page.getAnnotations();
std::vector<QPDFObjectHandle> new_annots;
std::string new_content;
int rotate = 0;
QPDFObjectHandle rotate_obj =
page.getObjectHandle().getKey("/Rotate");
if (rotate_obj.isInteger() && rotate_obj.getIntValue())
{
rotate = rotate_obj.getIntValue();
}
for (std::vector<QPDFAnnotationObjectHelper>::iterator iter =
annots.begin();
iter != annots.end(); ++iter)
{
QPDFAnnotationObjectHelper& aoh(*iter);
QPDFObjectHandle as = aoh.getAppearanceStream("/N");
bool is_widget = (aoh.getSubtype() == "/Widget");
bool process = true;
if (need_appearances && is_widget)
{
QTC::TC("qpdf", "QPDFPageDocumentHelper skip widget need appearances");
process = false;
}
if (process && (! as.isStream()))
{
process = false;
}
if (process)
{
resources.mergeDictionary(as.getDict().getKey("/Resources"));
if (is_widget)
{
QTC::TC("qpdf", "QPDFPageDocumentHelper merge DR");
QPDFFormFieldObjectHelper ff = afdh.getFieldForAnnotation(aoh);
resources.mergeDictionary(ff.getInheritableFieldValue("/DR"));
}
else
{
QTC::TC("qpdf", "QPDFPageDocumentHelper non-widget annotation");
}
new_content += aoh.getPageContentForAppearance(rotate);
}
else
{
new_annots.push_back(aoh.getObjectHandle());
}
}
if (new_annots.size() != annots.size())
{
QPDFObjectHandle page_oh = page.getObjectHandle();
if (new_annots.empty())
{
QTC::TC("qpdf", "QPDFPageDocumentHelper remove annots");
page_oh.removeKey("/Annots");
}
else
{
QPDFObjectHandle old_annots = page_oh.getKey("/Annots");
QPDFObjectHandle new_annots_oh =
QPDFObjectHandle::newArray(new_annots);
if (old_annots.isIndirect())
{
QTC::TC("qpdf", "QPDFPageDocumentHelper replace indirect annots");
this->qpdf.replaceObject(
old_annots.getObjGen(), new_annots_oh);
}
else
{
QTC::TC("qpdf", "QPDFPageDocumentHelper replace direct annots");
page_oh.replaceKey("/Annots", new_annots_oh);
}
}
page.addPageContents(
QPDFObjectHandle::newStream(&qpdf, "q\n"), true);
page.addPageContents(
QPDFObjectHandle::newStream(&qpdf, "\nQ\n" + new_content), false);
}
}

View File

@ -102,6 +102,7 @@ struct Options
keep_files_open_set(false), keep_files_open_set(false),
newline_before_endstream(false), newline_before_endstream(false),
coalesce_contents(false), coalesce_contents(false),
flatten_annotations(false),
show_npages(false), show_npages(false),
deterministic_id(false), deterministic_id(false),
static_id(false), static_id(false),
@ -174,6 +175,7 @@ struct Options
bool newline_before_endstream; bool newline_before_endstream;
std::string linearize_pass1; std::string linearize_pass1;
bool coalesce_contents; bool coalesce_contents;
bool flatten_annotations;
std::string min_version; std::string min_version;
std::string force_version; std::string force_version;
bool show_npages; bool show_npages;
@ -473,6 +475,7 @@ class ArgParser
void argNewlineBeforeEndstream(); void argNewlineBeforeEndstream();
void argLinearizePass1(char* parameter); void argLinearizePass1(char* parameter);
void argCoalesceContents(); void argCoalesceContents();
void argFlattenAnnotations();
void argMinVersion(char* parameter); void argMinVersion(char* parameter);
void argForceVersion(char* parameter); void argForceVersion(char* parameter);
void argSplitPages(char* parameter); void argSplitPages(char* parameter);
@ -670,6 +673,7 @@ ArgParser::initOptionTable()
(*t)["linearize-pass1"] = oe_requiredParameter( (*t)["linearize-pass1"] = oe_requiredParameter(
&ArgParser::argLinearizePass1, "filename"); &ArgParser::argLinearizePass1, "filename");
(*t)["coalesce-contents"] = oe_bare(&ArgParser::argCoalesceContents); (*t)["coalesce-contents"] = oe_bare(&ArgParser::argCoalesceContents);
(*t)["flatten-annotations"] = oe_bare(&ArgParser::argFlattenAnnotations);
(*t)["min-version"] = oe_requiredParameter( (*t)["min-version"] = oe_requiredParameter(
&ArgParser::argMinVersion, "version"); &ArgParser::argMinVersion, "version");
(*t)["force-version"] = oe_requiredParameter( (*t)["force-version"] = oe_requiredParameter(
@ -1118,6 +1122,12 @@ ArgParser::argCoalesceContents()
o.coalesce_contents = true; o.coalesce_contents = true;
} }
void
ArgParser::argFlattenAnnotations()
{
o.flatten_annotations = true;
}
void void
ArgParser::argMinVersion(char* parameter) ArgParser::argMinVersion(char* parameter)
{ {
@ -1759,6 +1769,9 @@ familiar with the PDF file format or who are PDF developers.\n\
preserve unreferenced page resources\n\ preserve unreferenced page resources\n\
--newline-before-endstream always put a newline before endstream\n\ --newline-before-endstream always put a newline before endstream\n\
--coalesce-contents force all pages' content to be a single stream\n\ --coalesce-contents force all pages' content to be a single stream\n\
--flatten-annotations incorporate rendering of annotations into page\n\
contents including those for interactive form\n\
fields\n\
--qdf turns on \"QDF mode\" (below)\n\ --qdf turns on \"QDF mode\" (below)\n\
--linearize-pass1=file write intermediate pass of linearized file\n\ --linearize-pass1=file write intermediate pass of linearized file\n\
for debugging\n\ for debugging\n\
@ -3124,6 +3137,10 @@ static void do_inspection(QPDF& pdf, Options& o)
static void handle_transformations(QPDF& pdf, Options& o) static void handle_transformations(QPDF& pdf, Options& o)
{ {
QPDFPageDocumentHelper dh(pdf); QPDFPageDocumentHelper dh(pdf);
if (o.flatten_annotations)
{
dh.flattenAnnotations();
}
if (o.coalesce_contents) if (o.coalesce_contents)
{ {
std::vector<QPDFPageObjectHelper> pages = dh.getAllPages(); std::vector<QPDFPageObjectHelper> pages = dh.getAllPages();

View File

@ -377,3 +377,15 @@ QPDFObjectHandle merge array dup 0
QPDFObjectHandle merge copy from other 0 QPDFObjectHandle merge copy from other 0
QPDFObjectHandle merge loop 0 QPDFObjectHandle merge loop 0
QPDFObjectHandle merge equal indirect 0 QPDFObjectHandle merge equal indirect 0
QPDFAnnotationObjectHelper explicit matrix 0
QPDFAnnotationObjectHelper default matrix 0
QPDFAnnotationObjectHelper rotate 90 0
QPDFAnnotationObjectHelper rotate 180 0
QPDFAnnotationObjectHelper rotate 270 0
QPDFPageDocumentHelper indirect resources 0
QPDFPageDocumentHelper skip widget need appearances 0
QPDFPageDocumentHelper merge DR 0
QPDFPageDocumentHelper non-widget annotation 0
QPDFPageDocumentHelper remove annots 0
QPDFPageDocumentHelper replace indirect annots 0
QPDFPageDocumentHelper replace direct annots 0

View File

@ -1445,6 +1445,62 @@ $td->runtest("check output",
{$td->FILE => "a.pdf"}, {$td->FILE => "a.pdf"},
{$td->FILE => "minimal-rotated.pdf"}); {$td->FILE => "minimal-rotated.pdf"});
show_ntests();
# ----------
$td->notify("--- Flatten Form/Annotations ---");
# manual-appearances was created by hand-coding appearance streams
# with graphics that make it easy to test matrix calculations. The
# result of flattening the annotations was compared visually with
# okular. Some PDF viewers don't actually display the original version
# correctly. The pages are as follows:
# - page 1: normal
# - page 2: rotate 90 with /F 20 (NoRotate)
# - page 3: non-trivial matrix
# - page 4: non-trivial matrix, rotate
# - page 5: rotate 180 with /F 20
# - page 6: rotate 90, /F 20, non-trivial matrix
# - page 7: normal -- available for additional testing
# - page 8: rotate 270 with /F 20
# - page 9: normal -- available for additional testing
#
# form-filled-by-acrobat was filled in using the Acrobat Reader
# android app. One of its appearance streams is actually an image.
#
# need-appearances is based on form-field-types with manual edits to
# turn on NeedAppearances, change /V for a field, and add the comment
# annotation from comment-annotation.pdf. The test output includes a
# flattened version of the comment annotation but not of the form
# fields.
my @annotation_files = (
'manual-appearances',
'form-filled-by-acrobat',
'comment-annotation',
'comment-annotation-direct',
'form-field-types',
'need-appearances',
);
$n_tests += 2 * scalar(@annotation_files);
foreach my $f (@annotation_files)
{
my $exp_out = {$td->STRING => "", $td->EXIT_STATUS => 0};
if (-f "$f-warn.out")
{
$exp_out = {$td->FILE => "$f-warn.out", $td->EXIT_STATUS => 3};
}
$td->runtest("flatten $f",
{$td->COMMAND =>
"qpdf --qdf --static-id --no-original-object-ids" .
" --flatten-annotations $f.pdf a.pdf"},
$exp_out,
$td->NORMALIZE_NEWLINES);
copy("a.pdf", "$f-out.pdf");
$td->runtest("check output",
{$td->FILE => "a.pdf"},
{$td->FILE => "$f-out.pdf"});
}
show_ntests(); show_ntests();
# ---------- # ----------
$td->notify("--- Merging and Splitting ---"); $td->notify("--- Merging and Splitting ---");

View File

@ -0,0 +1,232 @@
%PDF-1.3
%¿÷¢þ
%QDF-1.0
1 0 obj
<<
/Pages 2 0 R
/Type /Catalog
>>
endobj
2 0 obj
<<
/Count 1
/Kids [
3 0 R
]
/Type /Pages
>>
endobj
%% Page 1
3 0 obj
<<
/Annots [
4 0 R
]
/Contents [
5 0 R
7 0 R
9 0 R
]
/MediaBox [
0
0
612
792
]
/Parent 2 0 R
/Resources <<
/ExtGState <<
/GS0 <<
/AIS false
/BM /Normal
/CA .6
/Type /ExtGState
/ca .6
>>
>>
/Font <<
/F1 11 0 R
>>
/ProcSet 12 0 R
>>
/Type /Page
>>
endobj
4 0 obj
<<
/F 28
/Open false
/Parent 13 0 R
/Rect [
612
601
792
721
]
/Subtype /Popup
/Type /Annot
>>
endobj
%% Contents for page 1
5 0 obj
<<
/Length 6 0 R
>>
stream
q
endstream
endobj
6 0 obj
2
endobj
%% Contents for page 1
7 0 obj
<<
/Length 8 0 R
>>
stream
BT
/F1 24 Tf
72 720 Td
(Potato) Tj
ET
endstream
endobj
8 0 obj
44
endobj
%% Contents for page 1
9 0 obj
<<
/Length 10 0 R
>>
stream
Q
q
1.00000 0.00000 0.00000 1.00000 235.00000 703.00000 cm
0.00000 0.00000 18.00000 18.00000 re W n
q 1 1 1 rg 0 i 1 w 4 M 1 j 0 J []0 d /GS0 gs 1 0 0 1 9 5.0908 cm 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c h f Q 0 G 1 1 0 rg 0 i 0.60 w 4 M 1 j 0 J []0 d 1 1 0 rg 0 G 0 i 0.59 w 4 M 1 j 0 J []0 d 1 0 0 1 9 5.0908 cm 0 0 m -0.142 0 -0.28 0.008 -0.418 0.015 c -2.199 -1.969 -5.555 -2.242 -4.642 -1.42 c -4.024 -0.862 -3.916 0.111 -3.954 0.916 c -5.658 1.795 -6.772 3.222 -6.772 4.839 c -6.772 7.509 -3.74 9.674 0 9.674 c 3.74 9.674 6.772 7.509 6.772 4.839 c 6.772 2.167 3.74 0 0 0 c 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c b
Q
endstream
endobj
10 0 obj
1032
endobj
11 0 obj
<<
/BaseFont /Helvetica
/Encoding /WinAnsiEncoding
/Name /F1
/Subtype /Type1
/Type /Font
>>
endobj
12 0 obj
[
/PDF
/Text
]
endobj
13 0 obj
<<
/AP <<
/N 14 0 R
>>
/C [
1
1
0
]
/CA 1
/Contents (Salad)
/CreationDate (D:20181231235455Z00'00)
/F 28
/M (D:20181231235455Z00'00)
/Name /Comment
/P 3 0 R
/Popup 4 0 R
/Rect [
235
703
253
721
]
/Subtype /Text
/T (Jay Berkenbilt)
/Type /Annot
>>
endobj
14 0 obj
<<
/BBox [
0
0
18
18
]
/Resources <<
/ExtGState <<
/GS0 <<
/AIS false
/BM /Normal
/CA .6
/Type /ExtGState
/ca .6
>>
>>
>>
/Subtype /Form
/Type /XObject
/Length 15 0 R
>>
stream
q 1 1 1 rg 0 i 1 w 4 M 1 j 0 J []0 d /GS0 gs 1 0 0 1 9 5.0908 cm 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c h f Q 0 G 1 1 0 rg 0 i 0.60 w 4 M 1 j 0 J []0 d 1 1 0 rg 0 G 0 i 0.59 w 4 M 1 j 0 J []0 d 1 0 0 1 9 5.0908 cm 0 0 m -0.142 0 -0.28 0.008 -0.418 0.015 c -2.199 -1.969 -5.555 -2.242 -4.642 -1.42 c -4.024 -0.862 -3.916 0.111 -3.954 0.916 c -5.658 1.795 -6.772 3.222 -6.772 4.839 c -6.772 7.509 -3.74 9.674 0 9.674 c 3.74 9.674 6.772 7.509 6.772 4.839 c 6.772 2.167 3.74 0 0 0 c 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c b
endstream
endobj
%QDF: ignore_newline
15 0 obj
928
endobj
xref
0 16
0000000000 65535 f
0000000025 00000 n
0000000079 00000 n
0000000161 00000 n
0000000553 00000 n
0000000716 00000 n
0000000773 00000 n
0000000814 00000 n
0000000913 00000 n
0000000955 00000 n
0000002043 00000 n
0000002065 00000 n
0000002184 00000 n
0000002220 00000 n
0000002550 00000 n
0000003794 00000 n
trailer <<
/Root 1 0 R
/Size 16
/ID [<c5b1999a07a3fdcd0c04cfeed299c25a><31415926535897932384626433832795>]
>>
startxref
3815
%%EOF

View File

@ -0,0 +1,182 @@
%PDF-1.3
%¿÷¢þ
%QDF-1.0
1 0 obj
<<
/Pages 2 0 R
/Type /Catalog
>>
endobj
2 0 obj
<<
/Count 1
/Kids [
3 0 R
]
/Type /Pages
>>
endobj
%% Page 1
3 0 obj
<<
/Annots [
4 0 R
5 0 R
]
/Contents 6 0 R
/MediaBox [
0
0
612
792
]
/Parent 2 0 R
/Resources <<
/Font <<
/F1 8 0 R
>>
/ProcSet 9 0 R
>>
/Type /Page
>>
endobj
4 0 obj
<<
/AP <<
/N 10 0 R
>>
/C [
1
1
0
]
/CA 1
/Contents (Salad)
/CreationDate (D:20181231235455Z00'00)
/F 28
/M (D:20181231235455Z00'00)
/Name /Comment
/P 3 0 R
/Popup 5 0 R
/Rect [
235
703
253
721
]
/Subtype /Text
/T (Jay Berkenbilt)
/Type /Annot
>>
endobj
5 0 obj
<<
/F 28
/Open false
/Parent 4 0 R
/Rect [
612
601
792
721
]
/Subtype /Popup
/Type /Annot
>>
endobj
%% Contents for page 1
6 0 obj
<<
/Length 7 0 R
>>
stream
BT
/F1 24 Tf
72 720 Td
(Potato) Tj
ET
endstream
endobj
7 0 obj
44
endobj
8 0 obj
<<
/BaseFont /Helvetica
/Encoding /WinAnsiEncoding
/Name /F1
/Subtype /Type1
/Type /Font
>>
endobj
9 0 obj
[
/PDF
/Text
]
endobj
10 0 obj
<<
/BBox [
0
0
18
18
]
/Resources <<
/ExtGState <<
/GS0 <<
/AIS false
/BM /Normal
/CA .6
/Type /ExtGState
/ca .6
>>
>>
>>
/Subtype /Form
/Type /XObject
/Length 11 0 R
>>
stream
q 1 1 1 rg 0 i 1 w 4 M 1 j 0 J []0 d /GS0 gs 1 0 0 1 9 5.0908 cm 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c h f Q 0 G 1 1 0 rg 0 i 0.60 w 4 M 1 j 0 J []0 d 1 1 0 rg 0 G 0 i 0.59 w 4 M 1 j 0 J []0 d 1 0 0 1 9 5.0908 cm 0 0 m -0.142 0 -0.28 0.008 -0.418 0.015 c -2.199 -1.969 -5.555 -2.242 -4.642 -1.42 c -4.024 -0.862 -3.916 0.111 -3.954 0.916 c -5.658 1.795 -6.772 3.222 -6.772 4.839 c -6.772 7.509 -3.74 9.674 0 9.674 c 3.74 9.674 6.772 7.509 6.772 4.839 c 6.772 2.167 3.74 0 0 0 c 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c b
endstream
endobj
%QDF: ignore_newline
11 0 obj
928
endobj
xref
0 12
0000000000 65535 f
0000000025 00000 n
0000000079 00000 n
0000000161 00000 n
0000000389 00000 n
0000000718 00000 n
0000000880 00000 n
0000000979 00000 n
0000000998 00000 n
0000001116 00000 n
0000001151 00000 n
0000002395 00000 n
trailer <<
/Root 1 0 R
/Size 12
/ID [<c5b1999a07a3fdcd0c04cfeed299c25a><0ddac86998f1552ce51b2c402848bd8e>]
>>
startxref
2416
%%EOF

View File

@ -0,0 +1,237 @@
%PDF-1.3
%¿÷¢þ
%QDF-1.0
1 0 obj
<<
/Pages 2 0 R
/Type /Catalog
>>
endobj
2 0 obj
<<
/Count 1
/Kids [
3 0 R
]
/Type /Pages
>>
endobj
%% Page 1
3 0 obj
<<
/Annots 4 0 R
/Contents [
5 0 R
7 0 R
9 0 R
]
/MediaBox [
0
0
612
792
]
/Parent 2 0 R
/Resources <<
/ExtGState <<
/GS0 <<
/AIS false
/BM /Normal
/CA .6
/Type /ExtGState
/ca .6
>>
>>
/Font <<
/F1 11 0 R
>>
/ProcSet 12 0 R
>>
/Type /Page
>>
endobj
4 0 obj
[
13 0 R
]
endobj
%% Contents for page 1
5 0 obj
<<
/Length 6 0 R
>>
stream
q
endstream
endobj
6 0 obj
2
endobj
%% Contents for page 1
7 0 obj
<<
/Length 8 0 R
>>
stream
BT
/F1 24 Tf
72 720 Td
(Potato) Tj
ET
endstream
endobj
8 0 obj
44
endobj
%% Contents for page 1
9 0 obj
<<
/Length 10 0 R
>>
stream
Q
q
1.00000 0.00000 0.00000 1.00000 235.00000 703.00000 cm
0.00000 0.00000 18.00000 18.00000 re W n
q 1 1 1 rg 0 i 1 w 4 M 1 j 0 J []0 d /GS0 gs 1 0 0 1 9 5.0908 cm 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c h f Q 0 G 1 1 0 rg 0 i 0.60 w 4 M 1 j 0 J []0 d 1 1 0 rg 0 G 0 i 0.59 w 4 M 1 j 0 J []0 d 1 0 0 1 9 5.0908 cm 0 0 m -0.142 0 -0.28 0.008 -0.418 0.015 c -2.199 -1.969 -5.555 -2.242 -4.642 -1.42 c -4.024 -0.862 -3.916 0.111 -3.954 0.916 c -5.658 1.795 -6.772 3.222 -6.772 4.839 c -6.772 7.509 -3.74 9.674 0 9.674 c 3.74 9.674 6.772 7.509 6.772 4.839 c 6.772 2.167 3.74 0 0 0 c 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c b
Q
endstream
endobj
10 0 obj
1032
endobj
11 0 obj
<<
/BaseFont /Helvetica
/Encoding /WinAnsiEncoding
/Name /F1
/Subtype /Type1
/Type /Font
>>
endobj
12 0 obj
[
/PDF
/Text
]
endobj
13 0 obj
<<
/F 28
/Open false
/Parent 14 0 R
/Rect [
612
601
792
721
]
/Subtype /Popup
/Type /Annot
>>
endobj
14 0 obj
<<
/AP <<
/N 15 0 R
>>
/C [
1
1
0
]
/CA 1
/Contents (Salad)
/CreationDate (D:20181231235455Z00'00)
/F 28
/M (D:20181231235455Z00'00)
/Name /Comment
/P 3 0 R
/Popup 13 0 R
/Rect [
235
703
253
721
]
/Subtype /Text
/T (Jay Berkenbilt)
/Type /Annot
>>
endobj
15 0 obj
<<
/BBox [
0
0
18
18
]
/Resources <<
/ExtGState <<
/GS0 <<
/AIS false
/BM /Normal
/CA .6
/Type /ExtGState
/ca .6
>>
>>
>>
/Subtype /Form
/Type /XObject
/Length 16 0 R
>>
stream
q 1 1 1 rg 0 i 1 w 4 M 1 j 0 J []0 d /GS0 gs 1 0 0 1 9 5.0908 cm 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c h f Q 0 G 1 1 0 rg 0 i 0.60 w 4 M 1 j 0 J []0 d 1 1 0 rg 0 G 0 i 0.59 w 4 M 1 j 0 J []0 d 1 0 0 1 9 5.0908 cm 0 0 m -0.142 0 -0.28 0.008 -0.418 0.015 c -2.199 -1.969 -5.555 -2.242 -4.642 -1.42 c -4.024 -0.862 -3.916 0.111 -3.954 0.916 c -5.658 1.795 -6.772 3.222 -6.772 4.839 c -6.772 7.509 -3.74 9.674 0 9.674 c 3.74 9.674 6.772 7.509 6.772 4.839 c 6.772 2.167 3.74 0 0 0 c 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c b
endstream
endobj
%QDF: ignore_newline
16 0 obj
928
endobj
xref
0 17
0000000000 65535 f
0000000025 00000 n
0000000079 00000 n
0000000161 00000 n
0000000543 00000 n
0000000595 00000 n
0000000652 00000 n
0000000693 00000 n
0000000792 00000 n
0000000834 00000 n
0000001922 00000 n
0000001944 00000 n
0000002063 00000 n
0000002099 00000 n
0000002240 00000 n
0000002571 00000 n
0000003815 00000 n
trailer <<
/Root 1 0 R
/Size 17
/ID [<c5b1999a07a3fdcd0c04cfeed299c25a><31415926535897932384626433832795>]
>>
startxref
3836
%%EOF

View File

@ -0,0 +1,187 @@
%PDF-1.3
%¿÷¢þ
%QDF-1.0
1 0 obj
<<
/Pages 2 0 R
/Type /Catalog
>>
endobj
2 0 obj
<<
/Count 1
/Kids [
3 0 R
]
/Type /Pages
>>
endobj
%% Page 1
3 0 obj
<<
/Annots 4 0 R
/Contents 5 0 R
/MediaBox [
0
0
612
792
]
/Parent 2 0 R
/Resources <<
/Font <<
/F1 7 0 R
>>
/ProcSet 8 0 R
>>
/Type /Page
>>
endobj
4 0 obj
[
9 0 R
10 0 R
]
endobj
%% Contents for page 1
5 0 obj
<<
/Length 6 0 R
>>
stream
BT
/F1 24 Tf
72 720 Td
(Potato) Tj
ET
endstream
endobj
6 0 obj
44
endobj
7 0 obj
<<
/BaseFont /Helvetica
/Encoding /WinAnsiEncoding
/Name /F1
/Subtype /Type1
/Type /Font
>>
endobj
8 0 obj
[
/PDF
/Text
]
endobj
9 0 obj
<<
/AP <<
/N 11 0 R
>>
/C [
1
1
0
]
/CA 1
/Contents (Salad)
/CreationDate (D:20181231235455Z00'00)
/F 28
/M (D:20181231235455Z00'00)
/Name /Comment
/P 3 0 R
/Popup 10 0 R
/Rect [
235
703
253
721
]
/Subtype /Text
/T (Jay Berkenbilt)
/Type /Annot
>>
endobj
10 0 obj
<<
/F 28
/Open false
/Parent 9 0 R
/Rect [
612
601
792
721
]
/Subtype /Popup
/Type /Annot
>>
endobj
11 0 obj
<<
/BBox [
0
0
18
18
]
/Resources <<
/ExtGState <<
/GS0 <<
/AIS false
/BM /Normal
/CA .6
/Type /ExtGState
/ca .6
>>
>>
>>
/Subtype /Form
/Type /XObject
/Length 12 0 R
>>
stream
q 1 1 1 rg 0 i 1 w 4 M 1 j 0 J []0 d /GS0 gs 1 0 0 1 9 5.0908 cm 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c h f Q 0 G 1 1 0 rg 0 i 0.60 w 4 M 1 j 0 J []0 d 1 1 0 rg 0 G 0 i 0.59 w 4 M 1 j 0 J []0 d 1 0 0 1 9 5.0908 cm 0 0 m -0.142 0 -0.28 0.008 -0.418 0.015 c -2.199 -1.969 -5.555 -2.242 -4.642 -1.42 c -4.024 -0.862 -3.916 0.111 -3.954 0.916 c -5.658 1.795 -6.772 3.222 -6.772 4.839 c -6.772 7.509 -3.74 9.674 0 9.674 c 3.74 9.674 6.772 7.509 6.772 4.839 c 6.772 2.167 3.74 0 0 0 c 7.74 12.616 m -7.74 12.616 l -8.274 12.616 -8.707 12.184 -8.707 11.649 c -8.707 -3.831 l -8.707 -4.365 -8.274 -4.798 -7.74 -4.798 c 7.74 -4.798 l 8.274 -4.798 8.707 -4.365 8.707 -3.831 c 8.707 11.649 l 8.707 12.184 8.274 12.616 7.74 12.616 c b
endstream
endobj
%QDF: ignore_newline
12 0 obj
928
endobj
xref
0 13
0000000000 65535 f
0000000025 00000 n
0000000079 00000 n
0000000161 00000 n
0000000369 00000 n
0000000429 00000 n
0000000528 00000 n
0000000547 00000 n
0000000665 00000 n
0000000700 00000 n
0000001030 00000 n
0000001170 00000 n
0000002414 00000 n
trailer <<
/Root 1 0 R
/Size 13
/ID [<c5b1999a07a3fdcd0c04cfeed299c25a><c5b1999a07a3fdcd0c04cfeed299c25a>]
>>
startxref
2435
%%EOF

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,2 @@
WARNING: need-appearances.pdf object stream 1, object 2 0 at offset 438: document does not have updated appearance streams, so form fields will not be flattened
qpdf: operation succeeded with warnings; resulting file may have some problems

File diff suppressed because it is too large Load Diff