Merge pull request #13461 from Snuffleupagus/issue-6605
Improve text-selection for Type3 fonts with empty /FontBBox-entries (issue 6605)
This commit is contained in:
commit
2b63d97b9d
@ -2115,7 +2115,7 @@ class PartialEvaluator {
|
|||||||
|
|
||||||
if (
|
if (
|
||||||
font.isType3Font &&
|
font.isType3Font &&
|
||||||
textState.fontSize <= 1 &&
|
(textState.fontSize <= 1 || font.isCharBBox) &&
|
||||||
!isArrayEqual(textState.fontMatrix, FONT_IDENTITY_MATRIX)
|
!isArrayEqual(textState.fontMatrix, FONT_IDENTITY_MATRIX)
|
||||||
) {
|
) {
|
||||||
const glyphHeight = font.bbox[3] - font.bbox[1];
|
const glyphHeight = font.bbox[3] - font.bbox[1];
|
||||||
@ -2251,6 +2251,20 @@ class PartialEvaluator {
|
|||||||
function handleSetFont(fontName, fontRef) {
|
function handleSetFont(fontName, fontRef) {
|
||||||
return self
|
return self
|
||||||
.loadFont(fontName, fontRef, resources)
|
.loadFont(fontName, fontRef, resources)
|
||||||
|
.then(function (translated) {
|
||||||
|
if (!translated.font.isType3Font) {
|
||||||
|
return translated;
|
||||||
|
}
|
||||||
|
return translated
|
||||||
|
.loadType3Data(self, resources, task)
|
||||||
|
.catch(function () {
|
||||||
|
// Ignore Type3-parsing errors, since we only use `loadType3Data`
|
||||||
|
// here to ensure that we'll always obtain a useful /FontBBox.
|
||||||
|
})
|
||||||
|
.then(function () {
|
||||||
|
return translated;
|
||||||
|
});
|
||||||
|
})
|
||||||
.then(function (translated) {
|
.then(function (translated) {
|
||||||
textState.font = translated.font;
|
textState.font = translated.font;
|
||||||
textState.fontMatrix =
|
textState.fontMatrix =
|
||||||
@ -3815,7 +3829,7 @@ class PartialEvaluator {
|
|||||||
firstChar,
|
firstChar,
|
||||||
lastChar,
|
lastChar,
|
||||||
toUnicode,
|
toUnicode,
|
||||||
bbox: descriptor.getArray("FontBBox"),
|
bbox: descriptor.getArray("FontBBox") || dict.getArray("FontBBox"),
|
||||||
ascent: descriptor.get("Ascent"),
|
ascent: descriptor.get("Ascent"),
|
||||||
descent: descriptor.get("Descent"),
|
descent: descriptor.get("Descent"),
|
||||||
xHeight: descriptor.get("XHeight"),
|
xHeight: descriptor.get("XHeight"),
|
||||||
@ -3962,6 +3976,9 @@ class TranslatedFont {
|
|||||||
const fontResources = this.dict.get("Resources") || resources;
|
const fontResources = this.dict.get("Resources") || resources;
|
||||||
const charProcOperatorList = Object.create(null);
|
const charProcOperatorList = Object.create(null);
|
||||||
|
|
||||||
|
const isEmptyBBox =
|
||||||
|
!translatedFont.bbox || isArrayEqual(translatedFont.bbox, [0, 0, 0, 0]);
|
||||||
|
|
||||||
for (const key of charProcs.getKeys()) {
|
for (const key of charProcs.getKeys()) {
|
||||||
loadCharProcsPromise = loadCharProcsPromise.then(() => {
|
loadCharProcsPromise = loadCharProcsPromise.then(() => {
|
||||||
const glyphStream = charProcs.get(key);
|
const glyphStream = charProcs.get(key);
|
||||||
@ -3981,7 +3998,7 @@ class TranslatedFont {
|
|||||||
// colour-related parameters) in the graphics state;
|
// colour-related parameters) in the graphics state;
|
||||||
// any use of such operators shall be ignored."
|
// any use of such operators shall be ignored."
|
||||||
if (operatorList.fnArray[0] === OPS.setCharWidthAndBounds) {
|
if (operatorList.fnArray[0] === OPS.setCharWidthAndBounds) {
|
||||||
this._removeType3ColorOperators(operatorList);
|
this._removeType3ColorOperators(operatorList, isEmptyBBox);
|
||||||
}
|
}
|
||||||
charProcOperatorList[key] = operatorList.getIR();
|
charProcOperatorList[key] = operatorList.getIR();
|
||||||
|
|
||||||
@ -3996,8 +4013,12 @@ class TranslatedFont {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
this.type3Loaded = loadCharProcsPromise.then(function () {
|
this.type3Loaded = loadCharProcsPromise.then(() => {
|
||||||
translatedFont.charProcOperatorList = charProcOperatorList;
|
translatedFont.charProcOperatorList = charProcOperatorList;
|
||||||
|
if (this._bbox) {
|
||||||
|
translatedFont.isCharBBox = true;
|
||||||
|
translatedFont.bbox = this._bbox;
|
||||||
|
}
|
||||||
});
|
});
|
||||||
return this.type3Loaded;
|
return this.type3Loaded;
|
||||||
}
|
}
|
||||||
@ -4005,7 +4026,7 @@ class TranslatedFont {
|
|||||||
/**
|
/**
|
||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
_removeType3ColorOperators(operatorList) {
|
_removeType3ColorOperators(operatorList, isEmptyBBox = false) {
|
||||||
if (
|
if (
|
||||||
typeof PDFJSDev === "undefined" ||
|
typeof PDFJSDev === "undefined" ||
|
||||||
PDFJSDev.test("!PRODUCTION || TESTING")
|
PDFJSDev.test("!PRODUCTION || TESTING")
|
||||||
@ -4015,6 +4036,17 @@ class TranslatedFont {
|
|||||||
"Type3 glyph shall start with the d1 operator."
|
"Type3 glyph shall start with the d1 operator."
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
if (isEmptyBBox) {
|
||||||
|
if (!this._bbox) {
|
||||||
|
this._bbox = [Infinity, Infinity, -Infinity, -Infinity];
|
||||||
|
}
|
||||||
|
const charBBox = Util.normalizeRect(operatorList.argsArray[0].slice(2));
|
||||||
|
|
||||||
|
this._bbox[0] = Math.min(this._bbox[0], charBBox[0]);
|
||||||
|
this._bbox[1] = Math.min(this._bbox[1], charBBox[1]);
|
||||||
|
this._bbox[2] = Math.max(this._bbox[2], charBBox[2]);
|
||||||
|
this._bbox[3] = Math.max(this._bbox[3], charBBox[3]);
|
||||||
|
}
|
||||||
let i = 1,
|
let i = 1,
|
||||||
ii = operatorList.length;
|
ii = operatorList.length;
|
||||||
while (i < ii) {
|
while (i < ii) {
|
||||||
|
1
test/pdfs/.gitignore
vendored
1
test/pdfs/.gitignore
vendored
@ -437,6 +437,7 @@
|
|||||||
!quadpoints.pdf
|
!quadpoints.pdf
|
||||||
!transparent.pdf
|
!transparent.pdf
|
||||||
!xobject-image.pdf
|
!xobject-image.pdf
|
||||||
|
!issue6605.pdf
|
||||||
!ccitt_EndOfBlock_false.pdf
|
!ccitt_EndOfBlock_false.pdf
|
||||||
!issue9972-1.pdf
|
!issue9972-1.pdf
|
||||||
!issue9972-2.pdf
|
!issue9972-2.pdf
|
||||||
|
BIN
test/pdfs/issue6605.pdf
Normal file
BIN
test/pdfs/issue6605.pdf
Normal file
Binary file not shown.
@ -4935,6 +4935,12 @@
|
|||||||
"type": "eq",
|
"type": "eq",
|
||||||
"annotations": true
|
"annotations": true
|
||||||
},
|
},
|
||||||
|
{ "id": "issue6605",
|
||||||
|
"file": "pdfs/issue6605.pdf",
|
||||||
|
"md5": "67158a9c6d0e966ece55f7c433e18cc5",
|
||||||
|
"rounds": 1,
|
||||||
|
"type": "text"
|
||||||
|
},
|
||||||
{ "id": "annotation-choice-widget-forms",
|
{ "id": "annotation-choice-widget-forms",
|
||||||
"file": "pdfs/annotation-choice-widget.pdf",
|
"file": "pdfs/annotation-choice-widget.pdf",
|
||||||
"md5": "7dfb0d743a0da0f4a71b209ab43b0be5",
|
"md5": "7dfb0d743a0da0f4a71b209ab43b0be5",
|
||||||
|
Loading…
Reference in New Issue
Block a user