Merge pull request #14585 from Snuffleupagus/PDFObjects-private

Improve the `PDFObjects` class
This commit is contained in:
Tim van der Meij 2022-02-20 14:53:58 +01:00 committed by GitHub
commit 3635a9a333
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -91,7 +91,7 @@ const DefaultStandardFontDataFactory =
*/ */
/** /**
* @type IPDFStreamFactory * @type {IPDFStreamFactory}
* @private * @private
*/ */
let createPDFNetworkStream; let createPDFNetworkStream;
@ -1229,6 +1229,7 @@ class PDFPageProxy {
this._transport = transport; this._transport = transport;
this._stats = pdfBug ? new StatTimer() : null; this._stats = pdfBug ? new StatTimer() : null;
this._pdfBug = pdfBug; this._pdfBug = pdfBug;
/** @type {PDFObjects} */
this.commonObjs = transport.commonObjs; this.commonObjs = transport.commonObjs;
this.objs = new PDFObjects(); this.objs = new PDFObjects();
@ -3046,25 +3047,24 @@ class WorkerTransport {
* A PDF document and page is built of many objects. E.g. there are objects for * A PDF document and page is built of many objects. E.g. there are objects for
* fonts, images, rendering code, etc. These objects may get processed inside of * fonts, images, rendering code, etc. These objects may get processed inside of
* a worker. This class implements some basic methods to manage these objects. * a worker. This class implements some basic methods to manage these objects.
* @ignore
*/ */
class PDFObjects { class PDFObjects {
constructor() { #objs = Object.create(null);
this._objs = Object.create(null);
}
/** /**
* Ensures there is an object defined for `objId`. * Ensures there is an object defined for `objId`.
* @private *
* @param {string} objId
* @returns {Object}
*/ */
_ensureObj(objId) { #ensureObj(objId) {
if (this._objs[objId]) { const obj = this.#objs[objId];
return this._objs[objId]; if (obj) {
return obj;
} }
return (this._objs[objId] = { return (this.#objs[objId] = {
capability: createPromiseCapability(), capability: createPromiseCapability(),
data: null, data: null,
resolved: false,
}); });
} }
@ -3075,43 +3075,53 @@ class PDFObjects {
* If called *with* a callback, the callback is called with the data of the * If called *with* a callback, the callback is called with the data of the
* object once the object is resolved. That means, if you call this method * object once the object is resolved. That means, if you call this method
* and the object is already resolved, the callback gets called right away. * and the object is already resolved, the callback gets called right away.
*
* @param {string} objId
* @param {function} [callback]
* @returns {any}
*/ */
get(objId, callback = null) { get(objId, callback = null) {
// If there is a callback, then the get can be async and the object is // If there is a callback, then the get can be async and the object is
// not required to be resolved right now. // not required to be resolved right now.
if (callback) { if (callback) {
this._ensureObj(objId).capability.promise.then(callback); const obj = this.#ensureObj(objId);
obj.capability.promise.then(() => callback(obj.data));
return null; return null;
} }
// If there isn't a callback, the user expects to get the resolved data // If there isn't a callback, the user expects to get the resolved data
// directly. // directly.
const obj = this._objs[objId]; const obj = this.#objs[objId];
// If there isn't an object yet or the object isn't resolved, then the // If there isn't an object yet or the object isn't resolved, then the
// data isn't ready yet! // data isn't ready yet!
if (!obj || !obj.resolved) { if (!obj?.capability.settled) {
throw new Error(`Requesting object that isn't resolved yet ${objId}.`); throw new Error(`Requesting object that isn't resolved yet ${objId}.`);
} }
return obj.data; return obj.data;
} }
/**
* @param {string} objId
* @returns {boolean}
*/
has(objId) { has(objId) {
const obj = this._objs[objId]; const obj = this.#objs[objId];
return obj?.resolved || false; return obj?.capability.settled || false;
} }
/** /**
* Resolves the object `objId` with optional `data`. * Resolves the object `objId` with optional `data`.
*
* @param {string} objId
* @param {any} [data]
*/ */
resolve(objId, data) { resolve(objId, data = null) {
const obj = this._ensureObj(objId); const obj = this.#ensureObj(objId);
obj.resolved = true;
obj.data = data; obj.data = data;
obj.capability.resolve(data); obj.capability.resolve();
} }
clear() { clear() {
this._objs = Object.create(null); this.#objs = Object.create(null);
} }
} }