04-10-2023

This commit is contained in:
Jonathan Jenne
2023-10-04 11:44:26 +02:00
parent d7d457b82a
commit 6de7ec0050
7 changed files with 373 additions and 293 deletions

View File

@@ -15,28 +15,32 @@ export class App {
public static currentDocument: Document;
public static envelopeKey: string;
public static ui: UI;
public static UI: UI;
public static Network: Network;
public static Annotation: Annotation;
// This function will be called in the ShowEnvelope.razor page
// and will trigger loading of the Editor Interface
public static async loadPDFFromUrl(container: string, envelopeKey: string) {
App.ui = new UI();
App.UI = new UI();
App.Network = new Network();
App.Annotation = new Annotation();
console.debug("Loading PSPDFKit..");
const envelopeObject: EnvelopeResponse = await App.loadData(`/api/get-data/${envelopeKey}`);
const envelopeObject: EnvelopeResponse = await App.Network.loadData(envelopeKey);
App.envelopeKey = envelopeKey;
App.currentDocument = envelopeObject.envelope.documents[0];
let arrayBuffer
try {
arrayBuffer = await App.loadDocument(`/api/download/${envelopeKey}?id=${App.currentDocument.id}`);
arrayBuffer = await App.Network.loadDocument(envelopeKey, App.currentDocument.id);
} catch (e) {
console.error(e)
}
App.Instance = await App.loadPSPDFKit(arrayBuffer, container)
App.configurePSPDFKit(this.Instance)
App.Instance = await App.UI.loadPSPDFKit(arrayBuffer, container)
App.UI.configurePSPDFKit(this.Instance, App.handleClick)
console.debug(envelopeObject.envelope);
console.debug("PSPDFKit configured!");
@@ -46,7 +50,7 @@ export class App {
App.currentDocument.elements.forEach(function (element: Element) {
console.log("Creating annotation for element", element.id)
const [annotation, formField] = App.createAnnotationFromElement(element)
const [annotation, formField] = App.Annotation.createAnnotationFromElement(element)
annotations.push(annotation);
annotations.push(formField);
})
@@ -56,73 +60,15 @@ export class App {
console.debug(createdAnnotations)
}
private static inchToPoint(inch: number): number {
return inch * 72;
}
// Makes a call to the supplied url and fetches the binary response as an array buffer
private static loadDocument(url: string): Promise<ArrayBuffer> {
return fetch(url, { credentials: "include" })
.then(res => res.arrayBuffer());
}
// Makes a call to the supplied url and fetches the json response as an object
private static loadData(url: string): Promise<any> {
return fetch(url, { credentials: "include" })
.then(res => res.json());
}
private static postDocument(url: string, buffer: ArrayBuffer): Promise<any> {
return fetch(url, { credentials: "include", method: "POST", body: buffer })
.then(res => res.json());
}
// Load the PSPDFKit UI by setting a target element as the container to render in
// and a arraybuffer which represents the document that should be displayed.
private static loadPSPDFKit(arrayBuffer: ArrayBuffer, container: string): Promise<Instance> {
return PSPDFKit.load({
container: container,
document: arrayBuffer,
autoSaveMode: DISABLED,
annotationPresets: App.ui.getPresets(),
electronicSignatures: {
creationModes: [DRAW, TYPE]
},
isEditableAnnotation: function (annotation: WidgetAnnotation) {
// Check if the annotation is a signature
// This will allow new signatures, but not allow edits.
return !annotation.isSignature;
}
})
}
private static configurePSPDFKit(instance: Instance) {
instance.addEventListener("annotations.load", (loadedAnnotations) => {
console.log("annotations loaded", loadedAnnotations.toJS());
})
instance.addEventListener("annotations.change", () => {
console.log("annotations changed")
})
instance.addEventListener("annotations.create", async (createdAnnotations) => {
console.log("annotations created", createdAnnotations.toJS());
})
const filteredItems: Array<ToolbarItem> = instance.toolbarItems
.filter((item) => App.ui.allowedToolbarItems.includes(item.type))
instance.setToolbarItems(filteredItems.concat(App.ui.getToolbarItems(App.handleClick)))
}
public static async handleClick(eventType: string) {
switch (eventType) {
case "RESET":
await App.handleReset(null)
break;
await App.handleReset(null)
break;
case "FINISH":
await App.handleFinish(null)
break;
await App.handleFinish(null)
break;
}
}
@@ -133,31 +79,17 @@ export class App {
console.log(json);
const buffer = await App.Instance.exportPDF({ flatten: true });
await App.uploadDocument(buffer, App.envelopeKey, App.currentDocument.id);
const result = await App.Network.postDocument(App.envelopeKey, App.currentDocument.id, buffer);
console.log(result)
alert("Signatur wird gespeichert!")
}
public static async handleReset(event: any) {
if (confirm("Wollen Sie das Dokument und alle erstellten Signaturen zur<75>cksetzen?")) {
for (let i = 0; i < App.Instance.totalPageCount; i++) {
const annotations = await App.Instance.getAnnotations(i)
annotations.forEach((annotation) => {
//console.log(annotation)
// TODO: Delete only create signatures
//App.Instance.delete(annotation.id)
})
}
const result = App.Annotation.deleteAnnotations(App.Instance)
}
}
private static async uploadDocument(buffer: ArrayBuffer, envelopeKey: string, documentId: number) {
const result = await App.postDocument(`/api/upload/${envelopeKey}/${documentId}`, buffer);
console.log(result)
}
private static async downloadDocument() {
const buffer = await App.Instance.exportPDF({ flatten: true });
const supportsDownloadAttribute = HTMLAnchorElement.prototype.hasOwnProperty("download");
@@ -186,17 +118,17 @@ export class App {
document.body.removeChild(a);
}
}
}
private static createAnnotationFromElement(element: Element): [annotation: WidgetAnnotation, formField: SignatureFormFieldType] {
class Annotation {
public createAnnotationFromElement(element: Element): [annotation: WidgetAnnotation, formField: SignatureFormFieldType] {
const id = PSPDFKit.generateInstantId()
console.log("Creating Annotation", id)
const width = App.inchToPoint(element.width)
const height = App.inchToPoint(element.height)
const top = App.inchToPoint(element.top) - (height / 2)
const left = App.inchToPoint(element.left) - (width / 2)
const width = this.inchToPoint(element.width)
const height = this.inchToPoint(element.height)
const top = this.inchToPoint(element.top) - (height / 2)
const left = this.inchToPoint(element.left) - (width / 2)
const page = element.page - 1
const annotation: WidgetAnnotation = App.createSignatureAnnotation(id, width, height, top, left, page)
const annotation: WidgetAnnotation = this.createSignatureAnnotation(id, width, height, top, left, page)
console.log(annotation)
const formField = new SignatureFormField({
@@ -208,8 +140,19 @@ export class App {
return [annotation, formField]
}
public async deleteAnnotations(instance: Instance): Promise<any> {
let pageAnnotations = (
await Promise.all(Array.from({ length: instance.totalPageCount }).map((_, pageIndex) =>
instance.getAnnotations(pageIndex)
))
).flatMap((annotations) =>
annotations.reduce((acc, annotation) => acc.concat(annotation), [])
).filter((annotation) => !!annotation.isSignature);
//deleting all Annotations
return await instance.delete(pageAnnotations);
}
private static createSignatureAnnotation(id: string, width: number, height: number, top: number, left: number, pageIndex: number): WidgetAnnotation {
private createSignatureAnnotation(id: string, width: number, height: number, top: number, left: number, pageIndex: number): WidgetAnnotation {
const annotation = new PSPDFKit.Annotations.WidgetAnnotation({
id: id,
pageIndex: pageIndex,
@@ -220,14 +163,32 @@ export class App {
return annotation
}
private inchToPoint(inch: number): number {
return inch * 72;
}
}
class Network {
// Makes a call to the supplied url and fetches the binary response as an array buffer
public loadDocument(envelopeKey: string, documentId: number): Promise<ArrayBuffer> {
return fetch(`/api/file/${envelopeKey}?id=${documentId}`, { credentials: "include" })
.then(res => res.arrayBuffer());
}
// Makes a call to the supplied url and fetches the json response as an object
public loadData(envelopeKey): Promise<any> {
return fetch(`/api/envelope/${envelopeKey}`, { credentials: "include" })
.then(res => res.json());
}
public postDocument(envelopeKey: string, documentId: number, buffer: ArrayBuffer): Promise<any> {
return fetch(`/api/upload/${envelopeKey}/${documentId}`, { credentials: "include", method: "POST", body: buffer })
.then(res => res.json());
}
}
class UI {
constructor() {
}
public allowedToolbarItems: string[] = [
"sidebar-thumbnails",
"sidebar-document-ouline",
@@ -241,7 +202,49 @@ class UI {
"search"
]
public getToolbarItems = function (callback: any) {
// Load the PSPDFKit UI by setting a target element as the container to render in
// and a arraybuffer which represents the document that should be displayed.
public loadPSPDFKit(arrayBuffer: ArrayBuffer, container: string): Promise<Instance> {
return PSPDFKit.load({
container: container,
document: arrayBuffer,
autoSaveMode: DISABLED,
annotationPresets: this.getPresets(),
electronicSignatures: {
creationModes: [DRAW, TYPE]
},
isEditableAnnotation: function (annotation: WidgetAnnotation) {
// Check if the annotation is a signature
// This will allow new signatures, but not allow edits.
return !annotation.isSignature;
}
})
}
public configurePSPDFKit(instance: Instance, handler: any) {
instance.addEventListener("annotations.load", (loadedAnnotations) => {
console.log("annotations loaded", loadedAnnotations.toJS());
})
instance.addEventListener("annotations.change", () => {
console.log("annotations changed")
})
instance.addEventListener("annotations.create", async (createdAnnotations) => {
console.log("annotations created");
})
const toolbarItems = this.getToolbarItems(instance, handler)
instance.setToolbarItems(toolbarItems)
}
public getToolbarItems(instance: Instance, handler: any): ToolbarItem[] {
const customItems = this.getCustomItems(handler)
const defaultItems: Array<ToolbarItem> = this.getDefaultItems(instance.toolbarItems)
return defaultItems.concat(customItems)
}
private getCustomItems = function (callback: any) {
const customItems: ToolbarItem[] = [
{
type: "custom",
@@ -271,7 +274,11 @@ class UI {
return customItems
}
public getPresets() {
private getDefaultItems(items: ToolbarItem[]): ToolbarItem[] {
return items.filter((item) => this.allowedToolbarItems.includes(item.type))
}
private getPresets() {
const annotationPresets = PSPDFKit.defaultAnnotationPresets;
annotationPresets.ink = {
lineWidth: 10