1
0
mirror of https://github.com/janeczku/calibre-web synced 2025-11-03 00:33:02 +00:00

Update pdf.js to version 4.4.168

This commit is contained in:
Ozzie Isaacs
2024-07-13 10:49:47 +02:00
parent a6931b4936
commit 87c0b15f5f
10 changed files with 1155 additions and 559 deletions

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long

View File

@@ -142,7 +142,7 @@ function scrollIntoView(element, spot, scrollMatches = false) {
}
parent.scrollTop = offsetY;
}
function watchScroll(viewAreaElement, callback) {
function watchScroll(viewAreaElement, callback, abortSignal = undefined) {
const debounceScroll = function (evt) {
if (rAF) {
return;
@@ -172,7 +172,13 @@ function watchScroll(viewAreaElement, callback) {
_eventHandler: debounceScroll
};
let rAF = null;
viewAreaElement.addEventListener("scroll", debounceScroll, true);
viewAreaElement.addEventListener("scroll", debounceScroll, {
useCapture: true,
signal: abortSignal
});
abortSignal?.addEventListener("abort", () => window.cancelAnimationFrame(rAF), {
once: true
});
return state;
}
function parseQueryString(query) {
@@ -250,9 +256,8 @@ function approximateFraction(x) {
}
return result;
}
function roundToDivide(x, div) {
const r = x % div;
return r === 0 ? x : Math.round(x - r + div);
function floorToDivide(x, div) {
return x - x % div;
}
function getPageSizeInches({
view,
@@ -738,6 +743,10 @@ const defaultOptions = {
value: "",
kind: OptionKind.API
},
enableHWA: {
value: true,
kind: OptionKind.API + OptionKind.VIEWER + OptionKind.PREFERENCE
},
enableXfa: {
value: true,
kind: OptionKind.API + OptionKind.PREFERENCE
@@ -1357,9 +1366,18 @@ class EventBus {
}
}
}
class AutomationEventBus extends EventBus {
class FirefoxEventBus extends EventBus {
#externalServices;
#globalEventNames;
#isInAutomation;
constructor(globalEventNames, externalServices, isInAutomation) {
super();
this.#globalEventNames = globalEventNames;
this.#externalServices = externalServices;
this.#isInAutomation = isInAutomation;
}
dispatch(eventName, data) {
throw new Error("Not implemented: AutomationEventBus.dispatch");
throw new Error("Not implemented: FirefoxEventBus.dispatch");
}
}
@@ -1384,6 +1402,10 @@ class BaseExternalServices {
throw new Error("Not implemented: updateEditorStates");
}
async getNimbusExperimentData() {}
async getGlobalEventNames() {
return null;
}
dispatchGlobalEvent(_event) {}
}
;// CONCATENATED MODULE: ./web/preferences.js
@@ -1430,6 +1452,7 @@ class BasePreferences {
disableFontFace: false,
disableRange: false,
disableStream: false,
enableHWA: true,
enableXfa: true,
viewerCssTheme: 0
});
@@ -2743,6 +2766,9 @@ class DOMLocalization extends Localization {
this.pauseObserving();
if (this.roots.size === 0) {
this.mutationObserver = null;
if (this.windowElement && this.pendingrAF) {
this.windowElement.cancelAnimationFrame(this.pendingrAF);
}
this.windowElement = null;
this.pendingrAF = null;
this.pendingElements.clear();
@@ -2843,6 +2869,7 @@ class DOMLocalization extends Localization {
;// CONCATENATED MODULE: ./web/l10n.js
class L10n {
#dir;
#elements = new Set();
#lang;
#l10n;
constructor({
@@ -2877,11 +2904,19 @@ class L10n {
return messages?.[0].value || fallback;
}
async translate(element) {
this.#elements.add(element);
try {
this.#l10n.connectRoot(element);
await this.#l10n.translateRoots();
} catch {}
}
async destroy() {
for (const element of this.#elements) {
this.#l10n.disconnectRoot(element);
}
this.#elements.clear();
this.#l10n.pauseObserving();
}
pause() {
this.#l10n.pauseObserving();
}
@@ -2954,8 +2989,7 @@ class genericl10n_GenericL10n extends L10n {
const bundle = await this.#createBundle(lang, baseURL, paths);
if (bundle) {
yield bundle;
}
if (lang === "en-us") {
} else if (lang === "en-us") {
yield this.#createBundleFallback(lang);
}
}
@@ -3625,13 +3659,6 @@ function download(blobUrl, filename) {
}
class DownloadManager {
#openBlobUrls = new WeakMap();
downloadUrl(url, filename, _options) {
if (!createValidAbsoluteUrl(url, "http://example.com")) {
console.error(`downloadUrl - not a valid URL: ${url}`);
return;
}
download(url + "#pdfjs.action=download", filename);
}
downloadData(data, filename, contentType) {
const blobUrl = URL.createObjectURL(new Blob([data], {
type: contentType
@@ -3666,8 +3693,19 @@ class DownloadManager {
this.downloadData(data, filename, contentType);
return false;
}
download(blob, url, filename, _options) {
const blobUrl = URL.createObjectURL(blob);
download(data, url, filename, _options) {
let blobUrl;
if (data) {
blobUrl = URL.createObjectURL(new Blob([data], {
type: "application/pdf"
}));
} else {
if (!createValidAbsoluteUrl(url, "http://example.com")) {
console.error(`download - not a valid URL: ${url}`);
return;
}
blobUrl = url + "#pdfjs.action=download";
}
download(blobUrl, filename);
}
}
@@ -5180,6 +5218,7 @@ class PDFFindController {
source: this,
state,
previous,
entireWord: this.#state?.entireWord ?? null,
matchesCount: this.#requestMatchesCount(),
rawQuery: this.#state?.query ?? null
});
@@ -7711,7 +7750,8 @@ class PDFThumbnailView {
optionalContentConfigPromise,
linkService,
renderingQueue,
pageColors
pageColors,
enableHWA
}) {
this.id = id;
this.renderingId = "thumbnail" + id;
@@ -7722,6 +7762,7 @@ class PDFThumbnailView {
this.pdfPageRotate = defaultViewport.rotation;
this._optionalContentConfigPromise = optionalContentConfigPromise || null;
this.pageColors = pageColors || null;
this.enableHWA = enableHWA || false;
this.eventBus = eventBus;
this.linkService = linkService;
this.renderingQueue = renderingQueue;
@@ -7805,10 +7846,11 @@ class PDFThumbnailView {
}
this.resume = null;
}
#getPageDrawContext(upscaleFactor = 1) {
#getPageDrawContext(upscaleFactor = 1, enableHWA = this.enableHWA) {
const canvas = document.createElement("canvas");
const ctx = canvas.getContext("2d", {
alpha: false
alpha: false,
willReadFrequently: !enableHWA
});
const outputScale = new OutputScale();
canvas.width = upscaleFactor * this.canvasWidth * outputScale.sx | 0;
@@ -7927,7 +7969,7 @@ class PDFThumbnailView {
const {
ctx,
canvas
} = this.#getPageDrawContext();
} = this.#getPageDrawContext(1, true);
if (img.width <= 2 * canvas.width) {
ctx.drawImage(img, 0, 0, img.width, img.height, 0, 0, canvas.width, canvas.height);
return canvas;
@@ -7974,14 +8016,17 @@ class PDFThumbnailViewer {
eventBus,
linkService,
renderingQueue,
pageColors
pageColors,
abortSignal,
enableHWA
}) {
this.container = container;
this.eventBus = eventBus;
this.linkService = linkService;
this.renderingQueue = renderingQueue;
this.pageColors = pageColors || null;
this.scroll = watchScroll(this.container, this.#scrollUpdated.bind(this));
this.enableHWA = enableHWA || false;
this.scroll = watchScroll(this.container, this.#scrollUpdated.bind(this), abortSignal);
this.#resetView();
}
#scrollUpdated() {
@@ -8102,7 +8147,8 @@ class PDFThumbnailViewer {
optionalContentConfigPromise,
linkService: this.linkService,
renderingQueue: this.renderingQueue,
pageColors: this.pageColors
pageColors: this.pageColors,
enableHWA: this.enableHWA
});
this._thumbnails.push(thumbnail);
}
@@ -8932,13 +8978,6 @@ class TextLayerBuilder {
this.div.tabIndex = 0;
this.div.className = "textLayer";
}
#finishRendering() {
this.#renderingDone = true;
const endOfContent = document.createElement("div");
endOfContent.className = "endOfContent";
this.div.append(endOfContent);
this.#bindMouse(endOfContent);
}
async render(viewport, textContentParams = null) {
if (this.#renderingDone && this.#textLayer) {
this.#textLayer.update({
@@ -8964,7 +9003,11 @@ class TextLayerBuilder {
this.highlighter?.setTextMapping(textDivs, textContentItemsStr);
this.accessibilityManager?.setTextMapping(textDivs);
await this.#textLayer.render();
this.#finishRendering();
this.#renderingDone = true;
const endOfContent = document.createElement("div");
endOfContent.className = "endOfContent";
this.div.append(endOfContent);
this.#bindMouse(endOfContent);
this.#onAppend?.(this.div);
this.highlighter?.enable();
this.accessibilityManager?.enable();
@@ -9097,6 +9140,7 @@ const DEFAULT_LAYER_PROPERTIES = null;
const LAYERS_ORDER = new Map([["canvasWrapper", 0], ["textLayer", 1], ["annotationLayer", 2], ["annotationEditorLayer", 3], ["xfaLayer", 3]]);
class PDFPageView {
#annotationMode = AnnotationMode.ENABLE_FORMS;
#enableHWA = false;
#hasRestrictedScaling = false;
#layerProperties = null;
#loadingId = null;
@@ -9129,6 +9173,7 @@ class PDFPageView {
this.imageResourcesPath = options.imageResourcesPath || "";
this.maxCanvasPixels = options.maxCanvasPixels ?? AppOptions.get("maxCanvasPixels");
this.pageColors = options.pageColors || null;
this.#enableHWA = options.enableHWA || false;
this.eventBus = options.eventBus;
this.renderingQueue = options.renderingQueue;
this.l10n = options.l10n;
@@ -9739,7 +9784,8 @@ class PDFPageView {
canvasWrapper.append(canvas);
this.canvas = canvas;
const ctx = canvas.getContext("2d", {
alpha: false
alpha: false,
willReadFrequently: !this.#enableHWA
});
const outputScale = this.outputScale = new OutputScale();
if (this.maxCanvasPixels === 0) {
@@ -9760,13 +9806,13 @@ class PDFPageView {
}
const sfx = approximateFraction(outputScale.sx);
const sfy = approximateFraction(outputScale.sy);
canvas.width = roundToDivide(width * outputScale.sx, sfx[0]);
canvas.height = roundToDivide(height * outputScale.sy, sfy[0]);
canvas.width = floorToDivide(width * outputScale.sx, sfx[0]);
canvas.height = floorToDivide(height * outputScale.sy, sfy[0]);
const {
style
} = canvas;
style.width = roundToDivide(width, sfx[1]) + "px";
style.height = roundToDivide(height, sfy[1]) + "px";
style.width = floorToDivide(width, sfx[1]) + "px";
style.height = floorToDivide(height, sfy[1]) + "px";
this.#viewportMap.set(canvas, viewport);
const transform = outputScale.scaled ? [outputScale.sx, 0, 0, outputScale.sy, 0, 0] : null;
const renderContext = {
@@ -9870,8 +9916,8 @@ class PDFPageView {
const DEFAULT_CACHE_SIZE = 10;
const PagesCountLimit = {
FORCE_SCROLL_MODE_PAGE: 15000,
FORCE_LAZY_PAGE_INIT: 7500,
FORCE_SCROLL_MODE_PAGE: 10000,
FORCE_LAZY_PAGE_INIT: 5000,
PAUSE_EAGER_PAGE_INIT: 250
};
function isValidAnnotationEditorMode(mode) {
@@ -9933,6 +9979,7 @@ class PDFViewer {
#annotationEditorUIManager = null;
#annotationMode = AnnotationMode.ENABLE_FORMS;
#containerTopLeft = null;
#enableHWA = false;
#enableHighlightFloatingButton = false;
#enablePermissions = false;
#eventAbortController = null;
@@ -9946,7 +9993,7 @@ class PDFViewer {
#scaleTimeoutId = null;
#textLayerMode = TextLayerMode.ENABLE;
constructor(options) {
const viewerVersion = "4.3.136";
const viewerVersion = "4.4.168";
if (version !== viewerVersion) {
throw new Error(`The API version "${version}" does not match the Viewer version "${viewerVersion}".`);
}
@@ -9982,6 +10029,7 @@ class PDFViewer {
this.#enablePermissions = options.enablePermissions || false;
this.pageColors = options.pageColors || null;
this.#mlManager = options.mlManager || null;
this.#enableHWA = options.enableHWA || false;
this.defaultRenderingQueue = !options.renderingQueue;
if (this.defaultRenderingQueue) {
this.renderingQueue = new PDFRenderingQueue();
@@ -9989,7 +10037,16 @@ class PDFViewer {
} else {
this.renderingQueue = options.renderingQueue;
}
this.scroll = watchScroll(this.container, this._scrollUpdate.bind(this));
const {
abortSignal
} = options;
abortSignal?.addEventListener("abort", () => {
this.#resizeObserver.disconnect();
this.#resizeObserver = null;
}, {
once: true
});
this.scroll = watchScroll(this.container, this._scrollUpdate.bind(this), abortSignal);
this.presentationModeState = PresentationModeState.UNKNOWN;
this._resetView();
if (this.removePageBorders) {
@@ -10254,10 +10311,14 @@ class PDFViewer {
return;
}
this.#getAllTextInProgress = true;
const savedCursor = this.container.style.cursor;
this.container.style.cursor = "wait";
const interruptCopy = ev => this.#interruptCopyCondition = ev.key === "Escape";
window.addEventListener("keydown", interruptCopy);
const {
classList
} = this.viewer;
classList.add("copyAll");
const ac = new AbortController();
window.addEventListener("keydown", ev => this.#interruptCopyCondition = ev.key === "Escape", {
signal: ac.signal
});
this.getAllText().then(async text => {
if (text !== null) {
await navigator.clipboard.writeText(text);
@@ -10267,8 +10328,8 @@ class PDFViewer {
}).finally(() => {
this.#getAllTextInProgress = false;
this.#interruptCopyCondition = false;
window.removeEventListener("keydown", interruptCopy);
this.container.style.cursor = savedCursor;
ac.abort();
classList.remove("copyAll");
});
event.preventDefault();
event.stopPropagation();
@@ -10401,7 +10462,8 @@ class PDFViewer {
maxCanvasPixels: this.maxCanvasPixels,
pageColors,
l10n: this.l10n,
layerProperties: this._layerProperties
layerProperties: this._layerProperties,
enableHWA: this.#enableHWA
});
this._pages.push(pageView);
}
@@ -11549,26 +11611,26 @@ class SecondaryToolbar {
eventDetails
} of buttons) {
if ( element !== null ) {
element.addEventListener("click", evt => {
if (eventName !== null) {
eventBus.dispatch(eventName, {
source: this,
...eventDetails
});
element.addEventListener("click", evt => {
if (eventName !== null) {
eventBus.dispatch(eventName, {
source: this,
...eventDetails
});
}
if (close) {
this.close();
}
eventBus.dispatch("reporttelemetry", {
source: this,
details: {
type: "buttons",
data: {
id: element.id
}
if (close) {
this.close();
}
eventBus.dispatch("reporttelemetry", {
source: this,
details: {
type: "buttons",
data: {
id: element.id
}
}
});
}
});
});
}
}
eventBus._on("cursortoolchanged", this.#cursorToolChanged.bind(this));
@@ -12059,9 +12121,11 @@ const PDFViewerApplication = {
isViewerEmbedded: window.parent !== window,
url: "",
baseUrl: "",
_allowedGlobalEventsPromise: null,
_downloadUrl: "",
_eventBusAbortController: null,
_windowAbortController: null,
_globalAbortController: new AbortController(),
documentInfo: null,
metadata: null,
_contentDispositionFilename: null,
@@ -12202,7 +12266,8 @@ const PDFViewerApplication = {
externalServices,
l10n
} = this;
const eventBus = AppOptions.get("isInAutomation") ? new AutomationEventBus() : new EventBus();
let eventBus;
eventBus = new EventBus();
this.eventBus = eventBus;
this.overlayManager = new OverlayManager();
const pdfRenderingQueue = new PDFRenderingQueue();
@@ -12236,6 +12301,7 @@ const PDFViewerApplication = {
foreground: AppOptions.get("pageColorsForeground")
} : null;
const altTextManager = appConfig.altTextDialog ? new AltTextManager(appConfig.altTextDialog, container, this.overlayManager, eventBus) : null;
const enableHWA = AppOptions.get("enableHWA");
const pdfViewer = new PDFViewer({
container,
viewer,
@@ -12257,7 +12323,9 @@ const PDFViewerApplication = {
maxCanvasPixels: AppOptions.get("maxCanvasPixels"),
enablePermissions: AppOptions.get("enablePermissions"),
pageColors,
mlManager: this.mlManager
mlManager: this.mlManager,
abortSignal: this._globalAbortController.signal,
enableHWA
});
this.pdfViewer = pdfViewer;
pdfRenderingQueue.setViewer(pdfViewer);
@@ -12269,7 +12337,9 @@ const PDFViewerApplication = {
eventBus,
renderingQueue: pdfRenderingQueue,
linkService: pdfLinkService,
pageColors
pageColors,
abortSignal: this._globalAbortController.signal,
enableHWA
});
pdfRenderingQueue.setThumbnailViewer(this.pdfThumbnailViewer);
}
@@ -12378,7 +12448,7 @@ const PDFViewerApplication = {
const params = parseQueryString(queryString);
file = params.get("file") ?? AppOptions.get("defaultUrl");
validateFileURL(file);
/* const fileInput = this._openFileInput = document.createElement("input");
/*const fileInput = this._openFileInput = document.createElement("input");
fileInput.id = "fileInput";
fileInput.hidden = true;
fileInput.type = "file";
@@ -12395,24 +12465,28 @@ const PDFViewerApplication = {
source: this,
fileInput: evt.target
});
});*/
});
appConfig.mainContainer.addEventListener("dragover", function (evt) {
evt.preventDefault();
evt.dataTransfer.dropEffect = evt.dataTransfer.effectAllowed === "copy" ? "copy" : "move";
for (const item of evt.dataTransfer.items) {
if (item.type === "application/pdf") {
evt.dataTransfer.dropEffect = evt.dataTransfer.effectAllowed === "copy" ? "copy" : "move";
evt.preventDefault();
evt.stopPropagation();
return;
}
}
});
appConfig.mainContainer.addEventListener("drop", function (evt) {
evt.preventDefault();
const {
files
} = evt.dataTransfer;
if (!files || files.length === 0) {
if (evt.dataTransfer.files?.[0].type !== "application/pdf") {
return;
}
/*eventBus.dispatch("fileinputchange", {
evt.preventDefault();
evt.stopPropagation();
eventBus.dispatch("fileinputchange", {
source: this,
fileInput: evt.dataTransfer
});*/
});
});
});*/
if (!AppOptions.get("supportsDocumentFonts")) {
AppOptions.set("disableFontFace", true);
this.l10n.get("pdfjs-web-fonts-disabled").then(msg => {
@@ -12647,25 +12721,14 @@ const PDFViewerApplication = {
});
});
},
_ensureDownloadComplete() {
if (this.pdfDocument && this.downloadComplete) {
return;
}
throw new Error("PDF document not downloaded.");
},
async download(options = {}) {
const url = this._downloadUrl,
filename = this._docFilename;
let data;
try {
this._ensureDownloadComplete();
const data = await this.pdfDocument.getData();
const blob = new Blob([data], {
type: "application/pdf"
});
await this.downloadManager.download(blob, url, filename, options);
} catch {
await this.downloadManager.downloadUrl(url, filename, options);
}
if (this.downloadComplete) {
data = await this.pdfDocument.getData();
}
} catch {}
this.downloadManager.download(data, this._downloadUrl, this._docFilename, options);
},
async save(options = {}) {
if (this._saveInProgress) {
@@ -12673,15 +12736,9 @@ const PDFViewerApplication = {
}
this._saveInProgress = true;
await this.pdfScriptingManager.dispatchWillSave();
const url = this._downloadUrl,
filename = this._docFilename;
try {
this._ensureDownloadComplete();
const data = await this.pdfDocument.saveDocument();
const blob = new Blob([data], {
type: "application/pdf"
});
await this.downloadManager.download(blob, url, filename, options);
this.downloadManager.download(data, this._downloadUrl, this._docFilename, options);
} catch (reason) {
console.error(`Error when saving the document: ${reason.message}`);
await this.download(options);
@@ -12699,12 +12756,13 @@ const PDFViewerApplication = {
});
}
},
downloadOrSave(options = {}) {
if (this.pdfDocument?.annotationStorage.size > 0) {
this.save(options);
} else {
this.download(options);
}
async downloadOrSave(options = {}) {
const {
classList
} = this.appConfig.appContainer;
classList.add("wait");
await (this.pdfDocument?.annotationStorage.size > 0 ? this.save(options) : this.download(options));
classList.remove("wait");
},
async _documentError(key, moreInfo = null) {
this._unblockDocumentLoadEvent();
@@ -13471,6 +13529,14 @@ const PDFViewerApplication = {
this._windowAbortController?.abort();
this._windowAbortController = null;
},
async testingClose() {
this.unbindEvents();
this.unbindWindowEvents();
this._globalAbortController?.abort();
this._globalAbortController = null;
this.findBar?.close();
await Promise.all([this.l10n?.destroy(), this.close()]);
},
_accumulateTicks(ticks, prop) {
if (this[prop] > 0 && ticks < 0 || this[prop] < 0 && ticks > 0) {
this[prop] = 0;
@@ -13664,7 +13730,7 @@ function webViewerHashchange(evt) {
}
}
{
var webViewerFileInputChange = function (evt) {
/*var webViewerFileInputChange = function (evt) {
if (PDFViewerApplication.pdfViewer?.isInPresentationMode) {
return;
}
@@ -13674,7 +13740,7 @@ function webViewerHashchange(evt) {
originalUrl: file.name
});
};
/*var webViewerOpenFile = function (evt) {
var webViewerOpenFile = function (evt) {
PDFViewerApplication._openFileInput?.click();
};*/
}
@@ -13768,6 +13834,7 @@ function webViewerUpdateFindMatchesCount({
function webViewerUpdateFindControlState({
state,
previous,
entireWord,
matchesCount,
rawQuery
}) {
@@ -13775,6 +13842,7 @@ function webViewerUpdateFindControlState({
PDFViewerApplication.externalServices.updateFindControlState({
result: state,
findPrevious: previous,
entireWord,
matchesCount,
rawQuery
});
@@ -14066,14 +14134,14 @@ function webViewerKeyDown(evt) {
});
handled = true;
break;
/*case 79:
case 79:
{
eventBus.dispatch("openfile", {
source: window
});
handled = true;
}
break;*/
break;
}
}
if (cmd === 3 || cmd === 10) {
@@ -14273,8 +14341,8 @@ function webViewerReportTelemetry({
const pdfjsVersion = "4.3.136";
const pdfjsBuild = "0cec64437";
const pdfjsVersion = "4.4.168";
const pdfjsBuild = "19fbc8998";
const AppConstants = {
LinkTarget: LinkTarget,
RenderingStates: RenderingStates,