Skip to content

Commit 0308b80

Browse files
authored
Merge pull request #18824 from calixteman/issue18072
Write the display flags in F entry when saving an annotation (issue 18072)
2 parents 3cdc325 + 2481a4b commit 0308b80

File tree

5 files changed

+120
-11
lines changed

5 files changed

+120
-11
lines changed

src/core/annotation.js

+65-8
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ import {
2727
getModificationDate,
2828
IDENTITY_MATRIX,
2929
info,
30+
isArrayEqual,
3031
LINE_DESCENT_FACTOR,
3132
LINE_FACTOR,
3233
OPS,
@@ -723,6 +724,38 @@ class Annotation {
723724
return !!(flags & flag);
724725
}
725726

727+
_buildFlags(noView, noPrint) {
728+
let { flags } = this;
729+
if (noView === undefined) {
730+
if (noPrint === undefined) {
731+
return undefined;
732+
}
733+
if (noPrint) {
734+
return flags & ~AnnotationFlag.PRINT;
735+
}
736+
return (flags & ~AnnotationFlag.HIDDEN) | AnnotationFlag.PRINT;
737+
}
738+
739+
if (noView) {
740+
flags |= AnnotationFlag.PRINT;
741+
if (noPrint) {
742+
// display === 1.
743+
return (flags & ~AnnotationFlag.NOVIEW) | AnnotationFlag.HIDDEN;
744+
}
745+
// display === 3.
746+
return (flags & ~AnnotationFlag.HIDDEN) | AnnotationFlag.NOVIEW;
747+
}
748+
749+
flags &= ~(AnnotationFlag.HIDDEN | AnnotationFlag.NOVIEW);
750+
if (noPrint) {
751+
// display === 2.
752+
return flags & ~AnnotationFlag.PRINT;
753+
}
754+
755+
// display === 0.
756+
return flags | AnnotationFlag.PRINT;
757+
}
758+
726759
/**
727760
* @private
728761
*/
@@ -2073,10 +2106,15 @@ class WidgetAnnotation extends Annotation {
20732106

20742107
async save(evaluator, task, annotationStorage) {
20752108
const storageEntry = annotationStorage?.get(this.data.id);
2109+
const flags = this._buildFlags(storageEntry?.noView, storageEntry?.noPrint);
20762110
let value = storageEntry?.value,
20772111
rotation = storageEntry?.rotation;
20782112
if (value === this.data.fieldValue || value === undefined) {
2079-
if (!this._hasValueFromXFA && rotation === undefined) {
2113+
if (
2114+
!this._hasValueFromXFA &&
2115+
rotation === undefined &&
2116+
flags === undefined
2117+
) {
20802118
return null;
20812119
}
20822120
value ||= this.data.fieldValue;
@@ -2088,8 +2126,8 @@ class WidgetAnnotation extends Annotation {
20882126
!this._hasValueFromXFA &&
20892127
Array.isArray(value) &&
20902128
Array.isArray(this.data.fieldValue) &&
2091-
value.length === this.data.fieldValue.length &&
2092-
value.every((x, i) => x === this.data.fieldValue[i])
2129+
isArrayEqual(value, this.data.fieldValue) &&
2130+
flags === undefined
20932131
) {
20942132
return null;
20952133
}
@@ -2106,7 +2144,7 @@ class WidgetAnnotation extends Annotation {
21062144
RenderingIntentFlag.SAVE,
21072145
annotationStorage
21082146
);
2109-
if (appearance === null) {
2147+
if (appearance === null && flags === undefined) {
21102148
// Appearance didn't change.
21112149
return null;
21122150
}
@@ -2134,6 +2172,15 @@ class WidgetAnnotation extends Annotation {
21342172
dict.set(key, originalDict.getRaw(key));
21352173
}
21362174
}
2175+
if (flags !== undefined) {
2176+
dict.set("F", flags);
2177+
if (appearance === null && !needAppearances) {
2178+
const ap = originalDict.getRaw("AP");
2179+
if (ap) {
2180+
dict.set("AP", ap);
2181+
}
2182+
}
2183+
}
21372184

21382185
const xfa = {
21392186
path: this.data.fieldName,
@@ -3019,10 +3066,11 @@ class ButtonWidgetAnnotation extends WidgetAnnotation {
30193066
return null;
30203067
}
30213068
const storageEntry = annotationStorage.get(this.data.id);
3069+
const flags = this._buildFlags(storageEntry?.noView, storageEntry?.noPrint);
30223070
let rotation = storageEntry?.rotation,
30233071
value = storageEntry?.value;
30243072

3025-
if (rotation === undefined) {
3073+
if (rotation === undefined && flags === undefined) {
30263074
if (value === undefined) {
30273075
return null;
30283076
}
@@ -3033,10 +3081,11 @@ class ButtonWidgetAnnotation extends WidgetAnnotation {
30333081
}
30343082
}
30353083

3036-
const dict = evaluator.xref.fetchIfRef(this.ref);
3084+
let dict = evaluator.xref.fetchIfRef(this.ref);
30373085
if (!(dict instanceof Dict)) {
30383086
return null;
30393087
}
3088+
dict = dict.clone();
30403089

30413090
if (rotation === undefined) {
30423091
rotation = this.rotation;
@@ -3054,6 +3103,9 @@ class ButtonWidgetAnnotation extends WidgetAnnotation {
30543103
dict.set("V", name);
30553104
dict.set("AS", name);
30563105
dict.set("M", `D:${getModificationDate()}`);
3106+
if (flags !== undefined) {
3107+
dict.set("F", flags);
3108+
}
30573109

30583110
const maybeMK = this._getMKDict(rotation);
30593111
if (maybeMK) {
@@ -3071,10 +3123,11 @@ class ButtonWidgetAnnotation extends WidgetAnnotation {
30713123
return null;
30723124
}
30733125
const storageEntry = annotationStorage.get(this.data.id);
3126+
const flags = this._buildFlags(storageEntry?.noView, storageEntry?.noPrint);
30743127
let rotation = storageEntry?.rotation,
30753128
value = storageEntry?.value;
30763129

3077-
if (rotation === undefined) {
3130+
if (rotation === undefined && flags === undefined) {
30783131
if (value === undefined) {
30793132
return null;
30803133
}
@@ -3085,10 +3138,11 @@ class ButtonWidgetAnnotation extends WidgetAnnotation {
30853138
}
30863139
}
30873140

3088-
const dict = evaluator.xref.fetchIfRef(this.ref);
3141+
let dict = evaluator.xref.fetchIfRef(this.ref);
30893142
if (!(dict instanceof Dict)) {
30903143
return null;
30913144
}
3145+
dict = dict.clone();
30923146

30933147
if (value === undefined) {
30943148
value = this.data.fieldValue === this.data.buttonValue;
@@ -3121,6 +3175,9 @@ class ButtonWidgetAnnotation extends WidgetAnnotation {
31213175

31223176
dict.set("AS", name);
31233177
dict.set("M", `D:${getModificationDate()}`);
3178+
if (flags !== undefined) {
3179+
dict.set("F", flags);
3180+
}
31243181

31253182
const maybeMK = this._getMKDict(rotation);
31263183
if (maybeMK) {

src/core/document.js

-3
Original file line numberDiff line numberDiff line change
@@ -378,9 +378,6 @@ class Page {
378378
return this._parsedAnnotations.then(function (annotations) {
379379
const newRefsPromises = [];
380380
for (const annotation of annotations) {
381-
if (!annotation.mustBePrinted(annotationStorage)) {
382-
continue;
383-
}
384381
newRefsPromises.push(
385382
annotation
386383
.save(partialEvaluator, task, annotationStorage)

test/pdfs/.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -671,3 +671,4 @@
671671
!bug1919513.pdf
672672
!issue16038.pdf
673673
!highlight_popup.pdf
674+
!issue18072.pdf

test/pdfs/issue18072.pdf

7.03 KB
Binary file not shown.

test/test_manifest.json

+54
Original file line numberDiff line numberDiff line change
@@ -10524,5 +10524,59 @@
1052410524
"md5": "47262993e04689c327b7ce85396bce99",
1052510525
"rounds": 1,
1052610526
"type": "eq"
10527+
},
10528+
{
10529+
"id": "issue18072-save-print",
10530+
"file": "pdfs/issue18072.pdf",
10531+
"md5": "231fe6f035da1f2ddf84f2a78ada20c5",
10532+
"rounds": 1,
10533+
"type": "eq",
10534+
"save": true,
10535+
"print": true,
10536+
"annotationStorage": {
10537+
"28R": {
10538+
"noView": true,
10539+
"noPrint": true
10540+
},
10541+
"29R": {
10542+
"noView": true,
10543+
"noPrint": false
10544+
},
10545+
"30R": {
10546+
"noView": false,
10547+
"noPrint": true
10548+
},
10549+
"31R": {
10550+
"noView": false,
10551+
"noPrint": false
10552+
}
10553+
}
10554+
},
10555+
{
10556+
"id": "issue18072-save-annotations",
10557+
"file": "pdfs/issue18072.pdf",
10558+
"md5": "231fe6f035da1f2ddf84f2a78ada20c5",
10559+
"rounds": 1,
10560+
"type": "eq",
10561+
"save": true,
10562+
"annotations": true,
10563+
"annotationStorage": {
10564+
"28R": {
10565+
"noView": true,
10566+
"noPrint": true
10567+
},
10568+
"29R": {
10569+
"noView": true,
10570+
"noPrint": false
10571+
},
10572+
"30R": {
10573+
"noView": false,
10574+
"noPrint": true
10575+
},
10576+
"31R": {
10577+
"noView": false,
10578+
"noPrint": false
10579+
}
10580+
}
1052710581
}
1052810582
]

0 commit comments

Comments
 (0)