From 13b88516cac858dd481ba4974509de5b35dffdb1 Mon Sep 17 00:00:00 2001 From: en Date: Mon, 17 Feb 2025 19:06:19 +0100 Subject: [PATCH] feat(draft): serialize sigit and save/load to local storage --- src/types/draft.ts | 19 ++++++++ src/types/index.ts | 2 + src/utils/draft.ts | 112 +++++++++++++++++++++++++++++++++++++++++++++ src/utils/index.ts | 1 + 4 files changed, 134 insertions(+) create mode 100644 src/types/draft.ts create mode 100644 src/utils/draft.ts diff --git a/src/types/draft.ts b/src/types/draft.ts new file mode 100644 index 0000000..900d87e --- /dev/null +++ b/src/types/draft.ts @@ -0,0 +1,19 @@ +import { SigitFile } from '../utils/file' +import { User } from './core' +import { DrawnField } from './drawing' + +export interface SigitFileDraft { + name: string + file: string + pages: DrawnField[][] +} +export interface SigitDraft { + title: string + users: User[] + files: SigitFile[] +} +export interface SerializedSigitDraft { + title: string + users: User[] + files: SigitFileDraft[] +} diff --git a/src/types/index.ts b/src/types/index.ts index 5c5b715..40b240b 100644 --- a/src/types/index.ts +++ b/src/types/index.ts @@ -4,3 +4,5 @@ export * from './nostr' export * from './relay' export * from './zip' export * from './event' +export * from './drawing' +export * from './draft' diff --git a/src/utils/draft.ts b/src/utils/draft.ts new file mode 100644 index 0000000..4e9ae56 --- /dev/null +++ b/src/utils/draft.ts @@ -0,0 +1,112 @@ +import { + DrawnField, + SerializedSigitDraft, + SigitDraft, + SigitFileDraft +} from '../types' +import { + getMediaType, + extractFileExtension, + toFile, + getSigitFile +} from './file' + +let saveSigitDraftTimeout: number | null = null +const serializeSigitDraft = async ( + draft: SigitDraft +): Promise => { + const serializedFiles = draft.files.map((file) => { + return new Promise((resolve, reject) => { + const reader = new FileReader() + reader.onload = () => { + const pages = file.pages + ? file.pages.map((page) => + page.drawnFields.map( + (field) => + ({ + left: field.left, + top: field.top, + width: field.width, + height: field.height, + type: field.type, + counterpart: field.counterpart + }) as DrawnField + ) + ) + : [] + resolve({ + name: file.name, + pages: pages, + file: reader.result as string + }) + } + reader.onerror = (error) => reject(error) + reader.readAsDataURL(file) + }) + }) + + const serializedFileDraft = await Promise.all(serializedFiles) + return { + title: draft.title, + users: [...draft.users], + files: serializedFileDraft + } +} + +const deserializeSigitDraft = async ( + serializedDraft: SerializedSigitDraft +): Promise => { + const files = await Promise.all( + serializedDraft.files.map(async (draft) => { + const response = await fetch(draft.file) + const arrayBuffer = await response.arrayBuffer() + const type = getMediaType(extractFileExtension(draft.name)) + const file = toFile(arrayBuffer, draft.name, type) + const sigitFile = await getSigitFile(file) + if (draft.pages) { + for (let i = 0; i < draft.pages.length; i++) { + const drawnFields = draft.pages[i] + if (sigitFile.pages) sigitFile.pages[i].drawnFields = [...drawnFields] + } + } + return sigitFile + }) + ) + + return { + ...serializedDraft, + files: files + } +} + +export const saveSigitDraft = (draft: SigitDraft) => { + if (saveSigitDraftTimeout) { + clearTimeout(saveSigitDraftTimeout) + } + + saveSigitDraftTimeout = window.setTimeout(() => { + serializeSigitDraft(draft) + .then((draftToSave) => { + localStorage.setItem('sigitDraft', JSON.stringify(draftToSave)) + }) + .catch((error) => { + console.log(`Error while saving sigit draft. Error: `, error) + }) + }, 1000) +} + +export const getSigitDraft = async () => { + const sigitDraft = localStorage.getItem('sigitDraft') + if (!sigitDraft) return null + + try { + const serializedDraft = JSON.parse(sigitDraft) as SerializedSigitDraft + return await deserializeSigitDraft(serializedDraft) + } catch { + return null + } +} + +export const clearSigitDraft = () => { + localStorage.removeItem('sigitDraft') +} diff --git a/src/utils/index.ts b/src/utils/index.ts index 274ceab..9c4464a 100644 --- a/src/utils/index.ts +++ b/src/utils/index.ts @@ -12,3 +12,4 @@ export * from './string' export * from './url' export * from './utils' export * from './zip' +export * from './draft'