Merge pull request #7347 from Snuffleupagus/evaluator-more-Ref_toString
Slightly refactor the `fontRef` handling in `PartialEvaluator_loadFont` (issue 7403 and issue 7402)
This commit is contained in:
commit
5678486802
@ -662,8 +662,8 @@ var PartialEvaluator = (function PartialEvaluatorClosure() {
|
|||||||
return errorFont();
|
return errorFont();
|
||||||
}
|
}
|
||||||
|
|
||||||
// We are holding font.translated references just for fontRef that are not
|
// We are holding `font.translated` references just for `fontRef`s that
|
||||||
// dictionaries (Dict). See explanation below.
|
// are not actually `Ref`s, but rather `Dict`s. See explanation below.
|
||||||
if (font.translated) {
|
if (font.translated) {
|
||||||
return font.translated;
|
return font.translated;
|
||||||
}
|
}
|
||||||
@ -672,7 +672,12 @@ var PartialEvaluator = (function PartialEvaluatorClosure() {
|
|||||||
|
|
||||||
var preEvaluatedFont = this.preEvaluateFont(font, xref);
|
var preEvaluatedFont = this.preEvaluateFont(font, xref);
|
||||||
var descriptor = preEvaluatedFont.descriptor;
|
var descriptor = preEvaluatedFont.descriptor;
|
||||||
var fontID = fontRef.num + '_' + fontRef.gen;
|
|
||||||
|
var fontRefIsRef = isRef(fontRef), fontID;
|
||||||
|
if (fontRefIsRef) {
|
||||||
|
fontID = fontRef.toString();
|
||||||
|
}
|
||||||
|
|
||||||
if (isDict(descriptor)) {
|
if (isDict(descriptor)) {
|
||||||
if (!descriptor.fontAliases) {
|
if (!descriptor.fontAliases) {
|
||||||
descriptor.fontAliases = Object.create(null);
|
descriptor.fontAliases = Object.create(null);
|
||||||
@ -682,36 +687,53 @@ var PartialEvaluator = (function PartialEvaluatorClosure() {
|
|||||||
var hash = preEvaluatedFont.hash;
|
var hash = preEvaluatedFont.hash;
|
||||||
if (fontAliases[hash]) {
|
if (fontAliases[hash]) {
|
||||||
var aliasFontRef = fontAliases[hash].aliasRef;
|
var aliasFontRef = fontAliases[hash].aliasRef;
|
||||||
if (aliasFontRef && this.fontCache.has(aliasFontRef)) {
|
if (fontRefIsRef && aliasFontRef &&
|
||||||
|
this.fontCache.has(aliasFontRef)) {
|
||||||
this.fontCache.putAlias(fontRef, aliasFontRef);
|
this.fontCache.putAlias(fontRef, aliasFontRef);
|
||||||
return this.fontCache.get(fontRef);
|
return this.fontCache.get(fontRef);
|
||||||
}
|
}
|
||||||
}
|
} else {
|
||||||
|
|
||||||
if (!fontAliases[hash]) {
|
|
||||||
fontAliases[hash] = {
|
fontAliases[hash] = {
|
||||||
fontID: Font.getFontID()
|
fontID: Font.getFontID()
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
fontAliases[hash].aliasRef = fontRef;
|
if (fontRefIsRef) {
|
||||||
|
fontAliases[hash].aliasRef = fontRef;
|
||||||
|
}
|
||||||
fontID = fontAliases[hash].fontID;
|
fontID = fontAliases[hash].fontID;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Workaround for bad PDF generators that don't reference fonts
|
// Workaround for bad PDF generators that reference fonts incorrectly,
|
||||||
// properly, i.e. by not using an object identifier.
|
// where `fontRef` is a `Dict` rather than a `Ref` (fixes bug946506.pdf).
|
||||||
// Check if the fontRef is a Dict (as opposed to a standard object),
|
// In this case we should not put the font into `this.fontCache` (which is
|
||||||
// in which case we don't cache the font and instead reference it by
|
// a `RefSetCache`), since it's not meaningful to use a `Dict` as a key.
|
||||||
// fontName in font.loadedName below.
|
//
|
||||||
var fontRefIsDict = isDict(fontRef);
|
// However, if we don't cache the font it's not possible to remove it
|
||||||
if (!fontRefIsDict) {
|
// when `cleanup` is triggered from the API, which causes issues on
|
||||||
|
// subsequent rendering operations (see issue7403.pdf).
|
||||||
|
// A simple workaround would be to just not hold `font.translated`
|
||||||
|
// references in this case, but this would force us to unnecessarily load
|
||||||
|
// the same fonts over and over.
|
||||||
|
//
|
||||||
|
// Instead, we cheat a bit by attempting to use a modified `fontID` as a
|
||||||
|
// key in `this.fontCache`, to allow the font to be cached.
|
||||||
|
// NOTE: This works because `RefSetCache` calls `toString()` on provided
|
||||||
|
// keys. Also, since `fontRef` is used when getting cached fonts,
|
||||||
|
// we'll not accidentally match fonts cached with the `fontID`.
|
||||||
|
if (fontRefIsRef) {
|
||||||
this.fontCache.put(fontRef, fontCapability.promise);
|
this.fontCache.put(fontRef, fontCapability.promise);
|
||||||
|
} else {
|
||||||
|
if (!fontID) {
|
||||||
|
fontID = (this.uniquePrefix || 'F_') + (++this.idCounters.obj);
|
||||||
|
}
|
||||||
|
this.fontCache.put('id_' + fontID, fontCapability.promise);
|
||||||
}
|
}
|
||||||
|
assert(fontID, 'The "fontID" must be defined.');
|
||||||
|
|
||||||
// Keep track of each font we translated so the caller can
|
// Keep track of each font we translated so the caller can
|
||||||
// load them asynchronously before calling display on a page.
|
// load them asynchronously before calling display on a page.
|
||||||
font.loadedName = 'g_' + this.pdfManager.docId + '_f' + (fontRefIsDict ?
|
font.loadedName = 'g_' + this.pdfManager.docId + '_f' + fontID;
|
||||||
fontName.replace(/\W/g, '') : fontID);
|
|
||||||
|
|
||||||
font.translated = fontCapability.promise;
|
font.translated = fontCapability.promise;
|
||||||
|
|
||||||
@ -2121,7 +2143,7 @@ var PartialEvaluator = (function PartialEvaluatorClosure() {
|
|||||||
if (isName(encoding)) {
|
if (isName(encoding)) {
|
||||||
hash.update(encoding.name);
|
hash.update(encoding.name);
|
||||||
} else if (isRef(encoding)) {
|
} else if (isRef(encoding)) {
|
||||||
hash.update(encoding.num + '_' + encoding.gen);
|
hash.update(encoding.toString());
|
||||||
} else if (isDict(encoding)) {
|
} else if (isDict(encoding)) {
|
||||||
var keys = encoding.getKeys();
|
var keys = encoding.getKeys();
|
||||||
for (var i = 0, ii = keys.length; i < ii; i++) {
|
for (var i = 0, ii = keys.length; i < ii; i++) {
|
||||||
@ -2129,7 +2151,7 @@ var PartialEvaluator = (function PartialEvaluatorClosure() {
|
|||||||
if (isName(entry)) {
|
if (isName(entry)) {
|
||||||
hash.update(entry.name);
|
hash.update(entry.name);
|
||||||
} else if (isRef(entry)) {
|
} else if (isRef(entry)) {
|
||||||
hash.update(entry.num + '_' + entry.gen);
|
hash.update(entry.toString());
|
||||||
} else if (isArray(entry)) { // 'Differences' entry.
|
} else if (isArray(entry)) { // 'Differences' entry.
|
||||||
// Ideally we should check the contents of the array, but to avoid
|
// Ideally we should check the contents of the array, but to avoid
|
||||||
// parsing it here and then again in |extractDataStructures|,
|
// parsing it here and then again in |extractDataStructures|,
|
||||||
|
1
test/pdfs/.gitignore
vendored
1
test/pdfs/.gitignore
vendored
@ -28,6 +28,7 @@
|
|||||||
!issue7180.pdf
|
!issue7180.pdf
|
||||||
!issue7200.pdf
|
!issue7200.pdf
|
||||||
!issue7229.pdf
|
!issue7229.pdf
|
||||||
|
!issue7403.pdf
|
||||||
!issue7426.pdf
|
!issue7426.pdf
|
||||||
!issue7439.pdf
|
!issue7439.pdf
|
||||||
!issue7492.pdf
|
!issue7492.pdf
|
||||||
|
BIN
test/pdfs/issue7403.pdf
Normal file
BIN
test/pdfs/issue7403.pdf
Normal file
Binary file not shown.
@ -962,6 +962,13 @@
|
|||||||
"rounds": 1,
|
"rounds": 1,
|
||||||
"type": "eq"
|
"type": "eq"
|
||||||
},
|
},
|
||||||
|
{ "id": "issue7403",
|
||||||
|
"file": "pdfs/issue7403.pdf",
|
||||||
|
"md5": "0f7bb6b3c58e33bbf76ce5161cd665c3",
|
||||||
|
"link": false,
|
||||||
|
"rounds": 1,
|
||||||
|
"type": "eq"
|
||||||
|
},
|
||||||
{ "id": "protectip",
|
{ "id": "protectip",
|
||||||
"file": "pdfs/protectip.pdf",
|
"file": "pdfs/protectip.pdf",
|
||||||
"md5": "676e7a7b8f96d04825361832b1838a93",
|
"md5": "676e7a7b8f96d04825361832b1838a93",
|
||||||
|
Loading…
x
Reference in New Issue
Block a user