mirror of
https://github.com/mozilla/pdf.js.git
synced 2025-04-19 06:38:07 +02:00
[Editor] Add the possibility to change a signature description (bug 1948116)
This commit is contained in:
parent
a877493826
commit
1d82b2ce94
16 changed files with 480 additions and 141 deletions
|
@ -597,3 +597,15 @@ pdfjs-editor-add-signature-add-button = Add
|
||||||
pdfjs-editor-delete-signature-button =
|
pdfjs-editor-delete-signature-button =
|
||||||
.title = Remove signature
|
.title = Remove signature
|
||||||
pdfjs-editor-delete-signature-button-label = Remove signature
|
pdfjs-editor-delete-signature-button-label = Remove signature
|
||||||
|
|
||||||
|
## Editor toolbar
|
||||||
|
|
||||||
|
pdfjs-editor-add-signature-edit-button-label = Edit description
|
||||||
|
|
||||||
|
## Edit signature description dialog
|
||||||
|
|
||||||
|
pdfjs-editor-edit-signature-dialog-title = Edit description
|
||||||
|
|
||||||
|
## Dialog buttons
|
||||||
|
|
||||||
|
pdfjs-editor-edit-signature-update-button = Update
|
||||||
|
|
|
@ -606,7 +606,8 @@ class SignatureExtractor {
|
||||||
[pageWidth, pageHeight] = [pageHeight, pageWidth];
|
[pageWidth, pageHeight] = [pageHeight, pageWidth];
|
||||||
}
|
}
|
||||||
|
|
||||||
const { curves, thickness, width, height } = lines;
|
const { curves, width, height } = lines;
|
||||||
|
const thickness = lines.thickness ?? 0;
|
||||||
const linesAndPoints = [];
|
const linesAndPoints = [];
|
||||||
const ratio = Math.min(pageWidth / width, pageHeight / height);
|
const ratio = Math.min(pageWidth / width, pageHeight / height);
|
||||||
const xScale = ratio / pageWidth;
|
const xScale = ratio / pageWidth;
|
||||||
|
|
|
@ -62,10 +62,10 @@ class DrawnSignatureOptions extends InkDrawingOptions {
|
||||||
class SignatureEditor extends DrawingEditor {
|
class SignatureEditor extends DrawingEditor {
|
||||||
#isExtracted = false;
|
#isExtracted = false;
|
||||||
|
|
||||||
#signatureData = null;
|
|
||||||
|
|
||||||
#description = null;
|
#description = null;
|
||||||
|
|
||||||
|
#signatureData = null;
|
||||||
|
|
||||||
#signatureUUID = null;
|
#signatureUUID = null;
|
||||||
|
|
||||||
static _type = "signature";
|
static _type = "signature";
|
||||||
|
@ -78,6 +78,7 @@ class SignatureEditor extends DrawingEditor {
|
||||||
super({ ...params, mustBeCommitted: true, name: "signatureEditor" });
|
super({ ...params, mustBeCommitted: true, name: "signatureEditor" });
|
||||||
this._willKeepAspectRatio = true;
|
this._willKeepAspectRatio = true;
|
||||||
this.#signatureData = params.signatureData || null;
|
this.#signatureData = params.signatureData || null;
|
||||||
|
this.#description = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @inheritdoc */
|
/** @inheritdoc */
|
||||||
|
@ -155,9 +156,7 @@ class SignatureEditor extends DrawingEditor {
|
||||||
mustSmooth,
|
mustSmooth,
|
||||||
areContours,
|
areContours,
|
||||||
});
|
});
|
||||||
this.#signatureData = null;
|
this.addSignature(outline, heightInPage, description, uuid);
|
||||||
this.#signatureUUID = uuid;
|
|
||||||
this.addSignature(outline.outline, heightInPage, description);
|
|
||||||
} else {
|
} else {
|
||||||
this.div.hidden = true;
|
this.div.hidden = true;
|
||||||
this._uiManager.getSignature(this);
|
this._uiManager.getSignature(this);
|
||||||
|
@ -169,14 +168,65 @@ class SignatureEditor extends DrawingEditor {
|
||||||
|
|
||||||
setUuid(uuid) {
|
setUuid(uuid) {
|
||||||
this.#signatureUUID = uuid;
|
this.#signatureUUID = uuid;
|
||||||
|
this.addEditToolbar();
|
||||||
}
|
}
|
||||||
|
|
||||||
setDescription(description) {
|
getUuid() {
|
||||||
|
return this.#signatureUUID;
|
||||||
|
}
|
||||||
|
|
||||||
|
get description() {
|
||||||
|
return this.#description;
|
||||||
|
}
|
||||||
|
|
||||||
|
set description(description) {
|
||||||
this.#description = description;
|
this.#description = description;
|
||||||
|
super.addEditToolbar().then(toolbar => {
|
||||||
|
toolbar?.updateEditSignatureButton(description);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
addSignature(outline, heightInPage, description) {
|
getSignaturePreview() {
|
||||||
|
const { newCurves, areContours, thickness, width, height } =
|
||||||
|
this.#signatureData;
|
||||||
|
const maxDim = Math.max(width, height);
|
||||||
|
const outlineData = SignatureExtractor.processDrawnLines({
|
||||||
|
lines: {
|
||||||
|
curves: newCurves.map(points => ({ points })),
|
||||||
|
thickness,
|
||||||
|
width,
|
||||||
|
height,
|
||||||
|
},
|
||||||
|
pageWidth: maxDim,
|
||||||
|
pageHeight: maxDim,
|
||||||
|
rotation: 0,
|
||||||
|
innerMargin: 0,
|
||||||
|
mustSmooth: false,
|
||||||
|
areContours,
|
||||||
|
});
|
||||||
|
return { areContours, outline: outlineData.outline };
|
||||||
|
}
|
||||||
|
|
||||||
|
/** @inheritdoc */
|
||||||
|
async addEditToolbar() {
|
||||||
|
const toolbar = await super.addEditToolbar();
|
||||||
|
if (!toolbar) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (this._uiManager.signatureManager && this.#description !== null) {
|
||||||
|
await toolbar.addEditSignatureButton(
|
||||||
|
this._uiManager.signatureManager,
|
||||||
|
this.#signatureUUID,
|
||||||
|
this.#description
|
||||||
|
);
|
||||||
|
toolbar.show();
|
||||||
|
}
|
||||||
|
return toolbar;
|
||||||
|
}
|
||||||
|
|
||||||
|
addSignature(data, heightInPage, description, uuid) {
|
||||||
const { x: savedX, y: savedY } = this;
|
const { x: savedX, y: savedY } = this;
|
||||||
|
const { outline } = (this.#signatureData = data);
|
||||||
this.#isExtracted = outline instanceof ContourDrawOutline;
|
this.#isExtracted = outline instanceof ContourDrawOutline;
|
||||||
this.#description = description;
|
this.#description = description;
|
||||||
let drawingOptions;
|
let drawingOptions;
|
||||||
|
@ -208,6 +258,7 @@ class SignatureEditor extends DrawingEditor {
|
||||||
this.onScaleChanging();
|
this.onScaleChanging();
|
||||||
this.rotate();
|
this.rotate();
|
||||||
this._uiManager.addToAnnotationStorage(this);
|
this._uiManager.addToAnnotationStorage(this);
|
||||||
|
this.setUuid(uuid);
|
||||||
|
|
||||||
this.div.hidden = false;
|
this.div.hidden = false;
|
||||||
}
|
}
|
||||||
|
@ -335,7 +386,7 @@ class SignatureEditor extends DrawingEditor {
|
||||||
static async deserialize(data, parent, uiManager) {
|
static async deserialize(data, parent, uiManager) {
|
||||||
const editor = await super.deserialize(data, parent, uiManager);
|
const editor = await super.deserialize(data, parent, uiManager);
|
||||||
editor.#isExtracted = data.areContours;
|
editor.#isExtracted = data.areContours;
|
||||||
editor.#description = data.accessibilityData?.alt || "";
|
editor.description = data.accessibilityData?.alt || "";
|
||||||
editor.#signatureUUID = data.uuid;
|
editor.#signatureUUID = data.uuid;
|
||||||
return editor;
|
return editor;
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,6 +26,8 @@ class EditorToolbar {
|
||||||
|
|
||||||
#altText = null;
|
#altText = null;
|
||||||
|
|
||||||
|
#signatureDescriptionButton = null;
|
||||||
|
|
||||||
static #l10nRemove = null;
|
static #l10nRemove = null;
|
||||||
|
|
||||||
constructor(editor) {
|
constructor(editor) {
|
||||||
|
@ -154,6 +156,19 @@ class EditorToolbar {
|
||||||
this.#buttons.prepend(button, this.#divider);
|
this.#buttons.prepend(button, this.#divider);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async addEditSignatureButton(signatureManager) {
|
||||||
|
const button = (this.#signatureDescriptionButton =
|
||||||
|
await signatureManager.renderEditButton(this.#editor));
|
||||||
|
this.#addListenersToElement(button);
|
||||||
|
this.#buttons.prepend(button, this.#divider);
|
||||||
|
}
|
||||||
|
|
||||||
|
updateEditSignatureButton(description) {
|
||||||
|
if (this.#signatureDescriptionButton) {
|
||||||
|
this.#signatureDescriptionButton.title = description;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
remove() {
|
remove() {
|
||||||
this.#toolbar.remove();
|
this.#toolbar.remove();
|
||||||
this.#colorPicker?.destroy();
|
this.#colorPicker?.destroy();
|
||||||
|
|
|
@ -1012,6 +1012,10 @@ class AnnotationEditorUIManager {
|
||||||
this.#signatureManager?.getSignature({ uiManager: this, editor });
|
this.#signatureManager?.getSignature({ uiManager: this, editor });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get signatureManager() {
|
||||||
|
return this.#signatureManager;
|
||||||
|
}
|
||||||
|
|
||||||
switchToMode(mode, callback) {
|
switchToMode(mode, callback) {
|
||||||
// Switching to a mode can be asynchronous.
|
// Switching to a mode can be asynchronous.
|
||||||
this._eventBus.on("annotationeditormodechanged", callback, {
|
this._eventBus.on("annotationeditormodechanged", callback, {
|
||||||
|
|
|
@ -465,11 +465,15 @@ const PDFViewerApplication = {
|
||||||
AppOptions.get("enableSignatureEditor") && appConfig.addSignatureDialog
|
AppOptions.get("enableSignatureEditor") && appConfig.addSignatureDialog
|
||||||
? new SignatureManager(
|
? new SignatureManager(
|
||||||
appConfig.addSignatureDialog,
|
appConfig.addSignatureDialog,
|
||||||
|
appConfig.editSignatureDialog,
|
||||||
appConfig.annotationEditorParams?.editorSignatureAddSignature ||
|
appConfig.annotationEditorParams?.editorSignatureAddSignature ||
|
||||||
null,
|
null,
|
||||||
this.overlayManager,
|
this.overlayManager,
|
||||||
l10n,
|
l10n,
|
||||||
externalServices.createSignatureStorage(),
|
externalServices.createSignatureStorage(
|
||||||
|
eventBus,
|
||||||
|
this._globalAbortController.signal
|
||||||
|
),
|
||||||
eventBus
|
eventBus
|
||||||
)
|
)
|
||||||
: null;
|
: null;
|
||||||
|
|
|
@ -422,8 +422,8 @@ class ExternalServices extends BaseExternalServices {
|
||||||
return new GenericScripting(AppOptions.get("sandboxBundleSrc"));
|
return new GenericScripting(AppOptions.get("sandboxBundleSrc"));
|
||||||
}
|
}
|
||||||
|
|
||||||
createSignatureStorage() {
|
createSignatureStorage(eventBus, signal) {
|
||||||
return new SignatureStorage();
|
return new SignatureStorage(eventBus, signal);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -201,7 +201,7 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
button:not(:is(.toggle-button, .closeButton)) {
|
button:not(:is(.toggle-button, .closeButton, .clearInputButton)) {
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
border: 1px solid;
|
border: 1px solid;
|
||||||
font: menu;
|
font: menu;
|
||||||
|
|
|
@ -496,13 +496,33 @@ class MLManager {
|
||||||
}
|
}
|
||||||
|
|
||||||
class SignatureStorage {
|
class SignatureStorage {
|
||||||
|
#eventBus = null;
|
||||||
|
|
||||||
#signatures = null;
|
#signatures = null;
|
||||||
|
|
||||||
|
#signal = null;
|
||||||
|
|
||||||
|
constructor(eventBus, signal) {
|
||||||
|
this.#eventBus = eventBus;
|
||||||
|
this.#signal = signal;
|
||||||
|
}
|
||||||
|
|
||||||
#handleSignature(data) {
|
#handleSignature(data) {
|
||||||
return FirefoxCom.requestAsync("handleSignature", data);
|
return FirefoxCom.requestAsync("handleSignature", data);
|
||||||
}
|
}
|
||||||
|
|
||||||
async getAll() {
|
async getAll() {
|
||||||
|
if (this.#signal) {
|
||||||
|
window.addEventListener(
|
||||||
|
"storedSignaturesChanged",
|
||||||
|
() => {
|
||||||
|
this.#signatures = null;
|
||||||
|
this.#eventBus?.dispatch("storedsignatureschanged", { source: this });
|
||||||
|
},
|
||||||
|
{ signal: this.#signal }
|
||||||
|
);
|
||||||
|
this.#signal = null;
|
||||||
|
}
|
||||||
if (!this.#signatures) {
|
if (!this.#signatures) {
|
||||||
this.#signatures = new Map();
|
this.#signatures = new Map();
|
||||||
const data = await this.#handleSignature({ action: "get" });
|
const data = await this.#handleSignature({ action: "get" });
|
||||||
|
@ -546,19 +566,6 @@ class SignatureStorage {
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
async update(uuid, data) {
|
|
||||||
const signatures = await this.getAll();
|
|
||||||
const oldData = signatures.get(uuid);
|
|
||||||
if (!oldData) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (await this.#handleSignature({ action: "update", uuid, ...data })) {
|
|
||||||
Object.assign(oldData, data);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class ExternalServices extends BaseExternalServices {
|
class ExternalServices extends BaseExternalServices {
|
||||||
|
@ -647,8 +654,8 @@ class ExternalServices extends BaseExternalServices {
|
||||||
return FirefoxScripting;
|
return FirefoxScripting;
|
||||||
}
|
}
|
||||||
|
|
||||||
createSignatureStorage() {
|
createSignatureStorage(eventBus, signal) {
|
||||||
return new SignatureStorage();
|
return new SignatureStorage(eventBus, signal);
|
||||||
}
|
}
|
||||||
|
|
||||||
dispatchGlobalEvent(event) {
|
dispatchGlobalEvent(event) {
|
||||||
|
|
|
@ -15,24 +15,50 @@
|
||||||
|
|
||||||
import { getUuid } from "pdfjs-lib";
|
import { getUuid } from "pdfjs-lib";
|
||||||
|
|
||||||
|
const KEY_STORAGE = "pdfjs.signature";
|
||||||
|
|
||||||
class SignatureStorage {
|
class SignatureStorage {
|
||||||
// TODO: Encrypt the data in using a password and add a UI for entering it.
|
// TODO: Encrypt the data in using a password and add a UI for entering it.
|
||||||
// We could use the Web Crypto API for this (see https://bradyjoslin.com/blog/encryption-webcrypto/
|
// We could use the Web Crypto API for this (see https://bradyjoslin.com/blog/encryption-webcrypto/
|
||||||
// for an example).
|
// for an example).
|
||||||
|
|
||||||
|
#eventBus;
|
||||||
|
|
||||||
#signatures = null;
|
#signatures = null;
|
||||||
|
|
||||||
|
#signal = null;
|
||||||
|
|
||||||
|
constructor(eventBus, signal) {
|
||||||
|
this.#eventBus = eventBus;
|
||||||
|
this.#signal = signal;
|
||||||
|
}
|
||||||
|
|
||||||
#save() {
|
#save() {
|
||||||
localStorage.setItem(
|
localStorage.setItem(
|
||||||
"pdfjs.signature",
|
KEY_STORAGE,
|
||||||
JSON.stringify(Object.fromEntries(this.#signatures.entries()))
|
JSON.stringify(Object.fromEntries(this.#signatures.entries()))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
async getAll() {
|
async getAll() {
|
||||||
|
if (this.#signal) {
|
||||||
|
window.addEventListener(
|
||||||
|
"storage",
|
||||||
|
({ key }) => {
|
||||||
|
if (key === KEY_STORAGE) {
|
||||||
|
this.#signatures = null;
|
||||||
|
this.#eventBus?.dispatch("storedsignatureschanged", {
|
||||||
|
source: this,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{ signal: this.#signal }
|
||||||
|
);
|
||||||
|
this.#signal = null;
|
||||||
|
}
|
||||||
if (!this.#signatures) {
|
if (!this.#signatures) {
|
||||||
this.#signatures = new Map();
|
this.#signatures = new Map();
|
||||||
const data = localStorage.getItem("pdfjs.signature");
|
const data = localStorage.getItem(KEY_STORAGE);
|
||||||
if (data) {
|
if (data) {
|
||||||
for (const [key, value] of Object.entries(JSON.parse(data))) {
|
for (const [key, value] of Object.entries(JSON.parse(data))) {
|
||||||
this.#signatures.set(key, value);
|
this.#signatures.set(key, value);
|
||||||
|
@ -68,18 +94,6 @@ class SignatureStorage {
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
async update(uuid, data) {
|
|
||||||
const signatures = await this.getAll();
|
|
||||||
const oldData = signatures.get(uuid);
|
|
||||||
if (!oldData) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
Object.assign(oldData, data);
|
|
||||||
this.#save();
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export { SignatureStorage };
|
export { SignatureStorage };
|
||||||
|
|
|
@ -47,8 +47,8 @@ class ExternalServices extends BaseExternalServices {
|
||||||
return new GenericScripting(AppOptions.get("sandboxBundleSrc"));
|
return new GenericScripting(AppOptions.get("sandboxBundleSrc"));
|
||||||
}
|
}
|
||||||
|
|
||||||
createSignatureStorage() {
|
createSignatureStorage(eventBus, signal) {
|
||||||
return new SignatureStorage();
|
return new SignatureStorage(eventBus, signal);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
3
web/images/editor-toolbar-edit.svg
Normal file
3
web/images/editor-toolbar-edit.svg
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
<svg width="16" height="17" viewBox="0 0 16 17" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<path d="M14.9815 14.3461L14.3875 11.1451C14.3125 10.7361 14.1155 10.3621 13.8195 10.0641L5.0185 1.26214C4.2445 0.489141 2.9855 0.487141 2.2085 1.26214L0.5805 2.89014C-0.1935 3.66514 -0.1935 4.92514 0.5805 5.70014L9.3845 14.5031C9.6805 14.7981 10.0545 14.9941 10.4625 15.0691L13.6645 15.6631C13.7345 15.6751 13.8025 15.6821 13.8705 15.6821C14.1675 15.6821 14.4555 15.5651 14.6695 15.3511C14.9325 15.0871 15.0495 14.7121 14.9815 14.3461ZM2.5285 5.87814L1.3685 4.71814L1.3695 3.87014L3.1895 2.04914L4.0375 2.05014L5.1975 3.21014L2.5285 5.87814ZM10.6895 13.8401C10.5295 13.8101 10.3825 13.7331 10.2665 13.6161L3.4135 6.76314L6.0815 4.09514L12.9345 10.9471C13.0515 11.0651 13.1285 11.2121 13.1595 11.3731L13.6335 13.9301L13.2485 14.3151L10.6895 13.8401Z" fill="black"/>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 869 B |
|
@ -46,9 +46,80 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#addSignatureDialog {
|
.signatureDialog {
|
||||||
--border-color: #8f8f9d;
|
|
||||||
--primary-color: var(--text-primary-color);
|
--primary-color: var(--text-primary-color);
|
||||||
|
--description-input-color: var(--primary-color);
|
||||||
|
--border-color: #8f8f9d;
|
||||||
|
|
||||||
|
@media screen and (forced-colors: active) {
|
||||||
|
--primary-color: ButtonText;
|
||||||
|
--border-color: ButtonText;
|
||||||
|
}
|
||||||
|
|
||||||
|
width: 570px;
|
||||||
|
max-width: 100%;
|
||||||
|
min-width: 300px;
|
||||||
|
padding: 16px 0;
|
||||||
|
|
||||||
|
.mainContainer {
|
||||||
|
width: 100%;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: flex-start;
|
||||||
|
gap: 12px;
|
||||||
|
|
||||||
|
span:not([role="sectionhead"]) {
|
||||||
|
font-size: 13px;
|
||||||
|
font-style: normal;
|
||||||
|
font-weight: 400;
|
||||||
|
line-height: normal;
|
||||||
|
}
|
||||||
|
|
||||||
|
.title {
|
||||||
|
margin-inline-start: 16px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.inputWithClearButton {
|
||||||
|
--button-dimension: 24px;
|
||||||
|
|
||||||
|
--closing-button-icon: url(images/messageBar_closingButton.svg);
|
||||||
|
--closing-button-color: var(--primary-color);
|
||||||
|
|
||||||
|
width: 100%;
|
||||||
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
|
||||||
|
> input {
|
||||||
|
width: 100%;
|
||||||
|
height: 32px;
|
||||||
|
padding-inline: 8px calc(4px + var(--button-dimension));
|
||||||
|
box-sizing: border-box;
|
||||||
|
background-color: transparent;
|
||||||
|
border-radius: 4px;
|
||||||
|
border: 1px solid var(--border-color);
|
||||||
|
color: var(--description-input-color);
|
||||||
|
}
|
||||||
|
|
||||||
|
.clearInputButton {
|
||||||
|
position: absolute;
|
||||||
|
inset-block-start: 4px;
|
||||||
|
inset-inline-end: 4px;
|
||||||
|
display: inline-block;
|
||||||
|
width: var(--button-dimension);
|
||||||
|
height: var(--button-dimension);
|
||||||
|
background-color: var(--closing-button-color);
|
||||||
|
mask-size: cover;
|
||||||
|
mask-image: var(--closing-button-icon);
|
||||||
|
padding: 0;
|
||||||
|
border: 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#addSignatureDialog {
|
||||||
--secondary-color: var(--text-secondary-color);
|
--secondary-color: var(--text-secondary-color);
|
||||||
--bg-hover: #e0e0e6;
|
--bg-hover: #e0e0e6;
|
||||||
--tab-top-line-active-color: #0060df;
|
--tab-top-line-active-color: #0060df;
|
||||||
|
@ -69,9 +140,6 @@
|
||||||
--signature-placeholder-color: var(--secondary-color);
|
--signature-placeholder-color: var(--secondary-color);
|
||||||
--signature-draw-placeholder-color: var(--primary-color);
|
--signature-draw-placeholder-color: var(--primary-color);
|
||||||
--signature-color: var(--primary-color);
|
--signature-color: var(--primary-color);
|
||||||
--closing-button-icon: url(images/messageBar_closingButton.svg);
|
|
||||||
--closing-button-color: var(--primary-color);
|
|
||||||
--description-input-color: var(--primary-color);
|
|
||||||
--clear-signature-button-border-width: 0;
|
--clear-signature-button-border-width: 0;
|
||||||
--clear-signature-button-border-style: solid;
|
--clear-signature-button-border-style: solid;
|
||||||
--clear-signature-button-border-color: transparent;
|
--clear-signature-button-border-color: transparent;
|
||||||
|
@ -114,11 +182,9 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
@media screen and (forced-colors: active) {
|
@media screen and (forced-colors: active) {
|
||||||
--primary-color: ButtonText;
|
|
||||||
--secondary-color: ButtonText;
|
--secondary-color: ButtonText;
|
||||||
--bg: HighlightText;
|
--bg: HighlightText;
|
||||||
--bg-hover: var(--bg);
|
--bg-hover: var(--bg);
|
||||||
--border-color: ButtonText;
|
|
||||||
--tab-top-line-active-color: ButtonText;
|
--tab-top-line-active-color: ButtonText;
|
||||||
--tab-top-line-active-hover-color: HighlightText;
|
--tab-top-line-active-hover-color: HighlightText;
|
||||||
--tab-top-line-hover-color: SelectedItem;
|
--tab-top-line-hover-color: SelectedItem;
|
||||||
|
@ -152,11 +218,6 @@
|
||||||
--thickness-slider-color: ButtonText;
|
--thickness-slider-color: ButtonText;
|
||||||
}
|
}
|
||||||
|
|
||||||
width: 570px;
|
|
||||||
max-width: 100%;
|
|
||||||
min-width: 300px;
|
|
||||||
padding: 16px 0;
|
|
||||||
|
|
||||||
#addSignatureDialogLabel {
|
#addSignatureDialogLabel {
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
|
@ -174,26 +235,7 @@
|
||||||
height: 100%;
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
span {
|
|
||||||
font: menu;
|
|
||||||
font-size: 13px;
|
|
||||||
font-style: normal;
|
|
||||||
font-weight: 400;
|
|
||||||
line-height: normal;
|
|
||||||
}
|
|
||||||
|
|
||||||
.mainContainer {
|
.mainContainer {
|
||||||
width: 100%;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: flex-start;
|
|
||||||
gap: 12px;
|
|
||||||
|
|
||||||
.title {
|
|
||||||
margin-inline-start: 16px;
|
|
||||||
font-weight: 590;
|
|
||||||
}
|
|
||||||
|
|
||||||
[role="tablist"] {
|
[role="tablist"] {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
display: flex;
|
display: flex;
|
||||||
|
@ -465,43 +507,6 @@
|
||||||
gap: 4px;
|
gap: 4px;
|
||||||
flex: 1 0 0;
|
flex: 1 0 0;
|
||||||
|
|
||||||
> #inputWithClearButton {
|
|
||||||
--button-dimension: 24px;
|
|
||||||
|
|
||||||
width: 100%;
|
|
||||||
position: relative;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
|
|
||||||
> input {
|
|
||||||
width: 100%;
|
|
||||||
height: 32px;
|
|
||||||
padding: 8px 4px 8px 8px;
|
|
||||||
padding-block: 8px;
|
|
||||||
padding-inline: 8px calc(4px + var(--button-dimension));
|
|
||||||
box-sizing: border-box;
|
|
||||||
background-color: transparent;
|
|
||||||
border-radius: 4px;
|
|
||||||
border: 1px solid var(--border-color);
|
|
||||||
color: var(--description-input-color);
|
|
||||||
}
|
|
||||||
|
|
||||||
#addSignatureDescriptionClearButton {
|
|
||||||
position: absolute;
|
|
||||||
inset-block-start: 4px;
|
|
||||||
inset-inline-end: 4px;
|
|
||||||
display: inline-block;
|
|
||||||
width: var(--button-dimension);
|
|
||||||
height: var(--button-dimension);
|
|
||||||
background-color: var(--closing-button-color);
|
|
||||||
mask-size: cover;
|
|
||||||
mask-image: var(--closing-button-icon);
|
|
||||||
padding: 0;
|
|
||||||
border: 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
> label {
|
> label {
|
||||||
width: auto;
|
width: auto;
|
||||||
}
|
}
|
||||||
|
@ -626,6 +631,56 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#editSignatureDescriptionDialog {
|
||||||
|
.mainContainer {
|
||||||
|
padding-inline: 16px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
|
||||||
|
.title {
|
||||||
|
margin-inline-start: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#editSignatureDescriptionAndView {
|
||||||
|
width: auto;
|
||||||
|
display: flex;
|
||||||
|
justify-content: flex-end;
|
||||||
|
align-items: flex-start;
|
||||||
|
gap: 12px;
|
||||||
|
align-self: stretch;
|
||||||
|
|
||||||
|
#editSignatureDescriptionContainer {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: flex-start;
|
||||||
|
gap: 4px;
|
||||||
|
flex: 1 1 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
> svg {
|
||||||
|
width: 210px;
|
||||||
|
height: 180px;
|
||||||
|
padding: 8px;
|
||||||
|
background-color: var(--signature-bg);
|
||||||
|
|
||||||
|
> path {
|
||||||
|
stroke: var(--button-signature-color);
|
||||||
|
stroke-width: 1px;
|
||||||
|
stroke-linecap: round;
|
||||||
|
stroke-linejoin: round;
|
||||||
|
stroke-miterlimit: 10;
|
||||||
|
vector-effect: non-scaling-stroke;
|
||||||
|
fill: none;
|
||||||
|
|
||||||
|
&.contours {
|
||||||
|
fill: var(--button-signature-color);
|
||||||
|
stroke-width: 0.5px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#editorSignatureParamsToolbar {
|
#editorSignatureParamsToolbar {
|
||||||
padding: 10px;
|
padding: 10px;
|
||||||
|
|
||||||
|
@ -716,11 +771,11 @@
|
||||||
stroke-miterlimit: 10;
|
stroke-miterlimit: 10;
|
||||||
vector-effect: non-scaling-stroke;
|
vector-effect: non-scaling-stroke;
|
||||||
fill: none;
|
fill: none;
|
||||||
}
|
|
||||||
|
|
||||||
&.contours > path {
|
&.contours {
|
||||||
fill: var(--button-signature-color);
|
fill: var(--button-signature-color);
|
||||||
stroke-width: 0.5px;
|
stroke-width: 0.5px;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -760,3 +815,12 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.editDescription.altText {
|
||||||
|
--alt-text-add-image: url(images/editor-toolbar-edit.svg) !important;
|
||||||
|
|
||||||
|
&::before {
|
||||||
|
width: 16px !important;
|
||||||
|
height: 16px !important;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -92,6 +92,8 @@ class SignatureManager {
|
||||||
|
|
||||||
#overlayManager;
|
#overlayManager;
|
||||||
|
|
||||||
|
#editDescriptionDialog;
|
||||||
|
|
||||||
#signatureStorage;
|
#signatureStorage;
|
||||||
|
|
||||||
#uiManager = null;
|
#uiManager = null;
|
||||||
|
@ -114,7 +116,6 @@ class SignatureManager {
|
||||||
imagePicker,
|
imagePicker,
|
||||||
imagePickerLink,
|
imagePickerLink,
|
||||||
description,
|
description,
|
||||||
clearDescription,
|
|
||||||
clearButton,
|
clearButton,
|
||||||
cancelButton,
|
cancelButton,
|
||||||
addButton,
|
addButton,
|
||||||
|
@ -123,6 +124,7 @@ class SignatureManager {
|
||||||
saveCheckbox,
|
saveCheckbox,
|
||||||
saveContainer,
|
saveContainer,
|
||||||
},
|
},
|
||||||
|
editSignatureElements,
|
||||||
addSignatureToolbarButton,
|
addSignatureToolbarButton,
|
||||||
overlayManager,
|
overlayManager,
|
||||||
l10n,
|
l10n,
|
||||||
|
@ -131,8 +133,8 @@ class SignatureManager {
|
||||||
) {
|
) {
|
||||||
this.#addButton = addButton;
|
this.#addButton = addButton;
|
||||||
this.#clearButton = clearButton;
|
this.#clearButton = clearButton;
|
||||||
this.#clearDescription = clearDescription;
|
this.#clearDescription = description.lastElementChild;
|
||||||
this.#description = description;
|
this.#description = description.firstElementChild;
|
||||||
this.#dialog = dialog;
|
this.#dialog = dialog;
|
||||||
this.#drawSVG = drawSVG;
|
this.#drawSVG = drawSVG;
|
||||||
this.#drawPlaceholder = drawPlaceholder;
|
this.#drawPlaceholder = drawPlaceholder;
|
||||||
|
@ -150,6 +152,10 @@ class SignatureManager {
|
||||||
this.#l10n = l10n;
|
this.#l10n = l10n;
|
||||||
this.#signatureStorage = signatureStorage;
|
this.#signatureStorage = signatureStorage;
|
||||||
this.#eventBus = eventBus;
|
this.#eventBus = eventBus;
|
||||||
|
this.#editDescriptionDialog = new EditDescriptionDialog(
|
||||||
|
editSignatureElements,
|
||||||
|
overlayManager
|
||||||
|
);
|
||||||
|
|
||||||
SignatureManager.#l10nDescription ||= Object.freeze({
|
SignatureManager.#l10nDescription ||= Object.freeze({
|
||||||
signature: "pdfjs-editor-add-signature-description-default-when-drawing",
|
signature: "pdfjs-editor-add-signature-description-default-when-drawing",
|
||||||
|
@ -177,15 +183,15 @@ class SignatureManager {
|
||||||
description.addEventListener(
|
description.addEventListener(
|
||||||
"input",
|
"input",
|
||||||
() => {
|
() => {
|
||||||
clearDescription.disabled = description.value === "";
|
this.#clearDescription.disabled = description.value === "";
|
||||||
},
|
},
|
||||||
{ passive: true }
|
{ passive: true }
|
||||||
);
|
);
|
||||||
clearDescription.addEventListener(
|
this.#clearDescription.addEventListener(
|
||||||
"click",
|
"click",
|
||||||
() => {
|
() => {
|
||||||
this.#description.value = "";
|
this.#description.value = "";
|
||||||
clearDescription.disabled = true;
|
this.#clearDescription.disabled = true;
|
||||||
},
|
},
|
||||||
{ passive: true }
|
{ passive: true }
|
||||||
);
|
);
|
||||||
|
@ -200,6 +206,8 @@ class SignatureManager {
|
||||||
this.#initTabButtons(typeButton, drawButton, imageButton, panels);
|
this.#initTabButtons(typeButton, drawButton, imageButton, panels);
|
||||||
imagePicker.accept = SupportedImageMimeTypes.join(",");
|
imagePicker.accept = SupportedImageMimeTypes.join(",");
|
||||||
|
|
||||||
|
eventBus._on("storedsignatureschanged", this.#signaturesChanged.bind(this));
|
||||||
|
|
||||||
overlayManager.register(dialog);
|
overlayManager.register(dialog);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -650,6 +658,7 @@ class SignatureManager {
|
||||||
|
|
||||||
const div = document.createElement("div");
|
const div = document.createElement("div");
|
||||||
const button = document.createElement("button");
|
const button = document.createElement("button");
|
||||||
|
|
||||||
button.addEventListener("click", () => {
|
button.addEventListener("click", () => {
|
||||||
this.#eventBus.dispatch("switchannotationeditorparams", {
|
this.#eventBus.dispatch("switchannotationeditorparams", {
|
||||||
source: this,
|
source: this,
|
||||||
|
@ -690,7 +699,7 @@ class SignatureManager {
|
||||||
svg.setAttribute("viewBox", outline.viewBox);
|
svg.setAttribute("viewBox", outline.viewBox);
|
||||||
svg.setAttribute("preserveAspectRatio", "xMidYMid meet");
|
svg.setAttribute("preserveAspectRatio", "xMidYMid meet");
|
||||||
if (areContours) {
|
if (areContours) {
|
||||||
svg.classList.add("contours");
|
path.classList.add("contours");
|
||||||
}
|
}
|
||||||
path.setAttribute("d", outline.toSVGPath());
|
path.setAttribute("d", outline.toSVGPath());
|
||||||
|
|
||||||
|
@ -718,14 +727,23 @@ class SignatureManager {
|
||||||
this.#addSignatureToolbarButton.before(div);
|
this.#addSignatureToolbarButton.before(div);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async #signaturesChanged() {
|
||||||
|
const parent = this.#addSignatureToolbarButton.parentElement;
|
||||||
|
while (parent.firstElementChild !== this.#addSignatureToolbarButton) {
|
||||||
|
parent.firstElementChild.remove();
|
||||||
|
}
|
||||||
|
this.#loadSignaturesPromise = null;
|
||||||
|
await this.loadSignatures(/* reload = */ true);
|
||||||
|
}
|
||||||
|
|
||||||
getSignature(params) {
|
getSignature(params) {
|
||||||
return this.open(params);
|
return this.open(params);
|
||||||
}
|
}
|
||||||
|
|
||||||
async loadSignatures() {
|
async loadSignatures(reload = false) {
|
||||||
if (
|
if (
|
||||||
!this.#addSignatureToolbarButton ||
|
!this.#addSignatureToolbarButton ||
|
||||||
this.#addSignatureToolbarButton.previousElementSibling ||
|
(!reload && this.#addSignatureToolbarButton.previousElementSibling) ||
|
||||||
!this.#signatureStorage
|
!this.#signatureStorage
|
||||||
) {
|
) {
|
||||||
return;
|
return;
|
||||||
|
@ -744,7 +762,9 @@ class SignatureManager {
|
||||||
)
|
)
|
||||||
),
|
),
|
||||||
]);
|
]);
|
||||||
return;
|
if (!reload) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
const [signatures, signaturesData] = await this.#loadSignaturesPromise;
|
const [signatures, signaturesData] = await this.#loadSignaturesPromise;
|
||||||
this.#loadSignaturesPromise = null;
|
this.#loadSignaturesPromise = null;
|
||||||
|
@ -761,6 +781,27 @@ class SignatureManager {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async renderEditButton(editor) {
|
||||||
|
const button = document.createElement("button");
|
||||||
|
button.classList.add("altText", "editDescription");
|
||||||
|
button.tabIndex = 0;
|
||||||
|
button.title = editor.description;
|
||||||
|
const span = document.createElement("span");
|
||||||
|
button.append(span);
|
||||||
|
span.setAttribute(
|
||||||
|
"data-l10n-id",
|
||||||
|
"pdfjs-editor-add-signature-edit-button-label"
|
||||||
|
);
|
||||||
|
button.addEventListener(
|
||||||
|
"click",
|
||||||
|
() => {
|
||||||
|
this.#editDescriptionDialog.open(editor);
|
||||||
|
},
|
||||||
|
{ passive: true }
|
||||||
|
);
|
||||||
|
return button;
|
||||||
|
}
|
||||||
|
|
||||||
async open({ uiManager, editor }) {
|
async open({ uiManager, editor }) {
|
||||||
this.#tabsToAltText ||= new Map(
|
this.#tabsToAltText ||= new Map(
|
||||||
this.#tabButtons.keys().map(name => [name, ""])
|
this.#tabButtons.keys().map(name => [name, ""])
|
||||||
|
@ -822,11 +863,6 @@ class SignatureManager {
|
||||||
data = this.#extractedSignatureData;
|
data = this.#extractedSignatureData;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
this.#currentEditor.addSignature(
|
|
||||||
data.outline,
|
|
||||||
DEFAULT_HEIGHT_IN_PAGE,
|
|
||||||
this.#description.value
|
|
||||||
);
|
|
||||||
let uuid = null;
|
let uuid = null;
|
||||||
if (this.#saveCheckbox.checked) {
|
if (this.#saveCheckbox.checked) {
|
||||||
const description = this.#description.value;
|
const description = this.#description.value;
|
||||||
|
@ -858,7 +894,13 @@ class SignatureManager {
|
||||||
console.warn("SignatureManager.add: cannot save the signature.");
|
console.warn("SignatureManager.add: cannot save the signature.");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
this.#currentEditor.setUuid(uuid);
|
this.#currentEditor.addSignature(
|
||||||
|
data,
|
||||||
|
DEFAULT_HEIGHT_IN_PAGE,
|
||||||
|
this.#description.value,
|
||||||
|
uuid
|
||||||
|
);
|
||||||
|
|
||||||
this.#finish();
|
this.#finish();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -868,4 +910,100 @@ class SignatureManager {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class EditDescriptionDialog {
|
||||||
|
#currentEditor;
|
||||||
|
|
||||||
|
#previousDescription;
|
||||||
|
|
||||||
|
#description;
|
||||||
|
|
||||||
|
#dialog;
|
||||||
|
|
||||||
|
#overlayManager;
|
||||||
|
|
||||||
|
#signatureSVG;
|
||||||
|
|
||||||
|
#uiManager;
|
||||||
|
|
||||||
|
constructor(
|
||||||
|
{ dialog, description, cancelButton, updateButton, editSignatureView },
|
||||||
|
overlayManager
|
||||||
|
) {
|
||||||
|
const descriptionInput = (this.#description =
|
||||||
|
description.firstElementChild);
|
||||||
|
this.#signatureSVG = editSignatureView;
|
||||||
|
this.#dialog = dialog;
|
||||||
|
this.#overlayManager = overlayManager;
|
||||||
|
|
||||||
|
dialog.addEventListener("close", this.#close.bind(this));
|
||||||
|
dialog.addEventListener("contextmenu", e => {
|
||||||
|
if (e.target !== this.#description) {
|
||||||
|
e.preventDefault();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
cancelButton.addEventListener("click", this.#finish.bind(this));
|
||||||
|
updateButton.addEventListener("click", this.#update.bind(this));
|
||||||
|
|
||||||
|
const clearDescription = description.lastElementChild;
|
||||||
|
clearDescription.addEventListener("click", () => {
|
||||||
|
descriptionInput.value = "";
|
||||||
|
clearDescription.disabled = true;
|
||||||
|
});
|
||||||
|
descriptionInput.addEventListener(
|
||||||
|
"input",
|
||||||
|
() => {
|
||||||
|
const { value } = descriptionInput;
|
||||||
|
clearDescription.disabled = value === "";
|
||||||
|
updateButton.disabled = value === this.#previousDescription;
|
||||||
|
editSignatureView.setAttribute("aria-label", value);
|
||||||
|
},
|
||||||
|
{ passive: true }
|
||||||
|
);
|
||||||
|
|
||||||
|
overlayManager.register(dialog);
|
||||||
|
}
|
||||||
|
|
||||||
|
async open(editor) {
|
||||||
|
this.#uiManager = editor._uiManager;
|
||||||
|
this.#currentEditor = editor;
|
||||||
|
this.#previousDescription = this.#description.value = editor.description;
|
||||||
|
this.#description.dispatchEvent(new Event("input"));
|
||||||
|
this.#uiManager.removeEditListeners();
|
||||||
|
const { areContours, outline } = editor.getSignaturePreview();
|
||||||
|
const svgFactory = new DOMSVGFactory();
|
||||||
|
const path = svgFactory.createElement("path");
|
||||||
|
this.#signatureSVG.append(path);
|
||||||
|
this.#signatureSVG.setAttribute("viewBox", outline.viewBox);
|
||||||
|
path.setAttribute("d", outline.toSVGPath());
|
||||||
|
if (areContours) {
|
||||||
|
path.classList.add("contours");
|
||||||
|
}
|
||||||
|
|
||||||
|
await this.#overlayManager.open(this.#dialog);
|
||||||
|
}
|
||||||
|
|
||||||
|
async #update() {
|
||||||
|
const description = this.#description.value;
|
||||||
|
if (this.#previousDescription === description) {
|
||||||
|
this.#finish();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
this.#currentEditor.description = description;
|
||||||
|
this.#finish();
|
||||||
|
}
|
||||||
|
|
||||||
|
#finish() {
|
||||||
|
if (this.#overlayManager.active === this.#dialog) {
|
||||||
|
this.#overlayManager.close(this.#dialog);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#close() {
|
||||||
|
this.#uiManager?.addEditListeners();
|
||||||
|
this.#uiManager = null;
|
||||||
|
this.#currentEditor = null;
|
||||||
|
this.#signatureSVG.firstElementChild.remove();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
export { SignatureManager };
|
export { SignatureManager };
|
||||||
|
|
|
@ -684,13 +684,13 @@ See https://github.com/adobe-type-tools/cmap-resources
|
||||||
</div>
|
</div>
|
||||||
</dialog>
|
</dialog>
|
||||||
|
|
||||||
<dialog class="dialog" id="addSignatureDialog" aria-labelledby="addSignatureDialogLabel">
|
<dialog class="dialog signatureDialog" id="addSignatureDialog" aria-labelledby="addSignatureDialogLabel">
|
||||||
<span id="addSignatureDialogLabel" data-l10n-id="pdfjs-editor-add-signature-dialog-label">
|
<span id="addSignatureDialogLabel" data-l10n-id="pdfjs-editor-add-signature-dialog-label">
|
||||||
This modal allows the user to create a signature to add to a PDF document. The user can edit the name (which also serves as the alt text), and optionally save the signature for repeated use.
|
This modal allows the user to create a signature to add to a PDF document. The user can edit the name (which also serves as the alt text), and optionally save the signature for repeated use.
|
||||||
</span>
|
</span>
|
||||||
<div id="addSignatureContainer" class="mainContainer">
|
<div id="addSignatureContainer" class="mainContainer">
|
||||||
<div class="title">
|
<div class="title">
|
||||||
<span id="addSignatureTitle" role="sectionhead" data-l10n-id="pdfjs-editor-add-signature-dialog-title" tabindex="0" class="title">Add a signature</span>
|
<span role="sectionhead" data-l10n-id="pdfjs-editor-add-signature-dialog-title" tabindex="0">Add a signature</span>
|
||||||
</div>
|
</div>
|
||||||
<div role="tablist" id="addSignatureOptions">
|
<div role="tablist" id="addSignatureOptions">
|
||||||
<button id="addSignatureTypeButton" type="button" role="tab" aria-selected="true" aria-controls="addSignatureTypeContainer" data-l10n-id="pdfjs-editor-add-signature-type-button" tabindex="0">
|
<button id="addSignatureTypeButton" type="button" role="tab" aria-selected="true" aria-controls="addSignatureTypeContainer" data-l10n-id="pdfjs-editor-add-signature-type-button" tabindex="0">
|
||||||
|
@ -731,9 +731,9 @@ See https://github.com/adobe-type-tools/cmap-resources
|
||||||
<div id="horizontalContainer">
|
<div id="horizontalContainer">
|
||||||
<div id="addSignatureDescriptionContainer">
|
<div id="addSignatureDescriptionContainer">
|
||||||
<label for="addSignatureDescription" data-l10n-id="pdfjs-editor-add-signature-description-label">Description (alt text)</span></label>
|
<label for="addSignatureDescription" data-l10n-id="pdfjs-editor-add-signature-description-label">Description (alt text)</span></label>
|
||||||
<span id="inputWithClearButton">
|
<span id="addSignatureDescription" class="inputWithClearButton">
|
||||||
<input type="text" id="addSignatureDescription" data-l10n-id="pdfjs-editor-add-signature-description-input" data-l10n-args='{ "default": "", "useDefault": true }' tabindex="0"></input>
|
<input type="text" data-l10n-id="pdfjs-editor-add-signature-description-input" tabindex="0"></input>
|
||||||
<button id="addSignatureDescriptionClearButton" type="button" tabindex="0" aria-hidden="true"></button>
|
<button class="clearInputButton" type="button" tabindex="0" aria-hidden="true"></button>
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<button id="clearSignatureButton" type="button" data-l10n-id="pdfjs-editor-add-signature-clear-button" tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-clear-button-label">Clear signature</span></button>
|
<button id="clearSignatureButton" type="button" data-l10n-id="pdfjs-editor-add-signature-clear-button" tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-clear-button-label">Clear signature</span></button>
|
||||||
|
@ -754,7 +754,7 @@ See https://github.com/adobe-type-tools/cmap-resources
|
||||||
<button id="addSignatureErrorCloseButton" class="closeButton" type="button" tabindex="0" title="Close"><span data-l10n-id="pdfjs-editor-add-signature-error-close-button">Close</span></button>
|
<button id="addSignatureErrorCloseButton" class="closeButton" type="button" tabindex="0" title="Close"><span data-l10n-id="pdfjs-editor-add-signature-error-close-button">Close</span></button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div id="buttons" class="dialogButtonsGroup">
|
<div class="dialogButtonsGroup">
|
||||||
<button id="addSignatureCancelButton" type="button" class="secondaryButton" tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-cancel-button">Cancel</span></button>
|
<button id="addSignatureCancelButton" type="button" class="secondaryButton" tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-cancel-button">Cancel</span></button>
|
||||||
<button id="addSignatureAddButton" type="button" class="primaryButton" disabled tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-add-button">Add</span></button>
|
<button id="addSignatureAddButton" type="button" class="primaryButton" disabled tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-add-button">Add</span></button>
|
||||||
</div>
|
</div>
|
||||||
|
@ -762,6 +762,28 @@ See https://github.com/adobe-type-tools/cmap-resources
|
||||||
</div>
|
</div>
|
||||||
</dialog>
|
</dialog>
|
||||||
|
|
||||||
|
<dialog class="dialog signatureDialog" id="editSignatureDescriptionDialog" aria-labelledby="editSignatureDescriptionTitle">
|
||||||
|
<div id="editSignatureDescriptionContainer" class="mainContainer">
|
||||||
|
<div class="title">
|
||||||
|
<span id="editSignatureDescriptionTitle" role="sectionhead" data-l10n-id="pdfjs-editor-edit-signature-dialog-title" tabindex="0">Edit description</span>
|
||||||
|
</div>
|
||||||
|
<div id="editSignatureDescriptionAndView">
|
||||||
|
<div id="editSignatureDescriptionContainer">
|
||||||
|
<label for="editSignatureDescription" data-l10n-id="pdfjs-editor-add-signature-description-label">Description (alt text)</span></label>
|
||||||
|
<span id="editSignatureDescription" class="inputWithClearButton">
|
||||||
|
<input type="text" data-l10n-id="pdfjs-editor-add-signature-description-input" tabindex="0"></input>
|
||||||
|
<button class="clearInputButton" type="button" tabindex="0" aria-hidden="true"></button>
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
<svg id="editSignatureView" xmlns="http://www.w3.org/2000/svg"></svg>
|
||||||
|
</div>
|
||||||
|
<div class="dialogButtonsGroup">
|
||||||
|
<button id="editSignatureCancelButton" type="button" class="secondaryButton" tabindex="0"><span data-l10n-id="pdfjs-editor-add-signature-cancel-button">Cancel</span></button>
|
||||||
|
<button id="editSignatureUpdateButton" type="button" class="primaryButton" disabled tabindex="0"><span data-l10n-id="pdfjs-editor-edit-signature-update-button">Update</span></button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</dialog>
|
||||||
|
|
||||||
<!--#if !MOZCENTRAL-->
|
<!--#if !MOZCENTRAL-->
|
||||||
<dialog id="printServiceDialog" style="min-width: 200px;">
|
<dialog id="printServiceDialog" style="min-width: 200px;">
|
||||||
<div class="row">
|
<div class="row">
|
||||||
|
|
|
@ -229,9 +229,6 @@ function getViewerConfiguration() {
|
||||||
imagePicker: document.getElementById("addSignatureFilePicker"),
|
imagePicker: document.getElementById("addSignatureFilePicker"),
|
||||||
imagePickerLink: document.getElementById("addSignatureImageBrowse"),
|
imagePickerLink: document.getElementById("addSignatureImageBrowse"),
|
||||||
description: document.getElementById("addSignatureDescription"),
|
description: document.getElementById("addSignatureDescription"),
|
||||||
clearDescription: document.getElementById(
|
|
||||||
"addSignatureDescriptionClearButton"
|
|
||||||
),
|
|
||||||
clearButton: document.getElementById("clearSignatureButton"),
|
clearButton: document.getElementById("clearSignatureButton"),
|
||||||
saveContainer: document.getElementById("addSignatureSaveContainer"),
|
saveContainer: document.getElementById("addSignatureSaveContainer"),
|
||||||
saveCheckbox: document.getElementById("addSignatureSaveCheckbox"),
|
saveCheckbox: document.getElementById("addSignatureSaveCheckbox"),
|
||||||
|
@ -240,6 +237,13 @@ function getViewerConfiguration() {
|
||||||
cancelButton: document.getElementById("addSignatureCancelButton"),
|
cancelButton: document.getElementById("addSignatureCancelButton"),
|
||||||
addButton: document.getElementById("addSignatureAddButton"),
|
addButton: document.getElementById("addSignatureAddButton"),
|
||||||
},
|
},
|
||||||
|
editSignatureDialog: {
|
||||||
|
dialog: document.getElementById("editSignatureDescriptionDialog"),
|
||||||
|
description: document.getElementById("editSignatureDescription"),
|
||||||
|
editSignatureView: document.getElementById("editSignatureView"),
|
||||||
|
cancelButton: document.getElementById("editSignatureCancelButton"),
|
||||||
|
updateButton: document.getElementById("editSignatureUpdateButton"),
|
||||||
|
},
|
||||||
annotationEditorParams: {
|
annotationEditorParams: {
|
||||||
editorFreeTextFontSize: document.getElementById("editorFreeTextFontSize"),
|
editorFreeTextFontSize: document.getElementById("editorFreeTextFontSize"),
|
||||||
editorFreeTextColor: document.getElementById("editorFreeTextColor"),
|
editorFreeTextColor: document.getElementById("editorFreeTextColor"),
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue