@manifest-editor/shell 2.0.3-next.0.2f3498a → 2.0.3-next.0.3782be7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","names":["DEFAULT_CONFIG: Config","resolvedConfig: Config","config","Container","Header","IconButton","CloseIcon: React.FC<{\n inline?: boolean;\n height?: number;\n className?: string;\n}>","VaultProvider","ManifestContext","CollectionContext","map: Record<string, PreviewHandler>","providesMap: Record<string, string>","providesMap","context: any","handlers: PreviewHandler[]","PreviewProvider","context: PreviewContext","DownloadButton","config","AppHeader","Header","Container","ManifestEditorLogo","AtlasStoreReactContext","IIIFVault","e: any","responseData: ManifestNormalized | undefined","BackIcon: React.FC<{ style?: any }>","PaddedSidebarContainer","ErrorMessage","ReactVaultContext","ErrorBoundary","Vault","toDispatch: any","Vault","VaultProvider","create","Creator","RenderCreator","options: CreatorOptions","err: any","ErrorMessage","Spinner","EmptyState","ActionButton","Suspense","ModalBackSlot","IconButton","GridIcon","CreatorGrid","baseCreator: LayoutPanel","Tabs","TabList","Tab","TabPanel","ThemeProvider","defaultState: EditingStackState","EditorInstance","defaultState","create","sortKeys: string[]","sortKeyFallbacks: Record<string, EditorDefinition>","ResourceReactContext","resourceConfig: EditorConfig","resource","SidebarTabs","baseEditor: LayoutPanel","Sidebar","SidebarHeader","SidebarContent","Form","ActionButton","seenIds: string[]","sectionMap: Record<string, ContextMenuItem[]>","emptySections: ContextMenuItem[]","returnSections: Array<{ sectionTitle?: string; items: Array<ContextMenuItem> }>","$","noop","onKeyDown: KeyboardEventHandler<HTMLDivElement>","AccordionItem","onScroll: UIEventHandler<HTMLDivElement>","getValue","HandleControls","Tooltip","TooltipTrigger","DefaultTooltipContent","IconHandle","ResetIcon","ResizeHandle","$","CenterPanel","LeftPanel","PanelSideMenu","Layout","ReactVaultContext","Fragment","L.PanelContainer","L.PanelContent","L.PanelMenu","Modal","ErrorBoundary","L.OuterWrapper","L.Header","L.Main","M.Container","M.CenterPanel","M.MobileBar","M.LeftBarButton","M.DrawerContainer","M.DrawerButton","M.PreviewBarButton","M.DrawerBody","M.LeftPanel","M.Lightbox","PanelSideMenu","Transition","L.LeftPanel","L.CenterPanel","L.RightPanel","L.Footer","Component","LayoutProvider","actions","state","toEdit: EditableResource","create","previewConfigs: PreviewConfiguration[]","ImageServiceLoader","ImageServiceLoaderContext","ThemeProvider","AtlasStoreProvider","tempGlobalState: Record<string, Record<string, Task>>","res: (value: any) => void","rej: (reason?: any) => void","analyse","Component","onCopy","onPaste","e"],"sources":["../../../node_modules/.pnpm/tiny-invariant@1.3.3/node_modules/tiny-invariant/dist/esm/tiny-invariant.js","../src/ConfigContext/ConfigContext.tsx","../src/AppContext/AppContext.tsx","../src/AppContext/MultiAppContext.tsx","../src/AppHeader/AppHeader.styles.ts","../../ui/icons/CloseIcon.tsx","../../ui/icons/DownIcon.tsx","../src/AppResourceProvider/AppResourceProvider.tsx","../src/PreviewContext/previews/ExternalManifestUrlPreview.ts","../src/PreviewContext/previews/IIIFPreviewService.ts","../src/PreviewContext/PreviewContext.hooks.ts","../src/PreviewContext/PreviewContext.reducer.ts","../src/PreviewContext/PreviewContext.tsx","../../ui/atoms/Button.tsx","../src/PreviewButton/PreviewButton.styles.ts","../src/PreviewButton/PreviewButton.tsx","../src/AppHeader/AppHeader.tsx","../src/AppMenu/AppMenuContext.tsx","../src/AtlasStore/AtlasStoreProvider.tsx","../src/AtlasStore/polygon-to-bounding-box.ts","../src/analysis.ts","../src/helpers.ts","../src/highlighted-image-resources.ts","../../ui/icons/StarIcon.tsx","../../ui/icons/BackIcon.tsx","../src/Layout/Layout.context.tsx","../src/Layout/components/PanelError.tsx","../src/Layout/Layout.helpers.ts","../../ui/atoms/Dropdown.tsx","../src/Layout/components/ModularPanel.tsx","../src/PreviewVault/create-preview-vault.ts","../src/PreviewVault/PreviewVault.tsx","../src/BaseCreator/BaseCreator.hooks.tsx","../src/BaseCreator/CreatorInitialData.tsx","../src/BaseCreator/BaseCreator.tsx","../src/BaseCreator/index.tsx","../src/ShellContext/default-theme.ts","../src/BaseCreator/BaseAnnotationCreator.tsx","../src/EditingStack/EditingStack.reducer.ts","../src/EditingStack/EditingStack.tsx","../src/BaseEditor/BaseEditor.tsx","../src/BaseEditor/index.tsx","../src/hooks/use-decay-state.ts","../src/ConfigContext/ConfigEditor.tsx","../src/ContextMenu/ContextMenuContext.tsx","../../ui/ui/CenterPanelContainer/CenterPanelContainer.module.css","../../ui/ui/CenterPanelContainer/CenterPanelContainer.tsx","../../ui/atoms/Accordion.tsx","../../ui/icons/DownloadIcon.tsx","../../ui/atoms/ButtonRow.tsx","../src/ExportPanel/ExportPanel.tsx","../src/hooks/use-annotation-creator-state.ts","../src/hooks/use-event.tsx","../src/hooks/use-match-media.ts","../src/hooks/use-save-vault.ts","../src/hooks/use-svg-tools.tsx","../src/Layout/components/HandleControls.tsx","../../ui/madoc/components/icons/Spinner.tsx","../../ui/ui/GhostBlocks/GhostBlocks.module.css","../../ui/ui/GhostBlocks/GhostBlocks.tsx","../../ui/madoc/use-event-handler.ts","../src/Layout/components/use-resize-layouts.tsx","../src/Layout/Layout.mobile.tsx","../src/Layout/Layout.styles.ts","../src/Layout/Layout.tsx","../src/Layout/Layout.hooks.ts","../src/Layout/Layout.reducer.ts","../src/ResourceEditingContext/ResourceEditingContext.tsx","../../ui/atoms/ErrorBoundary.tsx","../src/Layout/Layout.context-internal.tsx","../src/ShellContext/ShellContext.tsx","../src/TaskBridge/TaskBridge.tsx","../src/Universal/UniversalCopyPaste.tsx"],"sourcesContent":["var isProduction = process.env.NODE_ENV === 'production';\nvar prefix = 'Invariant failed';\nfunction invariant(condition, message) {\n if (condition) {\n return;\n }\n if (isProduction) {\n throw new Error(prefix);\n }\n var provided = typeof message === 'function' ? message() : message;\n var value = provided ? \"\".concat(prefix, \": \").concat(provided) : prefix;\n throw new Error(value);\n}\n\nexport { invariant as default };\n","import type { Collection } from \"@iiif/presentation-3\";\nimport {\n createContext,\n type ReactNode,\n useCallback,\n useContext,\n useMemo,\n useState,\n} from \"react\";\nimport type { PreviewConfiguration } from \"../PreviewContext/PreviewContext.types\";\n\nexport interface Config {\n // Previous configuration.\n previews: PreviewConfiguration[];\n behaviorPresets: string[];\n newTemplates: Collection | null;\n\n defaultPreview: string | null;\n\n editorConfig: {\n All?: EditorConfig;\n Manifest?: EditorConfig;\n Canvas?: EditorConfig;\n Annotation?: EditorConfig;\n AnnotationPage?: EditorConfig;\n AnnotationCollection?: EditorConfig;\n Range?: EditorConfig;\n Collection?: EditorConfig;\n ContentResource?: EditorConfig;\n // Collection inside collection.\n EmbeddedCollection?: EditorConfig;\n };\n\n editorFeatureFlags: {\n enableMultiImageCanvases?: boolean;\n enableMultiMediaCanvases?: boolean;\n rememberCanvasId?: boolean;\n rememberLeftPanelId?: boolean;\n annotationPopups?: boolean;\n manifestGridOptions?: boolean;\n };\n\n // Internationalisation options\n i18n: {\n defaultLanguage: string;\n availableLanguages: string[];\n advancedLanguageMode: boolean;\n textGranularityEnabled?: boolean;\n };\n\n // Options when exporting from Vault.\n export: {\n baseIdentifier: string | null;\n version: 3 | 2;\n };\n\n uploadBackends: Array<UploadBackendConfig>;\n}\n\nexport interface EditorConfig {\n singleTab?: string;\n fields?: string[];\n hideTabs?: string[];\n onlyTabs?: string[];\n}\n\nexport interface UploadBackendConfig {\n id: string;\n label: string;\n resourceTypes: string[];\n canUpload?: () => Promise<boolean>;\n upload: (resource: File) => Promise<{ id: string; type: string }> | null;\n}\n\nconst DEFAULT_CONFIG: Config = {\n previews: [],\n behaviorPresets: [\n \"auto-advance\",\n \"no-auto-advance\",\n \"repeat\",\n \"no-repeat\",\n \"unordered\",\n \"individuals\",\n \"continuous\",\n \"paged\",\n \"non-paged\",\n \"facing-pages\",\n \"multi-part\",\n \"together\",\n \"sequence\",\n \"thumbnail-nav\",\n \"no-nav\",\n \"hidden\",\n ],\n defaultPreview: null,\n editorConfig: {},\n newTemplates: null,\n i18n: {\n advancedLanguageMode: false,\n availableLanguages: [\"en\", \"cy\", \"nl\", \"fr\"],\n defaultLanguage: \"en\",\n },\n editorFeatureFlags: {\n enableMultiImageCanvases: true,\n enableMultiMediaCanvases: true,\n annotationPopups: false,\n rememberCanvasId: true,\n manifestGridOptions: false,\n rememberLeftPanelId: false,\n },\n uploadBackends: [],\n export: {\n baseIdentifier: null,\n version: 3,\n },\n};\n\nexport const ConfigReactContext = createContext<Config>(DEFAULT_CONFIG);\nexport const SaveConfigReactContext = createContext<\n (config: Partial<Config>) => void\n>(() => {});\n\nexport function useConfig() {\n return useContext(ConfigReactContext);\n}\n\nexport function useSaveConfig() {\n return useContext(SaveConfigReactContext);\n}\n\nexport function ConfigProvider({\n children,\n config,\n saveConfig,\n}: {\n children: ReactNode;\n config?: Partial<Config>;\n saveConfig?: (config: Partial<Config>) => void;\n}) {\n const [runtimeConfig, setRuntimeConfig] = useState<Partial<Config> | null>(\n null,\n );\n const resolvedConfig: Config = useMemo(\n () => ({\n ...DEFAULT_CONFIG,\n ...(config || {}),\n ...(runtimeConfig || {}),\n editorFeatureFlags: {\n ...DEFAULT_CONFIG.editorFeatureFlags,\n ...(config?.editorFeatureFlags || {}),\n ...runtimeConfig?.editorFeatureFlags,\n },\n }),\n [config, runtimeConfig],\n );\n\n const memoSaveConfig = useCallback(\n (config: Partial<Config>) => {\n setRuntimeConfig(config);\n if (saveConfig) {\n saveConfig(config);\n }\n },\n [config],\n );\n\n return (\n <SaveConfigReactContext.Provider value={memoSaveConfig}>\n <ConfigReactContext.Provider value={resolvedConfig}>\n {children}\n </ConfigReactContext.Provider>\n </SaveConfigReactContext.Provider>\n );\n}\n","import type { CreatorDefinition } from \"@manifest-editor/creator-api\";\nimport { useLocalStorage } from \"../hooks/use-local-storage\";\nimport { createContext, type ReactNode, type SetStateAction, useCallback, useContext, useEffect, useMemo } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { type Config, ConfigProvider } from \"../ConfigContext/ConfigContext\";\nimport type {\n AnnotationPanel,\n BackgroundPanel,\n CanvasEditorDefinition,\n EditorDefinition,\n LayoutPanel,\n LayoutProps,\n} from \"../Layout/Layout.types\";\n\nexport type AppContext = {\n instanceId: string;\n appId: string;\n args?: any;\n};\n\nexport type LoadedApp = Partial<LayoutProps> & {\n config?: Partial<Config>;\n default: {\n id: string;\n title: string;\n type?: \"manifest\" | \"launcher\";\n project?: boolean;\n projectType?: \"Manifest\" | \"Collection\";\n dev?: boolean;\n desktop?: boolean;\n web?: boolean;\n drafts?: boolean;\n };\n};\n\nexport type MappedApp = {\n metadata: LoadedApp[\"default\"];\n layout: LayoutProps;\n config?: Partial<Config>;\n};\n\nexport interface AppExtension {\n config?: Partial<Config>;\n leftPanels?: LayoutPanel[];\n centerPanels?: LayoutPanel[];\n rightPanels?: LayoutPanel[];\n modalPanels?: LayoutPanel[];\n editors?: EditorDefinition[];\n creators?: CreatorDefinition[];\n canvasEditors?: CanvasEditorDefinition[];\n annotations?: AnnotationPanel[];\n background?: BackgroundPanel[];\n // Config.\n leftPanelIds?: string[];\n\n // Side-effects.\n disableSideEffects?: string[];\n}\n\nexport type AppState = { state: null | any; setState: SetStateAction<any> };\n\nexport const PrimeAppReactContext = createContext<MappedApp | null>(null);\nexport const AppReactContext = createContext<AppContext | null>(null);\nexport const AppStateReactContext = createContext<{\n state: null | any;\n setState: SetStateAction<any>;\n}>({\n state: null,\n setState: () => {\n // no-op\n },\n});\n\nexport function useAppInstance() {\n const ctx = useContext(AppReactContext);\n invariant(ctx, \"Hook useAppInstance must be used inside <AppProvider />\");\n\n return ctx;\n}\n\nexport function useApp() {\n const app = useContext(PrimeAppReactContext);\n\n invariant(app, \"Hook useApp must be used inside <AppProvider />\");\n\n return app;\n}\n\nexport function useAppState<S = any>() {\n return useContext(AppStateReactContext);\n}\n\nfunction AppStateProvider(props: {\n instanceId: string;\n appId: string;\n initialState?: any;\n args?: any;\n children: ReactNode;\n}) {\n const [state, _setState, stateRef] = useLocalStorage(\n `app-state/${props.appId}/${props.instanceId}`,\n props.initialState || {},\n );\n\n const setState = useCallback((partial: any) => {\n const existing = stateRef.current ? JSON.parse(stateRef.current || \"{}\") : {};\n const partialState = (typeof partial === \"function\" ? partial(existing) : partial) || {};\n\n _setState({\n ...existing,\n ...partialState,\n });\n }, []);\n\n useEffect(() => {\n if (props.args) {\n setState(props.args);\n }\n }, [props.appId]);\n\n const ctx = useMemo(() => ({ state: state || {}, setState }), [setState, state]);\n\n return <AppStateReactContext.Provider value={ctx}>{props.children}</AppStateReactContext.Provider>;\n}\n\nexport function AppProvider({\n instanceId,\n appId,\n args,\n definition,\n children,\n initialState,\n}: {\n initialState?: any;\n instanceId: string;\n appId: string;\n args?: any;\n definition: MappedApp;\n children: ReactNode;\n}) {\n const ctx = useMemo(() => ({ instanceId, appId, args }), [instanceId, appId, args]);\n const _initialState = useMemo(() => initialState || {}, [instanceId]);\n\n // Current App is now put in the \"Prime\" context.\n return (\n <ConfigProvider config={definition.config || {}}>\n <PrimeAppReactContext.Provider value={definition}>\n <AppReactContext.Provider value={ctx}>\n <AppStateProvider instanceId={ctx.instanceId} appId={ctx.appId} args={ctx.args} initialState={_initialState}>\n {children}\n </AppStateProvider>\n </AppReactContext.Provider>\n </PrimeAppReactContext.Provider>\n </ConfigProvider>\n );\n}\n","import { createContext, ReactNode, useContext, useMemo } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { useOptionalLocalStorage } from \"@manifest-editor/components\";\nimport { AppProvider } from \"./AppContext\";\n\ntype MappedApp = any;\n\nexport type MultiAppContext = {\n apps: Record<string, MappedApp>;\n currentApp: { id: string; args?: any };\n initialApp: { id: string; args?: any };\n changeApp: (app: { id: string; args?: any }) => void;\n changeProjectType: (type: \"Manifest\" | \"Collection\") => void;\n};\n\nconst MultiAppContext = createContext<MultiAppContext | null>(null);\n\nexport function useApps() {\n const ctx = useContext(MultiAppContext);\n\n invariant(ctx, \"Hook useApps must be used inside <MultiAppProvider />\");\n\n return ctx;\n}\n\nfunction useCurrentApp(\n initialApp?: { id: string; args?: any },\n enableLocalStorage = false,\n) {\n const [currentApp, changeApp] = useOptionalLocalStorage(\n \"SelectedApplication\",\n initialApp || { id: \"splash\" },\n !enableLocalStorage,\n );\n\n return [currentApp, changeApp] as const;\n}\n\nexport function MultiAppProvider({\n apps,\n initialApp,\n saveCurrentApp = true,\n instanceId,\n children,\n config = {},\n}: {\n apps: Record<string, MappedApp>;\n initialApp?: MultiAppContext[\"currentApp\"];\n saveCurrentApp?: boolean;\n instanceId: string;\n children: ReactNode;\n config?: {\n defaultApp?: string;\n manifestApp?: string;\n collectionApp?: string;\n };\n}) {\n const {\n defaultApp = \"splash\",\n collectionApp = \"collection-editor\",\n manifestApp = \"manifest-editor\",\n } = config;\n const [currentApp, changeApp] = useCurrentApp(initialApp, saveCurrentApp);\n\n const changeProjectType = (type: \"Manifest\" | \"Collection\") => {\n if (type === \"Manifest\") {\n changeApp({ id: manifestApp });\n }\n if (type === \"Collection\") {\n changeApp({ id: collectionApp });\n }\n };\n\n const ctx = useMemo<MultiAppContext>(\n () => ({\n currentApp: currentApp || { id: defaultApp },\n initialApp: initialApp || { id: defaultApp },\n apps,\n changeApp,\n changeProjectType,\n }),\n [initialApp, apps, currentApp],\n );\n\n const currentFullApp = apps[ctx.currentApp.id];\n if (!currentApp || !currentFullApp) {\n return null;\n }\n\n // Current App is now put in the \"Prime\" context.\n return (\n <AppProvider\n appId={currentApp.id}\n definition={currentFullApp}\n instanceId={currentApp.id + instanceId}\n args={currentApp.args}\n >\n <MultiAppContext.Provider value={ctx}>\n {children}\n </MultiAppContext.Provider>\n </AppProvider>\n );\n}\n","import styled from \"styled-components\";\nimport { SmallButton } from \"@manifest-editor/ui/atoms/Button\";\n\nexport const Container = styled.div`\n display: flex;\n align-items: center;\n height: 3em;\n padding: 0.5em;\n`;\n\nexport const Header = styled.div`\n display: flex;\n padding: 0.25em;\n flex-direction: column;\n`;\n\nexport const IconButton = styled.button`\n height: 1.75em;\n width: 1.75em;\n background: #e9e9e9;\n border-radius: 3px;\n display: flex;\n text-align: center;\n align-items: center;\n font-size: 1.1em;\n border: none;\n justify-content: center;\n\n &:focus {\n background: #e94581;\n color: #fff;\n svg {\n fill: #fff;\n }\n }\n`;\n\nexport const Spacer = styled.div`\n flex: 1;\n`;\n\nexport const Logo = styled.div`\n color: #6e6e6e;\n display: flex;\n align-items: center;\n margin-left: 1em;\n font-weight: bold;\n text-rendering: geometricPrecision;\n letter-spacing: -0.5px;\n user-select: none;\n cursor: pointer;\n margin-right: 0.5em;\n`;\n\nexport const ProjectPreview = styled.div`\n margin: 0 auto;\n padding: 3px;\n background: #f4f4f4;\n border: 1px solid #e0e0e0;\n border-radius: 5px;\n width: 26em;\n display: flex;\n flex-direction: row;\n\n @media (max-width: 450px) {\n display: none;\n }\n`;\n\nexport const ContextButton = styled.button`\n background: #e7fff4;\n border: 1px solid #c5e3cd;\n box-shadow: 0 1px 2px 0 rgba(0, 0, 0, 0.06);\n border-radius: 4px;\n color: #666666;\n padding: 0.35em 0.7em;\n letter-spacing: -0.42px;\n`;\n","export const CloseIcon: React.FC<{\n inline?: boolean;\n height?: number;\n className?: string;\n}> = ({ height = 16 }) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height={height} viewBox=\"0 0 24 24\" width=\"24px\" fill=\"currentColor\">\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path d=\"M19 6.41L17.59 5 12 10.59 6.41 5 5 6.41 10.59 12 5 17.59 6.41 19 12 13.41 17.59 19 19 17.59 13.41 12z\" />\n </svg>\n);\n","import { SVGProps } from \"react\";\n\nexport const DownIcon = ({ rotate = 0, ...props }: SVGProps<SVGSVGElement>) => (\n <svg\n version=\"1.2\"\n xmlns=\"http://www.w3.org/2000/svg\"\n overflow=\"visible\"\n preserveAspectRatio=\"none\"\n viewBox=\"0 0 24 24\"\n width=\"1em\"\n height=\"1em\"\n style={{\n fill: \"rgba(0, 0, 0, 0.6)\",\n transform: `rotate(${rotate}deg)`,\n transition: \"transform 0.2s\",\n }}\n {...props}\n >\n <path\n d=\"M8.12 9.29 12 13.17l3.88-3.88a.996.996 0 1 1 1.41 1.41l-4.59 4.59a.996.996 0 0 1-1.41 0L6.7 10.7a.996.996 0 0 1 0-1.41c.39-.38 1.03-.39 1.42 0z\"\n fill=\"currentColor\"\n />\n </svg>\n);\n","import { createContext, useContext } from \"react\";\nimport { CollectionContext, ManifestContext, VaultProvider, useExistingVault } from \"react-iiif-vault\";\nimport invariant from \"tiny-invariant\";\n\nexport interface Resource {\n id: string;\n type: string;\n}\n\nconst AppResourceReactProvider = createContext<Resource | null>(null);\nconst AppResourceInstanceReactProvider = createContext<string | null>(null);\n\nexport function useAppResourceInstance() {\n const ctx = useContext(AppResourceInstanceReactProvider);\n const resource = useContext(AppResourceReactProvider);\n\n const instanceId = ctx || resource?.id;\n\n invariant(instanceId, \"useResourceInstance can only be called from inside <ResourceProvider />\");\n\n return instanceId;\n}\n\nexport function useAppResource() {\n const ctx = useContext(AppResourceReactProvider);\n\n invariant(ctx, \"useResource can only be called from inside <ResourceProvider />\");\n\n return ctx;\n}\n\nexport function AppResourceInstanceProvider({ id, children }: { id?: string; children: React.ReactNode }) {\n if (!id) {\n return children;\n }\n return <AppResourceInstanceReactProvider.Provider value={id}>{children}</AppResourceInstanceReactProvider.Provider>;\n}\n\nexport function AppResourceProvider({ resource, children }: { resource?: Resource; children: React.ReactNode }) {\n const vault = useExistingVault();\n\n let inner = children;\n\n if (resource && resource.type === \"Manifest\") {\n inner = (\n <VaultProvider vault={vault || undefined}>\n <ManifestContext manifest={resource.id || \"\"}>{children}</ManifestContext>\n </VaultProvider>\n );\n }\n\n if (resource && resource.type === \"Collection\") {\n inner = (\n <VaultProvider vault={vault || undefined}>\n <CollectionContext collection={resource.id || \"\"}>{children}</CollectionContext>\n </VaultProvider>\n );\n }\n\n return <AppResourceReactProvider.Provider value={resource as any}>{inner}</AppResourceReactProvider.Provider>;\n}\n","import type { Vault } from \"@iiif/helpers/vault\";\nimport type { Preview, PreviewHandler } from \"../PreviewContext.types\";\n\nexport class ExternalManifestUrlPreview implements PreviewHandler {\n id: string;\n label: string;\n type = \"external-manifest-preview\";\n focusable = true;\n\n private readonly serviceUrl: string;\n private readonly windows: Record<string, { location: string; window: Window | null }> = {};\n\n constructor({ id, config, label }: { id: string; type?: string; label: string; config: { url: string } }) {\n this.id = id;\n this.label = label;\n this.serviceUrl = config.url;\n }\n\n isPreviewValid(instanceId: string): boolean {\n const current = this.windows[instanceId];\n if (current && current.window && !current.window.closed) {\n return true;\n }\n\n return false;\n }\n\n getRequires(): string[] {\n return [\"readOnlyManifest\"];\n }\n\n getProvides(): string[] {\n return [];\n }\n\n async createPreview(\n instanceId: string,\n resource: { id: string; type: string },\n vault: Vault,\n ctx: { readOnlyManifest: string },\n ): Promise<Preview> {\n // @todo change this to be a template, with more features.\n const location = `${this.serviceUrl}`\n .replace(/\\{manifestId}/, ctx.readOnlyManifest)\n .replace(/\\{time}/, `${Date.now()}`);\n const opened = window.open(location, this.id);\n\n this.windows[instanceId] = { location, window: opened };\n\n return {\n id: this.id,\n type: \"external-manifest-preview\",\n data: { url: location },\n };\n }\n\n async focus(instanceId: string) {\n const found = this.windows[instanceId];\n\n if (found && found.window) {\n found.window.focus();\n }\n }\n\n async updatePreview(\n instanceId: string,\n resource: { id: string; type: string },\n vault: Vault,\n ctx: { readOnlyManifest: string },\n ): Promise<Preview | null> {\n const found = this.windows[instanceId];\n\n if (found) {\n try {\n found.window?.close();\n } catch {}\n }\n\n return this.createPreview(instanceId, resource, vault, ctx);\n }\n\n async deletePreview(id: string): Promise<void> {\n const found = this.windows[id];\n if (found && found.window) {\n found.window.close();\n delete this.windows[id];\n }\n }\n}\n","import { Vault } from \"@iiif/helpers/vault\";\nimport { Preview, PreviewConfiguration, PreviewHandler } from \"../PreviewContext.types\";\nimport invariant from \"tiny-invariant\";\n\ntype IIIFPreviewResponse = {\n location: string;\n updateLocation?: string;\n deleteLocation?: string;\n expirationTtl: number;\n};\n\nexport class IIIFPreviewService implements PreviewHandler {\n id: string;\n label: string;\n type = \"iiif-preview-service\";\n focusable = false;\n\n private readonly serviceUrl: string;\n private readonly cache: Record<string, IIIFPreviewResponse & { time: number }> = {};\n\n constructor({ id, config, label }: PreviewConfiguration<{ url: string }>) {\n this.id = id;\n this.label = label;\n this.serviceUrl = config.url;\n }\n\n getRequires(): string[] {\n return [];\n }\n\n getProvides(): string[] {\n return [\"readOnlyManifest\"];\n }\n\n async isPreviewValid(instanceId: string, instance: Preview): Promise<boolean> {\n if (!!this.cache[instanceId]) {\n return true;\n }\n\n if (!instance || !instance.data || !instance.data.readOnlyManifest) {\n return false;\n }\n\n const urlToCheck = instance.data.readOnlyManifest;\n try {\n const resp = await fetch(urlToCheck, {\n cache: \"no-cache\",\n });\n return resp.ok;\n } catch (e) {\n return false;\n }\n }\n\n async createPreview(instanceId: string, resource: { id: string; type: string }, vault: Vault): Promise<Preview> {\n const manifest = vault.toPresentation3(resource as any);\n const response = await fetch(this.serviceUrl, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Origin: \"*\",\n },\n body: JSON.stringify(manifest),\n });\n\n invariant(response.ok, \"Unknown error creating preview\");\n\n const json = await response.json();\n\n invariant(json.location, \"Missing IIIF location while creating preview\");\n\n this.cache[instanceId] = { ...json, time: Date.now() };\n\n return {\n id: this.id,\n type: \"external-manifest-preview\",\n data: {\n readOnlyManifest: `${json.location}/${Date.now()}`,\n },\n };\n }\n\n async focus() {\n // no op.\n }\n\n async updatePreview(instanceId: string, resource: { id: string; type: string }, vault: Vault): Promise<Preview> {\n const cached = this.cache[instanceId];\n if (!cached || Date.now() > cached.expirationTtl + cached.time || !cached.updateLocation) {\n return this.createPreview(instanceId, resource, vault);\n }\n\n const updateUrl = cached.updateLocation;\n const manifest = vault.toPresentation3(resource as any);\n\n const response = await fetch(updateUrl, {\n method: \"PUT\",\n headers: {\n \"Content-Type\": \"application/json\",\n Origin: \"*\",\n },\n body: JSON.stringify(manifest),\n });\n\n invariant(response.ok, \"Unknown error updating preview\");\n\n const json = await response.json();\n\n invariant(json.location);\n\n if (json.updateLocation) {\n cached.updateLocation = json.updateLocation;\n }\n\n const readOnlyManifest = `${json.location}/${Date.now()}`;\n\n // Make a fetch, fill the cache (preview may not)\n await fetch(readOnlyManifest, {\n cache: \"no-cache\",\n });\n\n return {\n id: this.id,\n type: \"external-manifest-preview\",\n data: {\n readOnlyManifest: `${json.location}/${Date.now()}`,\n },\n };\n }\n\n async deletePreview(id: string): Promise<void> {\n const cached = this.cache[id];\n if (cached && cached.deleteLocation) {\n try {\n await fetch(cached.deleteLocation, {\n method: \"DELETE\",\n headers: {\n \"Content-Type\": \"application/json\",\n Origin: \"*\",\n },\n });\n } catch (e) {\n // no-op, we tried.\n }\n }\n }\n}\n","import { type Dispatch, useMemo } from \"react\";\nimport { useVault } from \"react-iiif-vault\";\nimport invariant from \"tiny-invariant\";\nimport { useAppResource, useAppResourceInstance } from \"../AppResourceProvider/AppResourceProvider\";\nimport type {\n Preview,\n PreviewActions,\n PreviewActionsType,\n PreviewConfiguration,\n PreviewHandler,\n PreviewState,\n} from \"./PreviewContext.types\";\nimport { ExternalManifestUrlPreview } from \"./previews/ExternalManifestUrlPreview\";\nimport { IIIFPreviewService } from \"./previews/IIIFPreviewService\";\n\nexport function usePreviewActions(\n state: PreviewState,\n dispatch: Dispatch<PreviewActionsType>,\n handlers: PreviewHandler[],\n previews: Preview[],\n setPreviews: (previews: Preview[] | ((prev: Preview[]) => Preview[])) => void,\n): PreviewActions {\n const resource = useAppResource();\n const instanceId = useAppResourceInstance();\n const vault = useVault();\n\n const previewActions = useMemo(\n () => ({\n setPreview: (preview: Preview) => {\n if (!preview) return;\n setPreviews((prev) => [...prev.filter((item) => item.id !== preview.id), preview]);\n },\n removePreview: (id: string) => {\n setPreviews((prev) => prev.filter((p) => p.id !== id));\n },\n }),\n [setPreviews, instanceId],\n );\n //\n const [handlerMap, providesMap] = useMemo(() => {\n const map: Record<string, PreviewHandler> = {};\n const providesMap: Record<string, string> = {};\n for (const handler of handlers) {\n map[handler.id] = handler;\n const provides = handler.getProvides();\n if (provides.length) {\n for (const singleProvides of provides) {\n if (!providesMap[singleProvides]) {\n providesMap[singleProvides] = handler.id;\n }\n }\n }\n }\n return [map, providesMap] as const;\n }, [handlers]);\n\n async function updatePreviews() {\n const selected = state.selected;\n const selectedPreview = previews.find((p) => p.id === selected);\n if (previews && previews.length && selectedPreview) {\n const selectedHandler = handlerMap[selectedPreview.id]!;\n const requires = selectedHandler.getRequires();\n // Build context.\n const context: any = {};\n for (const preview of previews) {\n const fullPreview = handlerMap[preview.id];\n if (fullPreview) {\n const provides = fullPreview.getProvides();\n for (const provide of provides) {\n if (requires.indexOf(provide) !== -1) {\n const newPreview = await fullPreview.updatePreview(instanceId, resource, vault, context);\n if (newPreview) {\n previewActions.setPreview(newPreview);\n dispatch({ type: \"activatePreview\", payload: newPreview.id });\n Object.assign(context, newPreview.data || {});\n }\n }\n }\n }\n }\n\n // Select\n const handler = handlerMap[selectedPreview.id];\n if (handler) {\n const newPreview = await handler.updatePreview(instanceId, resource, vault, context);\n if (newPreview) {\n previewActions.setPreview(newPreview);\n } else {\n previewActions.removePreview(selectedPreview.id);\n await handler.deletePreview(instanceId);\n }\n }\n }\n }\n\n async function selectPreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (selectedHandler && instanceId) {\n dispatch({ type: \"selectPreview\", payload: id });\n await activatePreview(id);\n }\n }\n\n // Be able to generate a preview link on demand from the iiif-preview-service, if available.\n async function getPreviewLink(): Promise<null | string> {\n const handlerId = providesMap[\"readOnlyManifest\"];\n const previewService = handlerId ? handlerMap[handlerId] : null;\n\n if (previewService && instanceId) {\n const existing = previews.find((p) => p.type === \"iiif-preview-service\");\n if (!existing || !(await previewService.isPreviewValid(instanceId, existing))) {\n const preview = await previewService.createPreview(instanceId, resource, vault, {});\n if (preview) {\n return preview.data.readOnlyManifest;\n }\n }\n }\n return null;\n }\n\n function deletePreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (selectedHandler && instanceId) {\n previewActions.removePreview(id);\n selectedHandler.deletePreview(instanceId).then(() => {\n dispatch({ type: \"deletePreview\", payload: id });\n });\n }\n }\n\n async function focusPreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (handlerMap[id] && instanceId && selectedHandler) {\n await selectedHandler.focus(instanceId);\n dispatch({ type: \"focusPreview\", payload: id });\n }\n }\n\n async function activatePreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (selectedHandler && instanceId) {\n const existingPreview = previews.find((p) => p.id === id);\n if (!existingPreview || !selectedHandler.isPreviewValid(instanceId, existingPreview)) {\n const context: any = {};\n const requires = selectedHandler.getRequires();\n // @todo this could be recursive, but not doing that yet.\n for (const requirement of requires) {\n const handlerId = providesMap[requirement];\n const handler = handlerId ? handlerMap[handlerId] : null;\n\n invariant(handler, `Missing handler for Preview requirement \"${requirement}\"`);\n const existing = previews.find((p) => p.id === handlerId);\n const existingIsActive = state.active.find((a) => a === handlerId);\n\n const alwaysCreate = true as boolean;\n\n if (alwaysCreate || !existing || !(await handler.isPreviewValid(instanceId, existing))) {\n const contextualPreview = await handler.createPreview(instanceId, resource, vault, context);\n Object.assign(context, contextualPreview?.data || {});\n previewActions.setPreview(contextualPreview);\n dispatch({\n type: \"activatePreview\",\n payload: contextualPreview.id,\n });\n } else {\n Object.assign(context, existing?.data || {});\n dispatch({ type: \"activatePreview\", payload: existing.id });\n }\n }\n const created = await selectedHandler.createPreview(instanceId, resource, vault, context);\n if (created) {\n previewActions.setPreview(created);\n dispatch({ type: \"activatePreview\", payload: created.id });\n }\n }\n }\n }\n\n return useMemo(\n () => ({\n selectPreview,\n deletePreview,\n focusPreview,\n activatePreview,\n updatePreviews,\n getPreviewLink,\n }),\n // Dispatch has a stable identity.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n [handlerMap, instanceId, vault, state.selected, state.active, previews],\n );\n}\n\nexport function usePreviewHandlers(configs: PreviewConfiguration[]): PreviewHandler[] {\n // @todo in the future the available classes could come from somewhere else and not hardcoded.\n return useMemo(() => {\n const handlers: PreviewHandler[] = [];\n\n for (const config of configs) {\n switch (config.type) {\n case \"iiif-preview-service\":\n handlers.push(new IIIFPreviewService(config));\n break;\n case \"external-manifest-preview\":\n handlers.push(new ExternalManifestUrlPreview(config));\n break;\n }\n }\n return handlers;\n\n // @todo if these ever become configurable, remove this.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n}\n","import { Draft, produce } from \"immer\";\nimport { PreviewActionsType, PreviewContext, PreviewState } from \"./PreviewContext.types\";\n\nexport const previewContextReducer = produce(function reducer(state: Draft<PreviewState>, action: PreviewActionsType) {\n switch (action.type) {\n case \"focusPreview\": {\n break;\n }\n\n case \"deletePreview\": {\n if (state.selected === action.payload) {\n state.selected = null;\n }\n state.active = state.active.filter((p) => p !== action.payload);\n break;\n }\n\n case \"activatePreview\": {\n if (state.active.indexOf(action.payload) === -1) {\n state.active.push(action.payload);\n }\n break;\n }\n\n case \"selectPreview\": {\n state.selected = action.payload;\n if (state.active.indexOf(action.payload) === -1) {\n state.active.push(action.payload);\n }\n break;\n }\n }\n});\n\nexport function getDefaultPreviewState(): PreviewState {\n return {\n active: [],\n selected: null,\n };\n}\n","import { createContext, memo, ReactNode, useContext, useEffect, useMemo, useReducer } from \"react\";\nimport { Preview, PreviewConfiguration, PreviewContext } from \"./PreviewContext.types\";\nimport invariant from \"tiny-invariant\";\nimport { usePreviewActions, usePreviewHandlers } from \"./PreviewContext.hooks\";\nimport { getDefaultPreviewState, previewContextReducer } from \"./PreviewContext.reducer\";\nimport { useAppResourceInstance } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useLocalStorage } from \"../hooks/use-local-storage\";\n\nconst PreviewReactContext = createContext<PreviewContext | null>(null);\nconst AvailablePreviewReactContext = createContext<Preview[]>([] as Preview[]);\n\nexport const PreviewProvider = memo(function PreviewProvider({\n children,\n configs = [],\n}: {\n previews: Preview[];\n children: ReactNode;\n configs: PreviewConfiguration[];\n}) {\n const instanceId = useAppResourceInstance();\n const handlers = usePreviewHandlers(configs); \n const [previews, setPreviews] = useLocalStorage<Preview[]>(`preview-${instanceId}`, []);\n\n const [state, dispatch] = useReducer(previewContextReducer, undefined, getDefaultPreviewState);\n const actions = usePreviewActions(state, dispatch, handlers, previews, setPreviews);\n const context: PreviewContext = useMemo(\n () => ({ configs, actions, handlers, ...state }),\n [actions, configs, handlers, state]\n );\n\n useEffect(() => {\n for (const preview of previews) {\n if (!state.active.includes(preview.id)) {\n const handler = handlers.find((h) => h.id === preview.id);\n if (handler) {\n Promise.resolve(handler.isPreviewValid(instanceId, preview)).then((valid) => {\n if (valid) {\n dispatch({ type: \"activatePreview\", payload: preview.id });\n } else {\n setPreviews((prev) => prev.filter((p) => p.id !== preview.id));\n }\n });\n }\n }\n }\n }, [instanceId]);\n\n return (\n <AvailablePreviewReactContext.Provider value={previews}>\n <PreviewReactContext.Provider value={context}>{children}</PreviewReactContext.Provider>\n </AvailablePreviewReactContext.Provider>\n );\n});\n\nexport function usePreviews() {\n return useContext(AvailablePreviewReactContext);\n}\n\nexport function usePreviewContext() {\n const ctx = useContext(PreviewReactContext);\n\n invariant(ctx, \"usePreviewContext() can only be called from inside <PreviewProvider />\");\n\n return ctx;\n}\n","import styled from \"styled-components\";\n\nexport const ButtonReset = styled.button`\n border: none;\n outline: none;\n background-color: transparent;\n margin: 0;\n padding: 0;\n font-size: inherit;\n color: inherit;\n cursor: pointer;\n &:hover {\n color: inherit;\n }\n`;\n\nexport const Button = styled.button<{ $active?: boolean }>`\n padding: 0.5rem 1rem;\n color: ${(props: any) => props.theme.color.main || \"none\"};\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n border-radius: inherit;\n border: none;\n cursor: pointer;\n display: flex;\n align-items: center;\n font-size: 0.85em;\n :disabled {\n opacity: 0.65;\n cursor: not-allowed;\n }\n\n &:hover {\n background: #eee;\n }\n`;\n\nexport const SmallButton = styled(Button as any)`\n padding: 0.25em ${(props: any) => props.theme.padding.xs || \"0.4em\"};\n height: unset;\n background: none;\n`;\n\nexport const SecondaryButton = styled(Button as any)`\n {\n padding: 0 ${(props: any) => props.theme.padding.medium || \"1rem\"};\n color: ${(props: any) => props.theme.color.main || \"#B84C74;\"};\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n border: 1px solid ${(props: any) => props.theme.color.main || \"#B84C74;\"};\n border-radius: 0.25rem;\n cursor: pointer;\n height: 2rem;\n display: flex;\n align-items: center;\n white-space: nowrap;\n font-size: 0.75rem;\n\n :disabled {\n opacity: 0.65;\n cursor: not-allowed;\n }\n }\n`;\n\nexport const CalltoButton = styled(Button as any)`\n padding: 0 ${(props: any) => props.theme.padding.medium || \"1rem\"};\n color: ${(props: any) => props.theme.color.white || \"white\"};\n background-color: ${(props: any) => props.theme.color.main || \"#B84C74;\"};\n border: 1px solid #eee;\n border-radius: 0.25rem;\n cursor: pointer;\n justify-content: center;\n display: flex;\n align-items: center;\n &:hover {\n background-color: ${(props: any) => props.theme.color.mainHover || \"#B84C74;\"};\n }\n`;\n\nexport const ButtonGroup = styled.div<{ $right?: boolean }>`\n display: flex;\n flex-direction: row;\n flex-wrap: wrap;\n align-items: flex-start;\n justify-content: ${(props) => (props.$right ? \"flex-end\" : \"flex-start\")};\n`;\n","import styled, { css } from \"styled-components\";\nimport { ButtonReset } from \"@manifest-editor/ui/atoms/Button\";\n\nexport const ButtonContainer = styled.div`\n display: flex;\n position: relative;\n width: 10em;\n`;\n\nconst variation = {\n light: {\n bg: { normal: \"#fff\", hover: \"#f8f5fe\", active: \"#f8f5fe\" },\n border: { main: \"\", divider: \"\" },\n color: \"\",\n },\n salmon: {\n bg: { normal: \"#B84C74\", hover: \"#892C4E\", active: \"#892C4E\" },\n border: { main: \"#B84C74\", divider: \"#e37266\" },\n color: \"\",\n },\n};\n\nexport const ButtonMain = styled(ButtonReset as any)`\n flex: 1;\n padding: 0.5em 0.8em;\n background: #b84c74;\n color: #fff;\n border-top-left-radius: 5px;\n font-size: 0.875em;\n border-bottom-left-radius: 5px;\n border: 1px solid #b84c74;\n border-right-width: 0;\n\n &:hover {\n color: #fff;\n background: #892c4e;\n border-color: #892c4e;\n }\n\n &:active {\n background: #892c4e;\n box-shadow: inset 0 2px 8px 0 rgba(0, 0, 0, 0.15);\n }\n`;\n\nexport const ButtonChange = styled(ButtonReset as any)<{ $open: boolean }>`\n background: #b84c74;\n border-top-right-radius: 5px;\n border-bottom-right-radius: 5px;\n border: 1px solid #b84c74;\n border-left: 1px solid #fff;\n padding: 0.4em;\n color: #fff;\n svg {\n fill: currentColor;\n }\n &:hover {\n color: #fff;\n background: #892c4e;\n }\n\n &:active {\n background: #892c4e;\n box-shadow: inset 0 2px 8px 0 rgba(0, 0, 0, 0.15);\n }\n\n ${(props) =>\n props.$open &&\n css`\n background: #892c4e;\n box-shadow: inset 0 2px 8px 0 rgba(0, 0, 0, 0.15);\n `}\n`;\n\nexport const MenuContainer = styled.div<{ $open: boolean }>`\n position: absolute;\n opacity: 0;\n top: 100%;\n margin-top: 0.3em;\n border-radius: 3px;\n left: -50%;\n width: 150%;\n pointer-events: none;\n box-shadow:\n 0 4px 15px 0 rgba(0, 0, 0, 0.18),\n 0 0px 0px 1px rgba(0, 0, 0, 0.15),\n inset 0 0 0 1px rgba(255, 255, 255, 0.2);\n background: #fff;\n overflow: hidden;\n\n ${(props) =>\n props.$open &&\n css`\n opacity: 1;\n pointer-events: visible;\n `}\n`;\n\nexport const MenuItem = styled.div`\n display: flex;\n background: #fff;\n padding: 0.4em;\n align-items: center;\n\n &:hover {\n background: #f9f9f9;\n }\n`;\n\nconst statusMap = {\n available: \"#ddd\",\n configured: \"#e37266\",\n active: \"#4cb235\",\n};\n\nexport const MenuItemStatus = styled.div<{ $status: \"available\" | \"configured\" | \"active\" }>`\n margin: 0.2em 0.5em;\n width: 8px;\n height: 8px;\n border-radius: 50%;\n background-color: ${(props) => statusMap[props.$status]};\n`;\n\nexport const MenuItemLabel = styled.div`\n flex: 1;\n font-size: 0.925em;\n padding: 0.2em;\n text-overflow: ellipsis;\n cursor: pointer;\n white-space: nowrap;\n overflow: hidden;\n`;\n\nexport const MenuItemClose = styled.div`\n background: #f9f9f9;\n font-size: 0.8em;\n`;\n\nexport const ButtonEmpty = styled.div`\n color: #999;\n font-size: 0.8em;\n padding: 0.6em 0.8em;\n border: 2px dashed #f9f9f9;\n border-radius: 5px;\n user-select: none;\n cursor: not-allowed;\n`;\n","import { DownloadButton } from \"@manifest-editor/components\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { DownIcon } from \"@manifest-editor/ui/icons/DownIcon\";\nimport useDropdownMenu from \"react-accessible-dropdown-menu-hook\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useConfig } from \"../ConfigContext/ConfigContext\";\nimport { usePreviewContext } from \"../PreviewContext/PreviewContext\";\nimport {\n ButtonChange,\n ButtonContainer,\n ButtonEmpty,\n ButtonMain,\n MenuContainer,\n MenuItem,\n MenuItemClose,\n MenuItemLabel,\n MenuItemStatus,\n} from \"./PreviewButton.styles\";\n\nexport function PreviewButton({ downloadEnabled, fileName }: { downloadEnabled?: boolean; fileName?: string }) {\n const { active, configs, actions, selected } = usePreviewContext();\n const vault = useVault();\n const config = useConfig();\n const resource = useAppResource();\n const configsToShow = configs.filter((c) => c.type === \"external-manifest-preview\");\n const { isOpen, buttonProps, itemProps } = useDropdownMenu(configsToShow.length);\n\n if (configsToShow.length === 0) {\n return <ButtonEmpty>Preview not available</ButtonEmpty>;\n }\n\n return (\n <>\n {downloadEnabled ? (\n <div className=\"mr-4\">\n <DownloadButton\n fileName={fileName || \"manifest.json\"}\n label=\"Download manifest\"\n getData={() => {\n if (config.export && config.export.version === 2) {\n return JSON.stringify(vault.toPresentation2(resource as any), null, 2);\n }\n return JSON.stringify(vault.toPresentation3(resource as any), null, 2);\n }}\n />\n </div>\n ) : null}\n <ButtonContainer>\n <ButtonMain\n onClick={() => {\n if (!selected) {\n const defaultPreviewId = config.defaultPreview;\n if (defaultPreviewId) {\n const found = configs.find((c) => c.id === defaultPreviewId);\n if (found) {\n actions.selectPreview(found.id);\n return;\n }\n }\n\n actions.selectPreview(configs[0]!.id);\n }\n actions.updatePreviews();\n }}\n >\n Preview\n </ButtonMain>\n <ButtonChange $open={isOpen} {...buttonProps}>\n <DownIcon />\n </ButtonChange>\n\n <MenuContainer $open={isOpen}>\n {configsToShow.map((config, key) => {\n const inactive = active.indexOf(config.id) === -1;\n return (\n <MenuItem key={config.id} {...(itemProps[key] as any)}>\n <MenuItemStatus $status={inactive ? \"available\" : config.id === selected ? \"active\" : \"configured\"} />\n <MenuItemLabel\n onClick={() => {\n actions.selectPreview(config.id);\n }}\n >\n {config.label}\n </MenuItemLabel>\n {!inactive ? (\n <MenuItemClose onClick={() => actions.deletePreview(config.id)}>\n <CloseIcon />\n </MenuItemClose>\n ) : null}\n </MenuItem>\n );\n })}\n </MenuContainer>\n </ButtonContainer>\n </>\n );\n}\n","import { Logo, Container, Header } from \"./AppHeader.styles\";\nimport { PreviewButton } from \"../PreviewButton/PreviewButton\";\nimport { ManifestEditorLogo } from \"@manifest-editor/components\";\n\nimport { memo } from \"react\";\nimport { useLocalStorage } from \"../hooks/use-local-storage\";\n\ninterface AppHeaderProps {\n onClickLogo?: () => void;\n}\n\nexport const AppHeader = memo(function AppHeader(props: AppHeaderProps) {\n const [isMenuHidden] = useLocalStorage(\"menu-hidden\");\n\n return (\n <Header>\n <Container>\n <Logo onClick={props.onClickLogo}>\n <ManifestEditorLogo />\n </Logo>\n\n <PreviewButton />\n\n {/*<IconButton>•</IconButton>*/}\n </Container>\n {/* {!isMenuHidden ? <ShellOptions /> : null} */}\n </Header>\n );\n});\n","import { createContext, useContext } from \"react\";\n\ntype MenuItem = {\n label: string;\n onClick?: () => void;\n active?: boolean;\n};\n\ninterface AppMenuContext {\n file: {\n new: MenuItem;\n edit: MenuItem;\n open: MenuItem;\n\n newOptions: MenuItem[];\n openOptions: MenuItem[];\n };\n}\n\nconst ReactAppMenuContext = createContext<AppMenuContext | null>(null);\n\nexport function useAppMenu() {\n const ctx = useContext(ReactAppMenuContext);\n\n if (!ctx) {\n return null;\n }\n\n return ctx;\n}\n\nexport function useAppMenuItem<\n Key extends keyof AppMenuContext,\n Name extends keyof AppMenuContext[Key],\n Return extends AppMenuContext[Key][Name],\n>(menu: Key, name: Name): Return | null {\n const ctx = useAppMenu();\n\n if (!ctx) {\n return null;\n }\n\n return ctx[menu][name] as Return;\n}\n\nexport function AppMenuProvider({ children, menu }: { children: React.ReactNode; menu: AppMenuContext }) {\n return <ReactAppMenuContext.Provider value={menu}>{children}</ReactAppMenuContext.Provider>;\n}\n","import { useContext } from \"react\";\nimport { type AtlasStore, AtlasStoreProvider, AtlasStoreReactContext } from \"react-iiif-vault\";\nimport type { StoreApi } from \"zustand\";\n\nexport { AtlasStoreProvider, AtlasStoreReactContext };\n\nexport function useAtlasStore() {\n return useContext(AtlasStoreReactContext) as StoreApi<AtlasStore>;\n}\n","import type { InputShape } from \"polygon-editor\";\n\nexport function polygonToBoundingBox(polygon: InputShape | null) {\n if (!polygon) {\n return null;\n }\n if (polygon.points.length > 2) {\n const x1 = Math.min(...polygon.points.map((p) => p[0]));\n const y1 = Math.min(...polygon.points.map((p) => p[1]));\n const x2 = Math.max(0, ...polygon.points.map((p) => p[0]));\n const y2 = Math.max(0, ...polygon.points.map((p) => p[1]));\n return {\n x: x1,\n y: y1,\n width: x2 - x1,\n height: y2 - y1,\n };\n }\n return null;\n}\n","import { getValue } from \"@iiif/helpers\";\nimport * as IIIFVault from \"@iiif/helpers/vault\";\n\n// This is from the ts version\n// Create an image in the DOM to measure height and width\nconst getImage = async (src: string): Promise<HTMLImageElement> => {\n return new Promise((resolve, reject) => {\n const $img = document.createElement(\"img\");\n $img.onload = () => resolve($img);\n $img.onerror = () => reject();\n $img.src = src;\n if ($img.complete) {\n resolve($img); // cached.\n }\n });\n};\n\nconst getAudioVideo = async (src: string) => {\n return new Promise<HTMLVideoElement>((resolve, reject) => {\n // Video tag accepts both.\n const $media = document.createElement(\"video\");\n $media.onloadedmetadata = () => resolve($media);\n $media.onerror = () => reject();\n $media.preload = \"metadata\";\n $media.src = src;\n });\n};\n\n// use the hints from the user (if any), plus defaults, to get the order\n// in which to try various analysis\nfunction makeTryList(suppliedExpectedTypes: string[]) {\n const defaults = [\"Image\", \"ImageService\", \"ManifestOrCollection\", \"ContentState\"];\n let tryList: string[] = [];\n if (!suppliedExpectedTypes || suppliedExpectedTypes.length === 0) {\n tryList = defaults;\n }\n mergeList(suppliedExpectedTypes, tryList);\n mergeList(defaults, tryList);\n return tryList;\n}\n\nfunction mergeList(inputList: string[], outputList: string[]) {\n inputList.map((t: string) => {\n if (t === \"Image\" && !outputList.includes(\"Image\")) {\n outputList.push(\"Image\");\n }\n if (t === \"ImageService\" && !outputList.includes(\"ImageService\")) {\n outputList.push(\"ImageService\");\n }\n if (t === \"Manifest\" && !outputList.includes(\"ManifestOrCollection\")) {\n outputList.push(\"ManifestOrCollection\");\n }\n if (t === \"Collection\" && !outputList.includes(\"ManifestOrCollection\")) {\n outputList.push(\"ManifestOrCollection\");\n }\n if (t === \"ManifestOrCollection\" && !outputList.includes(\"ManifestOrCollection\")) {\n outputList.push(\"ManifestOrCollection\");\n }\n if (t === \"ContentState\" && !outputList.includes(\"ContentState\")) {\n outputList.push(\"ContentState\");\n }\n });\n}\n\nexport async function detectMedia() {\n //\n}\n\nexport async function analyse(url: string, ...expectedTypes: string[]) {\n // const tryList = makeTryList(expectedTypes);\n\n if (!url) {\n return;\n }\n\n // 2 new options:\n // - Audio\n // - Video\n // Only support them if they end in mp3 or mp4\n if (url.endsWith(\".mp3\") || url.endsWith(\".mp4\") || url.endsWith(\".m4a\") || url.endsWith(\".m4v\")) {\n try {\n const av = await getAudioVideo(url);\n if (av) {\n const isAudio = av.videoWidth === 0;\n return {\n id: url,\n type: av.videoWidth === 0 ? \"Sound\" : \"Video\",\n width: av.videoWidth || undefined, // naturalWidth\n height: av.videoHeight || undefined, // naturalHeight\n duration: av.duration,\n format: isAudio ? \"audio/mp4\" : \"video/mp4\",\n };\n }\n } catch (e) {\n // fall through..\n }\n }\n\n // This doesn't use the tryList order yet.\n // One advantage of doing a fetch first _even if we expect an image_ is that\n // we might capture the content type, if the image is CORS-enabled.\n let response = null;\n try {\n // Try head request, if that works...\n await fetch(url, { method: \"HEAD\" });\n\n // then fetch the full resource.\n response = await fetch(url);\n } catch {\n // can handle the error better, but maybe CORS error happened so:\n return handleNonFetchableUrl(url);\n }\n\n if (!response.ok) {\n response = await fetch(url + \"/info.json\");\n if (!response.ok) {\n return handleNonFetchableUrl(url);\n }\n }\n\n // but... it might have been a CORS-enabled image, or an image from an image service.\n // In this scenario we can capture the content type right here.\n const contentTypeHeader = response.headers.get(\"Content-Type\");\n if (contentTypeHeader?.includes(\"image/\")) {\n return handleNonFetchableUrl(url, contentTypeHeader);\n }\n\n // OK, it's probably NOT an image, and we have an OK response, so can we get JSON from it?\n let data = null;\n try {\n data = await response.json();\n } catch {\n return null;\n }\n\n return await analyseJson(data, url);\n}\n\nfunction asImageService(data: any) {\n if (data.protocol && data.protocol === \"http://iiif.io/api/image\") {\n if (!data.type) {\n data.type = \"ImageService\";\n }\n // NB this will be ImageService3 if it's a v3 img service\n return data;\n }\n return null;\n}\n\nexport async function analyseJson(data: any, url: string) {\n // Is it an image service?\n const testImageService = asImageService(data);\n if (testImageService) {\n return testImageService;\n }\n\n // does it have an ID?\n const dataId = data.id || data[\"@id\"];\n if (!dataId) {\n return null;\n }\n const vault = new IIIFVault.Vault();\n const vaultData = await vault.load(url, data); // we could use dataId here, but just in case it's wrong...\n if (!vaultData) {\n return;\n }\n // @ts-ignore\n if ((vaultData && vaultData?.type === \"Manifest\") || vaultData?.type === \"Collection\") {\n return {\n id: url,\n // @ts-ignore\n type: vaultData.type,\n // @ts-ignore\n label: getValue(vaultData.label),\n };\n }\n}\n\nasync function handleNonFetchableUrl(url: string, capturedContentType?: string) {\n // it *is* an image... but is it an image from an image service?\n // In its current form this should be tried before any fetch happens\n // that is, does it match:\n // http<s>://<any.org>/<any-prefix>/region/size/rotation/format.quality ?\n // This should really call Stephen's IIIF Image API parser, and if it's a success, we know it's\n // probably an image service\n // https://github.com/atlas-viewer/iiif-image-api\n // https://github.com/atlas-viewer/iiif-image-api/blob/main/src/utility/parse-image-service-request.ts\n const parts = url.split(\"/\");\n if (parts.length >= 8) {\n // might be an image service\n const iiifParts = parts.slice(-4);\n // need to do more than this but the parser can do the hard work\n if (iiifParts[3]!.split(\".\").length === 2) {\n // This is not reliable! parse it properly!\n if (iiifParts[2]![0] === \"!\" || iiifParts[2] === iiifParts[2]) {\n // rotation param is numeric\n // this is worth trying as an image service\n const serviceUrl = parts.slice(0, parts.length - 4).join(\"/\") + \"/info.json\";\n // assume this is a low cost thing to try\n const imgService = await getImageService(serviceUrl);\n if (imgService && imgService?.type && imgService?.type?.startsWith(\"ImageService\")) {\n return imgService;\n }\n }\n }\n }\n\n // OK we didn't find an image service behind that image URL. So now it's time to use the DOM.\n\n try {\n const image = (await getImage(url)) as any;\n const data = {\n id: url,\n type: \"Image\",\n width: image.width, // naturalWidth\n height: image.height, // naturalHeight\n format: await getFormat(url, capturedContentType),\n };\n return data;\n } catch {}\n\n return null;\n}\n\nasync function getImageService(url: string) {\n try {\n const response = await fetch(url);\n if (response.ok) {\n const data = await response.json();\n return await analyseJson(data, url);\n }\n return null;\n } catch (e: any) {\n console.log(e);\n return null;\n }\n}\n\nexport async function getFormat(url: string, capturedContentType?: string) {\n if (capturedContentType) {\n // we managed to learn this earlier, the image had CORS\n return capturedContentType;\n }\n try {\n // a HEAD request doesn't have CORS issues... well it didn't used to...\n const response = await fetch(url, { method: \"HEAD\", mode: \"no-cors\" });\n const ct = response.headers.get(\"Content-type\");\n if (ct) {\n return ct;\n }\n } catch (e) {\n // ignore.\n }\n\n // if the above still fails, we could fall back to guessing\n // content-type from the URL (.jpg etc).\n const test = url.toLowerCase();\n if (test.endsWith(\"jpg\") || test.endsWith(\"jpeg\")) {\n return \"image/jpeg\";\n }\n if (test.endsWith(\"png\")) {\n return \"image/png\";\n }\n // Just a default.\n return \"image/jpeg\";\n}\n\nexport async function getImageDimensions(url: string) {\n try {\n const image = await getImage(url);\n if (image) {\n return {\n width: image.naturalWidth || image.width,\n height: image.naturalHeight || image.height,\n };\n }\n } catch (e) {\n return null;\n }\n return null;\n}\n","import { toRef } from \"@iiif/parser\";\nimport type { ManifestNormalized } from \"@iiif/presentation-3-normalized\";\nimport type { AppExtension, MappedApp } from \"./AppContext/AppContext\";\n\nexport async function getManifestNomalized(\n id: string,\n): Promise<ManifestNormalized | undefined> {\n let responseData: ManifestNormalized | undefined;\n try {\n await fetch(id)\n .then((response) => {\n return response.json().catch((err) => {\n console.error(`'${err}' happened!`);\n });\n })\n .then((data) => {\n responseData = { ...data };\n });\n } catch (error) {\n console.log(error);\n }\n return responseData;\n}\n\nexport function createActionIdentity(\n type: string,\n property: string,\n parent: any,\n) {\n return `create_${type}_${property}_${toRef(parent)?.type || \"unknown\"}`;\n}\n\nexport function createDownload(\n data: any,\n fileName: string,\n fileType = \"text/json\",\n) {\n // Create a blob with the data we want to download as a file\n const blob =\n data instanceof Blob ? data : new Blob([data], { type: fileType });\n // Create an anchor element and dispatch a click event on it\n // to trigger a download\n const a = document.createElement(\"a\");\n a.download = fileName;\n a.href = window.URL.createObjectURL(blob);\n const clickEvt = new MouseEvent(\"click\", {\n view: window,\n bubbles: true,\n cancelable: true,\n });\n a.dispatchEvent(clickEvt);\n a.remove();\n}\n\nexport async function copyToClipboard(json: string | any) {\n return navigator.clipboard.writeText(\n typeof json === \"string\" ? json : JSON.stringify(json, null, 2),\n );\n}\n\nexport function randomId() {\n return `${Math.random().toString(36).substr(2)}-${Date.now().toString(36)}`;\n}\n\nexport function mapApp(\n input: any,\n map?: (app: MappedApp) => MappedApp,\n): MappedApp {\n const { default: metadata, config, ...props } = input;\n const app = {\n metadata: metadata as any,\n layout: {\n leftPanels: [],\n rightPanels: [],\n centerPanels: [],\n ...(props as any),\n },\n config,\n };\n\n return map ? map(app) : app;\n}\n\nexport function extendApp(\n app: MappedApp,\n metadata: MappedApp[\"metadata\"],\n extensions: AppExtension,\n): MappedApp {\n return {\n ...app,\n metadata,\n config: {\n ...(app.config || {}),\n ...(extensions.config || {}),\n },\n layout: {\n ...app.layout,\n leftPanels: [\n ...(app.layout.leftPanels || []).filter((panel) => {\n if (extensions?.leftPanelIds) {\n return extensions.leftPanelIds.includes(panel.id);\n }\n return true;\n }),\n ...(extensions?.leftPanels || []),\n ],\n annotations: [\n ...(extensions?.annotations || []),\n ...(app.layout.annotations || []),\n ],\n canvasEditors: [\n ...(extensions?.canvasEditors || []),\n ...(app.layout.canvasEditors || []),\n ],\n creators: [\n ...(extensions?.creators || []),\n ...(app.layout.creators || []),\n ],\n background: [\n ...(app.layout?.background || []),\n ...(extensions?.background || []),\n ],\n editors: [\n //\n ...(extensions?.editors || []),\n ...(app.layout.editors || []),\n ],\n rightPanels: [\n ...(app.layout.rightPanels || []),\n ...(extensions?.rightPanels || []),\n ],\n centerPanels: [\n ...(app.layout.centerPanels || []),\n ...(extensions?.centerPanels || []),\n ],\n modals: [\n ...(app.layout.modals || []),\n ...(extensions?.modalPanels || []),\n ],\n },\n };\n}\n","import { create } from \"zustand\";\nimport { useEffect, useMemo } from \"react\";\nimport { randomId } from \"./helpers\";\n\ntype Projection = {\n x: number;\n y: number;\n width: number;\n height: number;\n};\n\ninterface HighlightedImageResources {\n regions: Record<string, Projection | null>;\n resources: string[];\n setRegion: (id: string, region?: Projection | null) => void;\n setHighlight: (id: string | string[]) => void;\n highlight: (id: string) => void;\n clearHighlight: (id: string) => void;\n}\n\nexport const useHighlightedImageResource = create<HighlightedImageResources>((set) => ({\n regions: {},\n resources: [],\n setRegion: (id, region) => {\n set((ex) => ({ ...ex.regions, regions: { [id]: region || null } }));\n },\n setHighlight: (id: string | string[]) => {\n set({ resources: Array.isArray(id) ? id : [id] });\n },\n highlight: (id) => {\n set((s) => {\n if (s.resources.indexOf(id) !== -1) {\n return s;\n }\n return { resources: [...s.resources, id] };\n });\n },\n clearHighlight: (id) => {\n set((s) => ({ resources: s.resources.filter((item) => item !== id) }));\n },\n}));\n\nexport function useTemporaryHighlight(newValue?: Projection | null) {\n const id = useMemo(() => randomId(), []);\n const value = useHighlightedImageResource((s) => s.regions[id]);\n const setRegion = useHighlightedImageResource((s) => s.setRegion);\n\n useEffect(() => {\n if (value && newValue) {\n if (\n value !== newValue &&\n (value.x !== newValue.x ||\n value.y !== newValue.y ||\n value.width !== newValue.width ||\n value.height !== newValue.height)\n ) {\n setRegion(id, newValue || null);\n }\n } else {\n setRegion(id, newValue || null);\n }\n }, [value]);\n\n useEffect(() => {\n return () => setRegion(id, null);\n }, []);\n}\n\nexport function useHoverHighlightImageResource(id?: string) {\n const highlight = useHighlightedImageResource((s) => s.highlight);\n const clear = useHighlightedImageResource((s) => s.clearHighlight);\n\n useEffect(() => {\n return () => {\n if (id) {\n clear(id);\n }\n };\n }, [clear, id]);\n\n return useMemo(() => {\n return {\n onMouseEnter() {\n if (id) {\n highlight(id);\n }\n },\n onMouseLeave() {\n if (id) {\n clear(id);\n }\n },\n };\n }, [id, highlight, clear]);\n}\n","import * as React from \"react\";\nimport { SVGProps } from \"react\";\n\nexport const StarIcon = (props: SVGProps<SVGSVGElement>) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"1em\" width=\"1em\" viewBox=\"0 0 24 24\" {...props}>\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path\n d=\"M12 17.27 18.18 21l-1.64-7.03L22 9.24l-7.19-.61L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21z\"\n fill=\"currentColor\"\n />\n </svg>\n);\n","export const BackIcon: React.FC<{ style?: any }> = ({ style }) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"1rem\" viewBox=\"0 0 24 24\" width=\"1rem\" fill=\"#000000\" style={style}>\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path d=\"M20 11H7.83l5.59-5.59L12 4l-8 8 8 8 1.41-1.41L7.83 13H20v-2z\" />\n </svg>\n);\n","import { createContext, useContext, useMemo } from \"react\";\nimport { LayoutActions, LayoutProviderProps, LayoutState } from \"./Layout.types\";\nimport { useApp } from \"../AppContext/AppContext\";\n\nexport const LayoutActionsReactContext = createContext<LayoutActions>(null as any);\nexport const LayoutStateReactContext = createContext<LayoutState>(null as any);\n\nexport function useLayoutState() {\n return useContext(LayoutStateReactContext);\n}\n\nexport function useLayoutActions() {\n return useContext(LayoutActionsReactContext);\n}\n\nexport function useAvailableLayouts() {\n const app = useApp();\n return app.layout;\n}\n\nexport function useLayoutProvider(): LayoutProviderProps & {\n loading?: true;\n actions: LayoutActions;\n state: LayoutState;\n} {\n const app = useApp();\n const layout = app.layout;\n const actions = useContext(LayoutActionsReactContext);\n const state = useContext(LayoutStateReactContext);\n\n return useMemo(() => {\n return { actions, state, ...layout };\n\n // The actions have a fully stable identity.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [app, state]);\n}\n","import { ErrorMessage, PaddedSidebarContainer } from \"@manifest-editor/components\";\nimport { Button, CalltoButton } from \"@manifest-editor/ui/atoms/Button\";\nimport { ExperimentalMessage } from \"@manifest-editor/ui/madoc/components/callouts/ExperimentalMessage\";\nimport { WarningMessage } from \"@manifest-editor/ui/madoc/components/callouts/WarningMessage\";\nimport { ExperimentalIcon } from \"@manifest-editor/ui/madoc/components/icons/ExperimentalIcon\";\n// import { LimitationError } from \"../../../helpers/limitation\";\n// import { FixMeError } from \"@/helpers/fix-me\";\nimport { useState } from \"react\";\n\nexport function PanelError(props: { error: Error; resetErrorBoundary: () => void }) {\n const error = props.error.toString();\n const [isFixing, setIsFixing] = useState(false);\n\n // @todo come back to.\n // if (props.error instanceof FixMeError) {\n // const errorObject = props.error;\n\n // return (\n // <PaddedSidebarContainer>\n // <WarningMessage $banner>\n // <ExperimentalIcon style={{ fontSize: \"2.2em\", margin: \"0 0.3em 0 0\" }} />\n // <div>\n // <h4 style={{ margin: 0 }}>There is a fixable error</h4>\n // <p>{errorObject.message}</p>\n // <Button\n // disabled={isFixing}\n // onClick={async () => {\n // setIsFixing(true);\n // await errorObject.fix();\n // props.resetErrorBoundary();\n // setIsFixing(false);\n // }}\n // >\n // Fix error\n // </Button>\n // </div>\n // </WarningMessage>\n // </PaddedSidebarContainer>\n // );\n // }\n\n // @todo come back to.\n // if (props.error instanceof LimitationError) {\n // error = props.error.message;\n\n // return (\n // <PaddedSidebarContainer>\n // <ExperimentalMessage $banner>\n // <ExperimentalIcon style={{ fontSize: \"2.2em\", margin: \"0 0.3em 0 0\" }} />\n // <div>\n // <h4 style={{ margin: 0 }}>The manifest editor is still in development</h4>\n // <p>{error}</p>\n // </div>\n // </ExperimentalMessage>\n // </PaddedSidebarContainer>\n // );\n // }\n\n return (\n <PaddedSidebarContainer>\n <ErrorMessage className=\"mb-2\">{error}</ErrorMessage>\n <CalltoButton onClick={props.resetErrorBoundary}>Try again</CalltoButton>\n </PaddedSidebarContainer>\n );\n}\n","import { PinnablePanelState } from \"./Layout.types\";\nimport { createElement, ReactNode } from \"react\";\n\nexport function isPinnableState(t: unknown): t is PinnablePanelState {\n return t && (t as any).pinnable;\n}\n\nexport function panelSizing({\n initial,\n\n fallback,\n options = {},\n}: {\n initial?: number;\n fallback: number;\n options?: { minWidth?: number; maxWidth?: number };\n}) {\n // panel min width\n // panel max width\n // default width\n // fallback width\n return Math.max(options.minWidth || 0, Math.min(options.maxWidth || Infinity, initial || fallback));\n}\n\nexport function renderHelper(htmlOrReact: string | ReactNode): ReactNode {\n if (typeof htmlOrReact === \"string\") {\n return createElement(\"div\", { dangerouslySetInnerHTML: { __html: htmlOrReact } });\n }\n return htmlOrReact;\n}\n","import styled, { css } from \"styled-components\";\nimport { Button } from \"./Button\";\n\nexport const Dropdown = styled.div`\n position: relative;\n display: inline-block;\n`;\n\nexport const DropdownContent = styled.div`\n display: flex;\n flex-direction: column;\n position: absolute;\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n color: ${(props: any) => props.theme.color.black || \" black\"};\n font-size: 0.75rem;\n min-width: 160px;\n box-shadow: 0px 8px 16px 0px rgba(0, 0, 0, 0.2);\n z-index: 150;\n button {\n &:hover {\n background-color: ${(props: any) => props.theme.color.lightgrey || \"lightgrey\"};\n }\n }\n`;\n\nexport const DropdownItem = styled.button<{ $active?: boolean }>`\n padding: 0 ${(props: any) => props.theme.padding.small || \"0.5rem\"};\n color: ${(props: any) => props.theme.color.main || \"none\"};\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n border-radius: 0;\n border: none;\n cursor: pointer;\n display: flex;\n padding: 0.65em 1em;\n align-items: center;\n :disabled {\n opacity: 0.65;\n cursor: not-allowed;\n }\n\n &:hover {\n background-color: ${(props: any) => props.theme.color.lightgrey || \"lightgrey\"};\n }\n\n ${(props) =>\n props.$active &&\n css`\n background: #b84c74;\n color: #fff;\n &:hover {\n background: #b84c74;\n color: #fff;\n }\n `}\n`;\n\nexport const DropdownMenu = styled.div<{ $open?: boolean; $center?: boolean }>`\n display: none;\n flex-direction: column;\n position: absolute;\n background: #fff;\n color: ${(props: any) => props.theme.color.black || \" black\"};\n font-size: 0.75rem;\n min-width: 190px;\n top: calc(100% + 0.5em);\n box-shadow:\n 0 4px 15px 0 rgba(0, 0, 0, 0.18),\n 0 0px 0px 1px rgba(0, 0, 0, 0.15),\n inset 0 0 0 1px rgba(255, 255, 255, 0.2);\n border-radius: 3px;\n z-index: 150;\n overflow: hidden;\n padding-bottom: 3px;\n\n ${Button} {\n &:hover {\n background-color: ${(props: any) => props.theme.color.lightgrey || \"lightgrey\"};\n }\n }\n\n ${(props) =>\n props.$open &&\n css`\n display: flex;\n `}\n`;\n\nexport const DropdownLabel = styled.div`\n color: #999;\n text-transform: uppercase;\n font-weight: 600;\n padding: 0.7em;\n font-size: 0.875em;\n`;\n\nexport const DropdownDivider = styled.div`\n height: 1px;\n margin: 0 0.5em;\n background: #eee;\n`;\n","import { TransitionStatus } from \"react-transition-group\";\nimport { LayoutPanel, PanelActions, PanelState, PinnablePanelActions, PinnablePanelState } from \"../Layout.types\";\nimport styled, { css } from \"styled-components\";\nimport { StarIcon } from \"@manifest-editor/ui/icons/StarIcon\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { BackIcon } from \"@manifest-editor/ui/icons/BackIcon\";\nimport { useLayoutProvider } from \"../Layout.context\";\nimport { ErrorBoundary } from \"react-error-boundary\";\nimport { createContext, useCallback, useContext, useEffect, useMemo, useRef, useState } from \"react\";\nimport { PanelError } from \"./PanelError\";\nimport { renderHelper } from \"../Layout.helpers\";\nimport { ReactVaultContext } from \"react-iiif-vault\";\nimport {\n DropdownDivider,\n DropdownLabel,\n DropdownMenu,\n Dropdown,\n DropdownItem,\n} from \"@manifest-editor/ui/atoms/Dropdown\";\nimport useDropdownMenu from \"react-accessible-dropdown-menu-hook\";\nimport { useAppState } from \"../../AppContext/AppContext\";\n\nconst OverrideScrollbar = 'OverrideScrollbar';\n\ninterface ModularPanelProps {\n panel?: LayoutPanel;\n isLeft?: boolean;\n state: PinnablePanelState | PanelState;\n actions: PanelActions;\n pinActions?: PinnablePanelActions;\n transition?: TransitionStatus;\n noHeader?: boolean;\n close?: () => void;\n available?: LayoutPanel[];\n style?: any;\n}\n\nconst LayoutTitleReactContext = createContext<(title: string) => void>(null as any);\n\nexport function useSetCustomTitle() {\n return useContext(LayoutTitleReactContext);\n}\n\nconst ModularPanelWrapper = styled.div<{ $floating?: boolean; $state?: TransitionStatus; $flipped?: boolean }>`\n display: flex;\n flex-direction: column;\n position: relative;\n height: 100%;\n overflow: hidden;\n transition: transform 300ms;\n\n &[data-header=\"false\"] {\n border-top: 1px solid #e4e7f0;\n }\n\n &[data-floating=\"true\"] {\n margin: 10px;\n border-radius: 5px;\n overflow: hidden;\n background: #fff;\n }\n\n &[data-state=\"entering\"],\n &[data-state=\"entered\"] {\n transform: translateX(0);\n }\n\n &[data-state=\"exiting\"],\n &[data-state=\"exited\"] {\n transform: translateX(100%);\n }\n\n &[data-state=\"exiting\"][data-flipped=\"true\"],\n &[data-state=\"exited\"][data-flipped=\"true\"] {\n transform: translateX(0);\n }\n\n &[data-state=\"exiting\"][data-flipped=\"false\"],\n &[data-state=\"exited\"][data-flipped=\"false\"] {\n transform: translateX(100%);\n }\n\n &[data-state=\"entering\"][data-flipped=\"true\"],\n &[data-state=\"entered\"][data-flipped=\"true\"] {\n transform: translateX(0);\n }\n\n &[data-state=\"entering\"][data-flipped=\"false\"],\n &[data-state=\"entered\"][data-flipped=\"false\"] {\n transform: translateX(100%);\n }\n\n &[data-state=\"unmounted\"] {\n transform: translateX(100%);\n }\n`;\n\nexport const ModularPanelHeader = styled.div<{ $tabs?: boolean; $error?: boolean }>`\n background: #fff;\n display: flex;\n height: 2.8em;\n align-items: center;\n z-index: 2;\n\n &[data-tabs=\"true\"] {\n box-shadow: inset 0 1px 0 0 rgba(0, 0, 0, 0.17);\n }\n\n &[data-tabs=\"false\"] {\n box-shadow:\n inset 0 -1px 0 0 rgba(0, 0, 0, 0.17),\n inset 0 1px 0 0 rgba(0, 0, 0, 0.17);\n }\n\n &[data-error=\"true\"] {\n color: #b61717;\n background: #ffc2d2;\n box-shadow: inset 0 -5px 10px 0 rgba(255, 255, 255, 0.5);\n }\n`;\n\nexport const ModulePanelButton = styled.button`\n border: none;\n background: transparent;\n padding: 0 0.4em;\n margin: 0.3em;\n border-radius: 3px;\n &:hover {\n background: #eee;\n }\n svg {\n font-size: 1.2em;\n }\n`;\n\nconst ModulePanelSpacer = styled.div`\n flex: 1 1 0px;\n`;\n\nconst ModularPanelLabel = styled.div`\n font-size: 0.875em;\n flex: 1 1 0px;\n padding-left: 1em;\n text-align: center;\n align-self: center;\n`;\n\nconst ModularPanelContent = styled.div`\n flex: 1 1 0px;\n display: flex;\n\n min-height: 0;\n overflow-y: auto;\n overflow-x: hidden;\n\n > * {\n min-width: 0;\n }\n`;\n\nexport function ModularPanel({\n panel,\n state,\n actions,\n isLeft,\n pinActions = actions as any,\n transition,\n close,\n available = [],\n style,\n noHeader,\n}: ModularPanelProps) {\n const vault = useContext(ReactVaultContext) || null;\n const [didError, setDidError] = useState(false);\n const appState = useAppState();\n const layout = useLayoutProvider();\n const { tabs, pinnable, hideHeader } = panel?.options || {};\n const resetKeys = [appState.state.canvasId, panel?.id];\n const switchablePanels = useMemo(() => {\n return (available || []).filter((p) => !p.requiresState);\n }, [available]);\n const { itemProps, isOpen, setIsOpen } = useDropdownMenu(switchablePanels.length);\n const [customTitle, setCustomTitle] = useState(\"\");\n const setCustomTitleRef = useRef<(title: string) => void | undefined>();\n\n useEffect(() => setDidError(false), resetKeys);\n\n useEffect(() => setCustomTitle(\"\"), [panel]);\n\n useEffect(() => {\n setCustomTitleRef.current = setCustomTitle;\n return () => {\n setCustomTitleRef.current = undefined;\n };\n }, []);\n\n const _setCustomTitle = useCallback((title: string) => {\n if (setCustomTitleRef.current) {\n setCustomTitleRef.current(title);\n }\n }, []);\n\n const backAction = useCallback(\n (e?: React.MouseEvent) => {\n const originalCallback = panel\n ? state.stack.length\n ? actions.popStack\n : panel.backAction\n ? () => panel && panel.backAction && panel.backAction(state, { ...layout, current: actions }, appState)\n : null\n : null;\n\n if (e && (!originalCallback || e.metaKey) && switchablePanels.length) {\n e.preventDefault();\n setIsOpen(true);\n } else {\n originalCallback && originalCallback();\n }\n },\n [actions, appState, layout, panel, setIsOpen, state, switchablePanels.length]\n );\n\n const menuHandler = (newPanel: LayoutPanel) => {\n actions.change({\n id: newPanel.id,\n state: newPanel.defaultState,\n stacked: !!(state.stack.length || panel?.backAction),\n });\n };\n\n if (!panel || !state.current) {\n return null;\n }\n\n const backButton =\n panel.backAction || state.stack.length ? (\n <ModulePanelButton onClick={backAction}>\n <BackIcon />\n </ModulePanelButton>\n ) : null;\n\n const closeButton = (\n <ModulePanelButton onClick={close || actions.close}>\n <CloseIcon />\n </ModulePanelButton>\n );\n\n return (\n <LayoutTitleReactContext.Provider value={_setCustomTitle}>\n <ModularPanelWrapper data-state={transition} data-flipped={isLeft} style={style} data-header={!noHeader}>\n {noHeader ? null : (\n <ModularPanelHeader data-tabs={!!tabs} data-error={didError}>\n <Dropdown style={{ display: \"flex\", height: \"100%\" }}>\n {panel.renderBackAction ? panel.renderBackAction({ backAction, fallback: backButton }) : backButton}\n {switchablePanels.length ? (\n <DropdownMenu $open={isOpen} style={{ left: \"0.5em\" }}>\n <DropdownLabel>All panels</DropdownLabel>\n <DropdownDivider />\n {switchablePanels.map((newPanel, i) => (\n <DropdownItem\n key={i}\n {...(itemProps as any)[i]}\n onClick={() => menuHandler(newPanel)}\n $active={panel.id === newPanel.id}\n >\n {newPanel.label}\n </DropdownItem>\n ))}\n </DropdownMenu>\n ) : null}\n </Dropdown>\n\n {customTitle ? (\n <ModularPanelLabel>{customTitle}</ModularPanelLabel>\n ) : hideHeader ? (\n <ModulePanelSpacer />\n ) : (\n <ModularPanelLabel>{panel.label}</ModularPanelLabel>\n )}\n {pinnable ? (\n (state as PinnablePanelState).pinned ? (\n <ModulePanelButton onClick={pinActions.unpin}>\n <StarIcon fill=\"orange\" />\n </ModulePanelButton>\n ) : (\n <ModulePanelButton onClick={() => pinActions.pin({ id: panel.id, state: state.state })}>\n <StarIcon fill=\"#ddd\" />\n </ModulePanelButton>\n )\n ) : null}\n {panel.renderCloseAction\n ? panel.renderCloseAction({ closeAction: close || actions.close, fallback: closeButton })\n : closeButton}\n </ModularPanelHeader>\n )}\n <ModularPanelContent className={OverrideScrollbar}>\n <ErrorBoundary\n // onResetKeysChange={() => setDidError(false)}\n onError={() => setDidError(true)}\n FallbackComponent={PanelError}\n resetKeys={resetKeys}\n onReset={() => setDidError(false)}\n >\n {renderHelper(\n panel.render(\n state.state || panel.defaultState || {},\n { ...layout, current: actions, vault: vault as any, transition },\n appState\n )\n )}\n </ErrorBoundary>\n </ModularPanelContent>\n </ModularPanelWrapper>\n </LayoutTitleReactContext.Provider>\n );\n}\n","import { Vault } from \"@iiif/helpers/vault\";\nimport {\n addReference,\n batchActions,\n modifyEntityField,\n reorderEntityField,\n requestResource,\n} from \"@iiif/helpers/vault/actions\";\nimport { actionListFromResource } from \"@iiif/helpers/vault/utility\";\n\nexport function createPreviewVault(homepageCollectionId = \"vault://homepage-collection.json\") {\n const vault = new Vault();\n\n // 1st - ensure that our \"default\" collection exists OR import one.\n const previewCollection = window.localStorage.getItem(\"preview-vault-collection\");\n let didImport = false;\n if (previewCollection) {\n try {\n const previewState = JSON.parse(previewCollection);\n if (previewState.id && previewState.id === homepageCollectionId) {\n vault.dispatch(requestResource({ id: previewState.id }));\n const toDispatch: any = actionListFromResource(previewState.id, previewState);\n vault.dispatch(batchActions({ actions: toDispatch }));\n didImport = true;\n }\n } catch (e) {\n //\n }\n }\n\n if (!didImport) {\n const toDispatch: any = actionListFromResource(homepageCollectionId, {\n \"@context\": \"http://iiif.io/api/presentation/3/context.json\",\n id: homepageCollectionId,\n type: \"Collection\",\n label: { en: [\"Recent items\"] },\n items: [],\n });\n vault.dispatch(requestResource({ id: homepageCollectionId }));\n vault.dispatch(batchActions({ actions: toDispatch }));\n }\n\n const clearHistory = () => {\n vault.dispatch(modifyEntityField({ id: homepageCollectionId, type: \"Collection\", key: \"items\", value: [] }));\n window.localStorage.setItem(\n \"preview-vault-collection\",\n JSON.stringify(vault.toPresentation3({ id: homepageCollectionId, type: \"Collection\" }))\n );\n };\n\n const addHistory = (id: string, type: string) => {\n const state = vault.getState();\n if (id && type && (type === \"Collection\" || type === \"Manifest\")) {\n const existingCollection = state.iiif.entities.Collection[homepageCollectionId];\n // This shouldn't happen... but it could.\n if (existingCollection) {\n const alreadyExists = existingCollection.items.findIndex((t) => t.id === id);\n if (alreadyExists === -1) {\n vault.dispatch(\n addReference({\n id: homepageCollectionId,\n type: \"Collection\",\n reference: { id, type },\n key: \"items\",\n index: 0,\n })\n );\n } else {\n vault.dispatch(\n reorderEntityField({\n id: homepageCollectionId,\n type: \"Collection\",\n key: \"items\",\n startIndex: alreadyExists,\n endIndex: 0,\n })\n );\n }\n\n window.localStorage.setItem(\n \"preview-vault-collection\",\n JSON.stringify(vault.toPresentation3({ id: homepageCollectionId, type: \"Collection\" }))\n );\n }\n }\n };\n\n const unsubscribe2 = vault.on(\"after:@iiif/REMOVE_REFERENCE\", (ctx) => {\n if (ctx.action.payload.id === homepageCollectionId) {\n window.localStorage.setItem(\n \"preview-vault-collection\",\n JSON.stringify(vault.toPresentation3({ id: homepageCollectionId, type: \"Collection\" }))\n );\n }\n });\n\n const unsubscribe = () => {\n // This isn't working, because React.\n // unsubscribe1();\n // unsubscribe2();\n };\n\n return { vault, unsubscribe, addHistory, clearHistory } as const;\n}\n","import { createContext, useContext, useEffect, useMemo } from \"react\";\nimport { Vault } from \"@iiif/helpers/vault\";\nimport { VaultProvider } from \"react-iiif-vault\";\nimport { createPreviewVault } from \"./create-preview-vault\";\n\nexport function usePreviewVault() {\n return useContext(PreviewVaultReactContext);\n}\n\nconst PreviewVaultReactContext = createContext<Vault>(new Vault());\n\nconst PreviewVaultAddHistory = createContext({\n addHistory: (id: string, type: string) => {},\n clearHistory: () => {},\n});\n\nexport const HOMEPAGE_COLLECTION = \"manifest-editor://homepage-collection.json\";\n\nexport function usePreviewHistory() {\n return useContext(PreviewVaultAddHistory);\n}\n\nexport function PreviewVaultContext(props: { children: any }) {\n const { vault, unsubscribe, addHistory, clearHistory } = useMemo(() => {\n return createPreviewVault(HOMEPAGE_COLLECTION);\n }, []);\n\n useEffect(() => {\n return unsubscribe;\n }, []);\n\n return (\n <PreviewVaultAddHistory.Provider value={{ addHistory, clearHistory }}>\n <PreviewVaultReactContext.Provider value={vault}>{props.children}</PreviewVaultReactContext.Provider>\n </PreviewVaultAddHistory.Provider>\n );\n}\n\nexport function PreviewVaultBoundary({ children }: { children: any }) {\n const vault = usePreviewVault();\n\n return <VaultProvider vault={vault}>{children}</VaultProvider>;\n}\n","import { toRef } from \"@iiif/parser\";\nimport type { Reference } from \"@iiif/presentation-3\";\nimport { Creator, matchBasedOnResource } from \"@manifest-editor/creator-api\";\nimport { useCallback, useMemo } from \"react\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { createActionIdentity } from \"../helpers\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { usePreviewVault } from \"../PreviewVault/PreviewVault\";\n\nexport function useCreator(\n parent: any,\n property: string,\n type: string,\n target?: Reference,\n options?: { isPainting?: boolean; onlyReference?: boolean },\n) {\n const vault = useVault();\n const app = useApp();\n const { create, edit } = useLayoutActions();\n const supported = useMemo(\n () => matchBasedOnResource({ type, parent, index: 0, property }, app.layout.creators || [], { vault }),\n [parent, property, app.layout.creators, type, vault],\n );\n const canCreate = parent && supported.length !== 0;\n\n const wrappedCreate = useCallback(\n (index?: number, initialData?: any) => {\n if (parent) {\n return create({\n type,\n parent: toRef(parent),\n property,\n index,\n target,\n initialData,\n ...(options || {}),\n });\n }\n },\n [create, parent, property, type, options, target],\n );\n\n const wrappedFilteredCreate = useCallback(\n (filter: string, index?: number, initialData?: any) => {\n if (parent) {\n return create({\n type,\n filter,\n parent: toRef(parent),\n property,\n index,\n target,\n initialData,\n ...(options || {}),\n });\n }\n },\n [create, parent, property, type, options, target],\n );\n\n const wrappedEdit = useCallback(\n (resource: any, index?: number) => {\n edit(resource, parent ? { parent: toRef(parent), property, index } : undefined);\n },\n [edit, parent, property],\n );\n\n const wrappedCreator = useCallback(\n (initialCreator: string, initialData?: any) => {\n if (parent) {\n return create({\n type,\n initialCreator,\n parent: toRef(parent),\n property,\n target,\n initialData,\n ...(options || {}),\n });\n }\n },\n [type, property, parent, target, create, options],\n );\n\n const buttonProps = useMemo(() => {\n return {\n \"data-action-id\": createActionIdentity(type, property, parent),\n };\n }, [type, property, parent]);\n\n return [\n canCreate,\n {\n create: wrappedCreate,\n edit: wrappedEdit,\n createFiltered: wrappedFilteredCreate,\n creator: wrappedCreator,\n buttonProps,\n },\n ] as const;\n}\n\nexport function useInlineCreator() {\n const vault = useVault();\n const previewVault = usePreviewVault();\n const app = useApp();\n return useMemo(() => {\n return new Creator(vault, app.layout.creators || [], previewVault);\n }, [app.layout.creators, vault]);\n}\n","import { createContext, useContext, useMemo } from \"react\";\n\nconst CreatorInitialDataReactContext = createContext<Record<string, unknown>>({});\n\nexport function useInitialData<T = unknown>(id: string): T | {} {\n const context = useContext(CreatorInitialDataReactContext);\n return context[id] || {};\n}\n\nexport function CreatorInitialData<T extends Record<string, unknown>>(props: { id: string; children: React.ReactNode; data: T }) {\n const existingContext = useContext(CreatorInitialDataReactContext);\n const newContext = useMemo(\n () => ({ ...existingContext, [props.id]: props.data }),\n [existingContext, props.id, props.data],\n );\n return (\n <CreatorInitialDataReactContext.Provider value={newContext}>\n {props.children}\n </CreatorInitialDataReactContext.Provider>\n );\n}\n","import { toRef } from \"@iiif/parser\";\nimport {\n ActionButton,\n BackIcon,\n CreatorGrid,\n EmptyState,\n ErrorMessage,\n GridIcon,\n IconButton,\n ModalBackSlot,\n Spinner,\n} from \"@manifest-editor/components\";\nimport {\n type CreatableResource,\n type CreatorDefinition,\n type CreatorOptions,\n matchBasedOnResource,\n} from \"@manifest-editor/creator-api\";\nimport { Button } from \"@manifest-editor/ui/atoms/Button\";\nimport { memo, Suspense, useEffect, useMemo, useRef, useState } from \"react\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { useTemporaryHighlight } from \"../highlighted-image-resources\";\nimport { ModulePanelButton, useSetCustomTitle } from \"../Layout/components/ModularPanel\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { useInlineCreator } from \"./BaseCreator.hooks\";\nimport { useInitialData } from \"./CreatorInitialData\";\n\ninterface BaseCreatorProps {\n resource: CreatableResource;\n}\n\nexport const RenderCreator = memo(function RenderCreator(props: {\n resource: CreatableResource;\n creator: CreatorDefinition;\n onCreate?: () => void;\n skipEditingOnCreate?: boolean;\n}) {\n const vault = useVault();\n const { edit, modal } = useLayoutActions();\n const [isCreating, setIsCreating] = useState(false);\n const [error, setError] = useState<string | null>(null);\n const creator = useInlineCreator();\n const isCreatingRef = useRef(false);\n\n const canvasSelector = props.resource.initialData?.selector;\n useTemporaryHighlight(canvasSelector);\n\n const initialData = useInitialData(props.creator.id);\n\n const options: CreatorOptions = {\n targetType: props.resource.type,\n parent: props.resource.parent\n ? {\n property: props.resource.property as string,\n atIndex: props.resource.index,\n resource: props.resource.parent,\n }\n : undefined,\n target: props.resource.target,\n initialData: { ...initialData, ...(props.resource.initialData || {}) },\n };\n\n const runCreate = (payload: any) => {\n try {\n if (isCreating || isCreatingRef.current) return;\n setIsCreating(true);\n isCreatingRef.current = true;\n creator\n .create(props.creator.id, payload, options)\n .catch((err) => {\n setError(err?.message || \"Unknown error\");\n return null;\n })\n .then(async (ref) => {\n props.onCreate?.();\n if (props.skipEditingOnCreate) return;\n if (!ref) return;\n const singleRef = Array.isArray(ref) ? ref[0] : ref;\n setIsCreating(false);\n modal.popStack();\n modal.close();\n // Ref might be an array?\n if (singleRef) {\n edit(singleRef!, {\n parent: toRef(props.resource.parent),\n property: props.resource.property,\n index: props.resource.index,\n });\n }\n });\n } catch (err: any) {\n setError(err?.message || \"Unknown error\");\n }\n };\n\n const validate = async () => {\n return true;\n };\n\n useEffect(() => {\n if (props.resource.initialData?.showEmptyForm) {\n return;\n }\n\n if (!props.creator.render && !isCreating) {\n runCreate({});\n }\n }, [props.creator]);\n\n if (error) {\n return (\n <div className=\"flex flex-col items-center p-4\">\n <ErrorMessage>{error}</ErrorMessage>\n </div>\n );\n }\n\n const spinner = (\n <div className=\"flex flex-col items-center py-8\">\n <div className=\"flex gap-2 items-center\">\n <Spinner /> <span>Loading</span>\n </div>\n </div>\n );\n\n if (isCreating) {\n return spinner;\n }\n\n if (!props.creator.render) {\n return (\n <>\n <EmptyState>No options available</EmptyState>\n <ActionButton primary onPress={() => runCreate({})}>\n {props.creator.actionButton || \"Create\"}\n </ActionButton>\n </>\n );\n }\n\n return (\n <>\n <Suspense fallback={spinner}>\n {props.creator.render({\n vault,\n runCreate,\n validate,\n options,\n })}\n </Suspense>\n </>\n );\n});\n\nexport function BaseCreator(props: BaseCreatorProps) {\n const app = useApp();\n const vault = useVault();\n const [currentId, setCurrentId] = useState(props.resource.initialCreator || \"\");\n const set = useSetCustomTitle();\n const supported = useMemo(\n () =>\n matchBasedOnResource(props.resource, app.layout.creators || [], {\n vault,\n }),\n [props.resource, app.layout.creators, vault],\n );\n if (supported.length === 1 && !currentId) {\n setCurrentId(supported[0]!.id);\n }\n\n const current = supported.find((t) => t.id === currentId);\n\n useEffect(() => {\n if (current) {\n set?.(current.label);\n }\n });\n\n if (supported.length === 0) {\n return <EmptyState>Not currently supported</EmptyState>;\n }\n\n const backButton = (\n <ModalBackSlot>\n <IconButton\n root={document.getElementById(\"headlessui-portal-root\") || undefined}\n label=\"Back to Add content options\"\n className=\"group\"\n placement=\"right\"\n onPress={() => setCurrentId(\"\")}\n >\n <GridIcon className=\"text-2xl opacity-50 group-hover:opacity-70\" />\n </IconButton>\n </ModalBackSlot>\n );\n\n if (current) {\n const shouldHideModal = current.hiddenModal;\n\n if (shouldHideModal) {\n return (\n <>\n {backButton}\n <RenderCreator creator={current} resource={props.resource} />\n </>\n );\n }\n\n return (\n <div>\n {backButton}\n <div className={\"p-2 py-6\"}>\n <RenderCreator creator={current} resource={props.resource} />\n </div>\n </div>\n );\n }\n\n return (\n <CreatorGrid\n label=\"Select a type\"\n items={supported.map((item) => ({\n id: item.id,\n title: item.label,\n description: item.summary || \"\",\n icon: item.icon,\n onClick: () => setCurrentId(item.id),\n }))}\n />\n );\n}\n","import type { CreatableResource } from \"@manifest-editor/creator-api\";\nimport type { LayoutPanel } from \"../Layout/Layout.types\";\nimport { BaseCreator } from \"./BaseCreator\";\n\nexport const baseCreator: LayoutPanel = {\n id: \"@manifest-editor/creator\",\n label: \"Add content\",\n options: { hideHeader: true, tabs: false },\n render(state: CreatableResource) {\n return <BaseCreator resource={state} />;\n },\n};\n","export const defaultTheme = {\n color: {\n main: \"#B84C74\",\n mainHover: \"#4a89ff\",\n logoPink: \"#E94581\",\n white: \"white\",\n grey: \"grey\",\n black: \"black\",\n lightgrey: \"#F8F9FA\",\n mediumgrey: \"#dddddd\",\n danger: \"#a90e21\",\n warning: \"#e38627\",\n lightdanger: \"#ffeaea\",\n lightsuccess: \"#c5e8c5\",\n success: \"#6ccd55\",\n greyOverlay: \"rgba(0, 0, 0, 0.2)\",\n highlight: \"#faeed7\",\n },\n iiifColor: {\n manifest: \"rgba(0, 0, 0, 0.2)\",\n canvas: \"rgba(255, 222, 219, 0.8)\",\n service: \"rgba(13, 110, 253, 0.8)\",\n annotation: \"rgba(247, 226, 173, 0.8)\",\n contentResource: \"rgba(207, 247, 255, 0.8)\",\n ranges: \"rgba(144, 213, 157, 0.8)\",\n },\n padding: {\n xs: \"0.25rem\",\n small: \"0.5rem\",\n medium: \"1rem\",\n large: \"2rem\",\n },\n device: {\n mobile: \"375px\",\n tablet: \"768px\",\n laptop: \"992px\",\n desktop: \"1200px\",\n },\n shadows: {\n standard: \"rgba(0, 0, 0, 0.1) 0px 1px 3px 0px, rgba(0, 0, 0, 0.05) 0px 5px 15px 0px\",\n bottom: \"rgba(0, 0, 0, 0.1) 0px 4px 2px -2px\",\n },\n};\n","import { useVault } from \"react-iiif-vault\";\nimport { useMemo } from \"react\";\nimport {\n type CreatableResource,\n matchBasedOnResource,\n} from \"@manifest-editor/creator-api\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { Tab, TabList, TabPanel, Tabs } from \"@manifest-editor/components\";\nimport { RenderCreator } from \"./BaseCreator\";\nimport { ThemeProvider } from \"styled-components\";\nimport { defaultTheme } from \"../ShellContext/default-theme\";\n\ninterface BaseAnnotationCreatorProps {\n resource: CreatableResource;\n onCreate: () => void;\n}\n\nexport function BaseAnnotationCreator(props: BaseAnnotationCreatorProps) {\n const {} = props;\n const vault = useVault();\n const app = useApp();\n const supported = useMemo(\n () =>\n matchBasedOnResource(props.resource, app.layout.creators || [], {\n vault,\n }),\n [props.resource, app.layout.creators, vault],\n );\n\n if (supported.length === 0) {\n return <div>No supported creators found</div>;\n }\n\n return (\n <div>\n <Tabs className=\"w-full flex-1 overflow-hidden flex flex-col\">\n <TabList\n className=\"flex-1 overflow-hidden w-full flex text-sm whitespace-nowrap\"\n items={supported}\n >\n {(item) => <Tab id={item.id}>{item.label}</Tab>}\n </TabList>\n {supported.map((item) => {\n return (\n <TabPanel key={item.id} id={item.id} className=\"p-2\">\n <ThemeProvider theme={defaultTheme}>\n <RenderCreator\n creator={item}\n resource={props.resource}\n onCreate={props.onCreate}\n skipEditingOnCreate\n />\n </ThemeProvider>\n </TabPanel>\n );\n })}\n </Tabs>\n </div>\n );\n}\n","import { toRef } from \"@iiif/parser\";\nimport type {\n EditingStackActionCreators,\n EditingStackState,\n} from \"./EditingStack.types\";\n\nexport function editingStackReducer(\n state: EditingStackState,\n action: EditingStackActionCreators,\n): EditingStackState {\n switch (action.type) {\n case \"setStack\": {\n return {\n ...state,\n stack: action.payload.resources,\n current: action.payload.resources[0] || null,\n };\n }\n\n case \"edit\": {\n let reset = action.payload.reset;\n if (\n action.payload.resource?.resource.source?.type === \"Manifest\" ||\n action.payload.resource?.resource.source?.type === \"Canvas\"\n ) {\n reset = true;\n }\n\n if (\n state.current?.resource.source.id ===\n action.payload.resource?.resource.source.id\n ) {\n return {\n ...state,\n current: action.payload.resource,\n };\n }\n\n return {\n ...state,\n current: action.payload.resource,\n stack: reset\n ? []\n : state.current\n ? [state.current, ...state.stack]\n : state.stack,\n };\n }\n case \"syncRemoval\": {\n const item = toRef(action.payload.resource.resource);\n if (!item) {\n return state;\n }\n const found = state.stack.find((r) => toRef(r.resource)?.id === item.id);\n\n if (!found) {\n return state;\n }\n\n const newCurrent =\n state.current?.resource.id === item.id ? null : state.current;\n const newStack = filterStack(\n state.stack.filter((r) => toRef(r.resource)?.id !== item.id),\n newCurrent,\n );\n\n return {\n ...state,\n stack: newStack,\n current: newCurrent,\n };\n }\n case \"updateCurrent\": {\n return {\n ...state,\n current: action.payload.resource,\n };\n }\n\n case \"back\": {\n const newCurrent = state.stack[0];\n return {\n ...state,\n stack: state.stack.slice(1),\n current: newCurrent || null,\n };\n }\n\n case \"close\": {\n return {\n ...state,\n stack: [], // @todo maybe not right?\n current: null,\n };\n }\n\n case \"create\": {\n if (action.payload.resource === null) {\n return { ...state, create: null };\n }\n\n return {\n ...state,\n create: action.payload as any,\n };\n }\n }\n\n return state;\n}\n\nfunction filterStack(\n newStackWithDuplicates: EditingStackState[\"stack\"],\n current: EditingStackState[\"current\"],\n): EditingStackState[\"stack\"] {\n const newStack = [];\n let prev = null;\n for (const stackItem of newStackWithDuplicates) {\n if (prev?.resource.id === stackItem.resource.id) {\n continue;\n }\n newStack.push(stackItem);\n prev = stackItem;\n }\n\n if (prev && prev.resource.id === current?.resource.id) {\n return newStack.slice(0, newStack.length - 1);\n }\n\n return newStack;\n}\n","import { toRef } from \"@iiif/parser\";\nimport type { Reference, SpecificResource } from \"@iiif/presentation-3\";\nimport { EditorInstance } from \"@manifest-editor/editor-api\";\nimport { createContext, useCallback, useContext, useEffect, useMemo, useReducer } from \"react\";\nimport { flushSync } from \"react-dom\";\nimport { useResourceContext, useVault } from \"react-iiif-vault\";\nimport invariant from \"tiny-invariant\";\nimport { useAppInstance } from \"../AppContext/AppContext\";\nimport { editingStackReducer } from \"./EditingStack.reducer\";\nimport type { EditableResource, EditingStackActions, EditingStackState } from \"./EditingStack.types\";\n\nconst defaultState: EditingStackState = { stack: [], current: null, create: null };\nexport const EditingStackContext = createContext<EditingStackState>(defaultState);\nconst EditingStackActionsContext = createContext<EditingStackActions>({\n edit() {},\n close() {},\n back() {},\n setStack() {},\n updateCurrent() {},\n create() {\n return () => {};\n },\n});\n\nexport function useEditingStack() {\n return useContext(EditingStackActionsContext);\n}\n\nexport function useEditingResource() {\n return useContext(EditingStackContext).current;\n}\n\nexport function useEditingResourceStack() {\n return useContext(EditingStackContext).stack;\n}\n\nexport function useCreatingResource() {\n return useContext(EditingStackContext).create;\n}\n\nexport function useManifestEditor() {\n const { manifest } = useResourceContext();\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n invariant(manifest, \"Manifest not found\");\n\n const editor = useMemo(() => {\n return new EditorInstance({\n reference: { id: manifest, type: \"Manifest\" },\n vault,\n });\n }, [manifest, vault]);\n\n useEffect(() => {\n return editor.observe.start(invalidate);\n }, [editor]);\n\n editor.observe.key = `${key}`;\n editor.observe.reset();\n\n return editor;\n}\n\nexport function useCollectionEditor() {\n const { collection } = useResourceContext();\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n invariant(collection, \"Collection not found\");\n\n const editor = useMemo(() => {\n return new EditorInstance({\n reference: { id: collection, type: \"Collection\" },\n vault,\n });\n }, [collection, vault]);\n\n useEffect(() => {\n return editor.observe.start(invalidate);\n }, [editor]);\n\n editor.observe.key = `${key}`;\n editor.observe.reset();\n\n return editor;\n}\n\nexport function useGenericEditor(\n ref: Reference<any> | SpecificResource | undefined,\n ctx: { parent?: Reference; parentProperty?: string; index?: number; allowNull?: boolean } = {},\n) {\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n !ctx.allowNull && invariant(ref, \"Resource not found\");\n\n const editor = useMemo(() => {\n if (ctx.allowNull && !ref) {\n return null as any as EditorInstance<{}>;\n }\n\n return new EditorInstance({\n reference: toRef(ref) as any,\n vault,\n context: { resource: ref!, parent: ctx.parent, index: ctx.index, parentProperty: ctx.parentProperty },\n });\n }, [ref, vault]);\n\n useEffect(() => {\n return editor?.observe.start(invalidate);\n }, [editor]);\n\n if (editor) {\n editor.observe.key = `${key}`;\n editor.observe.reset();\n }\n\n return editor!;\n}\n\nexport function useAnnotationPageEditor() {\n const { annotationPage } = useResourceContext();\n\n invariant(annotationPage, \"Annotation page not found\");\n\n return useGenericEditor({ id: annotationPage, type: \"AnnotationPage\" });\n}\n\nexport function useEditor() {\n const resource = useEditingResource();\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n invariant(resource, \"No resource selected\");\n\n const editor = useMemo(() => {\n return new EditorInstance({\n reference: resource.resource.source || resource.resource,\n vault,\n });\n }, [resource, vault]);\n\n useEffect(() => {\n return editor.observe.start(invalidate);\n }, [editor]);\n\n editor.observe.key = `${key}`;\n editor.observe.reset();\n\n return editor;\n}\n\nfunction useInternalEditingStackActions(defaultState: EditingStackState) {\n const vault = useVault();\n const [state, _dispatch] = useReducer(editingStackReducer, defaultState);\n\n const dispatch = useCallback((action: any) => {\n _dispatch(action);\n // (() => flushSync(() => _dispatch(action)))();\n }, []);\n\n useEffect(() => {\n return vault.on(\"@iiif/REMOVE_REFERENCE\", (payload: any) => {\n const action = payload.action;\n const parent = { id: action.payload.id, type: action.payload.type };\n const resource = action.payload.reference;\n _dispatch({ type: \"syncRemoval\", payload: { resource: { parent, resource } } });\n });\n }, [vault]);\n\n const edit = useCallback(\n (resource: EditableResource, reset = false) => dispatch({ type: \"edit\", payload: { resource, reset } }),\n [],\n );\n\n const setStack = useCallback(\n (resources: EditableResource[]) => dispatch({ type: \"setStack\", payload: { resources } }),\n [],\n );\n\n const updateCurrent = useCallback(\n (resource: EditableResource) => dispatch({ type: \"updateCurrent\", payload: { resource } }),\n [],\n );\n\n const close = useCallback(() => dispatch({ type: \"close\" }), []);\n\n const back = useCallback(() => dispatch({ type: \"back\" }), []);\n\n const create = useCallback<EditingStackActions[\"create\"]>((resource, options) => {\n dispatch({ type: \"create\", payload: { resource, options } });\n\n // Returns function when complete.\n return () => {\n dispatch({ type: \"create\", payload: { resource: null } });\n };\n }, []);\n\n const actions: EditingStackActions = useMemo(() => {\n return { edit, updateCurrent, close, back, create, setStack };\n }, []);\n\n return [state, actions] as const;\n}\n\nexport function EditingStack(props: {\n children?: any;\n initialState?: EditingStackState;\n editing?: { id: string; type: string };\n}) {\n const { instanceId } = useAppInstance();\n const [state, actions] = useInternalEditingStackActions(props.initialState || defaultState);\n\n return (\n <EditingStackActionsContext.Provider value={actions} key={instanceId}>\n <EditingStackContext.Provider value={state}>{props.children}</EditingStackContext.Provider>\n </EditingStackActionsContext.Provider>\n );\n}\n\nexport function InlineEditingStack({\n resource,\n children,\n}: {\n resource: { id: string; type: string };\n children?: React.ReactNode;\n}) {\n const { instanceId } = useAppInstance();\n const initialState = useMemo(() => {\n return {\n create: null,\n stack: [],\n current: {\n resource: {\n type: \"SpecificResource\",\n source: {\n id: resource.id,\n type: resource.type,\n },\n },\n },\n } as EditingStackState;\n }, []);\n const [state, actions] = useInternalEditingStackActions(initialState);\n\n return (\n <EditingStackActionsContext.Provider value={actions} key={instanceId}>\n <EditingStackContext.Provider value={state}>{children}</EditingStackContext.Provider>\n </EditingStackActionsContext.Provider>\n );\n}\n","import type { Vault } from \"@iiif/helpers\";\nimport { SidebarTabs } from \"@manifest-editor/components\";\nimport { BackIcon } from \"@manifest-editor/ui/icons/BackIcon\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { type ReactNode, useContext, useEffect, useMemo } from \"react\";\nimport { ResourceReactContext, useVault } from \"react-iiif-vault\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { type EditorConfig, useConfig } from \"../ConfigContext/ConfigContext\";\nimport { useEditingResource, useEditingResourceStack, useEditingStack } from \"../EditingStack/EditingStack\";\nimport type { EditableResource } from \"../EditingStack/EditingStack.types\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport type { EditorDefinition, ResourceDefinition } from \"../Layout/Layout.types\";\nimport { ModulePanelButton, useSetCustomTitle } from \"../Layout/components/ModularPanel\";\n\nexport function BaseEditorBackButton({ fallback, backAction }: any) {\n const stack = useEditingResourceStack();\n const { back } = useEditingStack();\n\n if (stack.length) {\n return (\n <ModulePanelButton onClick={back}>\n <BackIcon />\n </ModulePanelButton>\n );\n }\n\n return fallback;\n}\n\nexport function BaseEditorCloseButton({ closeAction, fallback }: any) {\n const stack = useEditingResourceStack();\n const current = useEditingResource();\n\n if (current || stack.length) {\n return (\n <ModulePanelButton\n onClick={() => {\n closeAction();\n }}\n >\n <CloseIcon />\n </ModulePanelButton>\n );\n }\n\n return fallback;\n}\n\nexport function editBasedOnResource(\n resource: EditableResource,\n list: ResourceDefinition[],\n options: { edit?: boolean; vault: Vault },\n config: EditorConfig,\n): ResourceDefinition | null {\n const filteredList = list.filter((l) => l.resourceType === resource.resource.source.type);\n\n if (filteredList.length === 0) {\n return null;\n }\n\n for (const item of filteredList) {\n // Check for a match in order.\n const sortKeys: string[] = [];\n const sortKeyFallbacks: Record<string, EditorDefinition> = {};\n // 1. Filter out the\n const editors = (item.editors || []).filter((editor) => {\n if (config.hideTabs && config.hideTabs.includes(editor.id)) {\n return false;\n }\n if (config.onlyTabs && !config.onlyTabs.includes(editor.id)) {\n return false;\n }\n if (editor.supports.sortKey) {\n if (sortKeys.includes(editor.supports.sortKey)) {\n return false;\n }\n if (editor.supports.sortFallback) {\n sortKeyFallbacks[editor.supports.sortKey] = editor;\n }\n }\n\n // Does this editor support the input resource.\n if (options.edit && !editor.supports.edit) {\n return false;\n }\n\n if (editor.supports.custom ? editor.supports.custom(resource, options.vault) === false : false) {\n return false;\n }\n\n // @todo more logic here, including \"custom\" supports check.\n\n if (editor.supports.sortKey) {\n sortKeys.push(editor.supports.sortKey);\n }\n\n return true;\n });\n\n const missingKeys = Object.keys(sortKeyFallbacks);\n for (const missingKey of missingKeys) {\n if (\n !sortKeys.includes(missingKey) &&\n sortKeyFallbacks[missingKey] &&\n !editors.includes(sortKeyFallbacks[missingKey]!)\n ) {\n editors.push(sortKeyFallbacks[missingKey]!);\n }\n }\n\n if (editors.length) {\n return {\n ...item,\n editors,\n };\n }\n }\n\n return null;\n}\n\nexport function BaseEditor({ currentTab = undefined }: { currentTab?: string }) {\n const resource = useEditingResource();\n const currentResourceContext = useContext(ResourceReactContext);\n const app = useApp();\n const rootResource = useAppResource();\n const vault = useVault();\n const { change } = useLayoutActions();\n const set = useSetCustomTitle();\n const { editorConfig } = useConfig();\n const resourceId = resource?.resource.source?.id;\n let resourceType = resource?.resource.source?.type;\n // Could use this is for later.\n const isNested = resourceId !== rootResource.id;\n if (resourceId && isNested && rootResource.type === \"Collection\" && resourceType === \"Collection\") {\n resourceType = \"EmbeddedCollection\";\n }\n\n const resourceConfig: EditorConfig = (resourceType ? (editorConfig as any)[resourceType] : editorConfig.All) || {};\n\n const newResourceContext = useMemo(() => {\n const newCtx = { ...currentResourceContext };\n const id = resource?.resource.source.id;\n const type = resource?.resource.source.type;\n const mapping = {\n Collection: \"collection\",\n Manifest: \"manifest\",\n Range: \"range\",\n Canvas: \"canvas\",\n Annotation: \"annotation\",\n AnnotationPage: \"annotationPage\",\n };\n\n if (type && (mapping as any)[type]) {\n (newCtx as any)[(mapping as any)[type]] = id;\n }\n return newCtx;\n }, [resource, currentResourceContext]);\n\n function wrap(children: ReactNode) {\n if (!resource) {\n return children;\n }\n\n return <ResourceReactContext.Provider value={newResourceContext}>{children}</ResourceReactContext.Provider>;\n }\n\n const match = useMemo(() => {\n if (!resource) {\n return null;\n }\n\n const editors = app.layout.editors || [];\n const resources = app.layout.resources || [];\n const mappedResources: ResourceDefinition[] = resources.map((resource: string | ResourceDefinition) => {\n if (typeof resource === \"string\") {\n return {\n id: \"@default/\" + resource,\n label: resource,\n resourceType: resource,\n auto: true,\n editors: editors.filter((e: any) => e.supports.resourceTypes.includes(resource)),\n };\n }\n return resource;\n });\n\n return editBasedOnResource(resource, mappedResources, { edit: true, vault }, resourceConfig);\n }, [resource, app]);\n\n useEffect(() => {\n set(match?.label || \"\");\n }, [match]);\n\n useEffect(() => {\n const availableKeys = match?.editors.map((editor) => editor.id) || [];\n const currentKey = availableKeys.find((key) => key === currentTab);\n if (!currentKey) {\n change(\"@manifest-editor/editor\", { currentTab: availableKeys[0] });\n }\n }, [match?.editors, currentTab, change]);\n\n // Problems to solve:\n // - Subscribing to updates to the reference\n // - Keeping track of changes to the item, by checking it's index\n // - If the items change - ensure we have the same index by doing an equality check on the reference?\n\n if (!resource || !match) {\n return null;\n }\n\n if (resourceConfig.singleTab) {\n const first = (match?.editors || []).find((editor) => editor.id === resourceConfig.singleTab);\n if (first) {\n return wrap(\n <div key={resource.resource.source?.id} className=\"w-full\">\n {first.component(resourceConfig)}\n </div>,\n );\n }\n }\n\n return wrap(\n <SidebarTabs\n isNested={isNested}\n rootResource={rootResource}\n key={resource.resource.source?.id}\n menuId={resource.resource.source.id}\n menu={(match?.editors || []).map((editor, key) => {\n return {\n id: editor.id,\n label: editor.label,\n renderComponent: () => editor.component(resourceConfig),\n };\n })}\n selectedKey={currentTab}\n onSelectionChange={(p: any) => {\n change(\"@manifest-editor/editor\", { currentTab: p });\n }}\n />,\n );\n}\n","import type { LayoutPanel } from \"../Layout/Layout.types\";\nimport {\n BaseEditor,\n BaseEditorBackButton,\n BaseEditorCloseButton,\n} from \"./BaseEditor\";\n\nexport const baseEditor: LayoutPanel = {\n id: \"@manifest-editor/editor\",\n label: \"Editor\",\n options: { hideHeader: true, tabs: true, minWidth: 400 },\n renderBackAction: ({ backAction, fallback }) => (\n <BaseEditorBackButton backAction={backAction} fallback={fallback} />\n ),\n renderCloseAction: ({ closeAction, fallback }) => (\n <BaseEditorCloseButton closeAction={closeAction} fallback={fallback} />\n ),\n render({ currentTab }) {\n return <BaseEditor currentTab={currentTab} />;\n },\n};\n","import { useMemo, useRef, useState } from \"react\";\n\nexport function useDecayState(time: number) {\n const [active, _setActive] = useState(false);\n const lastTimeout = useRef<any>();\n const focusCount = useRef<any>(0);\n\n function clear(existing?: boolean) {\n focusCount.current--;\n\n if (existing && focusCount.current !== 0) {\n return;\n }\n\n if (lastTimeout.current) {\n clearTimeout(lastTimeout.current);\n lastTimeout.current = 0;\n }\n lastTimeout.current = setTimeout(() => {\n _setActive(false);\n }, time);\n }\n\n function set() {\n focusCount.current++;\n if (lastTimeout.current) {\n clearTimeout(lastTimeout.current);\n }\n _setActive(true);\n }\n\n return useMemo(() => [active, { set, clear }] as const, [active]);\n}\n","import { ActionButton, Form, Sidebar, SidebarContent, SidebarHeader } from \"@manifest-editor/components\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useDecayState } from \"../hooks/use-decay-state\";\nimport { usePreviewContext, usePreviews } from \"../PreviewContext/PreviewContext\";\nimport { type Config, useConfig, useSaveConfig } from \"./ConfigContext\";\n\nexport function ConfigEditor() {\n const previews = usePreviewContext();\n const resource = useAppResource();\n const config = useConfig();\n const setConfig = useSaveConfig();\n const [isSaved, saveState] = useDecayState(2000);\n\n function onSubmit(e: React.FormEvent) {\n e.preventDefault();\n const formValues = new FormData(e.target as HTMLFormElement);\n\n const newConfig: Partial<Config> = {\n defaultPreview: formValues.get(\"defaultPreview\") as string,\n i18n: {\n ...(config.i18n || ({} as any)),\n advancedLanguageMode: formValues.get(\"advancedLanguageMode\") === \"on\",\n availableLanguages: ((formValues.get(\"availableLanguages\") as string) || \"\")\n .split(\",\")\n .map((t: string) => t.trim()),\n defaultLanguage: formValues.get(\"defaultLanguage\") as string,\n },\n export: {\n ...(config.export || ({} as any)),\n version: formValues.get(\"isVersion2\") === \"on\" ? 2 : 3,\n baseIdentifier: (formValues.get(\"base\") as string) || null,\n },\n editorFeatureFlags: {\n ...(config.editorFeatureFlags || ({} as any)),\n rememberCanvasId: formValues.get(\"rememberCanvasId\") === \"on\",\n rememberLeftPanelId: formValues.get(\"rememberLeftPanelId\") === \"on\",\n annotationPopups: formValues.get(\"annotationPopups\") === \"on\",\n manifestGridOptions: formValues.get(\"manifestGridOptions\") === \"on\",\n enableMultiImageCanvases: formValues.get(\"enableMultiImageCanvases\") === \"on\",\n enableMultiMediaCanvases: formValues.get(\"enableMultiMediaCanvases\") === \"on\",\n },\n };\n\n setConfig(newConfig);\n saveState.set();\n saveState.clear();\n }\n\n return (\n <Sidebar>\n <SidebarHeader title=\"Workspace configuration\" />\n {isSaved ? <div className=\"bg-me-primary-500 text-white p-3 text-sm\">Changes saved</div> : null}\n <SidebarContent className=\"p-4\">\n <Form.Form onSubmit={onSubmit} className=\"flex flex-col gap-3\">\n <Form.InputContainer>\n <Form.Label htmlFor=\"defaultLanguage\">Default Language</Form.Label>\n <Form.Input\n type=\"text\"\n name=\"defaultLanguage\"\n id=\"defaultLanguage\"\n defaultValue={config.i18n?.defaultLanguage || \"\"}\n />\n </Form.InputContainer>\n\n <Form.InputContainer>\n <Form.Label htmlFor=\"availableLanguages\">Available Languages</Form.Label>\n <Form.Input\n type=\"text\"\n name=\"availableLanguages\"\n id=\"availableLanguages\"\n defaultValue={(config.i18n?.availableLanguages || []).join(\", \")}\n />\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"advancedLanguageMode\"\n id=\"advancedLanguageMode\"\n defaultChecked={config.i18n?.advancedLanguageMode || false}\n />\n <Form.Label htmlFor=\"advancedLanguageMode\">Advanced Language Mode</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"textGranularityEnabled\"\n id=\"textGranularityEnabled\"\n defaultChecked={config.i18n?.textGranularityEnabled || false}\n />\n <Form.Label htmlFor=\"textGranularityEnabled\">Enable text granularity</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"rememberCanvasId\"\n id=\"rememberCanvasId\"\n defaultChecked={config.editorFeatureFlags?.rememberCanvasId || false}\n />\n <Form.Label htmlFor=\"rememberCanvasId\">Remember Canvas ID</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"rememberLeftPanelId\"\n id=\"rememberLeftPanelId\"\n defaultChecked={config.editorFeatureFlags?.rememberLeftPanelId || false}\n />\n <Form.Label htmlFor=\"rememberLeftPanelId\">Remember Left panel</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"manifestGridOptions\"\n id=\"manifestGridOptions\"\n defaultChecked={config.editorFeatureFlags?.manifestGridOptions || false}\n />\n <Form.Label htmlFor=\"manifestGridOptions\">Manifest Grid Options</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"isVersion2\"\n id=\"isVersion2\"\n defaultChecked={config.export?.version === 2}\n />\n <Form.Label htmlFor=\"isVersion2\">Export Presentation 2 {resource.type}s</Form.Label>\n </Form.InputContainer>\n\n {/* <Form.InputContainer>\n <Form.Label htmlFor=\"base\">Base Identifier</Form.Label>\n <Form.Input\n type=\"text\"\n name=\"base\"\n id=\"base\"\n autoComplete=\"none\"\n defaultValue={config.export?.baseIdentifier || \"\"}\n />\n </Form.InputContainer> */}\n\n <Form.InputContainer>\n <Form.Label htmlFor=\"defaultPreview\">Default preview</Form.Label>\n <div>\n {previews.configs.map((preview, key) => {\n if (preview.type === \"iiif-preview-service\") {\n return null;\n }\n return (\n <Form.InputContainer key={preview.id} horizontal>\n <Form.Input\n type=\"radio\"\n id={preview.id}\n name=\"defaultPreview\"\n value={preview.id}\n defaultChecked={!config.defaultPreview ? key === 0 : config.defaultPreview === preview.id}\n />\n <label htmlFor={preview.id}>{preview.label}</label>\n </Form.InputContainer>\n );\n })}\n </div>\n </Form.InputContainer>\n {resource.type === \"Manifest\" ? (\n <a\n className=\"text-sm text-me-primary-500 hover:underline hover:text-me-primary-600\"\n href={\n window.location.pathname.includes(\"/exhibition\")\n ? window.location.pathname.replace(\"/exhibition\", \"\") || \"/\"\n : `${window.location.pathname}/exhibition`\n }\n >\n {window.location.pathname.includes(\"/exhibition\")\n ? \"Return to Manifest Editor\"\n : \"Go to Exhibition Editor\"}\n </a>\n ) : null}\n\n <div className=\"mt-5\">\n <ActionButton type=\"submit\">{\"Save changes\"}</ActionButton>\n </div>\n </Form.Form>\n </SidebarContent>\n </Sidebar>\n );\n}\n","import { createContext, useContext, useEffect, useMemo } from \"react\";\nimport { createStore, type StoreApi, useStore } from \"zustand\";\nimport { randomId } from \"../helpers\";\n\nexport type ContextMenuItem = {\n id: string;\n label: string;\n onAction: (options: { position: { x: number; y: number }; resource: { id: string; type: string } }) => void;\n disabled?: boolean;\n enabled?: boolean;\n enabledFunction?: (options: { resource: { id: string; type: string } }) => boolean;\n order?: number;\n};\n\nexport type ContextMenuRequest = {\n resource?: { id?: string; type: string };\n sectionTitle?: string;\n items: Array<ContextMenuItem>;\n};\n\ntype ContextMenuStore = {\n specificMenus: Record<\n string,\n {\n menus: Record<\n string,\n | {\n sectionTitle?: string;\n items: Array<ContextMenuItem>;\n }\n | undefined\n >;\n }\n >;\n\n resourceMenus: Record<\n string,\n {\n menus: Record<\n string,\n | {\n sectionTitle?: string;\n items: Array<ContextMenuItem>;\n }\n | undefined\n >;\n }\n >;\n\n hookMenuItem(req: ContextMenuRequest): () => void;\n};\n\nfunction createContextMenuStore() {\n return createStore<ContextMenuStore>((set, get) => ({\n specificMenus: {},\n resourceMenus: {},\n hookMenuItem(req: ContextMenuRequest) {\n const requestId = randomId();\n const resourceId = req.resource?.id || \"\";\n const resourceType = req.resource?.type;\n if (!resourceType) return () => {};\n\n if (resourceId) {\n set((prev) => {\n return {\n specificMenus: {\n ...prev.specificMenus,\n [resourceId]: {\n ...(prev.specificMenus[resourceId] || {}),\n menus: {\n ...(prev.specificMenus[resourceId]?.menus || {}),\n [requestId]: {\n sectionTitle: req.sectionTitle,\n items: req.items,\n },\n },\n },\n },\n };\n });\n\n return () => {\n set((prev) => {\n return {\n specificMenus: {\n ...prev.specificMenus,\n [resourceId]: {\n ...(prev.specificMenus[resourceId] || {}),\n menus: {\n ...(prev.specificMenus[resourceId]?.menus || {}),\n [requestId]: undefined,\n },\n },\n },\n };\n });\n };\n }\n set((prev) => {\n return {\n resourceMenus: {\n ...prev.resourceMenus,\n [resourceType]: {\n ...(prev.resourceMenus[resourceType] || {}),\n menus: {\n ...(prev.resourceMenus[resourceType]?.menus || {}),\n [requestId]: {\n sectionTitle: req.sectionTitle,\n items: req.items,\n },\n },\n },\n },\n };\n });\n\n return () => {\n set((prev) => {\n return {\n resourceMenus: {\n ...prev.resourceMenus,\n [resourceType]: {\n ...(prev.resourceMenus[resourceType] || {}),\n menus: {\n ...(prev.resourceMenus[resourceType]?.menus || {}),\n [requestId]: undefined,\n },\n },\n },\n };\n });\n };\n },\n }));\n}\n\nexport const ContextMenuReactContext = createContext<StoreApi<ContextMenuStore> | null>(null);\n\nexport function ContextMenuProvider({ children }: { children: React.ReactNode }) {\n const store = useMemo(() => {\n return createContextMenuStore();\n }, []);\n\n return <ContextMenuReactContext.Provider value={store}>{children}</ContextMenuReactContext.Provider>;\n}\n\nfunction useContextMenuStore() {\n const ctx = useContext(ContextMenuReactContext);\n if (!ctx) {\n throw new Error(\"useContextMenuStore must be used within a ContextMenuProvider\");\n }\n return ctx;\n}\n\nexport function useResourceContextMenuItems(req: { id?: string; type: string }) {\n const store = useContextMenuStore();\n const resourceMenus = useStore(store, (s) => s.resourceMenus);\n const specificMenus = useStore(store, (s) => s.specificMenus);\n\n return useMemo(() => {\n const specificRequests = specificMenus[req.id || \"\"]?.menus || {};\n const resourceRequests = resourceMenus[req.type]?.menus || {};\n\n const specificItems = Object.values(specificRequests).flat();\n const resourceItems = Object.values(resourceRequests).flat();\n\n const items = [...resourceItems, ...specificItems].filter((t) => typeof t !== \"undefined\");\n const seenIds: string[] = [];\n const returnSections = [];\n\n for (const section of items) {\n const sectionItems = [];\n for (const sectionItem of section.items || []) {\n if (sectionItem.id && seenIds.includes(sectionItem.id)) continue;\n seenIds.push(sectionItem.id);\n sectionItems.push(sectionItem);\n }\n if (sectionItems.length) {\n returnSections.push({\n ...section,\n items: sectionItems,\n });\n }\n }\n\n return mergeSectionsWithTheSameTitle(returnSections);\n }, [specificMenus, resourceMenus, req.id, req.type]);\n}\n\nfunction mergeSectionsWithTheSameTitle(sections: Array<{ sectionTitle?: string; items: Array<ContextMenuItem> }>) {\n const sectionMap: Record<string, ContextMenuItem[]> = {};\n const emptySections: ContextMenuItem[] = [];\n\n sections.forEach((section) => {\n if (!section) return;\n const title = section.sectionTitle;\n if (!title) {\n emptySections.push(...(section.items || []));\n return;\n }\n if (!sectionMap[title]) {\n sectionMap[title] = [];\n }\n sectionMap[title].push(...section.items);\n });\n\n const returnSections: Array<{ sectionTitle?: string; items: Array<ContextMenuItem> }> = Object.entries(\n sectionMap,\n ).map(([title, items]) => ({\n sectionTitle: title,\n items,\n }));\n\n if (emptySections.length) {\n returnSections.push({ items: emptySections });\n }\n\n return returnSections;\n}\n\nexport function useCustomContextMenu(req: ContextMenuRequest, deps: any[] = []) {\n const store = useContextMenuStore();\n const hookMenuItem = useStore(store, (s) => s.hookMenuItem);\n\n useEffect(() => {\n return hookMenuItem(req);\n }, [hookMenuItem, req.resource?.id, req.resource?.type, ...deps]);\n}\n",".CenterPanelContainer {\n display: flex;\n flex-direction: column;\n flex: 1;\n overflow: hidden;\n background: #fff;\n margin: 1.2rem;\n padding: 1em;\n border-radius: 10px;\n box-shadow:\n 0 4px 15px 0 rgba(0, 0, 0, 0.18),\n 0 0px 0px 1px rgba(0, 0, 0, 0.15),\n inset 0 0 0 1px rgba(255, 255, 255, 0.2);\n}\n\n.CenterPanelHeader {\n height: 3em;\n display: flex;\n align-items: center;\n margin-bottom: 1em;\n}\n\n.CenterPanelClose {\n margin-left: auto;\n align-self: center;\n}\n\n.CenterPanelTitle {\n margin: 0;\n}\n","import { ReactNode } from \"react\";\nimport $ from \"./CenterPanelContainer.module.css\";\nimport { Button } from \"../../atoms/Button\";\nimport { CloseIcon } from \"../../icons/CloseIcon\";\n\ninterface CenterPanelContainerProps {\n close?: () => void;\n title?: string;\n children: ReactNode;\n}\n\nexport function CenterPanelContainer(props: CenterPanelContainerProps) {\n return (\n <div className={$.CenterPanelContainer}>\n {props.title || props.close ? (\n <div className={$.CenterPanelHeader}>\n {props.title ? <h2 className={$.CenterPanelTitle}>{props.title}</h2> : null}\n {props.close ? (\n <Button className={$.CenterPanelClose} onClick={props.close}>\n <CloseIcon />\n </Button>\n ) : null}\n </div>\n ) : null}\n {props.children}\n </div>\n );\n}\n","import styled from \"styled-components\";\nimport {\n createRef,\n forwardRef,\n KeyboardEventHandler,\n ReactNode,\n RefObject,\n UIEventHandler,\n useEffect,\n useImperativeHandle,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { DownIcon } from \"../icons/DownIcon\";\n\nexport const AccordionContainer = styled.div`\n flex: 1;\n display: flex;\n width: 100%;\n flex-direction: column;\n position: relative;\n`;\n\nconst ItemRow = styled.div`\n background: #fff;\n position: relative;\n border-bottom: 1px solid #d0d0d0;\n border-top: 1px solid #d0d0d0;\n\n & ~ & {\n border-top: none;\n }\n\n &[data-large=\"true\"] {\n background: #f7f7f7;\n border: none;\n margin-bottom: 1em;\n //display: flex;\n //flex-direction: column;\n //justify-content: center;\n }\n`;\n\nconst ItemDescription = styled.p`\n font-size: 0.9em;\n color: #777;\n font-weight: 400;\n`;\n\nconst ItemLabel = styled.button`\n color: inherit;\n text-rendering: geometricPrecision;\n border: none;\n text-align: left;\n background: transparent;\n font: inherit;\n text-transform: uppercase;\n padding: 0.6em 1.2em;\n flex: 1;\n font-size: 0.8em;\n font-weight: 600;\n white-space: nowrap;\n text-overflow: ellipsis;\n min-width: 0;\n overflow: hidden;\n\n &:focus {\n outline: none;\n }\n\n p {\n display: none;\n }\n\n [data-large=\"true\"] & {\n //padding: 1.5em;\n padding: 0.85em 1.25em;\n display: block;\n text-transform: initial;\n font-size: 1em;\n margin-bottom: 0;\n color: #000;\n\n p {\n display: block;\n color: #999;\n font-size: 0.9em;\n margin: 0;\n margin-top: 0.5em;\n }\n }\n`;\n\nconst ItemCollapse = styled.div`\n font-size: 1.4em;\n padding-right: 0.3em;\n display: flex;\n align-items: center;\n\n [data-large=\"true\"] & {\n font-size: 2em;\n }\n`;\n\nconst ItemIcon = styled.div`\n width: 2em;\n align-items: center;\n //padding-top: 0.5em;\n display: flex;\n justify-content: center;\n margin-left: 1.5em;\n svg {\n width: 1.75em;\n height: 1.75em;\n fill: #999;\n color: #999;\n }\n`;\n\nconst ItemBodyInner = styled.div<{ $full?: boolean }>`\n min-height: 0;\n overflow: visible;\n display: flex;\n`;\n\nconst ItemBodyPadding = styled.div<{ $full?: boolean; $max?: boolean }>`\n min-height: 0;\n overflow: visible;\n flex: 1;\n padding: 1em 1em 1.5em;\n\n &[data-full=\"true\"] {\n margin: 0;\n }\n\n &[data-max-height=\"true\"] {\n overflow-y: auto;\n }\n`;\n\nconst ItemBody = styled.section<{\n $initial?: boolean;\n $scrolled?: boolean;\n}>`\n display: grid;\n grid-template-rows: 0fr;\n overflow: hidden;\n opacity: 0;\n visibility: hidden;\n\n [data-open=\"true\"] & {\n opacity: 1;\n grid-template-rows: 1fr;\n visibility: visible;\n &[data-overflow=\"true\"] {\n overflow: visible;\n }\n }\n\n transition:\n all 0.4s,\n visibility 0.8s;\n\n &[data-has-icon=\"true\"] {\n padding-left: 4em;\n }\n\n box-shadow: inset 0px 2px 0px 0 rgba(0, 0, 0, 0);\n &[data-scrolled=\"true\"] {\n box-shadow: inset 0px 2px 0px 0 rgba(0, 0, 0, 0.1);\n }\n`;\n\nconst ItemHeading = styled.div<{ $open?: boolean }>`\n position: sticky;\n display: flex;\n top: 0;\n background: #fff;\n min-width: 0;\n width: 100%;\n color: #757575;\n z-index: 1;\n &:hover {\n color: #333;\n }\n\n [data-large=\"true\"] & {\n border: 1px solid #d0d0d0;\n &:after {\n display: none;\n }\n }\n\n [data-large=\"true\"]:focus-within & {\n border-color: #3579f6;\n }\n\n [data-open=\"true\"] & {\n color: #333;\n &:after {\n content: \"\";\n height: 1px;\n background: #eee;\n position: absolute;\n top: 100%;\n left: 0.5em;\n right: 0.5em;\n }\n }\n`;\n\ninterface AccordionItemProps {\n label: string | ReactNode;\n description?: string | ReactNode;\n icon?: ReactNode;\n children: ReactNode;\n initialOpen?: boolean;\n maxHeight?: number | false;\n fullWidth?: boolean;\n overflow?: boolean;\n onChange?: (value: boolean) => void;\n large?: boolean;\n}\n\nexport interface AccordionItemRef {\n open(): void;\n close(): void;\n toggle(): void;\n focus(): void;\n button?: RefObject<HTMLButtonElement>;\n}\n\nconst noop = (() => void 0) as any;\n\nlet keyIdIndex = 0;\nfunction useId() {\n return useMemo(() => keyIdIndex++, []);\n}\n\nexport function useAccordionItems(itemsLength: number, singleMode = false) {\n const [elRefs, setElRefs] = useState<RefObject<AccordionItemRef>[]>([]);\n const current = useRef(-1);\n\n const onKeyDown: KeyboardEventHandler<HTMLDivElement> = (e) => {\n const currentEl = document.activeElement;\n const currentIndex = elRefs.findIndex((r) => r.current?.button?.current === currentEl);\n if (currentIndex === -1) {\n return;\n }\n\n switch (e.code) {\n case \"Home\": {\n const next = 0;\n if (elRefs[next]) {\n elRefs[next].current?.focus();\n }\n break;\n }\n case \"End\": {\n const next = itemsLength - 1;\n if (elRefs[next]) {\n elRefs[next]!.current?.focus();\n }\n break;\n }\n\n case \"ArrowDown\": {\n if (currentIndex !== itemsLength - 1) {\n const next = currentIndex + 1;\n if (elRefs[next]) {\n elRefs[next]!.current?.focus();\n }\n }\n break;\n }\n // Focus previous\n case \"ArrowUp\": {\n if (currentIndex !== 0) {\n const next = currentIndex - 1;\n if (elRefs[next]) {\n elRefs[next]!.current?.focus();\n }\n }\n break;\n }\n // Focus next\n case \"ArrowLeft\": {\n // Close current\n const el = elRefs[currentIndex];\n if (el && el.current) {\n el.current.close();\n }\n break;\n }\n // Open current\n case \"ArrowRight\": {\n // Close current\n const el = elRefs[currentIndex];\n if (el && el.current) {\n el.current.open();\n }\n break;\n }\n }\n };\n\n const onChange = (key: number, isOpen: boolean) => {\n if (singleMode && isOpen && key !== current.current) {\n current.current = key;\n for (let i = 0; i < elRefs.length; i++) {\n const ref = elRefs[i];\n if (i === key) {\n continue;\n }\n ref!.current?.close();\n }\n }\n };\n\n useEffect(() => {\n // add or remove refs\n setElRefs((elRefs_) =>\n Array(itemsLength)\n .fill(0)\n .map((_, i) => elRefs_[i] || createRef())\n );\n }, [itemsLength]);\n\n const getItemProps = (key: number) => {\n return {\n ref: elRefs[key],\n onChange: (isOpen: boolean) => onChange(key, isOpen),\n };\n };\n\n const open = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.open();\n }\n };\n\n const close = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.close();\n }\n };\n\n const toggle = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.toggle();\n }\n };\n\n const focus = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.focus();\n }\n };\n\n const openAll = () => {\n for (let i = 0; i < elRefs.length; i++) {\n const ref = elRefs[i]!;\n ref.current?.open();\n }\n };\n\n const closeAll = () => {\n for (let i = 0; i < elRefs.length; i++) {\n const ref = elRefs[i]!;\n ref.current?.close();\n }\n };\n\n return {\n open,\n close,\n toggle,\n focus,\n openAll,\n closeAll,\n onKeyDown,\n getItemProps,\n };\n}\n\nexport const AccordionItem = forwardRef<AccordionItemRef, AccordionItemProps>(function AccordionItem(props, ref) {\n const content = useRef<HTMLDivElement>(null);\n const btn = useRef<HTMLButtonElement>(null);\n const id = useId();\n\n const [open, setIsOpen] = useState<boolean>(props.initialOpen || false);\n const onChange = props.onChange || noop;\n const toggle = () => {\n onChange(!open);\n setIsOpen((o) => !o);\n };\n const maxHeight = props.maxHeight;\n const [scrolled, setScrolled] = useState(false);\n\n useImperativeHandle(ref, () => ({\n open() {\n onChange(true);\n setIsOpen(true);\n },\n close() {\n onChange(false);\n setIsOpen(false);\n },\n toggle() {\n toggle();\n },\n focus() {\n if (btn.current) {\n btn.current.focus();\n }\n },\n button: btn,\n }));\n\n const onScroll: UIEventHandler<HTMLDivElement> = (e) => {\n if ((e.target as HTMLDivElement).scrollTop > 0) {\n setScrolled(true);\n } else {\n setScrolled(false);\n }\n };\n\n return (\n <ItemRow data-large={props.large} data-open={open}>\n <ItemHeading data-open={open}>\n {props.icon ? <ItemIcon onClick={toggle}>{props.icon}</ItemIcon> : null}\n <ItemLabel ref={btn} onClick={toggle} aria-expanded={open} aria-controls={`accordion-${id}`}>\n {props.label}\n {props.description ? <ItemDescription>{props.description}</ItemDescription> : null}\n </ItemLabel>\n <ItemCollapse onClick={toggle}>\n <DownIcon width=\"1em\" height=\"1em\" rotate={open ? 0 : 180} />\n </ItemCollapse>\n </ItemHeading>\n <ItemBody\n aria-labelledby={`accordion-${id}`}\n aria-hidden={!open}\n data-overflow={!!props.overflow}\n data-has-icon={!!props.icon}\n onScroll={onScroll}\n ref={content}\n $initial={!open}\n data-scrolled={scrolled}\n hidden={!open}\n >\n <ItemBodyInner>\n <ItemBodyPadding\n data-max-height={!!maxHeight}\n data-full={props.fullWidth}\n style={{ maxHeight: maxHeight || undefined }}\n >\n {props.children}\n </ItemBodyPadding>\n </ItemBodyInner>\n </ItemBody>\n </ItemRow>\n );\n});\n\ninterface AccordionProps {\n singleMode?: boolean;\n items: Array<AccordionItemProps>;\n maxHeight?: number | false;\n overflow?: boolean;\n}\n\nexport function Accordion(props: AccordionProps) {\n const { getItemProps, onKeyDown } = useAccordionItems(props.items.length, props.singleMode);\n\n return (\n <AccordionContainer onKeyDown={onKeyDown}>\n {props.items.map((item, key) => (\n <AccordionItem overflow={props.overflow} maxHeight={props.maxHeight} key={key} {...item} {...getItemProps(key)}>\n {item.children}\n </AccordionItem>\n ))}\n </AccordionContainer>\n );\n}\n","export function DownloadIcon() {\n return (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"48\" viewBox=\"0 -960 960 960\" width=\"48\">\n <path d=\"M220-160q-24 0-42-18t-18-42v-143h60v143h520v-143h60v143q0 24-18 42t-42 18H220Zm260-153L287-506l43-43 120 120v-371h60v371l120-120 43 43-193 193Z\" />\n </svg>\n );\n}\n","import styled from \"styled-components\";\n\nexport const ButtonRow = styled.div`\n padding: 0.3em;\n\n display: flex;\n background: #e4e7ef;\n border-radius: 3px;\n margin: 0.3em 0;\n gap: 0.3em;\n\n button,\n a {\n //\n\n & ~ & {\n margin-left: 0.3em;\n }\n }\n\n &[data-sticky=\"true\"] {\n position: sticky;\n bottom: 0;\n }\n`;\n","import { Button } from \"@manifest-editor/ui/atoms/Button\";\nimport { useMemo } from \"react\";\nimport { useManifest, useVault } from \"react-iiif-vault\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { CenterPanelContainer } from \"@manifest-editor/ui/CenterPanelContainer\";\nimport { Accordion } from \"@manifest-editor/ui/atoms/Accordion\";\nimport { copyToClipboard, createDownload } from \"../helpers\";\nimport { DownloadIcon } from \"@manifest-editor/ui/icons/DownloadIcon\";\nimport { ButtonRow } from \"@manifest-editor/ui/atoms/ButtonRow\";\n\nexport interface ExportPanelProps {\n // We could limit versions / download options etc.\n initialVersion?: 2 | 3;\n versions?: Array<2 | 3>;\n}\n\nexport function ExportPanel(props: ExportPanelProps) {\n const manifest = useManifest();\n const vault = useVault();\n const actions = useLayoutActions();\n\n const version3 = useMemo(() => {\n return JSON.stringify(vault.toPresentation3(manifest as any), null, 2);\n }, [manifest, vault]);\n\n const version2 = useMemo(() => {\n return JSON.stringify(vault.toPresentation2(manifest as any), null, 2);\n }, [manifest, vault]);\n\n return (\n <CenterPanelContainer title=\"Export manifest\" close={actions.centerPanel.popStack}>\n <div style={{ flex: 1, overflowY: \"auto\" }}>\n <Accordion\n items={[\n {\n label: \"Presentation 3\",\n description: 'Download this version by clicking the \"Download\" button.',\n maxHeight: 400,\n large: true,\n initialOpen: true,\n overflow: true,\n icon: (\n <Button onClick={() => createDownload(version3, \"manifest.json\")}>\n <DownloadIcon />\n </Button>\n ),\n children: (\n <div style={{ maxWidth: \"100%\" }}>\n <pre style={{ whiteSpace: \"pre-wrap\" }}>\n {JSON.stringify(vault.toPresentation3(manifest as any), null, 2)}\n </pre>\n <ButtonRow data-sticky=\"true\">\n <Button onClick={() => copyToClipboard(version3)}>Copy to clipboard</Button>\n <Button onClick={() => createDownload(version3, \"manifest.json\")}>Download</Button>\n </ButtonRow>\n </div>\n ),\n },\n {\n label: \"Presentation 2\",\n description: 'Download this version by clicking the \"Download\" button.',\n maxHeight: 400,\n large: true,\n icon: (\n <Button onClick={() => createDownload(version2, \"manifest.json\")}>\n <DownloadIcon />\n </Button>\n ),\n children: (\n <div style={{ maxWidth: \"100%\" }}>\n <pre style={{ whiteSpace: \"pre-wrap\" }}>\n {JSON.stringify(vault.toPresentation2(manifest as any), null, 2)}\n </pre>\n <ButtonRow data-sticky=\"true\">\n <Button onClick={() => copyToClipboard(version2)}>Copy to clipboard</Button>\n <Button onClick={() => createDownload(version2, \"manifest.json\")}>Download</Button>\n </ButtonRow>\n </div>\n ),\n },\n ]}\n />\n </div>\n </CenterPanelContainer>\n );\n}\n","import { useCallback, useState } from \"react\";\nimport { useCurrentAnnotationMetadata } from \"react-iiif-vault\";\n\nexport function useAnnotationCreatorState<Type = any>({ key, initialValue, requestId, getInitialValue }: {\n key: string,\n initialValue?: Type,\n requestId?: string;\n getInitialValue?: (metadata: any) => (Type | null)\n}) {\n const [metadata, setMetadata] = useCurrentAnnotationMetadata({ requestId });\n const [reactState, reactSetState] = useState<Type>(getInitialValue && getInitialValue(metadata) || (metadata[key] || initialValue));\n\n const setState = useCallback((newValue: Type) => {\n setMetadata({ [key]: newValue });\n reactSetState(newValue);\n }, []);\n\n return [\n reactState,\n setState,\n ] as const;\n}\n","import type { Emitter } from \"mitt\";\nimport mitt from \"mitt\";\nimport { createContext, useContext, useEffect } from \"react\";\n\nconst events = mitt();\n\nexport const ReactEmitterContext = createContext<Emitter<any>>(events);\n\nexport function EventEmitterProvider({\n children,\n emitter,\n}: { children: React.ReactNode; emitter: Emitter<any> }) {\n return (\n <ReactEmitterContext.Provider value={emitter}>\n {children}\n </ReactEmitterContext.Provider>\n );\n}\n\nexport function useEmitter<\n Event extends Record<string | symbol, unknown>,\n>(): Emitter<Event> {\n return useContext(ReactEmitterContext);\n}\n\nexport function useEvent<\n Event extends Record<string | symbol, unknown>,\n Key extends keyof Event,\n>(key: Key, listener: (data: Event[Key]) => void, deps: any[] = []) {\n const emitter = useContext(ReactEmitterContext);\n useEffect(() => {\n const handler = (data: Event[Key]) => {\n listener(data);\n };\n emitter.on(key as any, handler);\n return () => {\n emitter.off(key as any, handler);\n };\n }, [emitter, key, ...deps]);\n}\n","// MIT License\n//\n// Copyright (c) 2020 Jepser Bernardino\n//\n// Permission is hereby granted, free of charge, to any person obtaining a copy\n// of this software and associated documentation files (the \"Software\"), to deal\n// in the Software without restriction, including without limitation the rights\n// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n// copies of the Software, and to permit persons to whom the Software is\n// furnished to do so, subject to the following conditions:\n//\n// The above copyright notice and this permission notice shall be included in all\n// copies or substantial portions of the Software.\n//\n// THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n// SOFTWARE.\n//\n// Source: https://github.com/jepser/use-match-media\n\nimport { useState, useLayoutEffect } from \"react\";\n\ntype IMediaQuery = Array<string>;\n\ntype IMatchedMedia = Array<boolean>;\n\nexport function useMatchMedia(queries: IMediaQuery, defaultValues: IMatchedMedia = []): IMatchedMedia {\n const initialValues = defaultValues.length ? defaultValues : Array(queries.length).fill(false);\n\n if (typeof window === \"undefined\") return initialValues;\n\n const mediaQueryLists = queries.map((q) => window.matchMedia(q));\n const getValue = (): IMatchedMedia => {\n // Return the value for the given queries\n const matchedQueries = mediaQueryLists.map((mql) => mql.matches);\n\n return matchedQueries;\n };\n\n // State and setter for matched value\n const [value, setValue] = useState(getValue);\n\n useLayoutEffect(() => {\n // Event listener callback\n // Note: By defining getValue outside of useEffect we ensure that it has ...\n // ... current values of hook args (as this hook only runs on mount/dismount).\n const handler = (): void => setValue(getValue);\n // Set a listener for each media query with above handler as callback.\n mediaQueryLists.forEach((mql) => mql.addListener(handler));\n // Remove listeners on cleanup\n return (): void => mediaQueryLists.forEach((mql) => mql.removeListener(handler));\n }, []);\n\n return value;\n}\n","import { Vault } from \"@iiif/helpers\";\nimport { useEffect } from \"react\";\nimport { useDebounce } from \"tiny-use-debounce\";\n\nexport function useSaveVault(vault: Vault, saveChanges: () => void, saveInterval: number, enabled = true) {\n const debounceSaveChanges = useDebounce(saveChanges, saveInterval);\n\n useEffect(() => {\n if (typeof window === \"undefined\") {\n return () => void 0;\n }\n window.addEventListener(\"beforeunload\", saveChanges, false);\n\n return () => {\n saveChanges();\n window.removeEventListener(\"beforeunload\", saveChanges);\n };\n }, [saveChanges]);\n\n useEffect(() => {\n if (vault && enabled) {\n return vault.subscribe(debounceSaveChanges, true);\n }\n }, [debounceSaveChanges, vault, enabled]);\n}\n","import { useMemo } from \"react\";\nimport { useAtlasStore } from \"react-iiif-vault\";\nimport { useStore } from \"zustand\";\n\nexport function useSvgTools() {\n const store = useAtlasStore();\n const switchTool = useStore(store, (s) => s.switchTool);\n const currentTool = useStore(store, (s) => s.polygonState.currentTool);\n const selectedStamp = useStore(store, (s) => s.polygonState.selectedStamp);\n const showBoundingBox = useStore(store, (s) => s.polygonState.showBoundingBox);\n\n return useMemo(\n () => ({\n currentTool,\n selectedStamp,\n // Draw tool.\n draw: {\n active: currentTool === \"pencil\",\n enable: switchTool.draw,\n },\n\n // Polygon.\n polygon: {\n active: currentTool === \"pen\",\n enable: switchTool.pen,\n },\n\n // Line\n line: {\n active: currentTool === \"line\",\n enable: switchTool.line,\n },\n\n // Line box.\n lineBox: {\n active: currentTool === \"lineBox\",\n enable: switchTool.lineBox,\n },\n\n // Square.\n square: {\n active: currentTool === \"box\",\n enable: switchTool.box,\n },\n\n // Triangle.\n triangle: {\n active: selectedStamp?.id === \"triangle\",\n enable: switchTool.triangle,\n },\n\n // Hexagon.\n hexagon: {\n active: selectedStamp?.id === \"hexagon\",\n enable: switchTool.hexagon,\n },\n\n // Circle\n circle: {\n active: selectedStamp?.id === \"circle\",\n enable: switchTool.circle,\n },\n\n // Delete\n remove: {\n active: showBoundingBox,\n enable: switchTool.remove,\n },\n }),\n [showBoundingBox, selectedStamp, currentTool, switchTool],\n );\n}\n","import { useState } from \"react\";\nimport {\n DefaultTooltipContent,\n IconHandle,\n ResetIcon,\n ResizeHandle,\n Tooltip,\n TooltipTrigger,\n} from \"@manifest-editor/components\";\nimport { ButtonReset } from \"@manifest-editor/ui/atoms/Button\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { DownIcon } from \"@manifest-editor/ui/icons/DownIcon\";\nimport { forwardRef } from \"react\";\nimport type { TransitionStatus } from \"react-transition-group\";\nimport styled, { css } from \"styled-components\";\nimport type { PanelActions } from \"../Layout.types\";\n\nexport const HandleContainer = styled.div`\n position: relative;\n width: 1px;\n background: rgba(0, 0, 0, 0.2);\n z-index: 50;\n`;\n\nconst HandleControl = styled(ButtonReset)`\n transition:\n opacity 300ms,\n transform 300ms;\n margin-block-start: 0.2em;\n margin-block-end: 0.2em;\n user-select: none;\n opacity: 0;\n transform: scaleY(70%);\n &:focus {\n outline: 2px solid salmon;\n }\n`;\n\nconst IconControl = styled(HandleControl)`\n background: #fff;\n width: 30px;\n height: 30px;\n border-radius: 50%;\n display: flex;\n justify-content: center;\n align-items: center;\n box-shadow: 0 2px 4px 0 rgba(0, 0, 0, 0.2);\n cursor: default;\n\n svg {\n fill: #9999;\n }\n`;\n\nconst OpenControl = styled(HandleControl)<{ $dir: \"left\" | \"right\" }>`\n position: relative;\n display: flex;\n opacity: 1;\n background: #fff;\n height: 55px;\n pointer-events: visible;\n width: 21px;\n margin-bottom: auto;\n margin-top: 4.5em;\n cursor: pointer;\n border-radius: ${(props) => (props.$dir === \"right\" ? \"5px 0 0 5px\" : \"0 5px 5px 0\")};\n\n align-items: center;\n justify-content: center;\n box-shadow: 0 2px 3px 0 rgba(0, 0, 0, 0.2);\n transform: scaleX(100%);\n transform-origin: ${(props) => (props.$dir === \"right\" ? \"right\" : \"left\")};\n\n &:hover {\n background: #f9f9f9;\n transform: scaleX(125%);\n }\n\n svg {\n font-size: 1.5em;\n }\n`;\n\nconst InnerHandleContainer = styled.div<{ $open: boolean; $dir: \"left\" | \"right\" }>`\n background: rgba(0, 0, 0, 0);\n position: absolute;\n width: 16px;\n left: ${(props) => (props.$dir === \"left\" ? 0 : \"1px\")};\n top: 0;\n bottom: 0;\n z-index: 50; // This will always be quite high.\n transition:\n background-color 300ms,\n transform 300ms;\n transform: scaleX(70%);\n\n cursor: ${(props) => (props.$open ? \"col-resize\" : \"pointer\")};\n\n display: flex;\n flex-direction: column;\n align-items: center;\n justify-content: center;\n\n &:hover {\n transform: scaleX(100%);\n background: rgba(0, 0, 0, 0.1);\n ${HandleControl} {\n transform: scaleX(100%);\n opacity: 1;\n }\n }\n`;\n\nconst UnscaledContainer = styled.div<{ $open: boolean; $dir: \"left\" | \"right\" }>`\n background: rgba(0, 0, 0, 0);\n position: absolute;\n pointer-events: none;\n width: 16px;\n left: ${(props) => (props.$dir === \"left\" ? 0 : \"-16px\")};\n top: 0;\n bottom: 0;\n z-index: 51; // This will always be quite high.\n`;\n\nexport const HandleControls = forwardRef<\n HTMLDivElement,\n {\n dir: \"left\" | \"right\";\n open: boolean;\n actions: PanelActions;\n transition?: TransitionStatus;\n reset?: () => void;\n }\n>(function HandleControls({ dir, open, actions, reset }, ref) {\n const [showDragTooltip, setShowDragToolTip] = useState(true);\n const dragTooltipMt = \"mt-[calc(50vh+8px)]\";\n const dragTooltipClasses = dir === \"left\" ? `${dragTooltipMt} ml-[13px]` : `${dragTooltipMt} ml-[3px]`;\n return (\n <HandleContainer onClick={() => actions.open()}>\n <UnscaledContainer $open={open} $dir={dir} className=\"group\">\n {!open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger as={OpenControl} $dir={dir} onClick={(e) => actions.open()}>\n <DownIcon className=\"text-2xl\" rotate={dir === \"right\" ? 90 : 270} />\n </TooltipTrigger>\n <DefaultTooltipContent>Open</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n </UnscaledContainer>\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger aria-label=\"Resize panel\" asChild>\n <div>\n <InnerHandleContainer ref={ref} $open={open} $dir={dir} className=\"group\">\n {open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger as={IconHandle} onPress={() => actions.close()}>\n <div\n onMouseOut={() => {\n setShowDragToolTip(true);\n }}\n onMouseOver={() => {\n setShowDragToolTip(false);\n }}\n >\n <CloseIcon />\n </div>\n </TooltipTrigger>\n <DefaultTooltipContent>Close</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n {reset && open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger as={IconHandle} onPress={() => reset()}>\n <div\n onMouseOut={() => {\n setShowDragToolTip(true);\n }}\n onMouseOver={() => {\n setShowDragToolTip(false);\n }}\n >\n <ResetIcon />\n </div>\n </TooltipTrigger>\n <DefaultTooltipContent>Reset</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n {open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger asChild aria-label=\"Resize panel\">\n <div\n onMouseOut={() => {\n setShowDragToolTip(true);\n }}\n onMouseOver={() => {\n setShowDragToolTip(false);\n }}\n >\n <ResizeHandle aria-label=\"Resize panel\" />\n </div>\n </TooltipTrigger>\n <DefaultTooltipContent>Resize panel</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n </InnerHandleContainer>\n </div>\n </TooltipTrigger>\n {showDragTooltip && <DefaultTooltipContent className={dragTooltipClasses}>Resize panel</DefaultTooltipContent>}\n </Tooltip>\n </HandleContainer>\n );\n});\n","import type * as React from \"react\";\n\nexport function Spinner(props: React.SVGProps<SVGSVGElement>) {\n return (\n <svg\n width=\"1em\"\n height=\"1em\"\n viewBox=\"0 0 42 42\"\n xmlns=\"http://www.w3.org/2000/svg\"\n stroke=\"currentColor\"\n {...props}\n >\n <g transform=\"translate(2 2)\" strokeWidth={5} fill=\"none\" fillRule=\"evenodd\">\n <circle strokeOpacity={0.5} cx={18} cy={18} r={18} />\n <path d=\"M36 18c0-9.94-8.06-18-18-18\">\n <animateTransform\n attributeName=\"transform\"\n type=\"rotate\"\n from=\"0 18 18\"\n to=\"360 18 18\"\n dur=\"1s\"\n repeatCount=\"indefinite\"\n />\n </path>\n </g>\n </svg>\n );\n}\n",".ghostLoadingBlock[data-header=\"true\"] {\n box-shadow:\n inset 0 -1px 0 0 rgba(0, 0, 0, 0.17),\n inset 0 1px 0 0 rgba(0, 0, 0, 0.17);\n}\n\n.ghostLoadingBlock {\n display: block;\n width: 100%;\n height: 2.8em;\n margin-bottom: 1em;\n background-color: #e4e7f0;\n animation: ghost-loading 2s infinite ease-in-out;\n}\n\n@keyframes ghost-loading {\n 0% {\n opacity: 0.4;\n }\n 50% {\n opacity: 0.8;\n }\n 100% {\n opacity: 0.4;\n }\n}\n\n.ghostBlockList {\n padding: 1em;\n display: flex;\n flex-direction: column;\n}\n","import $ from \"./GhostBlocks.module.css\";\nexport function GhostBlocks() {\n return (\n <>\n <div data-header=\"true\" className={$.ghostLoadingBlock} />\n <div className={$.ghostBlockList}>\n <div className={$.ghostLoadingBlock} />\n <div className={$.ghostLoadingBlock} />\n <div className={$.ghostLoadingBlock} />\n <div className={$.ghostLoadingBlock} />\n </div>\n </>\n );\n}\n","import { useLayoutEffect } from \"react\";\n\nexport function useEventHandler(ref: any, name: string, callback: (e: any) => void, deps: any[] = []) {\n useLayoutEffect(() => {\n const current = ref.current;\n if (current) {\n current.addEventListener(name, callback);\n\n return () => {\n current.removeEventListener(name, callback);\n };\n }\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [name, ...deps]);\n}\n","import { useEventHandler } from \"@manifest-editor/ui/madoc/use-event-handler\";\nimport { useEffect, useRef, useState } from \"react\";\nimport { useLocalStorage } from \"../../hooks/use-local-storage\";\nimport { panelSizing } from \"../Layout.helpers\";\n\nfunction distance(x1: number, y1: number, x2: number, y2: number) {\n return Math.sqrt(Math.abs(x2 - x1) ** 2 + Math.abs(y2 - y1) ** 2);\n}\n\nfunction getMaxWidthPct(container: number, defaultMaxWidthPct: number, maxWidthPct?: number, maxWidthPixel?: number) {\n if (maxWidthPct) {\n return maxWidthPct;\n }\n\n if (maxWidthPixel) {\n return maxWidthPixel / container;\n }\n\n return defaultMaxWidthPct;\n}\n\nexport function useResizeLayout(\n name: string,\n options: {\n left?: boolean;\n widthA?: any;\n marginLeft?: number;\n widthB?: any;\n maxWidthPx?: number;\n maxWidthPct?: number;\n minWidthPx?: number;\n minWidthPct?: number;\n onDragEnd?: () => void;\n loading?: boolean;\n } = {},\n) {\n const container = useRef<HTMLDivElement | null>(null);\n const resizableDiv = useRef<HTMLDivElement | null>(null);\n const otherDiv = useRef<HTMLDivElement | null>(null);\n const resizer = useRef<HTMLDivElement | null>(null);\n const newPct = useRef(0.5);\n const [isDragging, setIsDragging] = useState(false);\n const isEventDragging = useRef(false);\n const isEventTimeout = useRef<number>(0);\n const startPos = useRef({ x: 0, y: 0 });\n const [{ widthA, widthB }, setWidths] = useLocalStorage(`resize-layout/${name}`, {\n widthA: \"auto\",\n widthB: `${panelSizing({\n initial: options.widthA,\n fallback: 320,\n options: { minWidth: options.minWidthPx, maxWidth: options.maxWidthPx },\n })}px`,\n });\n const { loading = false } = options;\n\n useEventHandler(\n resizer,\n \"mousedown\",\n (e) => {\n startPos.current.x = e.pageX;\n startPos.current.y = e.pageY;\n\n if (isEventTimeout.current) {\n clearTimeout(isEventTimeout.current);\n isEventTimeout.current = 0;\n }\n isEventTimeout.current = setTimeout(() => {\n setIsDragging(true);\n isEventDragging.current = true;\n }, 350) as any;\n },\n [loading],\n );\n\n useEventHandler(\n { current: typeof window !== \"undefined\" ? window : undefined },\n \"mouseup\",\n () => {\n const current = container.current;\n if (current && isEventDragging.current) {\n const { x, width } = current.getBoundingClientRect();\n\n const ml = options.marginLeft || 0;\n const maxWidthPct = getMaxWidthPct(width, 0.8, options.maxWidthPct, options.maxWidthPx) * width;\n const minWidthPct = getMaxWidthPct(width, 0.2, options.minWidthPct, options.minWidthPx) * width;\n\n if (options.left) {\n const newWidthB = (newPct.current * width) - ml;\n\n setWidths({\n widthA: `${((1 - newPct.current) * width) - ml}`,\n widthB: `${newWidthB > maxWidthPct ? maxWidthPct : newWidthB < minWidthPct ? minWidthPct : newWidthB}px`,\n });\n } else {\n const newWidthA = 1 - (newPct.current * width) - ml;\n\n setWidths({\n widthA: `${newWidthA > maxWidthPct ? maxWidthPct : newWidthA < minWidthPct ? minWidthPct : newWidthA}px`,\n widthB: `${(newPct.current * width) - ml}px`,\n });\n }\n\n setIsDragging(false);\n isEventDragging.current = false;\n if (options.onDragEnd) {\n options.onDragEnd();\n }\n }\n\n clearTimeout(isEventTimeout.current);\n isEventTimeout.current = 0;\n },\n [loading],\n );\n\n useEventHandler(\n container,\n \"mousemove\",\n (e) => {\n if (!isEventDragging.current && isEventTimeout.current) {\n if (distance(startPos.current.x, startPos.current.y, e.pageX, e.pageY) > 20) {\n setIsDragging(true);\n isEventDragging.current = true;\n clearTimeout(isEventTimeout.current);\n isEventTimeout.current = 0;\n }\n }\n\n if (isEventDragging.current && resizableDiv.current) {\n const current = container.current;\n if (current) {\n const { x, width } = current.getBoundingClientRect();\n\n const ml = options.marginLeft || 0;\n const isLeft = options.left || false;\n\n const maxWidthPct = getMaxWidthPct(width, 0.8, options.maxWidthPct, options.maxWidthPx);\n const minWidthPct = getMaxWidthPct(width, 0.2, options.minWidthPct, options.minWidthPx);\n\n newPct.current = (width + x - e.pageX - 5) / width;\n if (isLeft) {\n newPct.current = 1 - newPct.current;\n }\n newPct.current = newPct.current < minWidthPct ? minWidthPct : newPct.current;\n newPct.current = newPct.current > maxWidthPct ? maxWidthPct : newPct.current;\n\n resizableDiv.current.style.width = `${(newPct.current * width) - ml}px`;\n }\n }\n },\n [isDragging, loading],\n );\n\n return {\n refs: {\n container,\n resizer,\n resizableDiv,\n otherDiv,\n },\n setWidths,\n isDragging,\n widthA,\n widthB,\n };\n}\n","import styled, { css } from \"styled-components\";\nimport { ModularPanelHeader } from \"../Layout/components/ModularPanel\";\n\nexport const Container = styled.div`\n position: relative;\n display: flex;\n flex: 1;\n overflow: hidden;\n flex-direction: column;\n`;\n\nexport const CenterPanel = styled.div`\n flex: 1;\n position: relative;\n z-index: 7;\n`;\n\nexport const MobileBar = styled.div`\n display: flex;\n justify-content: space-around;\n width: 100%;\n background: #fff;\n border-top: 1px solid #cbcbcb;\n padding: 0.5em;\n height: 3.4rem;\n`;\n\nexport const LeftBarButton = styled.button`\n //background: red;\n padding: 0.5em 1em;\n width: 32%;\n\n border-radius: 5px;\n border: none;\n background: #ffffff;\n`;\n\nexport const PreviewBarButton = styled.button`\n padding: 0.5em 1em;\n width: 32%;\n\n border-radius: 5px;\n\n background: #5e59c2;\n border: 1px solid rgba(0, 0, 0, 0.21);\n color: #ffffff;\n`;\n\nexport const DrawerContainer = styled.div`\n position: relative;\n width: 32%;\n margin: 0 0.75em;\n z-index: 9;\n`;\n\nexport const DrawerButton = styled.button`\n padding: 0.4em 1em 0.65em;\n position: absolute;\n width: 100%;\n bottom: 1em;\n background: #ffffff;\n box-shadow: 0 3px 18px 0 rgba(0, 0, 0, 0.04);\n border-radius: 5px;\n border: 1px solid #979797;\n letter-spacing: -0.46px;\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n\n svg {\n display: block;\n margin: auto;\n font-size: 1.8em;\n }\n`;\n\nexport const DrawerBody = styled.div<{ $open?: boolean }>`\n background: #fff;\n display: flex;\n position: absolute;\n transform: translateY(100%);\n overflow-y: auto;\n left: 0;\n right: 0;\n top: 7em;\n z-index: 10;\n box-shadow:\n 0 -5px 15px 0 rgba(0, 0, 0, 0),\n 0 -3px 5px 0 rgba(0, 0, 0, 0);\n bottom: 0;\n transition:\n 0.3s transform ease-in-out,\n 0.3s box-shadow;\n ${(props) =>\n props.$open &&\n css`\n box-shadow:\n 0 -5px 15px 0 rgba(0, 0, 0, 0.1),\n 0 -3px 5px 0 rgba(0, 0, 0, 0.1);\n transform: translateY(0);\n `}\n\n ${ModularPanelHeader} {\n box-shadow: none;\n padding-left: 0.5em;\n padding-right: 0.5em;\n font-size: 1.1em;\n }\n`;\n\nexport const LeftPanel = styled.div<{ $open?: boolean }>`\n position: absolute;\n transform: translateX(-100%);\n background: #fff;\n left: 0;\n top: 0;\n bottom: 0;\n z-index: 10;\n overflow-y: auto;\n transition: 0.5s transform;\n ${(props) =>\n props.$open &&\n css`\n transform: translateX(0);\n `}\n`;\n\nexport const Lightbox = styled.div<{ $open?: boolean }>`\n background: rgba(0, 0, 0, 0.4);\n pointer-events: none;\n position: absolute;\n z-index: 8;\n top: 0;\n left: 0;\n right: 0;\n bottom: 0;\n opacity: 0;\n transition: opacity 0.5s;\n\n ${(props) =>\n props.$open &&\n css`\n pointer-events: visible;\n opacity: 1;\n `}\n`;\n","import styled, { css, keyframes } from \"styled-components\";\nimport { MenuPositions } from \"./Layout.types\";\nimport { TransitionStatus } from \"react-transition-group\";\n\nexport const OuterWrapper = styled.div`\n display: flex;\n flex-direction: column;\n flex: 1;\n min-height: 0;\n\n max-width: 100%;\n min-width: 0;\n overflow: hidden;\n`;\n\nexport const Header = styled.header`\n //box-shadow: 0 3px 2px 0 rgba(0, 0, 0, 0.04), 0 1px 0 0 rgba(0, 0, 0, 0.17);\n z-index: 200;\n`;\n\nexport const Footer = styled.div`\n background: #fff;\n`;\n\nexport const Main = styled.div`\n display: flex;\n flex: 1 1 0;\n min-height: 0;\n`;\n\nexport const LeftPanel = styled.div<{ $state?: TransitionStatus; $width: string; $motion?: boolean }>`\n background: #fff;\n display: flex;\n flex-direction: column;\n overflow: hidden;\n max-width: 720px;\n align-items: flex-end;\n\n ${(props) =>\n props.$motion\n ? css`\n transition: max-width 400ms;\n `\n : \"\"}\n\n ${(props) => {\n switch (props.$state) {\n case \"entering\":\n return css`\n max-width: ${props.$width};\n `;\n case \"exiting\":\n return css`\n max-width: 0;\n `;\n case \"unmounted\":\n case \"exited\":\n return css`\n max-width: 0;\n `;\n }\n }}\n`;\n\nexport const CenterPanel = styled.div`\n flex: 1 1 0;\n background: #e3e7f0;\n // background: #efefef;\n // box-shadow:\n // inset 0 3px 2px 0 rgba(0, 0, 0, 0.04),\n // inset 0 1px 0 0 rgba(0, 0, 0, 0.14);\n padding-top: 1px;\n // background: linear-gradient(0deg, rgba(251, 242, 237, 1) 0%, rgba(240, 229, 245, 1) 50%, rgba(236, 245, 255, 1) 100%);\n\n min-width: 320px;\n display: flex;\n\n min-height: 0;\n overflow: hidden;\n\n > * {\n min-width: 0;\n }\n`;\n\nexport const RightPanel = styled.div<{ $state?: TransitionStatus; $width: string; $motion?: boolean }>`\n background: #fff;\n display: flex;\n flex-direction: column;\n overflow: hidden;\n max-width: 720px;\n\n ${(props) => (props.$motion ? \"transition: max-width 400ms;\" : \"\")}\n\n ${(props) => {\n switch (props.$state) {\n case \"entering\":\n return css`\n max-width: ${props.$width};\n `;\n case \"exiting\":\n return css`\n max-width: 0;\n `;\n case \"unmounted\":\n case \"exited\":\n return css`\n max-width: 0;\n `;\n }\n }}\n`;\n\nexport const PanelContainer = styled.div<{ $menu?: MenuPositions }>`\n display: flex;\n flex: 1;\n height: 100%;\n min-width: 50px;\n transition: min-width 400ms;\n overflow: hidden;\n\n ${(props) => {\n switch (props.$menu) {\n case \"top\":\n return css`\n flex-direction: column;\n ${PanelMenu} {\n flex-direction: column;\n }\n `;\n case \"left\":\n return css`\n flex-direction: row;\n ${PanelMenu} {\n flex-direction: row;\n }\n `;\n default:\n case \"bottom\":\n return css`\n flex-direction: column-reverse;\n ${PanelMenu} {\n flex-direction: column;\n }\n `;\n case \"right\":\n return css`\n flex-direction: row-reverse;\n ${PanelMenu} {\n flex-direction: row;\n }\n `;\n }\n }}\n`;\n\nexport const PanelSideMenu = styled.div`\n background: #fff;\n border-top: 1px solid #e3e7f0;\n border-right: 1px solid #e3e7f0;\n display: flex;\n flex-direction: column;\n width: 3em;\n /* width: 3.35em;\n padding: 0.3em;\n gap: 0.3em; */\n`;\n\nexport const PanelSideMenuItem = styled.button`\n cursor: pointer;\n aspect-ratio: 1;\n width: 3em;\n height: 3em;\n display: flex;\n justify-content: center;\n align-items: center;\n &:hover {\n background: #fff6f9;\n }\n\n &:hover svg {\n color: #000;\n }\n\n &[data-selected=\"true\"] {\n background: #b84c74;\n svg {\n color: #ffffff;\n }\n }\n\n & svg {\n font-size: 1.5em;\n color: #999;\n }\n`;\n\nexport const PanelMenu = styled.div<{ $position: \"bottom\" | \"top\" | \"left\" | \"right\"; $open: boolean }>`\n display: flex;\n box-shadow:\n 0 -3px 2px 0 rgba(0, 0, 0, 0.04),\n 0 -1px 0 0 rgba(0, 0, 0, 0.17);\n\n ${(props) =>\n !props.$open && (props.$position === \"top\" || props.$position === \"bottom\")\n ? css`\n display: none;\n `\n : \"\"}\n`;\n\nexport const PanelContent = styled.div`\n display: flex;\n flex-direction: column;\n flex: 1;\n min-width: 0;\n overflow: hidden;\n`;\n","import { Modal, PanelSideMenu } from \"@manifest-editor/components\";\n// import { LayoutProps } from \"./Layout.types\";\nimport { DownIcon } from \"@manifest-editor/ui/icons/DownIcon\";\nimport { StarIcon } from \"@manifest-editor/ui/icons/StarIcon\";\nimport { Spinner } from \"@manifest-editor/ui/madoc/components/icons/Spinner\";\nimport { GhostBlocks } from \"@manifest-editor/ui/ui/GhostBlocks/GhostBlocks\";\nimport { Fragment, memo, useContext, useLayoutEffect, useMemo, useRef } from \"react\";\nimport { ErrorBoundary } from \"react-error-boundary\";\nimport { ReactVaultContext } from \"react-iiif-vault\";\nimport { Transition, type TransitionStatus } from \"react-transition-group\";\nimport equal from \"shallowequal\";\nimport { useAppState } from \"../AppContext/AppContext\";\nimport { useMatchMedia } from \"../hooks/use-match-media\";\nimport { HandleControls } from \"./components/HandleControls\";\nimport { ModularPanel } from \"./components/ModularPanel\";\nimport { PanelError } from \"./components/PanelError\";\nimport { useResizeLayout } from \"./components/use-resize-layouts\";\nimport { useLayoutProvider } from \"./Layout.context\";\nimport { panelSizing, renderHelper } from \"./Layout.helpers\";\nimport * as M from \"./Layout.mobile\";\nimport * as L from \"./Layout.styles\";\n\ninterface LayoutProps {\n header?: React.ReactNode;\n footer?: React.ReactNode;\n menu?: React.ReactNode;\n leftPanelMenu?: React.ReactNode;\n rightPanelMenu?: React.ReactNode;\n centerPanelMenu?: React.ReactNode;\n leftPanelMenuPosition?: \"top\" | \"bottom\";\n rightPanelMenuPosition?: \"top\" | \"bottom\";\n hideHeader?: boolean;\n isLoading?: boolean;\n className?: string;\n htmlId?: string;\n centerPanelMenuPosition?: \"top\" | \"bottom\";\n disableSideEffects?: string[];\n}\n\nexport const Layout = memo(function Layout(props: LayoutProps) {\n const appState = useAppState();\n const layout = useLayoutProvider();\n const { vault: _vault } = useContext(ReactVaultContext);\n const vault = _vault || undefined;\n const leftPanelRef = useRef<HTMLDivElement | null>(null);\n const rightPanelRef = useRef<HTMLDivElement | null>(null);\n const { loading, state, leftPanels, centerPanels, rightPanels, modals = [], actions } = layout;\n const leftPanel = leftPanels.find((panel) => panel.id === state.leftPanel.current);\n const rightPanel = rightPanels.find((panel) => panel.id === state.rightPanel.current);\n const centerPanel = centerPanels.find((panel) => panel.id === state.centerPanel.current);\n const modalToRender = modals.find((panel) => panel.id === state.modal.current);\n const enableMotion = true;\n const pinnedRightPanel = state.pinnedRightPanel.pinned\n ? rightPanels.find((panel) => panel.id === state.pinnedRightPanel.current)\n : undefined;\n const [mobile] = useMatchMedia([\"(max-width: 1020px)\"]);\n\n const isLoading = props.isLoading || false;\n const backgroundItems = useMemo(() => {\n return (layout.background || []).map((bg, key) => {\n return <Fragment key={key}>{bg.render()}</Fragment>;\n });\n }, [layout.background]);\n\n // Resizers\n const leftPanelResizer = useResizeLayout(`left-panel/${leftPanel?.id}`, {\n left: true,\n marginLeft: 60,\n minWidthPx: leftPanel?.options?.minWidth || 200,\n maxWidthPx: leftPanel?.options?.maxWidth || 720,\n loading,\n });\n const rightPanelResizer = useResizeLayout(`right-panel/${rightPanel?.id}`, {\n left: false,\n minWidthPx: rightPanel?.options?.minWidth || 320,\n maxWidthPx: rightPanel?.options?.maxWidth || 720,\n loading,\n });\n\n // Pinned state\n const showRightPanel =\n rightPanel &&\n (pinnedRightPanel?.id !== rightPanel.id || !equal(state.pinnedRightPanel.state, state.rightPanel.state));\n const resetLeftPanel =\n leftPanelResizer.widthB !== \"auto\"\n ? () =>\n leftPanelResizer.setWidths({\n widthA: \"auto\",\n widthB: panelSizing({\n options: leftPanel?.options,\n fallback: 320,\n }),\n } as any)\n : undefined;\n const resetRightPanel =\n rightPanelResizer.widthB !== \"auto\"\n ? () =>\n rightPanelResizer.setWidths({\n widthA: \"auto\",\n widthB: panelSizing({\n options: rightPanel?.options,\n fallback: 320,\n }),\n } as any)\n : undefined;\n\n // Remove dynamic layouts for now.\n // useEffect(() => {\n // // @todo to enable dynamic layouts, we need this effect to run IF the props change.\n // actions.setAvailable(props);\n // props.rightPanels.length && actions.rightPanel.change({ id: props.rightPanels[0]!.id });\n // props.leftPanels.length && actions.leftPanel.change({ id: props.leftPanels[0]!.id });\n // props.centerPanels.length && actions.centerPanel.change({ id: props.centerPanels[0]!.id });\n\n // // actions are stable.\n // // eslint-disable-next-line react-hooks/exhaustive-deps\n // }, []);\n\n useLayoutEffect(() => {\n if (mobile && state.leftPanel.open && state.rightPanel.open) {\n actions.leftPanel.close();\n actions.rightPanel.close();\n }\n }, [mobile]);\n\n useLayoutEffect(() => {\n if (centerPanel && centerPanel.onMount) {\n return centerPanel.onMount(\n state.centerPanel.state || centerPanel.defaultState || {},\n { ...layout, current: actions.centerPanel, vault: vault as any },\n appState,\n );\n }\n }, [state.centerPanel.current]);\n\n useLayoutEffect(() => {\n // @todo to enable dynamic layouts, we need this effect to run IF the props change.\n // actions.setAvailable(props);\n rightPanels.length && actions.rightPanel.change({ id: rightPanels[0]!.id });\n leftPanels.length && actions.leftPanel.change({ id: leftPanels[0]!.id });\n centerPanels.length && actions.centerPanel.change({ id: centerPanels[0]!.id });\n\n // actions are stable.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n if (loading) {\n // It will render as soon as possible, downside of hoisting the layout provider\n // Unlikely this will be hit because of flushSync, but best to check.\n return null;\n }\n\n // Build our panels here.\n\n const renderLeftPanel = (transition?: TransitionStatus) => (\n <L.PanelContainer\n $menu={props.leftPanelMenuPosition || \"bottom\"}\n ref={leftPanelResizer.refs.resizableDiv}\n className={[\"manifest-editor\", transition && enableMotion ? `transition transition-${transition}` : \"\"].join(\" \")}\n style={{\n width: state.leftPanel.open || transition !== \"exited\" ? leftPanelResizer.widthB : undefined,\n minWidth: leftPanel?.options?.minWidth,\n }}\n >\n {isLoading ? (\n <L.PanelContent>\n <GhostBlocks />\n </L.PanelContent>\n ) : (\n <>\n {props.leftPanelMenu ? (\n <L.PanelMenu\n $open={state.leftPanel.open && transition !== \"exited\"}\n $position={props.leftPanelMenuPosition || \"bottom\"}\n >\n {props.leftPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n {state.leftPanel.open || transition !== \"exited\" ? (\n <>\n {leftPanel ? (\n <ModularPanel\n isLeft\n noHeader\n transition={transition}\n panel={leftPanel}\n state={state.leftPanel}\n actions={actions.leftPanel}\n />\n ) : null}\n </>\n ) : null}\n </L.PanelContent>\n </>\n )}\n </L.PanelContainer>\n );\n\n const renderModal = () => {\n if (!modalToRender || state.modal.open === false) {\n return null;\n }\n\n return (\n <Modal title={modalToRender.label} onClose={() => actions.modal.close()}>\n {renderHelper(\n modalToRender.render(\n state.modal.state || modalToRender.defaultState || {},\n { ...layout, current: actions.modal, vault: vault },\n appState,\n ),\n )}\n </Modal>\n );\n };\n\n const renderCenterPanel = () => (\n <L.PanelContainer $menu={props.centerPanelMenuPosition || \"top\"}>\n {props.centerPanelMenu ? (\n <L.PanelMenu $open={state.centerPanel.open} $position={props.centerPanelMenuPosition || \"top\"}>\n {props.centerPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n <ErrorBoundary resetKeys={[centerPanel?.id]} FallbackComponent={PanelError}>\n {isLoading ? (\n <div\n style={{\n display: \"flex\",\n flex: 1,\n justifyContent: \"center\",\n alignItems: \"center\",\n }}\n >\n <Spinner stroke=\"rgba(0,0,0,.3)\" fontSize={\"2em\"} />\n </div>\n ) : state.centerPanel.open ? (\n centerPanel ? (\n renderHelper(\n centerPanel.render(\n state.centerPanel.state || centerPanel.defaultState || {},\n { ...layout, current: actions.centerPanel, vault: vault },\n appState,\n ),\n )\n ) : null\n ) : null}\n </ErrorBoundary>\n </L.PanelContent>\n </L.PanelContainer>\n );\n\n const renderRightPanel = (transition?: TransitionStatus) => (\n <L.PanelContainer\n $menu={props.rightPanelMenuPosition || \"bottom\"}\n ref={rightPanelResizer.refs.resizableDiv}\n className={transition && enableMotion ? `transition transition-${transition}` : \"\"}\n style={{\n width: state.rightPanel.open || transition !== \"exited\" ? rightPanelResizer.widthB : undefined,\n minWidth: rightPanel?.options?.minWidth,\n }}\n >\n {isLoading ? (\n <L.PanelContent>\n <GhostBlocks />\n </L.PanelContent>\n ) : (\n <>\n {props.rightPanelMenu ? (\n <L.PanelMenu $open={state.rightPanel.open} $position={props.rightPanelMenuPosition || \"bottom\"}>\n {props.rightPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n {state.rightPanel.open || transition !== \"exited\" ? (\n <>\n {showRightPanel ? (\n <ModularPanel\n panel={rightPanel}\n state={state.rightPanel}\n actions={actions.rightPanel}\n pinActions={actions.pinnedRightPanel}\n available={rightPanels}\n />\n ) : null}\n\n {pinnedRightPanel ? (\n <ModularPanel\n panel={pinnedRightPanel}\n state={state.pinnedRightPanel}\n actions={actions.pinnedRightPanel}\n close={actions.rightPanel.close}\n />\n ) : null}\n </>\n ) : null}\n </L.PanelContent>\n </>\n )}\n </L.PanelContainer>\n );\n\n if (mobile) {\n return (\n <L.OuterWrapper>\n {props.hideHeader ? null : (\n <L.Header>\n {props.header || null}\n {props.menu ? <menu>{props.menu}</menu> : null}\n </L.Header>\n )}\n <L.Main>\n <M.Container>\n <M.CenterPanel>{renderCenterPanel()}</M.CenterPanel>\n <M.MobileBar>\n {leftPanels.length > 0 ? (\n <M.LeftBarButton onClick={actions.leftPanel.toggle}>{leftPanel?.label}</M.LeftBarButton>\n ) : null}\n {rightPanels.length > 0 ? (\n <M.DrawerContainer>\n <M.DrawerButton onClick={actions.rightPanel.toggle}>\n <DownIcon rotate={180} />\n {rightPanel?.label}\n </M.DrawerButton>\n </M.DrawerContainer>\n ) : null}\n <M.PreviewBarButton>Preview</M.PreviewBarButton>\n </M.MobileBar>\n {rightPanels.length > 0 ? (\n <M.DrawerBody $open={state.rightPanel.open}>{renderRightPanel()}</M.DrawerBody>\n ) : null}\n {leftPanels.length > 0 ? <M.LeftPanel $open={state.leftPanel.open}>{renderLeftPanel()}</M.LeftPanel> : null}\n {leftPanels.length > 0 || rightPanels.length > 0 ? (\n <M.Lightbox\n $open={state.leftPanel.open || state.rightPanel.open}\n onClick={() => {\n actions.leftPanel.close();\n actions.rightPanel.close();\n }}\n />\n ) : null}\n </M.Container>\n </L.Main>\n </L.OuterWrapper>\n );\n }\n\n // This is a big ol' work in progress.\n return (\n <L.OuterWrapper\n id={props.htmlId || \"manifest-editor-container\"}\n className={`manifest-editor ${props.className || \"\"}`}\n >\n {props.hideHeader ? null : (\n <L.Header>\n {props.header || null}\n {props.menu ? <menu>{props.menu}</menu> : null}\n </L.Header>\n )}\n <L.Main\n ref={(div) => {\n leftPanelResizer.refs.container.current = div;\n rightPanelResizer.refs.container.current = div;\n }}\n >\n {leftPanels.length > 0 ? (\n <PanelSideMenu\n current={state.leftPanel.current}\n items={leftPanels.map((panel) => ({\n id: panel.id,\n label: panel.label,\n icon: panel.icon,\n divide: panel.divide,\n onClick: () => {\n if (state.leftPanel.current === panel.id) {\n actions.leftPanel.toggle();\n } else {\n actions.leftPanel.change({ id: panel.id });\n }\n },\n }))}\n open={state.leftPanel.open}\n />\n ) : null}\n\n {leftPanels.length > 0 ? (\n <Transition\n nodeRef={leftPanelRef}\n in={state.leftPanel.open}\n timeout={enableMotion ? 400 : 0}\n unmountOnExit={false}\n >\n {(transition) => (\n <>\n <L.LeftPanel\n ref={leftPanelRef}\n $width={leftPanelResizer.widthB}\n $state={transition}\n $motion={enableMotion}\n >\n {renderLeftPanel(transition)}\n </L.LeftPanel>\n <HandleControls\n ref={leftPanelResizer.refs.resizer}\n reset={resetLeftPanel}\n dir=\"left\"\n transition={transition}\n open={state.leftPanel.open || transition !== \"exited\"}\n actions={actions.leftPanel}\n />\n </>\n )}\n </Transition>\n ) : null}\n <L.CenterPanel>{renderCenterPanel()}</L.CenterPanel>\n {rightPanels.length > 0 ? (\n <Transition\n nodeRef={rightPanelRef}\n in={state.rightPanel.open}\n timeout={enableMotion ? 400 : 0}\n unmountOnExit={false}\n >\n {(transition) => (\n <>\n <HandleControls\n ref={rightPanelResizer.refs.resizer}\n dir=\"right\"\n reset={resetRightPanel}\n open={state.rightPanel.open}\n actions={actions.rightPanel}\n />\n <L.RightPanel\n ref={rightPanelRef}\n $width={rightPanelResizer.widthB}\n $state={transition}\n $motion={enableMotion}\n >\n {renderRightPanel(transition)}\n </L.RightPanel>\n </>\n )}\n </Transition>\n ) : null}\n </L.Main>\n <L.Footer>{props.footer || null}</L.Footer>\n\n <div className=\"hidden\">{backgroundItems}</div>\n\n <>{renderModal()}</>\n </L.OuterWrapper>\n );\n});\n","import { LayoutState, PanelActions, PanelActionType, PinnablePanelActions } from \"./Layout.types\";\nimport { Dispatch, useMemo } from \"react\";\nexport function usePanelActions(\n panel: keyof LayoutState,\n dispatch: Dispatch<PanelActionType>\n): PanelActions | PinnablePanelActions {\n function popStack() {\n dispatch({ type: \"popStack\", panel, payload: undefined });\n }\n function change(payload: { id: string; state?: any; stacked?: boolean }) {\n // flushSync(() => {\n dispatch({ type: \"change\", panel, payload });\n // });\n }\n function open(payload?: { id: string; state?: any; stacked?: boolean }) {\n // flushSync(() => {\n dispatch({ type: \"open\", panel, payload });\n // });\n }\n function close() {\n dispatch({ type: \"close\", panel, payload: undefined });\n }\n function toggle() {\n dispatch({ type: \"toggle\", panel, payload: undefined });\n }\n function minimise() {\n dispatch({ type: \"minimise\", panel, payload: undefined });\n }\n function maximise(payload?: { id: string; state?: any }) {\n dispatch({ type: \"maximise\", panel, payload });\n }\n function setCustomWidth(payload: number) {\n dispatch({ type: \"setCustomWidth\", panel, payload });\n }\n function resetSize() {\n dispatch({ type: \"resetSize\", panel, payload: undefined });\n }\n function pin(payload: { id: string; state?: any }) {\n dispatch({ type: \"pin\", panel, payload });\n }\n function unpin() {\n dispatch({ type: \"unpin\", panel, payload: undefined });\n }\n\n return useMemo(\n () => ({\n popStack,\n change,\n open,\n close,\n toggle,\n minimise,\n maximise,\n setCustomWidth,\n resetSize,\n pin,\n unpin,\n }),\n // Dispatch is stable here.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n []\n );\n}\n","import { produce, Draft, original } from \"immer\";\nimport { LayoutState, PanelActionType, PanelState, PinnablePanelState } from \"./Layout.types\";\nimport { isPinnableState } from \"./Layout.helpers\";\n\nfunction pushStack<T>(\n state: Draft<PinnablePanelState | PanelState>,\n action: T extends { payload: { stacked?: boolean; unique?: boolean } } ? T : never\n) {\n if (action.payload && action.payload.stacked) {\n if (state.current) {\n const latest = state.stack[state.stack.length - 1];\n if (latest && latest.id === state.current) {\n return;\n }\n\n if (action.payload.unique) {\n state.stack = state.stack.filter((i) => i.id !== state.current);\n }\n\n state.stack.push({\n id: state.current,\n state: state.state ? { ...original(state.state) } : {},\n });\n }\n } else {\n state.stack = [];\n }\n}\n\nfunction panelReducer(state: Draft<PinnablePanelState | PanelState>, action: PanelActionType) {\n switch (action.type) {\n case \"popStack\": {\n if (state.stack.length) {\n const latest = state.stack[state.stack.length - 1];\n if (latest) {\n state.current = latest.id;\n state.state = latest.state;\n }\n state.stack = state.stack.slice(0, -1);\n }\n break;\n }\n\n case \"change\": {\n if (action.payload.id !== state.current) {\n pushStack(state, action);\n }\n state.state = action.payload.state;\n state.current = action.payload.id;\n break;\n }\n case \"close\": {\n state.open = false;\n break;\n }\n case \"open\": {\n state.open = true;\n if (action.payload) {\n if (action.payload.id !== state.current) {\n pushStack<any>(state, action);\n }\n state.state = action.payload.state;\n state.current = action.payload.id;\n }\n break;\n }\n case \"toggle\": {\n state.open = !state.open;\n break;\n }\n case \"maximise\": {\n state.minimised = false;\n if (action.payload) {\n state.state = action.payload.state;\n state.current = action.payload.id;\n }\n break;\n }\n case \"minimise\": {\n state.minimised = true;\n break;\n }\n case \"setCustomWidth\": {\n state.customWidth = action.payload;\n break;\n }\n case \"resetSize\": {\n state.customWidth = undefined;\n }\n }\n\n if (isPinnableState(state)) {\n switch (action.type) {\n case \"pin\": {\n state.pinned = true;\n state.state = action.payload.state;\n state.current = action.payload.id;\n break;\n }\n case \"unpin\": {\n state.pinned = false;\n state.state = undefined;\n break;\n }\n }\n }\n}\n\nexport const layoutReducer = produce<LayoutState, [PanelActionType]>((state, action: PanelActionType) => {\n switch (action.panel) {\n case \"centerPanel\": {\n panelReducer(state.centerPanel, action);\n break;\n }\n case \"leftPanel\": {\n panelReducer(state.leftPanel, action);\n break;\n }\n case \"rightPanel\": {\n panelReducer(state.rightPanel, action);\n break;\n }\n case \"modal\": {\n panelReducer(state.modal, action);\n break;\n }\n case \"pinnedRightPanel\": {\n panelReducer(state.pinnedRightPanel, action);\n break;\n }\n }\n});\n\nexport function getDefaultPanelState(): PanelState {\n return {\n customWidth: undefined,\n minimised: false,\n open: true,\n current: null,\n state: null,\n stack: [],\n };\n}\n\nexport function getDefaultLayoutState(): LayoutState {\n return {\n leftPanel: getDefaultPanelState(),\n centerPanel: getDefaultPanelState(),\n rightPanel: getDefaultPanelState(),\n modal: getDefaultPanelState(),\n pinnedRightPanel: {\n ...getDefaultPanelState(),\n pinnable: true,\n pinned: false,\n },\n };\n}\n","import type { Reference } from \"@iiif/presentation-3\";\nimport { createContext, type ReactNode, useContext, useMemo } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { useVault, useVaultSelector } from \"react-iiif-vault\";\n\ninterface ResourceEditingContext {\n resource: Reference<any> | null;\n}\n\nexport const ResourceEditingReactContext =\n createContext<ResourceEditingContext>({\n resource: null,\n });\n\nexport function useEditingContext() {\n return useContext(ResourceEditingReactContext);\n}\n\n/**\n * useResource\n *\n * Only use this if you KNOW that there is a resource (e.g. in a panel)\n */\nexport function useResource<T = Record<string, never>>(): T & Reference<any> {\n const vault = useVault();\n const { resource } = useEditingContext();\n\n invariant(resource, \"Nothing selected\");\n\n const { id, type } = resource;\n\n const fullResource = useVaultSelector(() => {\n return vault.get({ id, type });\n }, [id, type]);\n\n return fullResource as T & Reference<any>;\n}\n\n/**\n * useOptionalResource\n *\n * Use in components where you don't know if something is editing. (e.g. canvas listing)\n */\nexport function useOptionalResource() {\n const { resource } = useEditingContext();\n\n return resource;\n}\n\nexport function ResourceEditingProvider({\n resource,\n children,\n}: {\n resource: { id: string; type: string } | null | undefined;\n children: ReactNode;\n}) {\n const { id, type } = resource || {};\n\n return (\n <ResourceEditingReactContext.Provider\n value={useMemo(\n () => ({\n // Current resource.\n resource: id && type ? { id, type } : null,\n }),\n [id, type],\n )}\n >\n {children}\n </ResourceEditingReactContext.Provider>\n );\n}\n","import React, { Component, ErrorInfo, ReactNode } from \"react\";\n\ninterface Props {\n children: ReactNode;\n}\n\ninterface State {\n hasError: boolean;\n}\n\nexport class ErrorBoundary extends Component<Props, State> {\n public state: State = {\n hasError: false,\n };\n\n public static getDerivedStateFromError(_: Error): State {\n console.error(_);\n // Update state so the next render will show the fallback UI.\n return { hasError: true };\n }\n\n public componentDidCatch(error: Error, errorInfo: ErrorInfo) {\n console.error(\"Uncaught error:\", error, errorInfo);\n }\n\n public render() {\n if (this.state.hasError) {\n return <h1>Sorry.. there was an error</h1>;\n }\n\n return this.props.children;\n }\n}\n","import { isSpecificResource } from \"@iiif/parser\";\nimport type { Reference, SpecificResource } from \"@iiif/presentation-3\";\nimport type { CreatableResource } from \"@manifest-editor/creator-api\";\nimport { type ReactNode, memo, useMemo, useReducer } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { useEditingStack } from \"../EditingStack/EditingStack\";\nimport type { EditableResource } from \"../EditingStack/EditingStack.types\";\nimport { LayoutActionsReactContext, LayoutStateReactContext } from \"./Layout.context\";\nimport { usePanelActions } from \"./Layout.hooks\";\nimport { getDefaultLayoutState, layoutReducer } from \"./Layout.reducer\";\nimport type { PinnablePanelActions } from \"./Layout.types\";\nimport { useEmitter } from \"../hooks/use-event\";\n\nfunction parse(args: string | { id: string; state?: any; stacked?: boolean }, _state?: any): any {\n if (typeof args === \"string\") {\n return { id: args, state: _state };\n }\n return args;\n}\n\nexport const LayoutProvider = memo(function LayoutProvider(props: { children: ReactNode }) {\n const app = useApp();\n const emitter = useEmitter();\n const available = app.layout;\n\n const [state, dispatch] = useReducer(layoutReducer, undefined, getDefaultLayoutState);\n const actions = {\n centerPanel: usePanelActions(\"centerPanel\", dispatch),\n leftPanel: usePanelActions(\"leftPanel\", dispatch),\n rightPanel: usePanelActions(\"rightPanel\", dispatch),\n pinnedRightPanel: usePanelActions(\"pinnedRightPanel\", dispatch) as PinnablePanelActions,\n modal: usePanelActions(\"modal\", dispatch),\n editingStack: useEditingStack(),\n };\n\n function find(id: any) {\n const right = available.rightPanels.find((r) => r.id === id);\n if (right) {\n return [right, actions.rightPanel, actions.pinnedRightPanel] as const;\n }\n\n const center = available.centerPanels.find((r) => r.id === id);\n if (center) {\n return [center, actions.centerPanel] as const;\n }\n\n const left = available.leftPanels.find((r) => r.id === id);\n if (left) {\n return [left, actions.leftPanel] as const;\n }\n\n invariant(false, `Was not able to find panel with id \"${id}\"`);\n }\n\n function open(args: string | { id: string; state?: any; stacked?: boolean }, _state?: any): void {\n const { id, state, stacked } = parse(args, _state);\n const [found, actions, pinnable] = find(id);\n\n if (pinnable && found.options?.openPinned) {\n pinnable.pin({\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n });\n } else {\n const openData = {\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n stacked,\n };\n\n emitter.emit(\"layout.open\", openData);\n actions.open(openData);\n }\n }\n\n function stack(args: string | { id: string; state?: any }, _state?: any): void {\n const { id, state } = parse(args, _state);\n const [found, actions] = find(id);\n\n const openData = {\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n stacked: true,\n };\n\n emitter.emit(\"layout.open\", openData);\n actions.open(openData);\n }\n\n function change(args: string | { id: string; state?: any; stacked?: boolean }, _state?: any): void {\n const { id, state, stacked } = parse(args, _state);\n const [found, actions] = find(id);\n const changeData = {\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n stacked,\n };\n\n emitter.emit(\"layout.change\", changeData);\n actions.change(changeData);\n }\n\n function close(args: string | { id: string; state?: any }, _state?: any): void {\n const { id } = parse(args, _state);\n const [, actions] = find(id);\n\n emitter.emit(\"layout.close\", { id });\n actions.close();\n }\n\n function toggle(args: string | { id: string; state?: any }, _state?: any): void {\n const { id } = parse(args, _state);\n const [, actions] = find(id);\n\n emitter.emit(\"layout.toggle\", { id });\n actions.toggle();\n }\n\n function edit(\n resource: Reference | SpecificResource,\n context: Omit<EditableResource, \"resource\"> = {},\n {\n reset,\n property,\n stacked,\n forceOpen,\n }: {\n reset?: boolean;\n property?: string;\n stacked?: boolean | undefined;\n forceOpen?: boolean;\n } = {}\n ) {\n const toEdit: EditableResource = {\n resource: isSpecificResource(resource)\n ? resource\n : {\n type: \"SpecificResource\",\n source: resource,\n },\n ...context,\n };\n\n emitter.emit(\"layout.edit\", toEdit);\n actions.editingStack.edit(toEdit, reset);\n\n if (available.rightPanels.find((e) => e.id === \"@manifest-editor/editor\")) {\n if (forceOpen) {\n actions.rightPanel.open({\n id: \"@manifest-editor/editor\",\n stacked: stacked !== false,\n state: { property },\n unique: true,\n });\n } else {\n actions.rightPanel.change({\n id: \"@manifest-editor/editor\",\n stacked: stacked !== false,\n state: { property },\n unique: true,\n });\n }\n }\n }\n\n function create(resource: CreatableResource) {\n actions.editingStack.create(resource, {});\n emitter.emit(\"layout.create\", resource);\n if (available.modals?.find((e) => e.id === \"@manifest-editor/creator\")) {\n actions.modal.open({\n id: \"@manifest-editor/creator\",\n stacked: true,\n unique: true,\n state: resource,\n });\n } else if (available.rightPanels.find((e) => e.id === \"@manifest-editor/creator\")) {\n actions.rightPanel.open({\n id: \"@manifest-editor/creator\",\n stacked: true,\n unique: true,\n state: resource,\n });\n }\n }\n\n const otherActions = {\n open,\n change,\n close,\n toggle,\n stack,\n edit,\n create,\n };\n\n return (\n <LayoutActionsReactContext.Provider\n // biome-ignore lint/correctness/useExhaustiveDependencies: actions do not change\n value={useMemo(() => ({ ...actions, ...otherActions }), [available])}\n >\n <LayoutStateReactContext.Provider value={state}>{props.children}</LayoutStateReactContext.Provider>\n </LayoutActionsReactContext.Provider>\n );\n});\n","import { ImageServiceLoader } from \"@atlas-viewer/iiif-image-api\";\nimport { ErrorBoundary } from \"@manifest-editor/ui/atoms/ErrorBoundary\";\nimport { type ReactNode, useMemo } from \"react\";\nimport {\n AtlasStoreProvider,\n ImageServiceLoaderContext,\n} from \"react-iiif-vault\";\nimport { ThemeProvider } from \"styled-components\";\nimport {\n AppResourceProvider,\n type Resource,\n} from \"../AppResourceProvider/AppResourceProvider\";\nimport {\n type Config,\n ConfigProvider,\n useConfig,\n} from \"../ConfigContext/ConfigContext\";\nimport { ContextMenuProvider } from \"../ContextMenu/ContextMenuContext\";\nimport { EditingStack } from \"../EditingStack/EditingStack\";\nimport { LayoutProvider } from \"../Layout/Layout.context-internal\";\nimport { PreviewProvider } from \"../PreviewContext/PreviewContext\";\nimport type {\n Preview,\n PreviewConfiguration,\n} from \"../PreviewContext/PreviewContext.types\";\nimport { PreviewVaultContext } from \"../PreviewVault/PreviewVault\";\nimport { defaultTheme } from \"./default-theme\";\n\nconst previewConfigs: PreviewConfiguration[] = [\n {\n id: \"universal-viewer\",\n config: {\n url: \"https://universalviewer.dev/#?iiifManifestId={manifestId}\",\n },\n type: \"external-manifest-preview\",\n label: \"Universal viewer\",\n },\n {\n id: \"mirador-3\",\n type: \"external-manifest-preview\",\n label: \"Mirador 3\",\n config: {\n url: \"https://tomcrane.github.io/scratch/mirador3/?iiif-content={manifestId}\",\n },\n },\n {\n id: \"annona\",\n type: \"external-manifest-preview\",\n label: \"Annona\",\n config: {\n url: \"https://ncsu-libraries.github.io/annona/tools/#/display?url={manifestId}&viewtype=iiif-storyboard&settings=%7B%22fullpage%22%3Atrue%7D\",\n },\n },\n {\n id: \"iiif-preview\",\n config: { url: \"https://iiif-preview.digirati.services/store\" },\n type: \"iiif-preview-service\",\n label: \"IIIF Preview\",\n },\n];\n\nconst imageServiceLoader = new ImageServiceLoader({\n approximateServices: true,\n verificationsRequired: 8,\n enableFetching: true,\n});\n\nexport function ShellProvider({\n config,\n saveConfig,\n children,\n theme,\n previews,\n resource,\n editing,\n}: {\n resource: Resource;\n config?: Partial<Config>;\n saveConfig?: (config: Partial<Config>) => void;\n children: ReactNode;\n theme?: any;\n previews?: Preview[];\n editing?: { id: string; type: string };\n}) {\n const existingConfig = useConfig();\n const mergedConfig = useMemo(() => {\n return {\n ...existingConfig,\n ...config,\n previews: config?.previews || existingConfig.previews || previewConfigs,\n };\n }, [existingConfig, config]);\n\n return (\n <ErrorBoundary>\n <ImageServiceLoaderContext.Provider value={imageServiceLoader}>\n <AppResourceProvider resource={resource}>\n <PreviewVaultContext>\n <ThemeProvider theme={theme || defaultTheme}>\n <ConfigProvider config={mergedConfig} saveConfig={saveConfig}>\n <EditingStack>\n <LayoutProvider>\n <ContextMenuProvider>\n {/* @todo swap these out for (config?.previews || []) */}\n <PreviewProvider\n previews={previews || []}\n configs={mergedConfig.previews}\n >\n <AtlasStoreProvider>{children}</AtlasStoreProvider>\n </PreviewProvider>\n </ContextMenuProvider>\n </LayoutProvider>\n </EditingStack>\n </ConfigProvider>\n </ThemeProvider>\n </PreviewVaultContext>\n </AppResourceProvider>\n </ImageServiceLoaderContext.Provider>\n </ErrorBoundary>\n );\n}\n","// TaskBridge.\nimport mitt, { Emitter } from \"mitt\";\nimport { createContext, ReactNode, useCallback, useContext, useEffect, useMemo, useReducer } from \"react\";\n\ninterface Task<Req = any, Res = any> {\n name: string;\n status: \"idle\" | \"running\" | \"complete\" | \"error\";\n emitter: Emitter<any>;\n promise: Promise<any>;\n abort: AbortController;\n resolve: (value?: any) => void;\n reject: (reason?: any) => void;\n error?: string;\n request?: Req;\n response?: Res;\n}\n\nconst tempGlobalState: Record<string, Record<string, Task>> = {};\n\nconst DispatchReactContext = createContext<string>(\"global\");\n\nfunction useCurrentDispatchId() {\n return useContext(DispatchReactContext);\n}\n\nfunction createDeferred() {\n let res: (value: any) => void = undefined as any;\n let rej: (reason?: any) => void = undefined as any;\n const promise = new Promise((resolve, reject) => {\n res = resolve;\n rej = reject;\n });\n\n return { promise, resolve: res, reject: rej };\n}\n\nexport function useTask(name: string) {\n const id = useCurrentDispatchId();\n const [, invalidate] = useReducer((r) => r + 1, 0);\n const task = useMemo(() => {\n if (!tempGlobalState[id]) {\n tempGlobalState[id] = {};\n }\n if (!tempGlobalState[id]![name]) {\n tempGlobalState[id]![name] = {\n name,\n emitter: mitt(),\n status: \"idle\",\n promise: Promise.resolve(),\n abort: new AbortController(),\n reject: () => void 0,\n resolve: () => void 0,\n };\n }\n\n return tempGlobalState[id]![name]!;\n }, [id, name]);\n\n useTaskEvent(task, \"abort\", invalidate);\n useTaskEvent(task, \"error\", invalidate);\n useTaskEvent(task, \"complete\", invalidate);\n useTaskEvent(task, \"running\", invalidate);\n\n return task;\n}\n\nexport function useTaskEvent<Req = any, Res = any>(\n task: Task<Req, Res>,\n name: string,\n _cb: (task: Task<Req, Res>) => any\n) {\n const cb = useCallback(() => _cb(task), [_cb]);\n useEffect(() => {\n const em = task.emitter;\n em.on(name, cb);\n return () => em.off(name, cb);\n }, [name, cb, task.emitter]);\n}\n\nconst noop = () => void 0;\n\nexport function useTaskDispatch<Req = any, Res = any>(\n name: string,\n onComplete?: (task: Task<Req, Res>) => void | Promise<void>\n) {\n const taskDetails = useTask(name);\n\n useTaskEvent(taskDetails, \"complete\", onComplete ? onComplete : noop);\n\n const runTask = (request?: any) => {\n // Abort running tasks.\n if (taskDetails.status === \"running\") {\n taskDetails.abort.abort();\n taskDetails.emitter.emit(\"abort\");\n }\n\n // Error clearing.\n if (taskDetails.error) {\n taskDetails.error = \"\";\n }\n\n // Creating new task.\n const d = createDeferred();\n d.promise.then(() => taskDetails.emitter.emit(\"complete\")).catch(() => taskDetails.emitter.emit(\"error\"));\n taskDetails.status = \"running\";\n taskDetails.request = request;\n taskDetails.promise = d.promise;\n taskDetails.resolve = d.resolve;\n taskDetails.reject = d.reject;\n taskDetails.emitter.emit(\"running\");\n };\n\n return [runTask, taskDetails] as const;\n}\n\nexport function useTaskRunner<Req = any, Res = any>(\n name: string,\n onRun: (task: Task<Req, Res>) => void | Promise<void>\n) {\n const taskDetails = useTask(name);\n\n useTaskEvent(taskDetails, \"running\", onRun);\n\n const completeTask = (response?: any) => {\n if (taskDetails.status === \"running\") {\n taskDetails.response = response;\n taskDetails.status = \"complete\";\n taskDetails.resolve();\n }\n //\n };\n\n const rejectTask = (reason?: any, error?: any) => {\n if (taskDetails.status === \"running\") {\n taskDetails.error = error || reason;\n taskDetails.status = \"error\";\n taskDetails.reject(reason);\n }\n };\n\n return [completeTask, taskDetails, rejectTask] as const;\n}\n\nexport function TaskBridge({ children }: { children?: ReactNode }) {\n return (\n <DispatchReactContext.Provider value={useMemo(() => `id-${Date.now()}`, [])}>\n {children}\n </DispatchReactContext.Provider>\n );\n}\n","import { HTMLAttributes, useCallback, useMemo } from \"react\";\nimport { UniversalCopyPasteProps } from \"./UniversalCopyPaste.types\";\n\n// @todo\nfunction analyse(t: any) {\n return false;\n}\n\nexport function UniversalCopyTarget<T>({\n as,\n reference: _ref,\n onReference,\n onLink,\n onAnalysis,\n onDropReference: _onDropReference,\n onDropLink: _onDropLink,\n onDropAnalysis: _onDropAnalysis,\n onPasteReference: _onPasteReference,\n onPasteLink: _onPasteLink,\n onPasteAnalysis: _onPasteAnalysis,\n ...props\n}: Partial<HTMLAttributes<HTMLElement>> & UniversalCopyPasteProps<T> & T) {\n // const vault = useVault();\n const Component = (as || \"div\") as any;\n\n const onDropReference = _onDropReference || onReference;\n const onDropLink = _onDropLink || onLink;\n const onDropAnalysis = _onDropAnalysis || onAnalysis;\n const onPasteReference = _onPasteReference || onReference;\n const onPasteLink = _onPasteLink || onLink;\n const onPasteAnalysis = _onPasteAnalysis || onAnalysis;\n\n const reference = useMemo(() => {\n return _ref;\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [_ref?.id, _ref?.type]);\n\n const onCopy = useCallback(\n function onCopy(e: ClipboardEvent) {\n if (e.defaultPrevented) {\n return;\n }\n e.preventDefault();\n if (e.clipboardData) {\n if (reference && reference.id && reference.type) {\n // const full = vault.get(reference);\n // if (full) {\n // e.clipboardData.setData(\"application/json\", JSON.stringify(vault.toPresentation3(vault.get(reference))));\n // }\n\n e.clipboardData.setData(\n \"application/json+vault\",\n JSON.stringify({\n id: reference.id,\n type: reference.type,\n })\n );\n }\n }\n },\n [reference]\n );\n\n const onPaste = useCallback(async function onPaste(e: ClipboardEvent) {\n if (e.defaultPrevented) {\n return;\n }\n e.preventDefault();\n if (e.clipboardData) {\n if (props.onLoading) {\n props.onLoading();\n }\n\n if (onPasteReference) {\n const data = e.clipboardData.getData(\"application/json+vault\");\n if (data) {\n try {\n const dataAsJson = JSON.parse(data);\n if (dataAsJson && dataAsJson.id && dataAsJson.type) {\n onPasteReference(dataAsJson);\n }\n } catch (e) {\n // ignore.\n }\n }\n }\n\n if (onPasteLink || onPasteAnalysis) {\n const data = e.clipboardData.getData(\"text\");\n if (data.startsWith(\"http\")) {\n const allLinks = data.split(\"\\n\");\n for (const link of allLinks) {\n if (onPasteAnalysis) {\n try {\n const result = await analyse(link);\n if (result) {\n onPasteAnalysis(result);\n continue;\n }\n } catch (e) {\n // let it fallback to onPasteLink\n }\n }\n if (onPasteLink) {\n onPasteLink(link);\n }\n }\n }\n }\n if (props.onComplete) {\n props.onComplete();\n }\n }\n }, []);\n\n // @todo not working..\n const onDragStart = useCallback(function onPaste(e: DragEvent) {\n if (e.defaultPrevented) {\n return;\n }\n e.preventDefault();\n if (e.dataTransfer && props.draggable) {\n e.dataTransfer.effectAllowed = \"all\";\n\n if (reference && reference.id && reference.type) {\n e.dataTransfer.setData(\n \"application/json+vault\",\n JSON.stringify({\n id: reference.id,\n type: reference.type,\n })\n );\n }\n }\n }, []);\n\n const onDrop = useCallback(async function onDrop(e: DragEvent) {\n e.preventDefault();\n if (e.dataTransfer) {\n if (onDropReference) {\n const data = e.dataTransfer.getData(\"application/json+vault\");\n if (data) {\n try {\n const dataAsJson = JSON.parse(data);\n if (dataAsJson && dataAsJson.id && dataAsJson.type) {\n onDropReference(dataAsJson, e);\n }\n } catch (e) {\n // ignore.\n return;\n }\n }\n }\n const json = e.dataTransfer.getData(\"application/json\");\n if (json) {\n const parsed = JSON.parse(json);\n // @todo this could be raw JSON or a Content State.\n return;\n }\n const link = e.dataTransfer.getData(\"text/plain\");\n if (link) {\n // console.log(\"link\", link);\n return;\n }\n }\n }, []);\n\n const onDragOver = useCallback((e: DragEvent) => {\n e.preventDefault();\n if (e.dataTransfer) {\n e.dataTransfer.dropEffect = \"copy\";\n }\n }, []);\n\n return (\n <Component\n onCopy={onCopy}\n onPaste={onPaste}\n onDrop={onDrop}\n onDragOver={onDragOver}\n onDragStart={onDragStart}\n tabIndex={-1}\n {...props}\n />\n );\n}\n"],"x_google_ignoreList":[0],"mappings":"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"}
1
+ {"version":3,"file":"index.cjs","names":["DEFAULT_CONFIG: Config","next: Config[\"editorConfig\"]","apps: NonNullable<Config[\"plugins\"]>[\"apps\"]","merged: Partial<Config>","resolvedConfig: Config","config","getResourceId","statuses: Record<string, CanvasProgressStatus>","statusConfig: Record<\n CanvasProgressActiveStatus,\n { label: string; stripClass: string; badgeClass: string; dimOverlay?: boolean }\n>","CheckIcon","uniqueExtensions: BackgroundActionDefinition[]","groups: BackgroundActionGroup[]","context: BackgroundActionContext","prefix","events","instances: Record<string, BackgroundActionInstance>","histories: Record<string, BackgroundActionInstance[]>","plans: Record<string, BackgroundActionPlan>","persistence: BackgroundActionPersistence | null","persistenceKey: BackgroundActionPersistenceKey | null","persistTimer: ReturnType<typeof setTimeout> | null","log: BackgroundActionLogEntry","defaultPersistence: BackgroundActionPersistence | null | undefined","responseData: ManifestNormalized | undefined","extensionListKeys: ExtensionListKey[]","emptyPluginState: PluginStoreSnapshot","apps: Record<string, PluginAppConfig>","plugin: MappedPlugin","enabled: MappedPlugin[]","enabledIds: string[]","blocked: string[]","next: T[]","next: AppExtension","unique","nextGlobalConfig: Config[\"plugins\"]","Container","Header","IconButton","CloseIcon: React.FC<{\n inline?: boolean;\n height?: number;\n className?: string;\n}>","VaultProvider","ManifestContext","CollectionContext","map: Record<string, PreviewHandler>","providesMap: Record<string, string>","providesMap","context: any","handlers: PreviewHandler[]","PreviewProvider","context: PreviewContext","DownloadButton","config","defaultState: EditingStackState","EditorInstance","defaultState","create","FLAG_TAG: ManifestEditorTag","EMPTY_TAGS: ManifestEditorTag[]","add: ToastApi[\"add\"]","ToastRegion","Fragment","context: BackgroundActionContext","logLevelConfig: Record<string, { label: string; className: string }>","milestoneEventBadgeClass: Record<string, string>","statusColourMap: Record<string, string>","tabs: Array<{ id: DetailsTab; label: string; count?: number }>","Modal","BackgroundActionMenuProgressBar","BackgroundActionMenuRoot","BackgroundActionMenuButton","BackgroundActionMenuPanel","BackgroundActionMenuDivider","BackgroundActionMenuSection","BackgroundActionMenuItem","BackgroundActionMenuTrigger","BackgroundActionMenuText","BackgroundActionMenuLabel","BackgroundActionMenuMeta","BackgroundActionMenuInlineAction","BackgroundActionMenuInfoButton","AppHeader","Header","Container","ManifestEditorLogo","AtlasStoreReactContext","getImage","IIIFVault","e: any","BackIcon: React.FC<{ style?: any }>","PaddedSidebarContainer","ErrorMessage","ReactVaultContext","BackIcon","ErrorBoundary","Vault","toDispatch: any","Vault","VaultProvider","create","Creator","RenderCreator","options: CreatorOptions","err: any","ErrorMessage","Spinner","EmptyState","ActionButton","Suspense","ModalBackSlot","IconButton","GridIcon","CreatorGrid","baseCreator: LayoutPanel","Tabs","TabList","Tab","TabPanel","ThemeProvider","BackIcon","sortKeys: string[]","sortKeyFallbacks: Record<string, EditorDefinition>","ResourceReactContext","resourceConfig: EditorConfig","resource","SidebarTabs","baseEditor: LayoutPanel","error","CheckIcon","Modal","Sidebar","SidebarHeader","SidebarContent","Form","ActionButton","seenIds: string[]","sectionMap: Record<string, ContextMenuItem[]>","emptySections: ContextMenuItem[]","returnSections: Array<{ sectionTitle?: string; items: Array<ContextMenuItem> }>","$","noop","onKeyDown: KeyboardEventHandler<HTMLDivElement>","AccordionItem","onScroll: UIEventHandler<HTMLDivElement>","getValue","HandleControls","Tooltip","TooltipTrigger","DefaultTooltipContent","IconHandle","ResetIcon","ResizeHandle","$","Main","CenterPanel","LeftPanel","CenterPanel","PanelSideMenu","FocusedLayout","ReactVaultContext","state","Fragment","previousValues: Array<[string, string]>","F.PanelSwitcher","Tooltip","TooltipTrigger","F.PanelSwitchButton","DefaultTooltipContent","F.PanelSwitchGroup","F.PanelSwitchDivider","Modal","L.PanelContainer","L.PanelMenu","L.PanelContent","ErrorBoundary","F.LoadingCenter","F.FloatingPanelBody","L.OuterWrapper","L.Header","F.Main","F.CenterPanel","F.FloatingPanel","L.Footer","Layout","ReactVaultContext","state","Fragment","L.PanelContainer","L.PanelContent","L.PanelMenu","Modal","ErrorBoundary","L.OuterWrapper","L.Header","L.Main","M.Container","M.CenterPanel","M.MobileBar","M.LeftBarButton","M.DrawerContainer","M.DrawerButton","M.PreviewBarButton","M.DrawerBody","M.LeftPanel","M.Lightbox","PanelSideMenu","Transition","L.LeftPanel","L.CenterPanel","L.RightPanel","L.Footer","ArrowRightIcon","BackIcon","target: BridgeTarget","wrapped: RemoteVaultAction","Component","LayoutProvider","actions","state","toEdit: EditableResource","create","previewConfigs: PreviewConfiguration[]","ImageServiceLoader","ImageServiceLoaderContext","ThemeProvider","AtlasStoreProvider","emptyCounts: Record<SpecificationReportStatus, number>","value","rules: SpecificationRule[]","fixedValue: SpecificationJsonValue | undefined","fixedValueRule: SpecificationPropertyPolicy[\"fixedValueRule\"]","results: SpecificationReportItem[]","collected: CollectedResource[]","status: SpecificationReportStatus","children: unknown[]","serviceIds: string[]","ids: string[]","tempGlobalState: Record<string, Record<string, Task>>","res: (value: any) => void","rej: (reason?: any) => void","analyse","Component","onCopy","onPaste","e"],"sources":["../../../node_modules/.pnpm/tiny-invariant@1.3.3/node_modules/tiny-invariant/dist/esm/tiny-invariant.js","../src/ConfigContext/ConfigContext.tsx","../src/CanvasProgress.tsx","../src/BackgroundTasks/BackgroundTasksStore.ts","../src/helpers.ts","../src/PluginContext/PluginContext.helpers.ts","../src/PluginContext/PluginContext.store.ts","../src/PluginContext/PluginContext.tsx","../src/AppContext/AppContext.tsx","../src/AppContext/MultiAppContext.tsx","../src/AppHeader/AppHeader.styles.ts","../../ui/icons/CloseIcon.tsx","../../ui/icons/DownIcon.tsx","../src/AppResourceProvider/AppResourceProvider.tsx","../src/PreviewContext/previews/ExternalManifestUrlPreview.ts","../src/PreviewContext/previews/IIIFPreviewService.ts","../src/PreviewContext/PreviewContext.hooks.ts","../src/PreviewContext/PreviewContext.reducer.ts","../src/PreviewContext/PreviewContext.tsx","../../ui/atoms/Button.tsx","../src/PreviewButton/PreviewButton.styles.ts","../src/PreviewButton/PreviewButton.tsx","../src/EditingStack/EditingStack.reducer.ts","../src/EditingStack/EditingStack.tsx","../src/Layout/Layout.context.tsx","../src/Tags.tsx","../src/Toast/ToastContext.tsx","../src/BackgroundTasks/BackgroundActionToasts.helpers.ts","../src/BackgroundTasks/BackgroundActions.tsx","../src/AppHeader/AppHeader.tsx","../src/AppMenu/AppMenuContext.tsx","../src/AtlasStore/AtlasStoreProvider.tsx","../src/AtlasStore/polygon-to-bounding-box.ts","../src/analysis.ts","../src/highlighted-image-resources.ts","../../ui/icons/StarIcon.tsx","../../ui/icons/BackIcon.tsx","../src/Layout/components/PanelError.tsx","../src/Layout/Layout.helpers.ts","../../ui/atoms/Dropdown.tsx","../src/Layout/components/ModularPanel.tsx","../src/PreviewVault/create-preview-vault.ts","../src/PreviewVault/PreviewVault.tsx","../src/BaseCreator/BaseCreator.hooks.tsx","../src/BaseCreator/CreatorInitialData.tsx","../src/BaseCreator/BaseCreator.tsx","../src/BaseCreator/index.tsx","../src/ShellContext/default-theme.ts","../src/BaseCreator/BaseAnnotationCreator.tsx","../src/BaseEditor/BaseEditor.tsx","../src/BaseEditor/index.tsx","../src/hooks/use-decay-state.ts","../src/PluginContext/PluginManager.tsx","../src/ConfigContext/ConfigEditor.tsx","../src/ContextMenu/ContextMenuContext.tsx","../../ui/ui/CenterPanelContainer/CenterPanelContainer.module.css","../../ui/ui/CenterPanelContainer/CenterPanelContainer.tsx","../../ui/atoms/Accordion.tsx","../../ui/icons/DownloadIcon.tsx","../../ui/atoms/ButtonRow.tsx","../src/ExportPanel/ExportPanel.tsx","../src/hooks/use-annotation-creator-state.ts","../src/hooks/use-event.tsx","../src/hooks/use-match-media.ts","../src/hooks/use-save-vault.ts","../src/hooks/use-svg-tools.tsx","../src/Layout/components/HandleControls.tsx","../../ui/madoc/components/icons/Spinner.tsx","../../ui/ui/GhostBlocks/GhostBlocks.module.css","../../ui/ui/GhostBlocks/GhostBlocks.tsx","../../ui/madoc/use-event-handler.ts","../src/Layout/components/use-resize-layouts.tsx","../src/Layout/Layout.supports.ts","../src/Layout/Layout.focused.styles.ts","../src/Layout/Layout.styles.ts","../src/Layout/Layout.focused.tsx","../src/Layout/Layout.mobile.tsx","../src/Layout/Layout.tsx","../src/Layout/Layout.hooks.ts","../src/Layout/Layout.reducer.ts","../src/ManifestPaginationNavigation.tsx","../src/PreviewVault/vault-message-bridge.ts","../src/ResourceEditingContext/ResourceEditingContext.tsx","../../ui/atoms/ErrorBoundary.tsx","../src/Layout/Layout.context-internal.tsx","../src/ShellContext/ShellContext.tsx","../src/SpecificationContext/SpecificationContext.helpers.ts","../src/SpecificationContext/SpecificationContext.tsx","../src/TaskBridge/TaskBridge.tsx","../src/Universal/UniversalCopyPaste.tsx"],"sourcesContent":["var isProduction = process.env.NODE_ENV === 'production';\nvar prefix = 'Invariant failed';\nfunction invariant(condition, message) {\n if (condition) {\n return;\n }\n if (isProduction) {\n throw new Error(prefix);\n }\n var provided = typeof message === 'function' ? message() : message;\n var value = provided ? \"\".concat(prefix, \": \").concat(provided) : prefix;\n throw new Error(value);\n}\n\nexport { invariant as default };\n","import type { Collection } from \"@iiif/presentation-3\";\nimport {\n createContext,\n type ReactNode,\n useCallback,\n useContext,\n useMemo,\n useState,\n} from \"react\";\nimport type { PreviewConfiguration } from \"../PreviewContext/PreviewContext.types\";\n\nexport interface Config {\n // Previous configuration.\n previews: PreviewConfiguration[];\n behaviorPresets: string[];\n newTemplates: Collection | null;\n\n defaultPreview: string | null;\n\n editorConfig: {\n All?: EditorConfig;\n Manifest?: EditorConfig;\n Canvas?: EditorConfig;\n Annotation?: EditorConfig;\n AnnotationPage?: EditorConfig;\n AnnotationCollection?: EditorConfig;\n Range?: EditorConfig;\n Collection?: EditorConfig;\n ContentResource?: EditorConfig;\n // Collection inside collection.\n EmbeddedCollection?: EditorConfig;\n };\n\n editorFeatureFlags: {\n enableMultiImageCanvases?: boolean;\n enableMultiMediaCanvases?: boolean;\n rememberCanvasId?: boolean;\n rememberLeftPanelId?: boolean;\n annotationPopups?: boolean;\n manifestGridOptions?: boolean;\n };\n\n // Internationalisation options\n i18n: {\n defaultLanguage: string;\n availableLanguages: string[];\n advancedLanguageMode: boolean;\n textGranularityEnabled?: boolean;\n };\n\n // Options when exporting from Vault.\n export: {\n baseIdentifier: string | null;\n version: 3 | 2;\n };\n\n uploadBackends: Array<UploadBackendConfig>;\n\n plugins?: {\n apps?: Record<\n string,\n {\n enabled?: string[];\n disabled?: string[];\n settings?: Record<string, Record<string, unknown>> & Record<string, unknown>;\n }\n >;\n };\n}\n\nexport interface EditorConfig {\n singleTab?: string;\n fields?: string[];\n hideTabs?: string[];\n onlyTabs?: string[];\n}\n\nexport interface UploadBackendConfig {\n id: string;\n label: string;\n resourceTypes: string[];\n canUpload?: () => Promise<boolean>;\n upload: (resource: File) => Promise<{ id: string; type: string }> | null;\n}\n\nconst DEFAULT_CONFIG: Config = {\n previews: [],\n behaviorPresets: [\n \"auto-advance\",\n \"no-auto-advance\",\n \"repeat\",\n \"no-repeat\",\n \"unordered\",\n \"individuals\",\n \"continuous\",\n \"paged\",\n \"non-paged\",\n \"facing-pages\",\n \"multi-part\",\n \"together\",\n \"sequence\",\n \"thumbnail-nav\",\n \"no-nav\",\n \"hidden\",\n ],\n defaultPreview: null,\n editorConfig: {},\n newTemplates: null,\n i18n: {\n advancedLanguageMode: false,\n availableLanguages: [\"en\", \"cy\", \"nl\", \"fr\"],\n defaultLanguage: \"en\",\n },\n editorFeatureFlags: {\n enableMultiImageCanvases: true,\n enableMultiMediaCanvases: true,\n annotationPopups: false,\n rememberCanvasId: true,\n manifestGridOptions: false,\n rememberLeftPanelId: false,\n },\n uploadBackends: [],\n plugins: {\n apps: {},\n },\n export: {\n baseIdentifier: null,\n version: 3,\n },\n};\n\nfunction mergeEditorConfig(\n base: Config[\"editorConfig\"] | undefined,\n override: Config[\"editorConfig\"] | undefined,\n): Config[\"editorConfig\"] | undefined {\n if (!base && !override) return undefined;\n\n const next: Config[\"editorConfig\"] = { ...(base || {}) };\n for (const [key, value] of Object.entries(override || {})) {\n next[key as keyof Config[\"editorConfig\"]] = {\n ...((next as any)[key] || {}),\n ...(value || {}),\n };\n }\n return next;\n}\n\nfunction mergePluginConfig(\n base: Config[\"plugins\"] | undefined,\n override: Config[\"plugins\"] | undefined,\n): Config[\"plugins\"] | undefined {\n if (!base && !override) return undefined;\n\n const apps: NonNullable<Config[\"plugins\"]>[\"apps\"] = {\n ...(base?.apps || {}),\n };\n\n for (const [appId, appConfig] of Object.entries(override?.apps || {})) {\n const existing = apps[appId] || {};\n apps[appId] = {\n ...existing,\n ...appConfig,\n settings: {\n ...(existing.settings || {}),\n ...(appConfig.settings || {}),\n },\n };\n }\n\n return { apps };\n}\n\nexport function mergePartialConfig(\n ...configs: Array<Partial<Config> | null | undefined>\n): Partial<Config> {\n let merged: Partial<Config> = {};\n\n for (const config of configs) {\n if (!config) continue;\n\n merged = {\n ...merged,\n ...config,\n editorConfig: mergeEditorConfig(merged.editorConfig, config.editorConfig),\n editorFeatureFlags:\n merged.editorFeatureFlags || config.editorFeatureFlags\n ? {\n ...(merged.editorFeatureFlags || {}),\n ...(config.editorFeatureFlags || {}),\n }\n : undefined,\n i18n:\n merged.i18n || config.i18n\n ? {\n ...(merged.i18n || {}),\n ...(config.i18n || {}),\n } as Config[\"i18n\"]\n : undefined,\n export:\n merged.export || config.export\n ? {\n ...(merged.export || {}),\n ...(config.export || {}),\n } as Config[\"export\"]\n : undefined,\n plugins: mergePluginConfig(merged.plugins, config.plugins),\n };\n }\n\n return merged;\n}\n\nexport function mergeConfig(\n ...configs: Array<Partial<Config> | null | undefined>\n): Config {\n return mergePartialConfig(DEFAULT_CONFIG, ...configs) as Config;\n}\n\nexport const ConfigReactContext = createContext<Config>(DEFAULT_CONFIG);\nexport const SaveConfigReactContext = createContext<\n (config: Partial<Config>) => void\n>(() => {});\n\nexport function useConfig() {\n return useContext(ConfigReactContext);\n}\n\nexport function useSaveConfig() {\n return useContext(SaveConfigReactContext);\n}\n\nexport function ConfigProvider({\n children,\n config,\n saveConfig,\n}: {\n children: ReactNode;\n config?: Partial<Config>;\n saveConfig?: (config: Partial<Config>) => void;\n}) {\n const [runtimeConfig, setRuntimeConfig] = useState<Partial<Config> | null>(\n null,\n );\n const resolvedConfig: Config = useMemo(\n () => mergeConfig(config, runtimeConfig),\n [config, runtimeConfig],\n );\n\n const memoSaveConfig = useCallback(\n (config: Partial<Config>) => {\n setRuntimeConfig((existing) => mergePartialConfig(existing, config));\n if (saveConfig) {\n saveConfig(config);\n }\n },\n [saveConfig],\n );\n\n return (\n <SaveConfigReactContext.Provider value={memoSaveConfig}>\n <ConfigReactContext.Provider value={resolvedConfig}>\n {children}\n </ConfigReactContext.Provider>\n </SaveConfigReactContext.Provider>\n );\n}\n","import type { Vault } from \"@iiif/helpers/vault\";\nimport { useMemo } from \"react\";\nimport { useVault, useVaultSelector } from \"react-iiif-vault\";\n\nexport const CANVAS_PROGRESS_META_NAMESPACE = \"@manifest-editor/canvas-progress\";\nexport const CANVAS_PROGRESS_STATUS_META_KEY = \"status\";\n\nexport type CanvasProgressActiveStatus = \"queued\" | \"pending\" | \"done\";\nexport type CanvasProgressStatus = CanvasProgressActiveStatus | \"none\";\nexport type CanvasProgressStatusInput = CanvasProgressStatus | null | undefined;\n\nexport type CanvasProgressResource =\n | string\n | {\n id: string;\n type?: string;\n }\n | null\n | undefined;\n\nconst ACTIVE_STATUSES = new Set<CanvasProgressActiveStatus>([\"queued\", \"pending\", \"done\"]);\n\nfunction getResourceId(resource: CanvasProgressResource) {\n return typeof resource === \"string\" ? resource : resource?.id || null;\n}\n\nfunction normaliseCanvasProgressStatus(status: unknown): CanvasProgressStatus {\n return typeof status === \"string\" && ACTIVE_STATUSES.has(status as CanvasProgressActiveStatus)\n ? (status as CanvasProgressActiveStatus)\n : \"none\";\n}\n\nfunction isActiveCanvasProgressStatus(status: CanvasProgressStatusInput): status is CanvasProgressActiveStatus {\n return typeof status === \"string\" && ACTIVE_STATUSES.has(status as CanvasProgressActiveStatus);\n}\n\nexport function getCanvasProgressStatus(vault: Vault, resource: CanvasProgressResource): CanvasProgressStatus {\n const id = getResourceId(resource);\n if (!id) {\n return \"none\";\n }\n\n const meta = vault.getResourceMeta(id, CANVAS_PROGRESS_META_NAMESPACE) as\n | { [CANVAS_PROGRESS_STATUS_META_KEY]?: CanvasProgressStatus }\n | undefined;\n\n return normaliseCanvasProgressStatus(meta?.[CANVAS_PROGRESS_STATUS_META_KEY]);\n}\n\nexport function getCanvasProgressStatusFromState(state: any, resource: CanvasProgressResource): CanvasProgressStatus {\n const id = getResourceId(resource);\n if (!id) {\n return \"none\";\n }\n\n return normaliseCanvasProgressStatus(\n state?.iiif?.meta?.[id]?.[CANVAS_PROGRESS_META_NAMESPACE]?.[CANVAS_PROGRESS_STATUS_META_KEY],\n );\n}\n\nexport function setCanvasProgressStatus(\n vault: Vault,\n resource: CanvasProgressResource,\n status: CanvasProgressStatusInput,\n): CanvasProgressStatus {\n const id = getResourceId(resource);\n if (!id) {\n return \"none\";\n }\n\n const nextStatus = isActiveCanvasProgressStatus(status) ? status : undefined;\n vault.setMetaValue([id, CANVAS_PROGRESS_META_NAMESPACE, CANVAS_PROGRESS_STATUS_META_KEY], nextStatus);\n return nextStatus || \"none\";\n}\n\nexport function clearCanvasProgressStatus(vault: Vault, resource: CanvasProgressResource): CanvasProgressStatus {\n return setCanvasProgressStatus(vault, resource, \"none\");\n}\n\nexport function setCanvasProgressStatuses(\n vault: Vault,\n resources: CanvasProgressResource[],\n status: CanvasProgressStatusInput,\n): Record<string, CanvasProgressStatus> {\n const statuses: Record<string, CanvasProgressStatus> = {};\n\n for (const resource of resources) {\n const id = getResourceId(resource);\n if (!id) {\n continue;\n }\n\n statuses[id] = setCanvasProgressStatus(vault, resource, status);\n }\n\n return statuses;\n}\n\nexport function clearCanvasProgressStatuses(\n vault: Vault,\n resources: CanvasProgressResource[],\n): Record<string, CanvasProgressStatus> {\n return setCanvasProgressStatuses(vault, resources, \"none\");\n}\n\nexport interface ManifestEditorCanvasProgressApi {\n getStatus(resource: CanvasProgressResource): CanvasProgressStatus;\n setStatus(resource: CanvasProgressResource, status: CanvasProgressStatusInput): CanvasProgressStatus;\n clearStatus(resource: CanvasProgressResource): CanvasProgressStatus;\n setStatuses(resources: CanvasProgressResource[], status: CanvasProgressStatusInput): Record<string, CanvasProgressStatus>;\n clearStatuses(resources: CanvasProgressResource[]): Record<string, CanvasProgressStatus>;\n}\n\nexport function createManifestEditorCanvasProgressApi(vault: Vault): ManifestEditorCanvasProgressApi {\n return {\n getStatus(resource) {\n return getCanvasProgressStatus(vault, resource);\n },\n setStatus(resource, status) {\n return setCanvasProgressStatus(vault, resource, status);\n },\n clearStatus(resource) {\n return clearCanvasProgressStatus(vault, resource);\n },\n setStatuses(resources, status) {\n return setCanvasProgressStatuses(vault, resources, status);\n },\n clearStatuses(resources) {\n return clearCanvasProgressStatuses(vault, resources);\n },\n };\n}\n\nexport function createTrackingCanvasProgressApi(\n baseApi: ManifestEditorCanvasProgressApi,\n trackedResourceIds = new Set<string>(),\n): ManifestEditorCanvasProgressApi & { clearTrackedStatuses(): void; trackedResourceIds: Set<string> } {\n function track(resource: CanvasProgressResource) {\n const id = getResourceId(resource);\n if (id) {\n trackedResourceIds.add(id);\n }\n }\n\n function trackMany(resources: CanvasProgressResource[]) {\n for (const resource of resources) {\n track(resource);\n }\n }\n\n return {\n trackedResourceIds,\n getStatus(resource) {\n return baseApi.getStatus(resource);\n },\n setStatus(resource, status) {\n track(resource);\n return baseApi.setStatus(resource, status);\n },\n clearStatus(resource) {\n track(resource);\n return baseApi.clearStatus(resource);\n },\n setStatuses(resources, status) {\n trackMany(resources);\n return baseApi.setStatuses(resources, status);\n },\n clearStatuses(resources) {\n trackMany(resources);\n return baseApi.clearStatuses(resources);\n },\n clearTrackedStatuses() {\n baseApi.clearStatuses(Array.from(trackedResourceIds).map((id) => ({ id, type: \"Canvas\" })));\n trackedResourceIds.clear();\n },\n };\n}\n\nexport function useCanvasProgressStatus(resource: CanvasProgressResource): CanvasProgressStatus {\n const resourceId = getResourceId(resource);\n\n return useVaultSelector((state) => {\n if (!resourceId) {\n return \"none\";\n }\n return getCanvasProgressStatusFromState(state, resourceId);\n }, [resourceId]);\n}\n\nexport function useCanvasProgressActions(resource: CanvasProgressResource) {\n const vault = useVault();\n const resourceId = getResourceId(resource);\n const progressActions = useMemo(() => createManifestEditorCanvasProgressApi(vault), [vault]);\n\n return useMemo(\n () => ({\n setStatus(status: CanvasProgressStatusInput) {\n return progressActions.setStatus(resourceId, status);\n },\n clearStatus() {\n return progressActions.clearStatus(resourceId);\n },\n getStatus() {\n return progressActions.getStatus(resourceId);\n },\n }),\n [progressActions, resourceId],\n );\n}\n\nconst statusConfig: Record<\n CanvasProgressActiveStatus,\n { label: string; stripClass: string; badgeClass: string; dimOverlay?: boolean }\n> = {\n queued: {\n label: \"Queued\",\n stripClass: \"bg-zinc-400/80\",\n badgeClass: \"bg-zinc-500\",\n dimOverlay: true,\n },\n pending: {\n label: \"In progress\",\n stripClass: \"bg-amber-400/90 animate-pulse\",\n badgeClass: \"bg-amber-500\",\n },\n done: {\n label: \"Done\",\n stripClass: \"bg-me-primary-500\",\n badgeClass: \"bg-me-primary-500\",\n },\n};\n\nfunction QueuedIcon({ className }: { className?: string }) {\n return (\n <svg className={className} viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2.5\" strokeLinecap=\"round\" strokeLinejoin=\"round\">\n <circle cx=\"12\" cy=\"12\" r=\"9\" />\n <path d=\"M12 7v5l2.5 2.5\" />\n </svg>\n );\n}\n\nfunction SpinnerIcon({ className }: { className?: string }) {\n return (\n <svg className={className} viewBox=\"0 0 24 24\" fill=\"none\">\n <circle cx=\"12\" cy=\"12\" r=\"9\" stroke=\"currentColor\" strokeWidth=\"2.5\" strokeOpacity=\"0.3\" />\n <path d=\"M12 3a9 9 0 0 1 9 9\" stroke=\"currentColor\" strokeWidth=\"2.5\" strokeLinecap=\"round\" />\n </svg>\n );\n}\n\nfunction CheckIcon({ className }: { className?: string }) {\n return (\n <svg className={className} viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" strokeWidth=\"2.5\" strokeLinecap=\"round\" strokeLinejoin=\"round\">\n <path d=\"M5 12l4 4 8-8\" />\n </svg>\n );\n}\n\nexport function ManifestEditorCanvasProgressOverlay({\n resource,\n status,\n className,\n}: {\n resource?: CanvasProgressResource;\n status?: CanvasProgressStatus;\n className?: string;\n}) {\n if (status) {\n return <ManifestEditorCanvasProgressOverlayContent status={status} className={className} />;\n }\n\n return <ManifestEditorResourceCanvasProgressOverlay resource={resource} className={className} />;\n}\n\nfunction ManifestEditorResourceCanvasProgressOverlay({\n resource,\n className,\n}: {\n resource?: CanvasProgressResource;\n className?: string;\n}) {\n const status = useCanvasProgressStatus(resource);\n\n return <ManifestEditorCanvasProgressOverlayContent status={status} className={className} />;\n}\n\nfunction ManifestEditorCanvasProgressOverlayContent({\n status,\n className,\n}: {\n status: CanvasProgressStatus;\n className?: string;\n}) {\n if (status === \"none\") {\n return null;\n }\n\n const config = statusConfig[status];\n\n return (\n <>\n {/* Dim overlay for queued — signals \"waiting, not yet active\" */}\n {config.dimOverlay && (\n <div aria-hidden=\"true\" className=\"pointer-events-none absolute inset-0 z-10 bg-white/40\" />\n )}\n {/* Full-width coloured strip at top edge */}\n <div\n aria-hidden=\"true\"\n className={`pointer-events-none absolute inset-x-0 top-0 z-10 h-[3px] rounded-t-sm ${config.stripClass} ${className || \"\"}`}\n />\n {/* Icon badge — top-right corner, doesn't conflict with tag overlay (top-left) */}\n <div\n className={`pointer-events-none absolute right-1.5 top-1.5 z-10 flex h-[18px] w-[18px] items-center justify-center rounded-full ${config.badgeClass} shadow-md ring-2 ring-white/70`}\n title={config.label}\n >\n <span className=\"sr-only\">{config.label}</span>\n {status === \"queued\" && <QueuedIcon className=\"h-2.5 w-2.5 text-white\" />}\n {status === \"pending\" && <SpinnerIcon className=\"h-2.5 w-2.5 animate-spin text-white\" />}\n {status === \"done\" && <CheckIcon className=\"h-2.5 w-2.5 text-white\" />}\n </div>\n </>\n );\n}\n","import localforage from \"localforage\";\nimport {\n createContext,\n createElement,\n type ReactNode,\n useContext,\n useEffect,\n useMemo,\n} from \"react\";\nimport { createStore, type StoreApi, useStore } from \"zustand\";\nimport { useApp, useAppInstance } from \"../AppContext/AppContext\";\nimport {\n createTrackingCanvasProgressApi,\n type ManifestEditorCanvasProgressApi,\n} from \"../CanvasProgress\";\nimport type {\n BackgroundActionContext,\n BackgroundActionDefinition,\n BackgroundActionError,\n BackgroundActionEvent,\n BackgroundActionEventType,\n BackgroundActionGroup,\n BackgroundActionInstance,\n BackgroundActionLogEntry,\n BackgroundActionLogLevel,\n BackgroundActionPersistence,\n BackgroundActionPersistenceKey,\n BackgroundActionPersistedState,\n BackgroundActionPlan,\n BackgroundActionProgress,\n BackgroundActionProgressInput,\n BackgroundActionRunContext,\n BackgroundActionStatus,\n BackgroundActionTarget,\n BackgroundActionTask,\n BackgroundActionTaskRunOptions,\n BackgroundActionTaskRunResult,\n BackgroundActionTaskStatus,\n BackgroundActionTasksApi,\n BackgroundActionSystemContext,\n} from \"./BackgroundTasks.types\";\n\nexport interface BackgroundActionsStore {\n definitions: BackgroundActionDefinition[];\n instances: Record<string, BackgroundActionInstance>;\n histories: Record<string, BackgroundActionInstance[]>;\n plans: Record<string, BackgroundActionPlan>;\n controllers: Record<string, AbortController>;\n hasHydrated: boolean;\n setDefinitions(definitions: BackgroundActionDefinition[]): void;\n setPersistence(\n persistence: BackgroundActionPersistence | null,\n key: BackgroundActionPersistenceKey | null,\n ): void;\n hydrate(snapshot?: BackgroundActionPersistedState | null): void;\n persist(immediate?: boolean): void;\n flushPersistence(): Promise<void>;\n registerAction(definition: BackgroundActionDefinition): () => void;\n unregisterAction(id: string): void;\n resetAction(instanceKey: string): void;\n startAction(\n instanceKey: string,\n definition: BackgroundActionDefinition,\n target: BackgroundActionTarget,\n controller?: AbortController,\n ): void;\n resumeAction(instanceKey: string, controller: AbortController): void;\n cancelAction(instanceKey: string): void;\n setActionLabel(instanceKey: string, label: string): void;\n setActionStatus(\n instanceKey: string,\n status: BackgroundActionStatus,\n statusText?: string,\n ): void;\n setActionError(\n instanceKey: string,\n error: unknown,\n statusText?: string,\n ): void;\n appendActionLog(\n instanceKey: string,\n message: string,\n level?: BackgroundActionLogLevel,\n data?: unknown,\n ): void;\n setActionProgress(\n instanceKey: string,\n progress: BackgroundActionProgressInput | null,\n ): void;\n setResult(instanceKey: string, result: unknown): void;\n setResultsAvailable(instanceKey: string, available: boolean): void;\n setActionPlan(instanceKey: string, plan: BackgroundActionPlan): void;\n updateActionTask(\n instanceKey: string,\n taskId: string,\n patch: Partial<BackgroundActionTask>,\n persistImmediately?: boolean,\n ): void;\n}\n\nexport interface RunBackgroundActionOptions {\n store: StoreApi<BackgroundActionsStore>;\n context: BackgroundActionContext;\n signal?: AbortSignal;\n resume?: boolean;\n prepareData?: unknown;\n}\n\nexport interface GetAvailableBackgroundActionGroupsOptions {\n definitions: BackgroundActionDefinition[];\n instances: Record<string, BackgroundActionInstance>;\n systemContext: BackgroundActionSystemContext;\n targets: BackgroundActionTarget[];\n onSupportsError?: (\n definition: BackgroundActionDefinition,\n error: unknown,\n ) => void;\n}\n\nexport function getBackgroundActionInstanceKey(\n actionId: string,\n target: BackgroundActionTarget,\n) {\n return `${actionId}::${target.type}::${target.id}`;\n}\n\nexport function mergeBackgroundActionDefinitions(\n base: BackgroundActionDefinition[] = [],\n extensions: BackgroundActionDefinition[] = [],\n) {\n const uniqueExtensions: BackgroundActionDefinition[] = [];\n const extensionIds = new Set<string>();\n\n for (let index = extensions.length - 1; index >= 0; index -= 1) {\n const definition = extensions[index];\n if (definition && !extensionIds.has(definition.id)) {\n extensionIds.add(definition.id);\n uniqueExtensions.unshift(definition);\n }\n }\n\n return [\n ...base.filter((definition) => !extensionIds.has(definition.id)),\n ...uniqueExtensions,\n ];\n}\n\nexport function sortBackgroundActionDefinitions(\n definitions: BackgroundActionDefinition[],\n) {\n return [...definitions].sort((a, b) => {\n const section = (a.section || \"\").localeCompare(b.section || \"\");\n if (section !== 0) return section;\n\n const order = (a.order || 0) - (b.order || 0);\n if (order !== 0) return order;\n\n const label = a.label.localeCompare(b.label);\n if (label !== 0) return label;\n\n return a.id.localeCompare(b.id);\n });\n}\n\nexport function normaliseBackgroundActionError(\n error: unknown,\n): BackgroundActionError {\n if (error instanceof Error) {\n return {\n message: error.message,\n stack: error.stack,\n detail: error,\n };\n }\n\n return {\n message: typeof error === \"string\" ? error : \"Background action failed\",\n detail: error,\n };\n}\n\nfunction normaliseStoredBackgroundActionError(\n error: unknown,\n): BackgroundActionError {\n if (\n error &&\n typeof error === \"object\" &&\n typeof (error as BackgroundActionError).message === \"string\"\n ) {\n return {\n message: (error as BackgroundActionError).message,\n stack:\n typeof (error as BackgroundActionError).stack === \"string\"\n ? (error as BackgroundActionError).stack\n : undefined,\n detail: (error as BackgroundActionError).detail,\n };\n }\n\n return normaliseBackgroundActionError(error);\n}\n\nfunction supportsTarget(\n definition: BackgroundActionDefinition,\n target: BackgroundActionTarget,\n) {\n if (!definition.resourceTypes?.length) {\n return true;\n }\n\n return definition.resourceTypes.includes(target.type);\n}\n\nexport function getAvailableBackgroundActionGroups({\n definitions,\n instances,\n systemContext,\n targets,\n onSupportsError,\n}: GetAvailableBackgroundActionGroupsOptions): BackgroundActionGroup[] {\n const sortedDefinitions = sortBackgroundActionDefinitions(definitions);\n const groups: BackgroundActionGroup[] = [];\n\n for (const target of targets) {\n const actions = [];\n\n for (const definition of sortedDefinitions) {\n if (!supportsTarget(definition, target)) {\n continue;\n }\n\n const instanceKey = getBackgroundActionInstanceKey(definition.id, target);\n const context: BackgroundActionContext = {\n ...systemContext,\n definition,\n target,\n instanceKey,\n instance: instances[instanceKey],\n };\n\n try {\n if (definition.supports && !definition.supports(context)) {\n continue;\n }\n } catch (error) {\n onSupportsError?.(definition, error);\n continue;\n }\n\n actions.push({\n definition,\n target,\n instanceKey,\n instance: instances[instanceKey],\n context,\n });\n }\n\n if (actions.length) {\n groups.push({\n id: `${target.scope}:${target.type}:${target.id}`,\n label: target.label,\n target,\n actions,\n });\n }\n }\n\n return groups;\n}\n\nlet backgroundActionEntryCounter = 0;\n\nfunction createBackgroundActionEntryId(prefix: string) {\n backgroundActionEntryCounter += 1;\n return `${prefix}-${Date.now()}-${backgroundActionEntryCounter}`;\n}\n\nfunction createBackgroundActionEvent(\n type: BackgroundActionEventType,\n message?: string,\n data?: unknown,\n createdAt = Date.now(),\n): BackgroundActionEvent {\n return {\n id: createBackgroundActionEntryId(\"event\"),\n createdAt,\n type,\n message,\n data,\n };\n}\n\nfunction appendEvent(\n instance: BackgroundActionInstance,\n type: BackgroundActionEventType,\n message?: string,\n data?: unknown,\n createdAt = Date.now(),\n) {\n return {\n ...instance,\n events: [\n ...instance.events,\n createBackgroundActionEvent(type, message, data, createdAt),\n ],\n };\n}\n\nfunction withoutProgressEvents(\n events: BackgroundActionEvent[],\n): BackgroundActionEvent[] {\n return events.filter((event) => String(event.type) !== \"progress\");\n}\n\nfunction cloneInstanceForHistory(\n instance: BackgroundActionInstance,\n): BackgroundActionInstance {\n return {\n ...instance,\n logs: [...instance.logs],\n events: withoutProgressEvents(instance.events),\n progress: instance.progress ? { ...instance.progress } : undefined,\n };\n}\n\nfunction upsertHistoryInstance(\n histories: Record<string, BackgroundActionInstance[]>,\n instanceKey: string,\n instance: BackgroundActionInstance,\n) {\n if (!isCompletedStatus(instance.status)) {\n return histories;\n }\n\n const history = histories[instanceKey] || [];\n const snapshot = cloneInstanceForHistory(instance);\n const existingIndex = history.findIndex(\n (item) => item.runId === instance.runId,\n );\n const nextHistory =\n existingIndex >= 0\n ? history.map((item, index) =>\n index === existingIndex ? snapshot : item,\n )\n : [...history, snapshot];\n\n return {\n ...histories,\n [instanceKey]: nextHistory,\n };\n}\n\nfunction updateStoredInstance(\n state: Pick<BackgroundActionsStore, \"instances\" | \"histories\">,\n instanceKey: string,\n updater: (instance: BackgroundActionInstance) => BackgroundActionInstance,\n) {\n const instance = state.instances[instanceKey];\n if (!instance) {\n return {\n instances: state.instances,\n histories: state.histories,\n };\n }\n\n const updated = updater(instance);\n const instances = {\n ...state.instances,\n [instanceKey]: updated,\n };\n\n return {\n instances,\n histories: upsertHistoryInstance(state.histories, instanceKey, updated),\n };\n}\n\nfunction clampProgressPercent(percent: number) {\n if (!Number.isFinite(percent)) {\n return 0;\n }\n\n return Math.min(100, Math.max(0, percent));\n}\n\nfunction normaliseProgress(\n progress: BackgroundActionProgressInput,\n): BackgroundActionProgress {\n const input = progress as {\n percent?: number;\n current?: number;\n total?: number;\n label?: string;\n };\n const current =\n typeof input.current === \"number\" && Number.isFinite(input.current)\n ? input.current\n : undefined;\n const total =\n typeof input.total === \"number\" && Number.isFinite(input.total)\n ? input.total\n : undefined;\n const percent =\n typeof input.percent === \"number\" && Number.isFinite(input.percent)\n ? input.percent\n : typeof current === \"number\" && typeof total === \"number\" && total > 0\n ? (current / total) * 100\n : 0;\n\n return {\n percent: clampProgressPercent(percent),\n current,\n total,\n label: input.label,\n };\n}\n\nfunction isActiveStatus(status: BackgroundActionStatus) {\n return status === \"preparing\" || status === \"running\";\n}\n\nfunction isCompletedStatus(status: BackgroundActionStatus) {\n return status === \"complete\" || status === \"error\" || status === \"cancelled\";\n}\n\nfunction isTaskStatus(status: unknown): status is BackgroundActionTaskStatus {\n return (\n status === \"queued\" ||\n status === \"running\" ||\n status === \"complete\" ||\n status === \"skipped\" ||\n status === \"error\" ||\n status === \"cancelled\"\n );\n}\n\nfunction isPendingTaskStatus(status: BackgroundActionTaskStatus | undefined) {\n return !status || status === \"queued\" || status === \"running\";\n}\n\nfunction isTerminalTaskStatus(status: BackgroundActionTaskStatus | undefined) {\n return (\n status === \"complete\" ||\n status === \"skipped\" ||\n status === \"error\" ||\n status === \"cancelled\"\n );\n}\n\nfunction toJsonValue<T>(value: T): T | undefined {\n if (typeof value === \"undefined\") {\n return undefined;\n }\n\n try {\n return JSON.parse(JSON.stringify(value)) as T;\n } catch {\n return undefined;\n }\n}\n\nfunction serialiseError(\n error: BackgroundActionError | null | undefined,\n): BackgroundActionError | null | undefined {\n if (!error) {\n return error;\n }\n\n return {\n message: error.message,\n stack: error.stack,\n detail: toJsonValue(error.detail),\n };\n}\n\nfunction serialiseInstance(\n instance: BackgroundActionInstance,\n): BackgroundActionInstance {\n return {\n ...instance,\n error: serialiseError(instance.error) || null,\n result: toJsonValue(instance.result),\n logs: instance.logs.map((log) => ({\n ...log,\n data: toJsonValue(log.data),\n })),\n events: withoutProgressEvents(instance.events).map((event) => ({\n ...event,\n data: toJsonValue(event.data),\n })),\n progress: instance.progress ? { ...instance.progress } : undefined,\n };\n}\n\nfunction serialiseTask(task: BackgroundActionTask): BackgroundActionTask {\n return {\n ...task,\n status: normaliseTaskStatus(task.status),\n input: toJsonValue(task.input),\n result: toJsonValue(task.result),\n error: serialiseError(task.error) || null,\n };\n}\n\nfunction serialisePlan(plan: BackgroundActionPlan): BackgroundActionPlan {\n return {\n version: 1,\n data: toJsonValue(plan.data),\n tasks: plan.tasks.map(serialiseTask),\n };\n}\n\nfunction createPersistedState(\n state: BackgroundActionsStore,\n): BackgroundActionPersistedState {\n return {\n version: 1,\n savedAt: Date.now(),\n instances: Object.fromEntries(\n Object.entries(state.instances).map(([key, instance]) => [\n key,\n serialiseInstance(instance),\n ]),\n ),\n histories: Object.fromEntries(\n Object.entries(state.histories).map(([key, history]) => [\n key,\n history.map(serialiseInstance),\n ]),\n ),\n plans: Object.fromEntries(\n Object.entries(state.plans).map(([key, plan]) => [\n key,\n serialisePlan(plan),\n ]),\n ),\n };\n}\n\nfunction createEmptyPersistedState(): BackgroundActionPersistedState {\n return {\n version: 1,\n savedAt: Date.now(),\n instances: {},\n histories: {},\n plans: {},\n };\n}\n\nfunction mergePersistedStates(\n deferred: BackgroundActionPersistedState,\n current: BackgroundActionPersistedState,\n): BackgroundActionPersistedState {\n return {\n version: 1,\n savedAt: current.savedAt,\n instances: {\n ...deferred.instances,\n ...current.instances,\n },\n histories: {\n ...deferred.histories,\n ...current.histories,\n },\n plans: {\n ...deferred.plans,\n ...current.plans,\n },\n };\n}\n\nfunction persistedStateIsEmpty(state: BackgroundActionPersistedState) {\n return (\n !Object.keys(state.instances).length &&\n !Object.keys(state.histories).length &&\n !Object.keys(state.plans).length\n );\n}\n\nfunction normaliseTaskStatus(status: unknown): BackgroundActionTaskStatus {\n return isTaskStatus(status) ? status : \"queued\";\n}\n\nfunction normaliseTask(\n task: BackgroundActionTask,\n fallbackIndex: number,\n): BackgroundActionTask {\n const now = Date.now();\n const id =\n typeof task.id === \"string\" && task.id\n ? task.id\n : `task-${fallbackIndex + 1}`;\n return {\n ...task,\n id,\n label: typeof task.label === \"string\" && task.label ? task.label : id,\n status: normaliseTaskStatus(task.status),\n error: task.error ? normaliseStoredBackgroundActionError(task.error) : null,\n createdAt: typeof task.createdAt === \"number\" ? task.createdAt : now,\n };\n}\n\nfunction normalisePlan(\n plan: BackgroundActionPlan | undefined | null,\n): BackgroundActionPlan | null {\n if (!plan || plan.version !== 1 || !Array.isArray(plan.tasks)) {\n return null;\n }\n\n return {\n version: 1,\n data: plan.data,\n tasks: plan.tasks.map(normaliseTask),\n };\n}\n\nfunction requeueActivePlanTasks(\n plan: BackgroundActionPlan,\n): BackgroundActionPlan {\n return {\n ...plan,\n tasks: plan.tasks.map((task) =>\n task.status === \"running\"\n ? {\n ...task,\n status: \"queued\",\n statusText: \"Queued after reload\",\n startedAt: undefined,\n }\n : task,\n ),\n };\n}\n\nfunction cancelPendingPlanTasks(\n plan: BackgroundActionPlan,\n completedAt = Date.now(),\n): BackgroundActionPlan {\n return {\n ...plan,\n tasks: plan.tasks.map((task) =>\n isPendingTaskStatus(task.status)\n ? {\n ...task,\n status: \"cancelled\",\n statusText: \"Cancelled\",\n error: null,\n completedAt,\n }\n : task,\n ),\n };\n}\n\nfunction normaliseInstance(\n instance: BackgroundActionInstance,\n): BackgroundActionInstance {\n return {\n ...instance,\n error: instance.error\n ? normaliseStoredBackgroundActionError(instance.error)\n : null,\n logs: Array.isArray(instance.logs) ? instance.logs : [],\n events: withoutProgressEvents(\n Array.isArray(instance.events) ? instance.events : [],\n ),\n resultsAvailable: instance.resultsAvailable === true,\n };\n}\n\nfunction normalisePersistedState(\n snapshot?: BackgroundActionPersistedState | null,\n): BackgroundActionPersistedState {\n if (!snapshot || snapshot.version !== 1) {\n return createEmptyPersistedState();\n }\n\n return {\n version: 1,\n savedAt:\n typeof snapshot.savedAt === \"number\" ? snapshot.savedAt : Date.now(),\n instances: snapshot.instances || {},\n histories: snapshot.histories || {},\n plans: snapshot.plans || {},\n };\n}\n\nfunction restorePersistedInstance(\n instance: BackgroundActionInstance,\n plan: BackgroundActionPlan | null,\n definition: BackgroundActionDefinition,\n): {\n instance: BackgroundActionInstance;\n plan: BackgroundActionPlan | null;\n} {\n let nextInstance = instance;\n let nextPlan = plan;\n\n if (isActiveStatus(instance.status)) {\n if (instance.cancelRequestedAt) {\n const cancelledAt = Date.now();\n nextPlan = nextPlan\n ? cancelPendingPlanTasks(nextPlan, cancelledAt)\n : nextPlan;\n nextInstance = appendEvent(\n {\n ...instance,\n status: \"cancelled\",\n statusText: \"Cancelled\",\n completedAt: cancelledAt,\n cancelledAt,\n },\n \"status\",\n \"Cancelled\",\n { status: \"cancelled\" },\n cancelledAt,\n );\n } else if (definition.resumable && nextPlan) {\n nextPlan = requeueActivePlanTasks(nextPlan);\n nextInstance = appendEvent(\n {\n ...instance,\n status: \"running\",\n statusText: \"Resuming\",\n completedAt: undefined,\n cancelledAt: undefined,\n },\n \"status\",\n \"Resuming\",\n { status: \"running\" },\n );\n } else {\n const cancelledAt = Date.now();\n nextInstance = appendEvent(\n {\n ...instance,\n status: \"cancelled\",\n statusText: \"Interrupted by page reload\",\n completedAt: cancelledAt,\n cancelledAt,\n },\n \"status\",\n \"Interrupted by page reload\",\n { status: \"cancelled\" },\n cancelledAt,\n );\n }\n }\n\n return { instance: nextInstance, plan: nextPlan };\n}\n\nfunction restorePersistedState(\n snapshot: BackgroundActionPersistedState,\n definitions: BackgroundActionDefinition[],\n): {\n instances: Record<string, BackgroundActionInstance>;\n histories: Record<string, BackgroundActionInstance[]>;\n plans: Record<string, BackgroundActionPlan>;\n deferred: BackgroundActionPersistedState;\n} {\n const persisted = normalisePersistedState(snapshot);\n const definitionsById = new Map(\n definitions.map((definition) => [definition.id, definition]),\n );\n const instances: Record<string, BackgroundActionInstance> = {};\n let histories: Record<string, BackgroundActionInstance[]> = {};\n const plans: Record<string, BackgroundActionPlan> = {};\n const deferred = createEmptyPersistedState();\n\n for (const [key, history] of Object.entries(persisted.histories)) {\n const nextHistory = (Array.isArray(history) ? history : []).map(\n normaliseInstance,\n );\n const knownHistory = nextHistory.filter((instance) =>\n definitionsById.has(instance.actionId),\n );\n const deferredHistory = nextHistory.filter(\n (instance) => !definitionsById.has(instance.actionId),\n );\n\n if (knownHistory.length) {\n histories[key] = knownHistory;\n }\n\n if (deferredHistory.length) {\n deferred.histories[key] = deferredHistory;\n }\n }\n\n for (const [key, rawInstance] of Object.entries(persisted.instances)) {\n const instance = normaliseInstance(rawInstance);\n const plan = normalisePlan(persisted.plans[key]);\n const definition = definitionsById.get(instance.actionId);\n\n if (!definition) {\n deferred.instances[key] = serialiseInstance(instance);\n if (plan) {\n deferred.plans[key] = serialisePlan(plan);\n }\n continue;\n }\n\n const restored = restorePersistedInstance(instance, plan, definition);\n instances[key] = restored.instance;\n histories = upsertHistoryInstance(histories, key, restored.instance);\n\n if (restored.plan) {\n plans[key] = restored.plan;\n }\n }\n\n return { instances, histories, plans, deferred };\n}\n\nfunction getPlanProgress(\n plan: BackgroundActionPlan,\n label?: string,\n): BackgroundActionProgress | undefined {\n const total = plan.tasks.length;\n if (!total) {\n return undefined;\n }\n\n const current = plan.tasks.filter((task) =>\n isTerminalTaskStatus(task.status),\n ).length;\n return normaliseProgress({ current, total, label });\n}\n\nfunction getTaskRunResult(result: BackgroundActionTaskRunResult): {\n taskStatus: \"complete\" | \"skipped\";\n result: unknown;\n statusText?: string;\n} {\n if (\n result &&\n typeof result === \"object\" &&\n \"taskStatus\" in result &&\n ((result as any).taskStatus === \"complete\" ||\n (result as any).taskStatus === \"skipped\")\n ) {\n return {\n taskStatus: (result as any).taskStatus,\n result: (result as any).result,\n statusText: (result as any).statusText,\n };\n }\n\n return {\n taskStatus: \"complete\",\n result,\n };\n}\n\nfunction restoreCanvasProgressFromPlan(\n canvasProgress: ManifestEditorCanvasProgressApi,\n plan: BackgroundActionPlan,\n) {\n for (const task of plan.tasks) {\n if (!task.target || task.target.type !== \"Canvas\") {\n continue;\n }\n\n if (task.status === \"running\") {\n canvasProgress.setStatus(task.target, \"pending\");\n } else if (task.status === \"queued\") {\n canvasProgress.setStatus(task.target, \"queued\");\n }\n }\n}\n\nfunction createTaskApi(\n options: RunBackgroundActionOptions,\n signal: AbortSignal,\n canvasProgress: ManifestEditorCanvasProgressApi,\n): BackgroundActionTasksApi {\n const { store, context } = options;\n const { instanceKey } = context;\n\n function getPlan() {\n return store.getState().plans[instanceKey];\n }\n\n function getAll() {\n return getPlan()?.tasks || [];\n }\n\n function getPending(\n statuses: BackgroundActionTaskStatus[] = [\"queued\", \"running\"],\n ) {\n const allowed = new Set(statuses);\n return getAll().filter((task) =>\n allowed.has(normaliseTaskStatus(task.status)),\n );\n }\n\n function update(\n id: string,\n patch: Partial<BackgroundActionTask>,\n persistImmediately = false,\n ) {\n store\n .getState()\n .updateActionTask(instanceKey, id, patch, persistImmediately);\n }\n\n async function runEach(\n handler: (\n task: BackgroundActionTask,\n context: {\n index: number;\n total: number;\n pendingIndex: number;\n pendingTotal: number;\n },\n ) => BackgroundActionTaskRunResult | Promise<BackgroundActionTaskRunResult>,\n runOptions: BackgroundActionTaskRunOptions = {},\n ) {\n const statuses = runOptions.statuses || [\"queued\", \"running\"];\n const pending = getPending(statuses);\n const total = getAll().length;\n const pendingTotal = pending.length;\n const yieldEveryMs =\n runOptions.yieldEveryMs === false ? false : runOptions.yieldEveryMs ?? 16;\n let lastYieldAt = 0;\n\n for (const [pendingIndex, pendingTask] of pending.entries()) {\n if (signal.aborted) {\n throw new Error(\"Background action cancelled.\");\n }\n\n if (shouldYieldToBrowser(lastYieldAt, yieldEveryMs)) {\n await yieldToBrowser();\n lastYieldAt = Date.now();\n if (signal.aborted) {\n throw new Error(\"Background action cancelled.\");\n }\n }\n\n const latestTask =\n getAll().find((task) => task.id === pendingTask.id) || pendingTask;\n const index = getAll().findIndex((task) => task.id === latestTask.id);\n const label =\n runOptions.progressLabel?.(latestTask, index, total) ||\n latestTask.label ||\n `Task ${index + 1}/${total}`;\n\n if (latestTask.target?.type === \"Canvas\") {\n canvasProgress.setStatus(latestTask.target, \"pending\");\n }\n update(\n latestTask.id,\n {\n status: \"running\",\n statusText: label,\n error: null,\n startedAt: Date.now(),\n completedAt: undefined,\n },\n true,\n );\n store.getState().setActionStatus(instanceKey, \"running\", label);\n store.getState().setActionProgress(instanceKey, {\n current: getAll().filter((task) => isTerminalTaskStatus(task.status))\n .length,\n total,\n label,\n });\n\n try {\n const handlerResult = await handler(latestTask, {\n index,\n total,\n pendingIndex,\n pendingTotal,\n });\n\n if (signal.aborted) {\n throw new Error(\"Background action cancelled.\");\n }\n\n const taskResult = getTaskRunResult(handlerResult);\n update(\n latestTask.id,\n {\n status: taskResult.taskStatus,\n statusText:\n taskResult.statusText ||\n (taskResult.taskStatus === \"skipped\" ? \"Skipped\" : \"Complete\"),\n result: taskResult.result,\n error: null,\n completedAt: Date.now(),\n },\n true,\n );\n if (latestTask.target?.type === \"Canvas\") {\n canvasProgress.setStatus(latestTask.target, \"done\");\n }\n } catch (error) {\n if (signal.aborted || isAbortLikeError(error)) {\n update(\n latestTask.id,\n {\n status: \"cancelled\",\n statusText: \"Cancelled\",\n error: null,\n completedAt: Date.now(),\n },\n true,\n );\n throw error;\n }\n\n const normalisedError = normaliseBackgroundActionError(error);\n update(\n latestTask.id,\n {\n status: \"error\",\n statusText: normalisedError.message,\n error: normalisedError,\n completedAt: Date.now(),\n },\n true,\n );\n store\n .getState()\n .appendActionLog(\n instanceKey,\n `Task failed: ${latestTask.label}`,\n \"warn\",\n {\n taskId: latestTask.id,\n error: normalisedError.message,\n },\n );\n } finally {\n const latestPlan = getPlan();\n if (latestPlan) {\n store.getState().setActionProgress(instanceKey, {\n current: latestPlan.tasks.filter((task) =>\n isTerminalTaskStatus(task.status),\n ).length,\n total,\n label,\n });\n }\n }\n }\n\n return getAll();\n }\n\n return {\n getAll,\n getPending: () => getPending(),\n update,\n runEach,\n };\n}\n\nfunction shouldYieldToBrowser(\n lastYieldAt: number,\n yieldEveryMs: number | false,\n) {\n return (\n yieldEveryMs !== false &&\n (!lastYieldAt || Date.now() - lastYieldAt >= yieldEveryMs)\n );\n}\n\nfunction yieldToBrowser() {\n return new Promise<void>((resolve) => {\n setTimeout(resolve, 0);\n });\n}\n\nexport function createBackgroundActionsStore(\n initialDefinitions: BackgroundActionDefinition[] = [],\n) {\n let persistence: BackgroundActionPersistence | null = null;\n let persistenceKey: BackgroundActionPersistenceKey | null = null;\n let persistTimer: ReturnType<typeof setTimeout> | null = null;\n let deferredPersistedState = createEmptyPersistedState();\n\n return createStore<BackgroundActionsStore>((set, get) => {\n function applyDefinitions(\n prev: BackgroundActionsStore,\n definitions: BackgroundActionDefinition[],\n ) {\n const nextDefinitions = mergeBackgroundActionDefinitions([], definitions);\n const restored = restorePersistedState(\n deferredPersistedState,\n nextDefinitions,\n );\n deferredPersistedState = restored.deferred;\n\n return {\n definitions: nextDefinitions,\n instances: {\n ...prev.instances,\n ...restored.instances,\n },\n histories: {\n ...prev.histories,\n ...restored.histories,\n },\n plans: {\n ...prev.plans,\n ...restored.plans,\n },\n controllers: Object.fromEntries(\n Object.entries(prev.controllers).filter(\n ([key, controller]) =>\n controller &&\n prev.instances[key]?.status &&\n isActiveStatus(prev.instances[key].status),\n ),\n ),\n };\n }\n\n async function flushPersistence() {\n if (persistTimer) {\n clearTimeout(persistTimer);\n persistTimer = null;\n }\n\n if (!persistence || !persistenceKey || !get().hasHydrated) {\n return;\n }\n\n const snapshot = mergePersistedStates(\n deferredPersistedState,\n createPersistedState(get()),\n );\n if (persistedStateIsEmpty(snapshot)) {\n await persistence.clear(persistenceKey);\n return;\n }\n\n await persistence.save(persistenceKey, snapshot);\n }\n\n function queuePersist(immediate = false) {\n if (!persistence || !persistenceKey || !get().hasHydrated) {\n return;\n }\n\n if (immediate) {\n void flushPersistence();\n return;\n }\n\n if (persistTimer) {\n clearTimeout(persistTimer);\n }\n\n persistTimer = setTimeout(() => {\n void flushPersistence();\n }, 300);\n }\n\n return {\n definitions: mergeBackgroundActionDefinitions([], initialDefinitions),\n instances: {},\n histories: {},\n plans: {},\n controllers: {},\n hasHydrated: true,\n\n setDefinitions(definitions) {\n set((prev) => applyDefinitions(prev, definitions));\n queuePersist();\n },\n\n setPersistence(nextPersistence, nextKey) {\n persistence = nextPersistence;\n persistenceKey = nextPersistence && nextKey ? nextKey : null;\n set({ hasHydrated: !persistence });\n },\n\n hydrate(snapshot) {\n const restored = restorePersistedState(\n normalisePersistedState(snapshot),\n get().definitions,\n );\n deferredPersistedState = restored.deferred;\n\n set({\n instances: restored.instances,\n histories: restored.histories,\n plans: restored.plans,\n controllers: {},\n hasHydrated: true,\n });\n queuePersist(true);\n },\n\n persist(immediate = false) {\n queuePersist(immediate);\n },\n\n flushPersistence,\n\n registerAction(definition) {\n set((prev) =>\n applyDefinitions(\n prev,\n mergeBackgroundActionDefinitions(prev.definitions, [definition]),\n ),\n );\n queuePersist();\n\n return () => get().unregisterAction(definition.id);\n },\n\n unregisterAction(id) {\n set((prev) => {\n const instances: Record<string, BackgroundActionInstance> = {};\n for (const [key, instance] of Object.entries(prev.instances)) {\n if (instance.actionId !== id) {\n instances[key] = instance;\n }\n }\n\n const histories: Record<string, BackgroundActionInstance[]> = {};\n for (const [key, history] of Object.entries(prev.histories)) {\n const nextHistory = history.filter(\n (instance) => instance.actionId !== id,\n );\n if (nextHistory.length) {\n histories[key] = nextHistory;\n }\n }\n\n const plans = { ...prev.plans };\n const controllers = { ...prev.controllers };\n for (const [key, instance] of Object.entries(prev.instances)) {\n if (instance.actionId === id) {\n controllers[key]?.abort();\n delete controllers[key];\n delete plans[key];\n }\n }\n\n return {\n definitions: prev.definitions.filter(\n (definition) => definition.id !== id,\n ),\n instances,\n histories,\n plans,\n controllers,\n };\n });\n queuePersist(true);\n },\n\n resetAction(instanceKey) {\n set((prev) => {\n prev.controllers[instanceKey]?.abort();\n const instances = { ...prev.instances };\n const histories = { ...prev.histories };\n const plans = { ...prev.plans };\n const controllers = { ...prev.controllers };\n delete instances[instanceKey];\n delete histories[instanceKey];\n delete plans[instanceKey];\n delete controllers[instanceKey];\n return { instances, histories, plans, controllers };\n });\n queuePersist(true);\n },\n\n startAction(instanceKey, definition, target, controller) {\n const startedAt = Date.now();\n set((prev) => {\n const plans = { ...prev.plans };\n delete plans[instanceKey];\n return {\n instances: {\n ...prev.instances,\n [instanceKey]: {\n id: instanceKey,\n runId: createBackgroundActionEntryId(\"run\"),\n actionId: definition.id,\n target,\n label: definition.label,\n status: \"preparing\",\n statusText: \"Preparing\",\n error: null,\n result: undefined,\n resultsAvailable: false,\n logs: [],\n events: [\n createBackgroundActionEvent(\n \"started\",\n \"Preparing\",\n { status: \"preparing\" },\n startedAt,\n ),\n ],\n progress: undefined,\n startedAt,\n completedAt: undefined,\n cancelRequestedAt: undefined,\n cancelledAt: undefined,\n },\n },\n plans,\n controllers: controller\n ? {\n ...prev.controllers,\n [instanceKey]: controller,\n }\n : prev.controllers,\n };\n });\n queuePersist(true);\n },\n\n resumeAction(instanceKey, controller) {\n const createdAt = Date.now();\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n {\n ...instance,\n status: \"running\",\n statusText: \"Resuming\",\n completedAt: undefined,\n cancelledAt: undefined,\n },\n \"status\",\n \"Resuming\",\n { status: \"running\" },\n createdAt,\n ),\n ),\n controllers: {\n ...prev.controllers,\n [instanceKey]: controller,\n },\n }));\n queuePersist(true);\n },\n\n cancelAction(instanceKey) {\n const controller = get().controllers[instanceKey];\n const instance = get().instances[instanceKey];\n if (!instance || !isActiveStatus(instance.status)) {\n return;\n }\n\n const requestedAt = Date.now();\n set((prev) => {\n const updated = updateStoredInstance(prev, instanceKey, (current) =>\n appendEvent(\n appendEvent(\n {\n ...current,\n status: \"cancelled\",\n statusText: \"Cancelled\",\n completedAt: requestedAt,\n cancelledAt: requestedAt,\n cancelRequestedAt: current.cancelRequestedAt || requestedAt,\n },\n \"cancel-requested\",\n \"Cancelling\",\n undefined,\n requestedAt,\n ),\n \"status\",\n \"Cancelled\",\n { status: \"cancelled\" },\n requestedAt,\n ),\n );\n const plan = prev.plans[instanceKey];\n\n return {\n ...updated,\n plans: plan\n ? {\n ...prev.plans,\n [instanceKey]: cancelPendingPlanTasks(plan, requestedAt),\n }\n : prev.plans,\n controllers: Object.fromEntries(\n Object.entries(prev.controllers).filter(\n ([key]) => key !== instanceKey,\n ),\n ),\n };\n });\n queuePersist(true);\n controller?.abort();\n },\n\n setActionLabel(instanceKey, label) {\n const createdAt = Date.now();\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n { ...instance, label },\n \"label\",\n label,\n { label },\n createdAt,\n ),\n ),\n }));\n queuePersist();\n },\n\n setActionStatus(instanceKey, status, statusText) {\n const createdAt = Date.now();\n const completedAt = isCompletedStatus(status) ? createdAt : undefined;\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n {\n ...instance,\n status,\n statusText,\n completedAt,\n cancelledAt: status === \"cancelled\" ? createdAt : undefined,\n },\n \"status\",\n statusText || status,\n { status },\n createdAt,\n ),\n ),\n controllers: isActiveStatus(status)\n ? prev.controllers\n : Object.fromEntries(\n Object.entries(prev.controllers).filter(\n ([key]) => key !== instanceKey,\n ),\n ),\n }));\n queuePersist(isCompletedStatus(status));\n },\n\n setActionError(instanceKey, error, statusText) {\n const createdAt = Date.now();\n const normalisedError = normaliseBackgroundActionError(error);\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n {\n ...instance,\n status: \"error\",\n statusText,\n error: normalisedError,\n completedAt: createdAt,\n cancelledAt: undefined,\n },\n \"error\",\n statusText || normalisedError.message,\n normalisedError,\n createdAt,\n ),\n ),\n controllers: Object.fromEntries(\n Object.entries(prev.controllers).filter(\n ([key]) => key !== instanceKey,\n ),\n ),\n }));\n queuePersist(true);\n },\n\n appendActionLog(instanceKey, message, level = \"info\", data) {\n const createdAt = Date.now();\n const log: BackgroundActionLogEntry = {\n id: createBackgroundActionEntryId(\"log\"),\n createdAt,\n level,\n message,\n data,\n };\n\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n {\n ...instance,\n logs: [...instance.logs, log],\n },\n \"log\",\n message,\n { level, data },\n createdAt,\n ),\n ),\n }));\n queuePersist();\n },\n\n setActionProgress(instanceKey, progress) {\n const nextProgress = progress ? normaliseProgress(progress) : undefined;\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) => ({\n ...instance,\n progress: nextProgress,\n })),\n }));\n },\n\n setResult(instanceKey, result) {\n const createdAt = Date.now();\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n { ...instance, result },\n \"result\",\n \"Result recorded\",\n undefined,\n createdAt,\n ),\n ),\n }));\n queuePersist(true);\n },\n\n setResultsAvailable(instanceKey, available) {\n const createdAt = Date.now();\n set((prev) => ({\n ...updateStoredInstance(prev, instanceKey, (instance) =>\n appendEvent(\n { ...instance, resultsAvailable: available },\n \"results-available\",\n available ? \"Results available\" : \"Results hidden\",\n { available },\n createdAt,\n ),\n ),\n }));\n queuePersist(true);\n },\n\n setActionPlan(instanceKey, plan) {\n const normalisedPlan = normalisePlan(plan);\n if (!normalisedPlan) {\n return;\n }\n\n set((prev) => {\n const nextState = updateStoredInstance(\n prev,\n instanceKey,\n (instance) => ({\n ...instance,\n progress: getPlanProgress(normalisedPlan, \"Queued\"),\n }),\n );\n\n return {\n ...nextState,\n plans: {\n ...prev.plans,\n [instanceKey]: normalisedPlan,\n },\n };\n });\n queuePersist(true);\n },\n\n updateActionTask(instanceKey, taskId, patch, persistImmediately = false) {\n set((prev) => {\n const plan = prev.plans[instanceKey];\n if (!plan) {\n return prev;\n }\n\n const tasks = plan.tasks.map((task) => {\n if (task.id !== taskId) {\n return task;\n }\n\n return normaliseTask(\n {\n ...task,\n ...patch,\n status: patch.status\n ? normaliseTaskStatus(patch.status)\n : task.status,\n error: patch.error\n ? normaliseStoredBackgroundActionError(patch.error)\n : patch.error === null\n ? null\n : task.error,\n },\n 0,\n );\n });\n const nextPlan = {\n ...plan,\n tasks,\n };\n const nextState = updateStoredInstance(\n prev,\n instanceKey,\n (instance) => ({\n ...instance,\n progress: getPlanProgress(\n nextPlan,\n patch.statusText || patch.label,\n ),\n }),\n );\n\n return {\n ...nextState,\n plans: {\n ...prev.plans,\n [instanceKey]: nextPlan,\n },\n };\n });\n queuePersist(persistImmediately);\n },\n };\n });\n}\n\nfunction createRunContext(\n options: RunBackgroundActionOptions,\n signal: AbortSignal,\n canvasProgress: ManifestEditorCanvasProgressApi,\n): BackgroundActionRunContext {\n const { store, context } = options;\n const { instanceKey } = context;\n const tasks = createTaskApi(options, signal, canvasProgress);\n\n return {\n ...context,\n canvasProgress,\n instance: store.getState().instances[instanceKey],\n plan: store.getState().plans[instanceKey],\n tasks,\n signal,\n prepareData: options.prepareData,\n setActionLabel(label) {\n store.getState().setActionLabel(instanceKey, label);\n },\n setActionStatus(status, statusText) {\n store.getState().setActionStatus(instanceKey, status, statusText);\n },\n setActionError(error, statusText) {\n store.getState().setActionError(instanceKey, error, statusText);\n },\n appendActionLog(message, level, data) {\n store.getState().appendActionLog(instanceKey, message, level, data);\n },\n setActionProgress(progress) {\n store.getState().setActionProgress(instanceKey, progress);\n },\n setResult(result) {\n store.getState().setResult(instanceKey, result);\n },\n setResultsAvailable(available) {\n store.getState().setResultsAvailable(instanceKey, available);\n },\n };\n}\n\nfunction isBackgroundActionPlan(value: unknown): value is BackgroundActionPlan {\n return (\n !!value &&\n typeof value === \"object\" &&\n (value as BackgroundActionPlan).version === 1 &&\n Array.isArray((value as BackgroundActionPlan).tasks)\n );\n}\n\nexport async function runBackgroundAction(options: RunBackgroundActionOptions) {\n const { store, context } = options;\n const { definition, instanceKey, target } = context;\n const existing = store.getState().instances[instanceKey];\n const existingController = store.getState().controllers[instanceKey];\n\n if (existing?.status === \"preparing\" || existing?.status === \"running\") {\n if (!options.resume || existingController) {\n return existing;\n }\n }\n\n const controller = new AbortController();\n const signal = controller.signal;\n const canvasProgress = createTrackingCanvasProgressApi(\n context.canvasProgress,\n );\n const abortFromExternalSignal = () => controller.abort();\n\n if (options.signal) {\n if (options.signal.aborted) {\n controller.abort();\n } else {\n options.signal.addEventListener(\"abort\", abortFromExternalSignal, {\n once: true,\n });\n }\n }\n\n if (options.resume && existing && isActiveStatus(existing.status)) {\n store.getState().resumeAction(instanceKey, controller);\n } else {\n store.getState().startAction(instanceKey, definition, target, controller);\n }\n\n const markCancelledIfActive = () => {\n const latest = store.getState().instances[instanceKey];\n if (latest && !isCompletedStatus(latest.status)) {\n store.getState().setActionStatus(instanceKey, \"cancelled\", \"Cancelled\");\n }\n };\n\n try {\n if (!options.resume && definition.prepare) {\n const prepareResult = await definition.prepare(\n createRunContext(options, signal, canvasProgress),\n );\n if (signal.aborted) {\n markCancelledIfActive();\n return store.getState().instances[instanceKey];\n }\n\n if (prepareResult === false) {\n store.getState().setActionStatus(instanceKey, \"idle\");\n return store.getState().instances[instanceKey];\n }\n\n if (isBackgroundActionPlan(prepareResult)) {\n store.getState().setActionPlan(instanceKey, prepareResult);\n }\n }\n\n if (signal.aborted) {\n markCancelledIfActive();\n return store.getState().instances[instanceKey];\n }\n\n const plan = store.getState().plans[instanceKey];\n if (plan) {\n restoreCanvasProgressFromPlan(canvasProgress, plan);\n }\n\n store\n .getState()\n .setActionStatus(\n instanceKey,\n \"running\",\n options.resume ? \"Resuming\" : \"Running\",\n );\n const result = await definition.run(\n createRunContext(options, signal, canvasProgress),\n );\n\n if (signal.aborted) {\n markCancelledIfActive();\n return store.getState().instances[instanceKey];\n }\n\n let latest = store.getState().instances[instanceKey];\n if (\n typeof result !== \"undefined\" &&\n latest &&\n !isCompletedStatus(latest.status)\n ) {\n store.getState().setResult(instanceKey, result);\n }\n\n latest = store.getState().instances[instanceKey];\n if (latest && isActiveStatus(latest.status)) {\n if (typeof result !== \"undefined\" || latest?.resultsAvailable) {\n store.getState().setResultsAvailable(instanceKey, true);\n }\n store.getState().setActionStatus(instanceKey, \"complete\", \"Complete\");\n }\n } catch (error) {\n if (signal.aborted || isAbortLikeError(error)) {\n markCancelledIfActive();\n } else {\n store.getState().setActionError(instanceKey, error, \"Error\");\n }\n } finally {\n canvasProgress.clearTrackedStatuses();\n options.signal?.removeEventListener(\"abort\", abortFromExternalSignal);\n await store.getState().flushPersistence();\n }\n\n return store.getState().instances[instanceKey];\n}\n\nfunction isAbortLikeError(error: unknown) {\n return (\n error instanceof Error &&\n (error.name === \"AbortError\" ||\n error.message.toLowerCase().includes(\"aborted\"))\n );\n}\n\nfunction createBackgroundActionStorageKey(key: BackgroundActionPersistenceKey) {\n return JSON.stringify([\n key.appId,\n key.instanceId,\n key.rootResource.type,\n key.rootResource.id,\n ]);\n}\n\nlet defaultPersistence: BackgroundActionPersistence | null | undefined;\n\nexport function createLocalForageBackgroundActionPersistence(): BackgroundActionPersistence | null {\n if (typeof window === \"undefined\") {\n return null;\n }\n\n const storage = localforage.createInstance({\n name: \"manifest-editor-background-actions-v1\",\n storeName: \"background-actions\",\n });\n\n return {\n async load(key) {\n return storage.getItem<BackgroundActionPersistedState>(\n createBackgroundActionStorageKey(key),\n );\n },\n async save(key, state) {\n await storage.setItem(createBackgroundActionStorageKey(key), state);\n },\n async clear(key) {\n await storage.removeItem(createBackgroundActionStorageKey(key));\n },\n };\n}\n\nfunction getDefaultBackgroundActionPersistence() {\n if (typeof defaultPersistence === \"undefined\") {\n defaultPersistence = createLocalForageBackgroundActionPersistence();\n }\n\n return defaultPersistence;\n}\n\nexport const BackgroundActionsReactContext =\n createContext<StoreApi<BackgroundActionsStore> | null>(null);\n\nexport function BackgroundActionsProvider({\n children,\n persistence,\n persistenceKey,\n}: {\n children: ReactNode;\n persistence?: BackgroundActionPersistence | false | null;\n persistenceKey?: BackgroundActionPersistenceKey;\n}) {\n const app = useApp();\n const appInstance = useAppInstance();\n const store = useMemo(() => createBackgroundActionsStore(), []);\n const definitions = app.layout.backgroundActions || [];\n const resolvedPersistence = useMemo(\n () =>\n persistence === false\n ? null\n : persistence || getDefaultBackgroundActionPersistence(),\n [persistence],\n );\n const resolvedPersistenceKey =\n useMemo<BackgroundActionPersistenceKey | null>(() => {\n if (!persistenceKey) {\n return null;\n }\n\n return persistenceKey;\n }, [persistenceKey]);\n\n useEffect(() => {\n store.getState().setDefinitions(definitions);\n }, [store, definitions]);\n\n useEffect(() => {\n const key = resolvedPersistenceKey || {\n appId: appInstance.appId,\n instanceId: appInstance.instanceId,\n rootResource: { id: \"global\", type: \"Manifest\" },\n };\n let cancelled = false;\n\n store.getState().setPersistence(resolvedPersistence, key);\n\n if (!resolvedPersistence) {\n store.getState().hydrate(null);\n return () => void 0;\n }\n\n resolvedPersistence\n .load(key)\n .then((snapshot) => {\n if (!cancelled) {\n store.getState().hydrate(snapshot);\n }\n })\n .catch((error) => {\n console.warn(\n \"[manifest-editor/background-actions] Failed to load persisted actions\",\n error,\n );\n if (!cancelled) {\n store.getState().hydrate(null);\n }\n });\n\n return () => {\n cancelled = true;\n void store.getState().flushPersistence();\n };\n }, [\n appInstance.appId,\n appInstance.instanceId,\n resolvedPersistence,\n resolvedPersistenceKey?.appId,\n resolvedPersistenceKey?.instanceId,\n resolvedPersistenceKey?.rootResource.id,\n resolvedPersistenceKey?.rootResource.type,\n store,\n ]);\n\n useEffect(() => {\n const flush = () => {\n void store.getState().flushPersistence();\n };\n\n window.addEventListener(\"beforeunload\", flush);\n return () => window.removeEventListener(\"beforeunload\", flush);\n }, [store]);\n\n return createElement(\n BackgroundActionsReactContext.Provider,\n { value: store },\n children,\n );\n}\n\nexport function useBackgroundActionsStoreApi() {\n const store = useContext(BackgroundActionsReactContext);\n\n if (!store) {\n throw new Error(\n \"useBackgroundActionsStore must be used within a BackgroundActionsProvider\",\n );\n }\n\n return store;\n}\n\nexport function useBackgroundActionsStore<T = BackgroundActionsStore>(\n selector: (state: BackgroundActionsStore) => T = (state) => state as T,\n) {\n return useStore(useBackgroundActionsStoreApi(), selector);\n}\n\nexport function useBackgroundActionInstance(instanceKey: string) {\n return useBackgroundActionsStore((state) => state.instances[instanceKey]);\n}\n\nexport function useBackgroundActionHistory(instanceKey: string) {\n return useBackgroundActionsStore(\n (state) => state.histories[instanceKey] || [],\n );\n}\n","import { toRef } from \"@iiif/parser\";\nimport type { ManifestNormalized } from \"@iiif/presentation-3-normalized\";\nimport type { AppExtension, MappedApp } from \"./AppContext/AppContext\";\nimport { mergeBackgroundActionDefinitions } from \"./BackgroundTasks/BackgroundTasksStore\";\nimport { mergePartialConfig } from \"./ConfigContext/ConfigContext\";\n\nexport async function getManifestNomalized(\n id: string,\n): Promise<ManifestNormalized | undefined> {\n let responseData: ManifestNormalized | undefined;\n try {\n await fetch(id)\n .then((response) => {\n return response.json().catch((err) => {\n console.error(`'${err}' happened!`);\n });\n })\n .then((data) => {\n responseData = { ...data };\n });\n } catch (error) {\n console.log(error);\n }\n return responseData;\n}\n\nexport function createActionIdentity(\n type: string,\n property: string,\n parent: any,\n) {\n return `create_${type}_${property}_${toRef(parent)?.type || \"unknown\"}`;\n}\n\nexport function createDownload(\n data: any,\n fileName: string,\n fileType = \"text/json\",\n) {\n // Create a blob with the data we want to download as a file\n const blob =\n data instanceof Blob ? data : new Blob([data], { type: fileType });\n // Create an anchor element and dispatch a click event on it\n // to trigger a download\n const a = document.createElement(\"a\");\n a.download = fileName;\n a.href = window.URL.createObjectURL(blob);\n const clickEvt = new MouseEvent(\"click\", {\n view: window,\n bubbles: true,\n cancelable: true,\n });\n a.dispatchEvent(clickEvt);\n a.remove();\n}\n\nexport async function copyToClipboard(json: string | any) {\n return navigator.clipboard.writeText(\n typeof json === \"string\" ? json : JSON.stringify(json, null, 2),\n );\n}\n\nexport function randomId() {\n return `${Math.random().toString(36).substr(2)}-${Date.now().toString(36)}`;\n}\n\nexport function mapApp(\n input: any,\n map?: (app: MappedApp) => MappedApp,\n): MappedApp {\n const { default: metadata, config, ...props } = input;\n const app = {\n metadata: metadata as any,\n layout: {\n leftPanels: [],\n rightPanels: [],\n centerPanels: [],\n ...(props as any),\n },\n config,\n };\n\n return map ? map(app) : app;\n}\n\nexport function extendApp(\n app: MappedApp,\n metadata: MappedApp[\"metadata\"],\n extensions: AppExtension,\n): MappedApp {\n return {\n ...app,\n metadata,\n config: mergePartialConfig(app.config || {}, extensions.config || {}),\n layout: {\n ...app.layout,\n leftPanels: [\n ...(app.layout.leftPanels || []).filter((panel) => {\n if (extensions?.leftPanelIds) {\n return extensions.leftPanelIds.includes(panel.id);\n }\n return true;\n }),\n ...(extensions?.leftPanels || []),\n ],\n annotations: [\n ...(extensions?.annotations || []),\n ...(app.layout.annotations || []),\n ],\n canvasEditors: [\n ...(extensions?.canvasEditors || []),\n ...(app.layout.canvasEditors || []),\n ],\n creators: [\n ...(extensions?.creators || []),\n ...(app.layout.creators || []),\n ],\n background: [\n ...(app.layout?.background || []),\n ...(extensions?.background || []),\n ],\n backgroundActions: mergeBackgroundActionDefinitions(\n app.layout?.backgroundActions || [],\n extensions?.backgroundActions || [],\n ),\n editors: [\n //\n ...(extensions?.editors || []),\n ...(app.layout.editors || []),\n ],\n rightPanels: [\n ...(app.layout.rightPanels || []),\n ...(extensions?.rightPanels || []),\n ],\n centerPanels: [\n ...(app.layout.centerPanels || []),\n ...(extensions?.centerPanels || []),\n ],\n modals: [\n ...(app.layout.modals || []),\n ...(extensions?.modalPanels || []),\n ],\n },\n };\n}\n","import type { AppExtension, MappedApp } from \"../AppContext/AppContext\";\nimport { mergeBackgroundActionDefinitions } from \"../BackgroundTasks/BackgroundTasksStore\";\nimport { mergePartialConfig } from \"../ConfigContext/ConfigContext\";\nimport { extendApp } from \"../helpers\";\nimport type {\n MappedPlugin,\n PluginAppConfig,\n PluginConfigScope,\n PluginHostApp,\n PluginInput,\n LazyPluginModule,\n PluginModule,\n PluginRuntimeApi,\n PluginSettingsValue,\n PluginStoreSnapshot,\n} from \"./PluginContext.types\";\n\ntype ExtensionListKey =\n | \"leftPanels\"\n | \"centerPanels\"\n | \"rightPanels\"\n | \"modalPanels\"\n | \"annotations\"\n | \"canvasEditors\"\n | \"editors\"\n | \"creators\"\n | \"background\"\n | \"backgroundActions\";\n\nconst extensionListKeys: ExtensionListKey[] = [\n \"leftPanels\",\n \"centerPanels\",\n \"rightPanels\",\n \"modalPanels\",\n \"annotations\",\n \"canvasEditors\",\n \"editors\",\n \"creators\",\n \"background\",\n \"backgroundActions\",\n];\n\nconst emptyPluginState: PluginStoreSnapshot = {\n plugins: [],\n enabled: [],\n disabled: [],\n globalApps: {},\n apps: {},\n};\n\nexport function getEmptyPluginState(): PluginStoreSnapshot {\n return emptyPluginState;\n}\n\nfunction unique(values: string[] = []) {\n return Array.from(new Set(values.filter(Boolean)));\n}\n\nfunction isPlainObject(value: unknown): value is Record<string, unknown> {\n return !!value && typeof value === \"object\" && !Array.isArray(value);\n}\n\nexport function normalisePluginAppConfig(config: PluginAppConfig = {}): PluginAppConfig {\n return {\n ...config,\n enabled: unique(config.enabled || []),\n disabled: unique(config.disabled || []),\n settings: config.settings ? { ...config.settings } : undefined,\n };\n}\n\nexport function normalisePluginAppsConfig(config?: { apps?: Record<string, PluginAppConfig> }) {\n const apps: Record<string, PluginAppConfig> = {};\n\n for (const [appId, appConfig] of Object.entries(config?.apps || {})) {\n apps[appId] = normalisePluginAppConfig(appConfig);\n }\n\n return apps;\n}\n\nexport function enablePluginInConfig(config: PluginAppConfig = {}, id: string): PluginAppConfig {\n return {\n ...config,\n enabled: unique([...(config.enabled || []).filter((existing) => existing !== id), id]),\n disabled: (config.disabled || []).filter((existing) => existing !== id),\n };\n}\n\nexport function disablePluginInConfig(config: PluginAppConfig = {}, id: string): PluginAppConfig {\n return {\n ...config,\n enabled: (config.enabled || []).filter((existing) => existing !== id),\n disabled: unique([...(config.disabled || []).filter((existing) => existing !== id), id]),\n };\n}\n\nexport function resetPluginInConfig(config: PluginAppConfig = {}, id: string): PluginAppConfig {\n return {\n ...config,\n enabled: (config.enabled || []).filter((existing) => existing !== id),\n disabled: (config.disabled || []).filter((existing) => existing !== id),\n };\n}\n\nexport function pluginAppConfigEquals(a: PluginAppConfig = {}, b: PluginAppConfig = {}) {\n const aEnabled = a.enabled || [];\n const bEnabled = b.enabled || [];\n const aDisabled = a.disabled || [];\n const bDisabled = b.disabled || [];\n\n return (\n aEnabled.length === bEnabled.length &&\n aEnabled.every((id, index) => id === bEnabled[index]) &&\n aDisabled.length === bDisabled.length &&\n aDisabled.every((id, index) => id === bDisabled[index]) &&\n JSON.stringify(a.settings || {}) === JSON.stringify(b.settings || {})\n );\n}\n\nexport function mapPlugin(input: PluginModule, map?: (plugin: MappedPlugin) => MappedPlugin): MappedPlugin {\n const { default: metadata, config, settings, ...props } = input;\n const plugin: MappedPlugin = {\n metadata,\n extension: {\n ...(props as AppExtension),\n config,\n },\n settings,\n };\n\n return map ? map(plugin) : plugin;\n}\n\nexport function mapLazyPlugin(input: LazyPluginModule): MappedPlugin {\n return {\n metadata: input.default,\n extension: {},\n settings: input.settings,\n load: input.load,\n loadStatus: \"idle\",\n };\n}\n\nexport function isMappedPlugin(input: PluginInput): input is MappedPlugin {\n return !!input && \"metadata\" in input && \"extension\" in input;\n}\n\nexport function isLazyPlugin(input: PluginInput): input is LazyPluginModule {\n return !!input && \"load\" in input && \"default\" in input;\n}\n\nexport function normalisePlugin(input: PluginInput): MappedPlugin {\n if (isMappedPlugin(input)) return input;\n if (isLazyPlugin(input)) return mapLazyPlugin(input);\n return mapPlugin(input);\n}\n\nexport function normalisePlugins(plugins: PluginInput[] = []): MappedPlugin[] {\n return plugins.map(normalisePlugin);\n}\n\nexport function mergeProviderPlugins(previous: MappedPlugin[], next: MappedPlugin[]) {\n const previousById = new Map(previous.map((plugin) => [plugin.metadata.id, plugin]));\n\n return next.map((plugin) => {\n const previousPlugin = previousById.get(plugin.metadata.id);\n if (!previousPlugin) return plugin;\n\n if (previousPlugin.loadStatus === \"loaded\" && plugin.load) {\n return {\n ...previousPlugin,\n metadata: plugin.metadata,\n load: plugin.load,\n };\n }\n\n if (previousPlugin.loadStatus === \"loading\" && plugin.load) {\n return {\n ...plugin,\n loadStatus: \"loading\" as const,\n };\n }\n\n if (previousPlugin.loadStatus === \"error\" && plugin.load) {\n return {\n ...plugin,\n loadStatus: \"error\" as const,\n loadError: previousPlugin.loadError,\n };\n }\n\n return plugin;\n });\n}\n\nexport function isPluginCompatible(plugin: MappedPlugin, app?: PluginHostApp | null, appId?: string | null) {\n const supports = plugin.metadata.supports;\n if (!supports) return true;\n\n if (supports.apps?.length) {\n const appIds = new Set([appId, app?.metadata.id].filter(Boolean));\n if (!supports.apps.some((supportedAppId) => appIds.has(supportedAppId))) {\n return false;\n }\n }\n\n if (supports.projectTypes?.length) {\n const projectType = app?.metadata.projectType;\n if (!projectType || !supports.projectTypes.includes(projectType)) {\n return false;\n }\n }\n\n return true;\n}\n\nexport function getPluginCompatibilityReason(plugin: MappedPlugin, app?: PluginHostApp | null, appId?: string | null) {\n const supports = plugin.metadata.supports;\n if (!supports) return null;\n\n if (supports.apps?.length) {\n const appIds = new Set([appId, app?.metadata.id].filter(Boolean));\n if (!supports.apps.some((supportedAppId) => appIds.has(supportedAppId))) {\n return \"This plugin does not support the current app.\";\n }\n }\n\n if (supports.projectTypes?.length) {\n const projectType = app?.metadata.projectType;\n if (!projectType || !supports.projectTypes.includes(projectType)) {\n return \"This plugin does not support the current project type.\";\n }\n }\n\n return null;\n}\n\nexport function isPluginSelected(plugin: MappedPlugin, state: PluginStoreSnapshot, appId?: string | null) {\n const appConfig = appId ? state.apps[appId] : undefined;\n const globalAppConfig = appId ? state.globalApps[appId] : undefined;\n const id = plugin.metadata.id;\n\n if (appConfig?.disabled?.includes(id)) return false;\n if (appConfig?.enabled?.includes(id)) return true;\n if (globalAppConfig?.disabled?.includes(id)) return false;\n if (globalAppConfig?.enabled?.includes(id)) return true;\n if (state.disabled.includes(id)) return false;\n if (state.enabled.includes(id)) return true;\n\n return plugin.metadata.defaultEnabled === true;\n}\n\nexport function getPluginSelectionSource(\n plugin: MappedPlugin,\n state: PluginStoreSnapshot,\n appId?: string | null,\n): PluginConfigScope | \"provider\" | \"default\" {\n const appConfig = appId ? state.apps[appId] : undefined;\n const globalAppConfig = appId ? state.globalApps[appId] : undefined;\n const id = plugin.metadata.id;\n\n if (appConfig?.disabled?.includes(id) || appConfig?.enabled?.includes(id)) return \"workspace\";\n if (globalAppConfig?.disabled?.includes(id) || globalAppConfig?.enabled?.includes(id)) return \"global\";\n if (state.disabled.includes(id) || state.enabled.includes(id)) return \"provider\";\n return \"default\";\n}\n\nexport function getEnabledPluginsForApp(\n state: PluginStoreSnapshot,\n app?: PluginHostApp | null,\n appId?: string | null,\n): MappedPlugin[] {\n const enabled: MappedPlugin[] = [];\n const activeIds = new Set<string>();\n const skippedIds = new Set<string>();\n const selected = new Set(\n state.plugins\n .filter((plugin) => isPluginCompatible(plugin, app, appId) && isPluginSelected(plugin, state, appId))\n .map((plugin) => plugin.metadata.id),\n );\n const byId = new Map(state.plugins.map((plugin) => [plugin.metadata.id, plugin]));\n const visiting = new Set<string>();\n\n function activate(plugin: MappedPlugin): boolean {\n const id = plugin.metadata.id;\n if (activeIds.has(id)) return true;\n if (skippedIds.has(id)) return false;\n\n if (visiting.has(id)) {\n warnPlugin(`Plugin \"${id}\" was not enabled because its dependency graph contains a cycle.`);\n skippedIds.add(id);\n return false;\n }\n\n visiting.add(id);\n\n for (const dependencyId of plugin.metadata.dependencies || []) {\n const dependency = byId.get(dependencyId);\n if (!dependency || !selected.has(dependencyId)) {\n warnPlugin(`Plugin \"${id}\" was not enabled because dependency \"${dependencyId}\" is not enabled.`);\n visiting.delete(id);\n skippedIds.add(id);\n return false;\n }\n\n if (!isPluginCompatible(dependency, app, appId)) {\n warnPlugin(`Plugin \"${id}\" was not enabled because dependency \"${dependencyId}\" is not compatible.`);\n visiting.delete(id);\n skippedIds.add(id);\n return false;\n }\n\n if (!activate(dependency)) {\n visiting.delete(id);\n skippedIds.add(id);\n return false;\n }\n }\n\n visiting.delete(id);\n enabled.push(plugin);\n activeIds.add(id);\n return true;\n }\n\n for (const plugin of state.plugins) {\n if (!isPluginCompatible(plugin, app, appId)) {\n continue;\n }\n\n if (!isPluginSelected(plugin, state, appId)) {\n continue;\n }\n\n activate(plugin);\n }\n\n return enabled;\n}\n\nexport function getPluginSettingsFromConfig<T extends PluginSettingsValue = PluginSettingsValue>(\n config: PluginAppConfig | undefined,\n pluginId: string,\n): Partial<T> {\n const settings = config?.settings?.[pluginId];\n return isPlainObject(settings) ? (settings as Partial<T>) : {};\n}\n\nexport function setPluginSettingsInConfig<T extends PluginSettingsValue = PluginSettingsValue>(\n config: PluginAppConfig = {},\n pluginId: string,\n settings: T,\n): PluginAppConfig {\n return {\n ...config,\n settings: {\n ...(config.settings || {}),\n [pluginId]: settings,\n },\n };\n}\n\nexport function resetPluginSettingsInConfig(config: PluginAppConfig = {}, pluginId: string): PluginAppConfig {\n const settings = { ...(config.settings || {}) };\n delete settings[pluginId];\n\n return {\n ...config,\n settings,\n };\n}\n\nexport function getPluginDefaultSettings<T extends PluginSettingsValue = PluginSettingsValue>(\n plugin?: MappedPlugin,\n): T {\n return ({ ...(plugin?.settings?.defaults || {}) } as unknown) as T;\n}\n\nexport function getEffectivePluginSettings<T extends PluginSettingsValue = PluginSettingsValue>(\n state: PluginStoreSnapshot,\n pluginId: string,\n appId?: string | null,\n): T {\n const plugin = state.plugins.find((item) => item.metadata.id === pluginId);\n const globalAppConfig = appId ? state.globalApps[appId] : undefined;\n const workspaceAppConfig = appId ? state.apps[appId] : undefined;\n\n return {\n ...getPluginDefaultSettings<T>(plugin),\n ...getPluginSettingsFromConfig<T>(globalAppConfig, pluginId),\n ...getPluginSettingsFromConfig<T>(workspaceAppConfig, pluginId),\n };\n}\n\nexport function createPluginRuntimeApi(state: PluginStoreSnapshot, appId?: string | null): PluginRuntimeApi {\n return {\n getSettings<T extends PluginSettingsValue = PluginSettingsValue>(pluginId: string): T {\n return getEffectivePluginSettings<T>(state, pluginId, appId);\n },\n };\n}\n\nexport function enablePluginAndDependenciesInConfig(\n config: PluginAppConfig,\n state: PluginStoreSnapshot,\n plugin: MappedPlugin,\n app?: PluginHostApp | null,\n appId?: string | null,\n): { config: PluginAppConfig; enabledIds: string[]; blocked: string[] } {\n const byId = new Map(state.plugins.map((item) => [item.metadata.id, item]));\n const enabledIds: string[] = [];\n const blocked: string[] = [];\n const visiting = new Set<string>();\n let nextConfig = config;\n\n function enableOne(current: MappedPlugin) {\n const id = current.metadata.id;\n if (enabledIds.includes(id)) return;\n if (visiting.has(id)) {\n blocked.push(`${id} has a circular dependency`);\n return;\n }\n\n visiting.add(id);\n\n for (const dependencyId of current.metadata.dependencies || []) {\n const dependency = byId.get(dependencyId);\n if (!dependency) {\n blocked.push(`${dependencyId} is not available`);\n continue;\n }\n\n if (!isPluginCompatible(dependency, app, appId)) {\n blocked.push(`${dependency.metadata.label} is not compatible`);\n continue;\n }\n\n enableOne(dependency);\n }\n\n visiting.delete(id);\n nextConfig = enablePluginInConfig(nextConfig, id);\n enabledIds.push(id);\n }\n\n enableOne(plugin);\n\n if (blocked.length) {\n return { config, enabledIds: [], blocked };\n }\n\n return { config: nextConfig, enabledIds, blocked };\n}\n\nfunction getLayoutList(app: MappedApp, key: ExtensionListKey): Array<{ id: string }> {\n if (key === \"modalPanels\") {\n return (app.layout.modals || []) as Array<{ id: string }>;\n }\n return ((app.layout as any)[key] || []) as Array<{ id: string }>;\n}\n\nfunction warnPlugin(message: string) {\n const processEnv = (globalThis as any).process?.env;\n if (processEnv?.NODE_ENV === \"production\") return;\n console.warn(`[manifest-editor/plugin] ${message}`);\n}\n\nfunction filterPluginList<T extends { id: string }>(\n plugin: MappedPlugin,\n key: ExtensionListKey,\n existing: Set<string>,\n items: T[] | undefined,\n) {\n if (!items?.length) return undefined;\n\n const next: T[] = [];\n for (const item of items) {\n if (existing.has(item.id)) {\n warnPlugin(`Plugin \"${plugin.metadata.id}\" contribution \"${item.id}\" for \"${key}\" was skipped because that id already exists.`);\n continue;\n }\n\n existing.add(item.id);\n next.push(item);\n }\n\n return next.length ? next : undefined;\n}\n\nfunction sanitisePluginExtension(app: MappedApp, plugin: MappedPlugin): AppExtension {\n const extension = plugin.extension;\n const next: AppExtension = {\n config: extension.config,\n disableSideEffects: extension.disableSideEffects,\n };\n\n for (const key of extensionListKeys) {\n const existing = new Set(getLayoutList(app, key).map((item) => item.id));\n const filtered = filterPluginList(plugin, key, existing, (extension as any)[key]);\n if (filtered) {\n (next as any)[key] = filtered;\n }\n }\n\n return next;\n}\n\nexport function applyPlugins(app: MappedApp, plugins: MappedPlugin[], appId?: string): MappedApp {\n if (!plugins.length) return app;\n\n let nextApp = app;\n const activeIds = new Set<string>();\n\n for (const plugin of plugins) {\n if (!isPluginCompatible(plugin, app, appId)) {\n continue;\n }\n\n const missingDependencies = (plugin.metadata.dependencies || []).filter((dependency) => !activeIds.has(dependency));\n if (missingDependencies.length) {\n warnPlugin(\n `Plugin \"${plugin.metadata.id}\" was not applied because dependencies are missing or later in the plugin order: ${missingDependencies.join(\", \")}`,\n );\n continue;\n }\n\n const extension = sanitisePluginExtension(nextApp, plugin);\n nextApp = extendApp(nextApp, nextApp.metadata, extension);\n activeIds.add(plugin.metadata.id);\n }\n\n // Reorder leftPanels: built-ins first, then plugin panels (with separator before first),\n // then divide panels (e.g. settings) always last.\n const originalIds = new Set(app.layout.leftPanels.map((p) => p.id));\n const dividePanels = nextApp.layout.leftPanels.filter((p) => p.divide);\n const nonDividePanels = nextApp.layout.leftPanels.filter((p) => !p.divide);\n\n let firstPluginPanelMarked = false;\n const orderedPanels = nonDividePanels.map((panel) => {\n if (!firstPluginPanelMarked && !originalIds.has(panel.id)) {\n firstPluginPanelMarked = true;\n return { ...panel, separator: true };\n }\n return panel;\n });\n\n return {\n ...nextApp,\n config: mergePartialConfig(\n app.config || {},\n ...plugins\n .filter((plugin) => activeIds.has(plugin.metadata.id))\n .map((plugin) => plugin.extension.config || {}),\n nextApp.config || {},\n ),\n layout: {\n ...nextApp.layout,\n leftPanels: [...orderedPanels, ...dividePanels],\n backgroundActions: mergeBackgroundActionDefinitions([], nextApp.layout.backgroundActions || []),\n },\n };\n}\n","import { createStore } from \"zustand\";\nimport {\n disablePluginInConfig,\n enablePluginInConfig,\n mergeProviderPlugins,\n normalisePluginAppConfig,\n normalisePluginAppsConfig,\n pluginAppConfigEquals,\n} from \"./PluginContext.helpers\";\nimport type { Config } from \"../ConfigContext/ConfigContext\";\nimport type {\n MappedPlugin,\n PluginAppConfig,\n PluginConfigScope,\n PluginStore,\n} from \"./PluginContext.types\";\n\nexport function createPluginStore({\n plugins = [],\n enabled = [],\n disabled = [],\n globalPluginConfig,\n}: {\n plugins?: MappedPlugin[];\n enabled?: string[];\n disabled?: string[];\n globalPluginConfig?: Config[\"plugins\"];\n} = {}) {\n const unique = (values: string[] = []) => Array.from(new Set(values.filter(Boolean)));\n\n return createStore<PluginStore>((set) => ({\n plugins,\n enabled: unique(enabled),\n disabled: unique(disabled),\n globalApps: normalisePluginAppsConfig(globalPluginConfig),\n apps: {},\n\n setProviderState(state) {\n set((prev) => ({\n ...prev,\n plugins: mergeProviderPlugins(prev.plugins, state.plugins || []),\n enabled: unique(state.enabled || []),\n disabled: unique(state.disabled || []),\n globalApps: normalisePluginAppsConfig(state.globalPluginConfig),\n }));\n },\n\n setPluginLoading(id) {\n set((prev) => ({\n ...prev,\n plugins: prev.plugins.map((plugin) =>\n plugin.metadata.id === id\n ? { ...plugin, loadStatus: \"loading\", loadError: undefined }\n : plugin,\n ),\n }));\n },\n\n setPluginLoaded(id, plugin) {\n set((prev) => ({\n ...prev,\n plugins: prev.plugins.map((existing) =>\n existing.metadata.id === id\n ? {\n ...plugin,\n metadata: {\n ...existing.metadata,\n ...plugin.metadata,\n },\n settings: plugin.settings || existing.settings,\n load: existing.load,\n loadStatus: \"loaded\",\n loadError: undefined,\n }\n : existing,\n ),\n }));\n },\n\n setPluginLoadError(id, error) {\n set((prev) => ({\n ...prev,\n plugins: prev.plugins.map((plugin) =>\n plugin.metadata.id === id\n ? { ...plugin, loadStatus: \"error\", loadError: error }\n : plugin,\n ),\n }));\n },\n\n setAppConfig(appId, config) {\n const nextConfig = normalisePluginAppConfig(config);\n set((prev) => {\n if (pluginAppConfigEquals(prev.apps[appId], nextConfig)) {\n return prev;\n }\n\n return {\n ...prev,\n apps: {\n ...prev.apps,\n [appId]: nextConfig,\n },\n };\n });\n },\n\n setGlobalConfig(config) {\n set((prev) => ({\n ...prev,\n globalApps: normalisePluginAppsConfig(config),\n }));\n },\n\n setGlobalAppConfig(appId, config) {\n const nextConfig = normalisePluginAppConfig(config);\n set((prev) => {\n if (pluginAppConfigEquals(prev.globalApps[appId], nextConfig)) {\n return prev;\n }\n\n return {\n ...prev,\n globalApps: {\n ...prev.globalApps,\n [appId]: nextConfig,\n },\n };\n });\n },\n\n enable(appId, id, scope: PluginConfigScope = \"workspace\") {\n set((prev) => ({\n ...prev,\n plugins: prev.plugins.map((plugin) =>\n plugin.metadata.id === id && plugin.loadStatus === \"error\"\n ? { ...plugin, loadStatus: \"idle\", loadError: undefined }\n : plugin,\n ),\n ...(scope === \"global\"\n ? {\n globalApps: {\n ...prev.globalApps,\n [appId]: enablePluginInConfig(prev.globalApps[appId], id),\n },\n }\n : {\n apps: {\n ...prev.apps,\n [appId]: enablePluginInConfig(prev.apps[appId], id),\n },\n }),\n }));\n },\n\n disable(appId, id, scope: PluginConfigScope = \"workspace\") {\n set((prev) => ({\n ...prev,\n ...(scope === \"global\"\n ? {\n globalApps: {\n ...prev.globalApps,\n [appId]: disablePluginInConfig(prev.globalApps[appId], id),\n },\n }\n : {\n apps: {\n ...prev.apps,\n [appId]: disablePluginInConfig(prev.apps[appId], id),\n },\n }),\n }));\n },\n }));\n}\n","import {\n createContext,\n createElement,\n type ReactElement,\n type ReactNode,\n useCallback,\n useContext,\n useEffect,\n useMemo,\n} from \"react\";\nimport { type StoreApi, useStore } from \"zustand\";\nimport {\n AppReactContext,\n type MappedApp,\n PrimeAppReactContext,\n} from \"../AppContext/AppContext\";\nimport { type Config, useConfig, useSaveConfig } from \"../ConfigContext/ConfigContext\";\nimport {\n applyPlugins,\n createPluginRuntimeApi,\n getEmptyPluginState,\n getEnabledPluginsForApp,\n getEffectivePluginSettings,\n getPluginDefaultSettings,\n getPluginSettingsFromConfig,\n normalisePlugin,\n normalisePlugins,\n resetPluginSettingsInConfig,\n setPluginSettingsInConfig,\n} from \"./PluginContext.helpers\";\nimport { createPluginStore } from \"./PluginContext.store\";\nimport type {\n MappedPlugin,\n PluginAppConfig,\n PluginConfigScope,\n PluginRuntimeApi,\n PluginSettingsValue,\n PluginStore,\n PluginStoreSnapshot,\n PluginInput,\n} from \"./PluginContext.types\";\n\nexport const PluginReactContext = createContext<StoreApi<PluginStore> | null>(null);\nexport const PluginGlobalConfigReactContext = createContext<{\n globalPluginConfig?: Config[\"plugins\"];\n saveGlobalPluginConfig?: (config: Config[\"plugins\"]) => void | Promise<void>;\n}>({});\n\nexport function PluginProvider({\n plugins,\n enabled,\n disabled,\n globalPluginConfig,\n saveGlobalPluginConfig,\n children,\n}: {\n plugins: PluginInput[];\n enabled?: string[];\n disabled?: string[];\n globalPluginConfig?: Config[\"plugins\"];\n saveGlobalPluginConfig?: (config: Config[\"plugins\"]) => void | Promise<void>;\n children: ReactNode;\n}): ReactElement {\n const mappedPlugins = useMemo(() => normalisePlugins(plugins), [plugins]);\n const store = useMemo(\n () => createPluginStore({ plugins: mappedPlugins, enabled, disabled, globalPluginConfig }),\n [],\n );\n\n useEffect(() => {\n store.getState().setProviderState({\n plugins: mappedPlugins,\n enabled,\n disabled,\n globalPluginConfig,\n });\n }, [store, mappedPlugins, enabled, disabled, globalPluginConfig]);\n\n const globalConfigContext = useMemo(\n () => ({ globalPluginConfig, saveGlobalPluginConfig }),\n [globalPluginConfig, saveGlobalPluginConfig],\n );\n\n return createElement(\n PluginGlobalConfigReactContext.Provider,\n { value: globalConfigContext },\n createElement(PluginReactContext.Provider, { value: store }, children),\n );\n}\n\nexport function useOptionalPluginStoreApi() {\n return useContext(PluginReactContext);\n}\n\nexport function usePluginStoreApi() {\n const store = useOptionalPluginStoreApi();\n if (!store) {\n throw new Error(\"usePluginStoreApi must be used within <PluginProvider />\");\n }\n return store;\n}\n\nfunction usePluginStore<T>(selector: (state: PluginStoreSnapshot) => T): T {\n const store = useOptionalPluginStoreApi();\n if (!store) {\n return selector(getEmptyPluginState());\n }\n return useStore(store, selector);\n}\n\nexport function usePlugins(): PluginStoreSnapshot {\n return usePluginStore((state) => ({\n plugins: state.plugins,\n enabled: state.enabled,\n disabled: state.disabled,\n globalApps: state.globalApps,\n apps: state.apps,\n }));\n}\n\nexport function useEnabledPlugins(appId?: string): MappedPlugin[] {\n const appContext = useContext(AppReactContext);\n const app = useContext(PrimeAppReactContext);\n const state = usePlugins();\n const resolvedAppId = appId || appContext?.appId;\n\n return useMemo(\n () => getEnabledPluginsForApp(state, app, resolvedAppId),\n [state, app, resolvedAppId],\n );\n}\n\nexport function usePluginActions(): {\n enable(appId: string, id: string, scope?: PluginConfigScope): void;\n disable(appId: string, id: string, scope?: PluginConfigScope): void;\n setAppConfig(appId: string, config: PluginAppConfig): void;\n setGlobalAppConfig(appId: string, config: PluginAppConfig): void;\n} {\n const store = useOptionalPluginStoreApi();\n\n return useMemo(() => {\n if (!store) {\n return {\n enable() {\n // no-op\n },\n disable() {\n // no-op\n },\n setAppConfig() {\n // no-op\n },\n setGlobalAppConfig() {\n // no-op\n },\n };\n }\n\n return {\n enable(appId: string, id: string, scope?: PluginConfigScope) {\n store.getState().enable(appId, id, scope || \"workspace\");\n },\n disable(appId: string, id: string, scope?: PluginConfigScope) {\n store.getState().disable(appId, id, scope || \"workspace\");\n },\n setAppConfig(appId: string, config: PluginAppConfig) {\n store.getState().setAppConfig(appId, config);\n },\n setGlobalAppConfig(appId: string, config: PluginAppConfig) {\n store.getState().setGlobalAppConfig(appId, config);\n },\n };\n }, [store]);\n}\n\nexport function usePluginRuntimeApi(appId?: string): PluginRuntimeApi {\n const appContext = useContext(AppReactContext);\n const state = usePlugins();\n const resolvedAppId = appId || appContext?.appId;\n\n return useMemo(() => createPluginRuntimeApi(state, resolvedAppId), [state, resolvedAppId]);\n}\n\nexport function usePluginSettings<T extends PluginSettingsValue = PluginSettingsValue>(\n pluginId: string,\n appId?: string,\n): T {\n const appContext = useContext(AppReactContext);\n const state = usePlugins();\n const resolvedAppId = appId || appContext?.appId;\n\n return useMemo(\n () => getEffectivePluginSettings<T>(state, pluginId, resolvedAppId),\n [state, pluginId, resolvedAppId],\n );\n}\n\nexport function usePluginConfigApi<T extends PluginSettingsValue = PluginSettingsValue>(\n pluginId: string,\n appId?: string,\n) {\n const appContext = useContext(AppReactContext);\n const store = useOptionalPluginStoreApi();\n const state = usePlugins();\n const config = useConfig();\n const saveConfig = useSaveConfig();\n const { saveGlobalPluginConfig } = useContext(PluginGlobalConfigReactContext);\n const resolvedAppId = appId || appContext?.appId || \"\";\n const plugin = state.plugins.find((item) => item.metadata.id === pluginId) || null;\n const globalAppConfig = resolvedAppId ? state.globalApps[resolvedAppId] : undefined;\n const workspaceAppConfig = resolvedAppId ? state.apps[resolvedAppId] : undefined;\n\n const defaults = useMemo(() => getPluginDefaultSettings<T>(plugin || undefined), [plugin]);\n const global = useMemo(\n () => getPluginSettingsFromConfig<T>(globalAppConfig, pluginId) as T,\n [globalAppConfig, pluginId],\n );\n const workspace = useMemo(\n () => getPluginSettingsFromConfig<T>(workspaceAppConfig, pluginId) as T,\n [workspaceAppConfig, pluginId],\n );\n const effective = useMemo(\n () => getEffectivePluginSettings<T>(state, pluginId, resolvedAppId),\n [state, pluginId, resolvedAppId],\n );\n\n const persistWorkspaceAppConfig = useCallback(\n (nextAppConfig: PluginAppConfig) => {\n if (!resolvedAppId) return;\n store?.getState().setAppConfig(resolvedAppId, nextAppConfig);\n saveConfig({\n plugins: {\n ...(config.plugins || {}),\n apps: {\n ...(config.plugins?.apps || {}),\n [resolvedAppId]: nextAppConfig,\n },\n },\n });\n },\n [config.plugins, resolvedAppId, saveConfig, store],\n );\n\n const setWorkspaceSettings = useCallback(\n (settings: T) => {\n persistWorkspaceAppConfig(setPluginSettingsInConfig(workspaceAppConfig || {}, pluginId, settings));\n },\n [persistWorkspaceAppConfig, pluginId, workspaceAppConfig],\n );\n\n const resetWorkspaceSettings = useCallback(() => {\n persistWorkspaceAppConfig(resetPluginSettingsInConfig(workspaceAppConfig || {}, pluginId));\n }, [persistWorkspaceAppConfig, pluginId, workspaceAppConfig]);\n\n const persistGlobalAppConfig = useCallback(\n async (nextAppConfig: PluginAppConfig) => {\n if (!resolvedAppId || !saveGlobalPluginConfig) return;\n\n const previousAppConfig = state.globalApps[resolvedAppId] || {};\n const nextGlobalConfig: Config[\"plugins\"] = {\n apps: {\n ...state.globalApps,\n [resolvedAppId]: nextAppConfig,\n },\n };\n\n store?.getState().setGlobalAppConfig(resolvedAppId, nextAppConfig);\n\n try {\n await saveGlobalPluginConfig(nextGlobalConfig);\n } catch (error) {\n store?.getState().setGlobalAppConfig(resolvedAppId, previousAppConfig);\n throw error;\n }\n },\n [resolvedAppId, saveGlobalPluginConfig, state.globalApps, store],\n );\n\n const setGlobalSettings = useCallback(\n async (settings: T) => {\n await persistGlobalAppConfig(setPluginSettingsInConfig(globalAppConfig || {}, pluginId, settings));\n },\n [globalAppConfig, persistGlobalAppConfig, pluginId],\n );\n\n const resetGlobalSettings = useCallback(async () => {\n await persistGlobalAppConfig(resetPluginSettingsInConfig(globalAppConfig || {}, pluginId));\n }, [globalAppConfig, persistGlobalAppConfig, pluginId]);\n\n return {\n plugin,\n appId: resolvedAppId,\n defaults,\n global,\n workspace,\n effective,\n canSaveGlobal: !!saveGlobalPluginConfig,\n setWorkspaceSettings,\n resetWorkspaceSettings,\n setGlobalSettings,\n resetGlobalSettings,\n };\n}\n\nexport function useResolvedPluginApp(definition: MappedApp, appId: string): MappedApp {\n const state = usePlugins();\n const store = useOptionalPluginStoreApi();\n const enabledPlugins = useMemo(\n () => getEnabledPluginsForApp(state, definition, appId),\n [state, definition, appId],\n );\n\n useEffect(() => {\n if (!store) {\n return;\n }\n\n for (const plugin of enabledPlugins) {\n if (\n !plugin.load ||\n plugin.loadStatus === \"loading\" ||\n plugin.loadStatus === \"loaded\" ||\n plugin.loadStatus === \"error\"\n ) {\n continue;\n }\n\n store.getState().setPluginLoading(plugin.metadata.id);\n plugin\n .load()\n .then((loadedPlugin) => {\n store.getState().setPluginLoaded(plugin.metadata.id, normalisePlugin(loadedPlugin));\n })\n .catch((error) => {\n store\n .getState()\n .setPluginLoadError(plugin.metadata.id, getPluginLoadErrorMessage(error));\n });\n }\n }, [store, enabledPlugins]);\n\n return useMemo(\n () =>\n applyPlugins(\n definition,\n enabledPlugins.filter((plugin) => !plugin.load || plugin.loadStatus === \"loaded\"),\n appId,\n ),\n [definition, enabledPlugins, appId],\n );\n}\n\nfunction getPluginLoadErrorMessage(error: unknown) {\n if (error instanceof Error) return error.message;\n if (typeof error === \"string\") return error;\n return \"Plugin failed to load.\";\n}\n\nexport function PluginConfigBridge({ config }: { config?: Partial<Config> }) {\n const app = useContext(AppReactContext);\n const store = useOptionalPluginStoreApi();\n const appId = app?.appId;\n const appConfig = appId ? config?.plugins?.apps?.[appId] : undefined;\n\n useEffect(() => {\n if (!store || !appId) {\n return;\n }\n\n store.getState().setAppConfig(appId, appConfig || {});\n }, [store, appId, appConfig]);\n\n return null;\n}\n","import type { CreatorDefinition } from \"@manifest-editor/creator-api\";\nimport { useLocalStorage } from \"../hooks/use-local-storage\";\nimport { createContext, type ReactNode, type SetStateAction, useCallback, useContext, useEffect, useMemo } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport type { BackgroundActionDefinition } from \"../BackgroundTasks/BackgroundTasks.types\";\nimport { type Config, ConfigProvider } from \"../ConfigContext/ConfigContext\";\nimport type {\n AnnotationPanel,\n BackgroundPanel,\n CanvasEditorDefinition,\n EditorDefinition,\n LayoutPanel,\n LayoutProps,\n} from \"../Layout/Layout.types\";\nimport { useResolvedPluginApp } from \"../PluginContext/PluginContext\";\n\nexport type AppContext = {\n instanceId: string;\n appId: string;\n args?: any;\n};\n\nexport type LoadedApp = Partial<LayoutProps> & {\n config?: Partial<Config>;\n default: {\n id: string;\n title: string;\n type?: \"manifest\" | \"launcher\";\n project?: boolean;\n projectType?: \"Manifest\" | \"Collection\";\n dev?: boolean;\n desktop?: boolean;\n web?: boolean;\n drafts?: boolean;\n };\n};\n\nexport type MappedApp = {\n metadata: LoadedApp[\"default\"];\n layout: LayoutProps;\n config?: Partial<Config>;\n};\n\nexport interface AppExtension {\n config?: Partial<Config>;\n leftPanels?: LayoutPanel[];\n centerPanels?: LayoutPanel[];\n rightPanels?: LayoutPanel[];\n modalPanels?: LayoutPanel[];\n editors?: EditorDefinition[];\n creators?: CreatorDefinition[];\n canvasEditors?: CanvasEditorDefinition[];\n annotations?: AnnotationPanel[];\n background?: BackgroundPanel[];\n backgroundActions?: BackgroundActionDefinition[];\n // Config.\n leftPanelIds?: string[];\n\n // Side-effects.\n disableSideEffects?: string[];\n}\n\nexport type AppState = { state: null | any; setState: SetStateAction<any> };\n\nexport const PrimeAppReactContext = createContext<MappedApp | null>(null);\nexport const AppReactContext = createContext<AppContext | null>(null);\nexport const AppStateReactContext = createContext<{\n state: null | any;\n setState: SetStateAction<any>;\n}>({\n state: null,\n setState: () => {\n // no-op\n },\n});\n\nexport function useAppInstance() {\n const ctx = useContext(AppReactContext);\n invariant(ctx, \"Hook useAppInstance must be used inside <AppProvider />\");\n\n return ctx;\n}\n\nexport function useApp() {\n const app = useContext(PrimeAppReactContext);\n\n invariant(app, \"Hook useApp must be used inside <AppProvider />\");\n\n return app;\n}\n\nexport function useAppState<S = any>() {\n return useContext(AppStateReactContext);\n}\n\nfunction AppStateProvider(props: {\n instanceId: string;\n appId: string;\n initialState?: any;\n args?: any;\n children: ReactNode;\n}) {\n const [state, _setState, stateRef] = useLocalStorage(\n `app-state/${props.appId}/${props.instanceId}`,\n props.initialState || {},\n );\n\n const setState = useCallback((partial: any) => {\n const existing = stateRef.current ? JSON.parse(stateRef.current || \"{}\") : {};\n const partialState = (typeof partial === \"function\" ? partial(existing) : partial) || {};\n\n _setState({\n ...existing,\n ...partialState,\n });\n }, []);\n\n useEffect(() => {\n if (props.args) {\n setState(props.args);\n }\n }, [props.appId]);\n\n const ctx = useMemo(() => ({ state: state || {}, setState }), [setState, state]);\n\n return <AppStateReactContext.Provider value={ctx}>{props.children}</AppStateReactContext.Provider>;\n}\n\nexport function AppProvider({\n instanceId,\n appId,\n args,\n definition,\n children,\n initialState,\n}: {\n initialState?: any;\n instanceId: string;\n appId: string;\n args?: any;\n definition: MappedApp;\n children: ReactNode;\n}) {\n const ctx = useMemo(() => ({ instanceId, appId, args }), [instanceId, appId, args]);\n const _initialState = useMemo(() => initialState || {}, [instanceId]);\n const resolvedDefinition = useResolvedPluginApp(definition, appId);\n\n // Current App is now put in the \"Prime\" context.\n return (\n <ConfigProvider config={resolvedDefinition.config || {}}>\n <PrimeAppReactContext.Provider value={resolvedDefinition}>\n <AppReactContext.Provider value={ctx}>\n <AppStateProvider instanceId={ctx.instanceId} appId={ctx.appId} args={ctx.args} initialState={_initialState}>\n {children}\n </AppStateProvider>\n </AppReactContext.Provider>\n </PrimeAppReactContext.Provider>\n </ConfigProvider>\n );\n}\n","import { createContext, ReactNode, useContext, useMemo } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { useOptionalLocalStorage } from \"@manifest-editor/components\";\nimport { AppProvider } from \"./AppContext\";\n\ntype MappedApp = any;\n\nexport type MultiAppContext = {\n apps: Record<string, MappedApp>;\n currentApp: { id: string; args?: any };\n initialApp: { id: string; args?: any };\n changeApp: (app: { id: string; args?: any }) => void;\n changeProjectType: (type: \"Manifest\" | \"Collection\") => void;\n};\n\nconst MultiAppContext = createContext<MultiAppContext | null>(null);\n\nexport function useApps() {\n const ctx = useContext(MultiAppContext);\n\n invariant(ctx, \"Hook useApps must be used inside <MultiAppProvider />\");\n\n return ctx;\n}\n\nfunction useCurrentApp(\n initialApp?: { id: string; args?: any },\n enableLocalStorage = false,\n) {\n const [currentApp, changeApp] = useOptionalLocalStorage(\n \"SelectedApplication\",\n initialApp || { id: \"splash\" },\n !enableLocalStorage,\n );\n\n return [currentApp, changeApp] as const;\n}\n\nexport function MultiAppProvider({\n apps,\n initialApp,\n saveCurrentApp = true,\n instanceId,\n children,\n config = {},\n}: {\n apps: Record<string, MappedApp>;\n initialApp?: MultiAppContext[\"currentApp\"];\n saveCurrentApp?: boolean;\n instanceId: string;\n children: ReactNode;\n config?: {\n defaultApp?: string;\n manifestApp?: string;\n collectionApp?: string;\n };\n}) {\n const {\n defaultApp = \"splash\",\n collectionApp = \"collection-editor\",\n manifestApp = \"manifest-editor\",\n } = config;\n const [currentApp, changeApp] = useCurrentApp(initialApp, saveCurrentApp);\n\n const changeProjectType = (type: \"Manifest\" | \"Collection\") => {\n if (type === \"Manifest\") {\n changeApp({ id: manifestApp });\n }\n if (type === \"Collection\") {\n changeApp({ id: collectionApp });\n }\n };\n\n const ctx = useMemo<MultiAppContext>(\n () => ({\n currentApp: currentApp || { id: defaultApp },\n initialApp: initialApp || { id: defaultApp },\n apps,\n changeApp,\n changeProjectType,\n }),\n [initialApp, apps, currentApp],\n );\n\n const currentFullApp = apps[ctx.currentApp.id];\n if (!currentApp || !currentFullApp) {\n return null;\n }\n\n // Current App is now put in the \"Prime\" context.\n return (\n <AppProvider\n appId={currentApp.id}\n definition={currentFullApp}\n instanceId={currentApp.id + instanceId}\n args={currentApp.args}\n >\n <MultiAppContext.Provider value={ctx}>\n {children}\n </MultiAppContext.Provider>\n </AppProvider>\n );\n}\n","import styled from \"styled-components\";\nimport { SmallButton } from \"@manifest-editor/ui/atoms/Button\";\n\nexport const Container = styled.div`\n display: flex;\n align-items: center;\n height: 3em;\n padding: 0.5em;\n`;\n\nexport const Header = styled.div`\n display: flex;\n padding: 0.25em;\n flex-direction: column;\n`;\n\nexport const IconButton = styled.button`\n height: 1.75em;\n width: 1.75em;\n background: #e9e9e9;\n border-radius: 3px;\n display: flex;\n text-align: center;\n align-items: center;\n font-size: 1.1em;\n border: none;\n justify-content: center;\n\n &:focus {\n background: #e94581;\n color: #fff;\n svg {\n fill: #fff;\n }\n }\n`;\n\nexport const Spacer = styled.div`\n flex: 1;\n`;\n\nexport const Logo = styled.div`\n color: #6e6e6e;\n display: flex;\n align-items: center;\n margin-left: 1em;\n font-weight: bold;\n text-rendering: geometricPrecision;\n letter-spacing: -0.5px;\n user-select: none;\n cursor: pointer;\n margin-right: 0.5em;\n`;\n\nexport const ProjectPreview = styled.div`\n margin: 0 auto;\n padding: 3px;\n background: #f4f4f4;\n border: 1px solid #e0e0e0;\n border-radius: 5px;\n width: 26em;\n display: flex;\n flex-direction: row;\n\n @media (max-width: 450px) {\n display: none;\n }\n`;\n\nexport const ContextButton = styled.button`\n background: #e7fff4;\n border: 1px solid #c5e3cd;\n box-shadow: 0 1px 2px 0 rgba(0, 0, 0, 0.06);\n border-radius: 4px;\n color: #666666;\n padding: 0.35em 0.7em;\n letter-spacing: -0.42px;\n`;\n","export const CloseIcon: React.FC<{\n inline?: boolean;\n height?: number;\n className?: string;\n}> = ({ height = 16 }) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height={height} viewBox=\"0 0 24 24\" width=\"24px\" fill=\"currentColor\">\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path d=\"M19 6.41L17.59 5 12 10.59 6.41 5 5 6.41 10.59 12 5 17.59 6.41 19 12 13.41 17.59 19 19 17.59 13.41 12z\" />\n </svg>\n);\n","import { SVGProps } from \"react\";\n\nexport const DownIcon = ({ rotate = 0, ...props }: SVGProps<SVGSVGElement>) => (\n <svg\n version=\"1.2\"\n xmlns=\"http://www.w3.org/2000/svg\"\n overflow=\"visible\"\n preserveAspectRatio=\"none\"\n viewBox=\"0 0 24 24\"\n width=\"1em\"\n height=\"1em\"\n style={{\n fill: \"rgba(0, 0, 0, 0.6)\",\n transform: `rotate(${rotate}deg)`,\n transition: \"transform 0.2s\",\n }}\n {...props}\n >\n <path\n d=\"M8.12 9.29 12 13.17l3.88-3.88a.996.996 0 1 1 1.41 1.41l-4.59 4.59a.996.996 0 0 1-1.41 0L6.7 10.7a.996.996 0 0 1 0-1.41c.39-.38 1.03-.39 1.42 0z\"\n fill=\"currentColor\"\n />\n </svg>\n);\n","import { createContext, useContext } from \"react\";\nimport { CollectionContext, ManifestContext, VaultProvider, useExistingVault } from \"react-iiif-vault\";\nimport invariant from \"tiny-invariant\";\n\nexport interface Resource {\n id: string;\n type: string;\n}\n\nconst AppResourceReactProvider = createContext<Resource | null>(null);\nconst AppResourceInstanceReactProvider = createContext<string | null>(null);\n\nexport function useAppResourceInstance() {\n const ctx = useContext(AppResourceInstanceReactProvider);\n const resource = useContext(AppResourceReactProvider);\n\n const instanceId = ctx || resource?.id;\n\n invariant(instanceId, \"useResourceInstance can only be called from inside <ResourceProvider />\");\n\n return instanceId;\n}\n\nexport function useAppResource() {\n const ctx = useContext(AppResourceReactProvider);\n\n invariant(ctx, \"useResource can only be called from inside <ResourceProvider />\");\n\n return ctx;\n}\n\nexport function AppResourceInstanceProvider({ id, children }: { id?: string; children: React.ReactNode }) {\n if (!id) {\n return children;\n }\n return <AppResourceInstanceReactProvider.Provider value={id}>{children}</AppResourceInstanceReactProvider.Provider>;\n}\n\nexport function AppResourceProvider({ resource, children }: { resource?: Resource; children: React.ReactNode }) {\n const vault = useExistingVault();\n\n let inner = children;\n\n if (resource && resource.type === \"Manifest\") {\n inner = (\n <VaultProvider vault={vault || undefined}>\n <ManifestContext manifest={resource.id || \"\"}>{children}</ManifestContext>\n </VaultProvider>\n );\n }\n\n if (resource && resource.type === \"Collection\") {\n inner = (\n <VaultProvider vault={vault || undefined}>\n <CollectionContext collection={resource.id || \"\"}>{children}</CollectionContext>\n </VaultProvider>\n );\n }\n\n return <AppResourceReactProvider.Provider value={resource as any}>{inner}</AppResourceReactProvider.Provider>;\n}\n","import type { Vault } from \"@iiif/helpers/vault\";\nimport type { Preview, PreviewHandler } from \"../PreviewContext.types\";\n\nexport class ExternalManifestUrlPreview implements PreviewHandler {\n id: string;\n label: string;\n type = \"external-manifest-preview\";\n focusable = true;\n\n private readonly serviceUrl: string;\n private readonly windows: Record<string, { location: string; window: Window | null }> = {};\n\n constructor({ id, config, label }: { id: string; type?: string; label: string; config: { url: string } }) {\n this.id = id;\n this.label = label;\n this.serviceUrl = config.url;\n }\n\n isPreviewValid(instanceId: string): boolean {\n const current = this.windows[instanceId];\n if (current && current.window && !current.window.closed) {\n return true;\n }\n\n return false;\n }\n\n getRequires(): string[] {\n return [\"readOnlyManifest\"];\n }\n\n getProvides(): string[] {\n return [];\n }\n\n async createPreview(\n instanceId: string,\n resource: { id: string; type: string },\n vault: Vault,\n ctx: { readOnlyManifest: string },\n ): Promise<Preview> {\n // @todo change this to be a template, with more features.\n const location = `${this.serviceUrl}`\n .replace(/\\{manifestId}/, ctx.readOnlyManifest)\n .replace(/\\{time}/, `${Date.now()}`);\n const opened = window.open(location, this.id);\n\n this.windows[instanceId] = { location, window: opened };\n\n return {\n id: this.id,\n type: \"external-manifest-preview\",\n data: { url: location },\n };\n }\n\n async focus(instanceId: string) {\n const found = this.windows[instanceId];\n\n if (found && found.window) {\n found.window.focus();\n }\n }\n\n async updatePreview(\n instanceId: string,\n resource: { id: string; type: string },\n vault: Vault,\n ctx: { readOnlyManifest: string },\n ): Promise<Preview | null> {\n const found = this.windows[instanceId];\n\n if (found) {\n try {\n found.window?.close();\n } catch {}\n }\n\n return this.createPreview(instanceId, resource, vault, ctx);\n }\n\n async deletePreview(id: string): Promise<void> {\n const found = this.windows[id];\n if (found && found.window) {\n found.window.close();\n delete this.windows[id];\n }\n }\n}\n","import { Vault } from \"@iiif/helpers/vault\";\nimport { Preview, PreviewConfiguration, PreviewHandler } from \"../PreviewContext.types\";\nimport invariant from \"tiny-invariant\";\n\ntype IIIFPreviewResponse = {\n location: string;\n updateLocation?: string;\n deleteLocation?: string;\n expirationTtl: number;\n};\n\nexport class IIIFPreviewService implements PreviewHandler {\n id: string;\n label: string;\n type = \"iiif-preview-service\";\n focusable = false;\n\n private readonly serviceUrl: string;\n private readonly cache: Record<string, IIIFPreviewResponse & { time: number }> = {};\n\n constructor({ id, config, label }: PreviewConfiguration<{ url: string }>) {\n this.id = id;\n this.label = label;\n this.serviceUrl = config.url;\n }\n\n getRequires(): string[] {\n return [];\n }\n\n getProvides(): string[] {\n return [\"readOnlyManifest\"];\n }\n\n async isPreviewValid(instanceId: string, instance: Preview): Promise<boolean> {\n if (!!this.cache[instanceId]) {\n return true;\n }\n\n if (!instance || !instance.data || !instance.data.readOnlyManifest) {\n return false;\n }\n\n const urlToCheck = instance.data.readOnlyManifest;\n try {\n const resp = await fetch(urlToCheck, {\n cache: \"no-cache\",\n });\n return resp.ok;\n } catch (e) {\n return false;\n }\n }\n\n async createPreview(instanceId: string, resource: { id: string; type: string }, vault: Vault): Promise<Preview> {\n const manifest = vault.toPresentation3(resource as any);\n const response = await fetch(this.serviceUrl, {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Origin: \"*\",\n },\n body: JSON.stringify(manifest),\n });\n\n invariant(response.ok, \"Unknown error creating preview\");\n\n const json = await response.json();\n\n invariant(json.location, \"Missing IIIF location while creating preview\");\n\n this.cache[instanceId] = { ...json, time: Date.now() };\n\n return {\n id: this.id,\n type: \"external-manifest-preview\",\n data: {\n readOnlyManifest: `${json.location}/${Date.now()}`,\n },\n };\n }\n\n async focus() {\n // no op.\n }\n\n async updatePreview(instanceId: string, resource: { id: string; type: string }, vault: Vault): Promise<Preview> {\n const cached = this.cache[instanceId];\n if (!cached || Date.now() > cached.expirationTtl + cached.time || !cached.updateLocation) {\n return this.createPreview(instanceId, resource, vault);\n }\n\n const updateUrl = cached.updateLocation;\n const manifest = vault.toPresentation3(resource as any);\n\n const response = await fetch(updateUrl, {\n method: \"PUT\",\n headers: {\n \"Content-Type\": \"application/json\",\n Origin: \"*\",\n },\n body: JSON.stringify(manifest),\n });\n\n invariant(response.ok, \"Unknown error updating preview\");\n\n const json = await response.json();\n\n invariant(json.location);\n\n if (json.updateLocation) {\n cached.updateLocation = json.updateLocation;\n }\n\n const readOnlyManifest = `${json.location}/${Date.now()}`;\n\n // Make a fetch, fill the cache (preview may not)\n await fetch(readOnlyManifest, {\n cache: \"no-cache\",\n });\n\n return {\n id: this.id,\n type: \"external-manifest-preview\",\n data: {\n readOnlyManifest: `${json.location}/${Date.now()}`,\n },\n };\n }\n\n async deletePreview(id: string): Promise<void> {\n const cached = this.cache[id];\n if (cached && cached.deleteLocation) {\n try {\n await fetch(cached.deleteLocation, {\n method: \"DELETE\",\n headers: {\n \"Content-Type\": \"application/json\",\n Origin: \"*\",\n },\n });\n } catch (e) {\n // no-op, we tried.\n }\n }\n }\n}\n","import { type Dispatch, useMemo } from \"react\";\nimport { useVault } from \"react-iiif-vault\";\nimport invariant from \"tiny-invariant\";\nimport { useAppResource, useAppResourceInstance } from \"../AppResourceProvider/AppResourceProvider\";\nimport type {\n Preview,\n PreviewActions,\n PreviewActionsType,\n PreviewConfiguration,\n PreviewHandler,\n PreviewState,\n} from \"./PreviewContext.types\";\nimport { ExternalManifestUrlPreview } from \"./previews/ExternalManifestUrlPreview\";\nimport { IIIFPreviewService } from \"./previews/IIIFPreviewService\";\n\nexport function usePreviewActions(\n state: PreviewState,\n dispatch: Dispatch<PreviewActionsType>,\n handlers: PreviewHandler[],\n previews: Preview[],\n setPreviews: (previews: Preview[] | ((prev: Preview[]) => Preview[])) => void,\n): PreviewActions {\n const resource = useAppResource();\n const instanceId = useAppResourceInstance();\n const vault = useVault();\n\n const previewActions = useMemo(\n () => ({\n setPreview: (preview: Preview) => {\n if (!preview) return;\n setPreviews((prev) => [...prev.filter((item) => item.id !== preview.id), preview]);\n },\n removePreview: (id: string) => {\n setPreviews((prev) => prev.filter((p) => p.id !== id));\n },\n }),\n [setPreviews, instanceId],\n );\n //\n const [handlerMap, providesMap] = useMemo(() => {\n const map: Record<string, PreviewHandler> = {};\n const providesMap: Record<string, string> = {};\n for (const handler of handlers) {\n map[handler.id] = handler;\n const provides = handler.getProvides();\n if (provides.length) {\n for (const singleProvides of provides) {\n if (!providesMap[singleProvides]) {\n providesMap[singleProvides] = handler.id;\n }\n }\n }\n }\n return [map, providesMap] as const;\n }, [handlers]);\n\n async function updatePreviews() {\n const selected = state.selected;\n const selectedPreview = previews.find((p) => p.id === selected);\n if (previews && previews.length && selectedPreview) {\n const selectedHandler = handlerMap[selectedPreview.id]!;\n const requires = selectedHandler.getRequires();\n // Build context.\n const context: any = {};\n for (const preview of previews) {\n const fullPreview = handlerMap[preview.id];\n if (fullPreview) {\n const provides = fullPreview.getProvides();\n for (const provide of provides) {\n if (requires.indexOf(provide) !== -1) {\n const newPreview = await fullPreview.updatePreview(instanceId, resource, vault, context);\n if (newPreview) {\n previewActions.setPreview(newPreview);\n dispatch({ type: \"activatePreview\", payload: newPreview.id });\n Object.assign(context, newPreview.data || {});\n }\n }\n }\n }\n }\n\n // Select\n const handler = handlerMap[selectedPreview.id];\n if (handler) {\n const newPreview = await handler.updatePreview(instanceId, resource, vault, context);\n if (newPreview) {\n previewActions.setPreview(newPreview);\n } else {\n previewActions.removePreview(selectedPreview.id);\n await handler.deletePreview(instanceId);\n }\n }\n }\n }\n\n async function selectPreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (selectedHandler && instanceId) {\n dispatch({ type: \"selectPreview\", payload: id });\n await activatePreview(id);\n }\n }\n\n // Be able to generate a preview link on demand from the iiif-preview-service, if available.\n async function getPreviewLink(): Promise<null | string> {\n const handlerId = providesMap[\"readOnlyManifest\"];\n const previewService = handlerId ? handlerMap[handlerId] : null;\n\n if (previewService && instanceId) {\n const existing = previews.find((p) => p.type === \"iiif-preview-service\");\n if (!existing || !(await previewService.isPreviewValid(instanceId, existing))) {\n const preview = await previewService.createPreview(instanceId, resource, vault, {});\n if (preview) {\n return preview.data.readOnlyManifest;\n }\n }\n }\n return null;\n }\n\n function deletePreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (selectedHandler && instanceId) {\n previewActions.removePreview(id);\n selectedHandler.deletePreview(instanceId).then(() => {\n dispatch({ type: \"deletePreview\", payload: id });\n });\n }\n }\n\n async function focusPreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (handlerMap[id] && instanceId && selectedHandler) {\n await selectedHandler.focus(instanceId);\n dispatch({ type: \"focusPreview\", payload: id });\n }\n }\n\n async function activatePreview(id: string) {\n const selectedHandler = handlerMap[id];\n if (selectedHandler && instanceId) {\n const existingPreview = previews.find((p) => p.id === id);\n if (!existingPreview || !selectedHandler.isPreviewValid(instanceId, existingPreview)) {\n const context: any = {};\n const requires = selectedHandler.getRequires();\n // @todo this could be recursive, but not doing that yet.\n for (const requirement of requires) {\n const handlerId = providesMap[requirement];\n const handler = handlerId ? handlerMap[handlerId] : null;\n\n invariant(handler, `Missing handler for Preview requirement \"${requirement}\"`);\n const existing = previews.find((p) => p.id === handlerId);\n const existingIsActive = state.active.find((a) => a === handlerId);\n\n const alwaysCreate = true as boolean;\n\n if (alwaysCreate || !existing || !(await handler.isPreviewValid(instanceId, existing))) {\n const contextualPreview = await handler.createPreview(instanceId, resource, vault, context);\n Object.assign(context, contextualPreview?.data || {});\n previewActions.setPreview(contextualPreview);\n dispatch({\n type: \"activatePreview\",\n payload: contextualPreview.id,\n });\n } else {\n Object.assign(context, existing?.data || {});\n dispatch({ type: \"activatePreview\", payload: existing.id });\n }\n }\n const created = await selectedHandler.createPreview(instanceId, resource, vault, context);\n if (created) {\n previewActions.setPreview(created);\n dispatch({ type: \"activatePreview\", payload: created.id });\n }\n }\n }\n }\n\n return useMemo(\n () => ({\n selectPreview,\n deletePreview,\n focusPreview,\n activatePreview,\n updatePreviews,\n getPreviewLink,\n }),\n // Dispatch has a stable identity.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n [handlerMap, instanceId, vault, state.selected, state.active, previews],\n );\n}\n\nexport function usePreviewHandlers(configs: PreviewConfiguration[]): PreviewHandler[] {\n // @todo in the future the available classes could come from somewhere else and not hardcoded.\n return useMemo(() => {\n const handlers: PreviewHandler[] = [];\n\n for (const config of configs) {\n switch (config.type) {\n case \"iiif-preview-service\":\n handlers.push(new IIIFPreviewService(config));\n break;\n case \"external-manifest-preview\":\n handlers.push(new ExternalManifestUrlPreview(config));\n break;\n }\n }\n return handlers;\n\n // @todo if these ever become configurable, remove this.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n}\n","import { Draft, produce } from \"immer\";\nimport { PreviewActionsType, PreviewContext, PreviewState } from \"./PreviewContext.types\";\n\nexport const previewContextReducer = produce(function reducer(state: Draft<PreviewState>, action: PreviewActionsType) {\n switch (action.type) {\n case \"focusPreview\": {\n break;\n }\n\n case \"deletePreview\": {\n if (state.selected === action.payload) {\n state.selected = null;\n }\n state.active = state.active.filter((p) => p !== action.payload);\n break;\n }\n\n case \"activatePreview\": {\n if (state.active.indexOf(action.payload) === -1) {\n state.active.push(action.payload);\n }\n break;\n }\n\n case \"selectPreview\": {\n state.selected = action.payload;\n if (state.active.indexOf(action.payload) === -1) {\n state.active.push(action.payload);\n }\n break;\n }\n }\n});\n\nexport function getDefaultPreviewState(): PreviewState {\n return {\n active: [],\n selected: null,\n };\n}\n","import { createContext, memo, ReactNode, useContext, useEffect, useMemo, useReducer } from \"react\";\nimport { Preview, PreviewConfiguration, PreviewContext } from \"./PreviewContext.types\";\nimport invariant from \"tiny-invariant\";\nimport { usePreviewActions, usePreviewHandlers } from \"./PreviewContext.hooks\";\nimport { getDefaultPreviewState, previewContextReducer } from \"./PreviewContext.reducer\";\nimport { useAppResourceInstance } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useLocalStorage } from \"../hooks/use-local-storage\";\n\nconst PreviewReactContext = createContext<PreviewContext | null>(null);\nconst AvailablePreviewReactContext = createContext<Preview[]>([] as Preview[]);\n\nexport const PreviewProvider = memo(function PreviewProvider({\n children,\n configs = [],\n}: {\n previews: Preview[];\n children: ReactNode;\n configs: PreviewConfiguration[];\n}) {\n const instanceId = useAppResourceInstance();\n const handlers = usePreviewHandlers(configs); \n const [previews, setPreviews] = useLocalStorage<Preview[]>(`preview-${instanceId}`, []);\n\n const [state, dispatch] = useReducer(previewContextReducer, undefined, getDefaultPreviewState);\n const actions = usePreviewActions(state, dispatch, handlers, previews, setPreviews);\n const context: PreviewContext = useMemo(\n () => ({ configs, actions, handlers, ...state }),\n [actions, configs, handlers, state]\n );\n\n useEffect(() => {\n for (const preview of previews) {\n if (!state.active.includes(preview.id)) {\n const handler = handlers.find((h) => h.id === preview.id);\n if (handler) {\n Promise.resolve(handler.isPreviewValid(instanceId, preview)).then((valid) => {\n if (valid) {\n dispatch({ type: \"activatePreview\", payload: preview.id });\n } else {\n setPreviews((prev) => prev.filter((p) => p.id !== preview.id));\n }\n });\n }\n }\n }\n }, [instanceId]);\n\n return (\n <AvailablePreviewReactContext.Provider value={previews}>\n <PreviewReactContext.Provider value={context}>{children}</PreviewReactContext.Provider>\n </AvailablePreviewReactContext.Provider>\n );\n});\n\nexport function usePreviews() {\n return useContext(AvailablePreviewReactContext);\n}\n\nexport function usePreviewContext() {\n const ctx = useContext(PreviewReactContext);\n\n invariant(ctx, \"usePreviewContext() can only be called from inside <PreviewProvider />\");\n\n return ctx;\n}\n","import styled from \"styled-components\";\n\nexport const ButtonReset = styled.button`\n border: none;\n outline: none;\n background-color: transparent;\n margin: 0;\n padding: 0;\n font-size: inherit;\n color: inherit;\n cursor: pointer;\n &:hover {\n color: inherit;\n }\n`;\n\nexport const Button = styled.button<{ $active?: boolean }>`\n padding: 0.5rem 1rem;\n color: ${(props: any) => props.theme.color.main || \"none\"};\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n border-radius: inherit;\n border: none;\n cursor: pointer;\n display: flex;\n align-items: center;\n font-size: 0.85em;\n :disabled {\n opacity: 0.65;\n cursor: not-allowed;\n }\n\n &:hover {\n background: #eee;\n }\n`;\n\nexport const SmallButton = styled(Button as any)`\n padding: 0.25em ${(props: any) => props.theme.padding.xs || \"0.4em\"};\n height: unset;\n background: none;\n`;\n\nexport const SecondaryButton = styled(Button as any)`\n {\n padding: 0 ${(props: any) => props.theme.padding.medium || \"1rem\"};\n color: ${(props: any) => props.theme.color.main || \"#B84C74;\"};\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n border: 1px solid ${(props: any) => props.theme.color.main || \"#B84C74;\"};\n border-radius: 0.25rem;\n cursor: pointer;\n height: 2rem;\n display: flex;\n align-items: center;\n white-space: nowrap;\n font-size: 0.75rem;\n\n :disabled {\n opacity: 0.65;\n cursor: not-allowed;\n }\n }\n`;\n\nexport const CalltoButton = styled(Button as any)`\n padding: 0 ${(props: any) => props.theme.padding.medium || \"1rem\"};\n color: ${(props: any) => props.theme.color.white || \"white\"};\n background-color: ${(props: any) => props.theme.color.main || \"#B84C74;\"};\n border: 1px solid #eee;\n border-radius: 0.25rem;\n cursor: pointer;\n justify-content: center;\n display: flex;\n align-items: center;\n &:hover {\n background-color: ${(props: any) => props.theme.color.mainHover || \"#B84C74;\"};\n }\n`;\n\nexport const ButtonGroup = styled.div<{ $right?: boolean }>`\n display: flex;\n flex-direction: row;\n flex-wrap: wrap;\n align-items: flex-start;\n justify-content: ${(props) => (props.$right ? \"flex-end\" : \"flex-start\")};\n`;\n","import styled, { css } from \"styled-components\";\nimport { ButtonReset } from \"@manifest-editor/ui/atoms/Button\";\n\nexport const ButtonContainer = styled.div`\n display: flex;\n position: relative;\n width: 10em;\n`;\n\nconst variation = {\n light: {\n bg: { normal: \"#fff\", hover: \"#f8f5fe\", active: \"#f8f5fe\" },\n border: { main: \"\", divider: \"\" },\n color: \"\",\n },\n salmon: {\n bg: { normal: \"#B84C74\", hover: \"#892C4E\", active: \"#892C4E\" },\n border: { main: \"#B84C74\", divider: \"#e37266\" },\n color: \"\",\n },\n};\n\nexport const ButtonMain = styled(ButtonReset as any)`\n flex: 1;\n padding: 0.5em 0.8em;\n background: #b84c74;\n color: #fff;\n border-top-left-radius: 5px;\n font-size: 0.875em;\n border-bottom-left-radius: 5px;\n border: 1px solid #b84c74;\n border-right-width: 0;\n\n &:hover {\n color: #fff;\n background: #892c4e;\n border-color: #892c4e;\n }\n\n &:active {\n background: #892c4e;\n box-shadow: inset 0 2px 8px 0 rgba(0, 0, 0, 0.15);\n }\n`;\n\nexport const ButtonChange = styled(ButtonReset as any)<{ $open: boolean }>`\n background: #b84c74;\n border-top-right-radius: 5px;\n border-bottom-right-radius: 5px;\n border: 1px solid #b84c74;\n border-left: 1px solid #fff;\n padding: 0.4em;\n color: #fff;\n svg {\n fill: currentColor;\n }\n &:hover {\n color: #fff;\n background: #892c4e;\n }\n\n &:active {\n background: #892c4e;\n box-shadow: inset 0 2px 8px 0 rgba(0, 0, 0, 0.15);\n }\n\n ${(props) =>\n props.$open &&\n css`\n background: #892c4e;\n box-shadow: inset 0 2px 8px 0 rgba(0, 0, 0, 0.15);\n `}\n`;\n\nexport const MenuContainer = styled.div<{ $open: boolean }>`\n position: absolute;\n opacity: 0;\n top: 100%;\n margin-top: 0.3em;\n border-radius: 3px;\n left: -50%;\n width: 150%;\n pointer-events: none;\n box-shadow:\n 0 4px 15px 0 rgba(0, 0, 0, 0.18),\n 0 0px 0px 1px rgba(0, 0, 0, 0.15),\n inset 0 0 0 1px rgba(255, 255, 255, 0.2);\n background: #fff;\n color: #25211f;\n overflow: hidden;\n\n ${(props) =>\n props.$open &&\n css`\n opacity: 1;\n pointer-events: visible;\n `}\n`;\n\nexport const MenuItem = styled.div`\n display: flex;\n background: #fff;\n color: #25211f;\n padding: 0.4em;\n align-items: center;\n\n &:hover {\n background: #f9f9f9;\n }\n`;\n\nconst statusMap = {\n available: \"#ddd\",\n configured: \"#e37266\",\n active: \"#4cb235\",\n};\n\nexport const MenuItemStatus = styled.div<{ $status: \"available\" | \"configured\" | \"active\" }>`\n margin: 0.2em 0.5em;\n width: 8px;\n height: 8px;\n border-radius: 50%;\n background-color: ${(props) => statusMap[props.$status]};\n`;\n\nexport const MenuItemLabel = styled.div`\n flex: 1;\n font-size: 0.925em;\n color: #25211f;\n padding: 0.2em;\n text-overflow: ellipsis;\n cursor: pointer;\n white-space: nowrap;\n overflow: hidden;\n`;\n\nexport const MenuItemClose = styled.div`\n background: #f9f9f9;\n font-size: 0.8em;\n`;\n\nexport const ButtonEmpty = styled.div`\n color: #999;\n font-size: 0.8em;\n padding: 0.6em 0.8em;\n border: 2px dashed #f9f9f9;\n border-radius: 5px;\n user-select: none;\n cursor: not-allowed;\n`;\n","import { DownloadButton } from \"@manifest-editor/components\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { DownIcon } from \"@manifest-editor/ui/icons/DownIcon\";\nimport useDropdownMenu from \"react-accessible-dropdown-menu-hook\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useConfig } from \"../ConfigContext/ConfigContext\";\nimport { usePreviewContext } from \"../PreviewContext/PreviewContext\";\nimport {\n ButtonChange,\n ButtonContainer,\n ButtonEmpty,\n ButtonMain,\n MenuContainer,\n MenuItem,\n MenuItemClose,\n MenuItemLabel,\n MenuItemStatus,\n} from \"./PreviewButton.styles\";\n\nexport function PreviewButton({ downloadEnabled, fileName }: { downloadEnabled?: boolean; fileName?: string }) {\n const { active, configs, actions, selected } = usePreviewContext();\n const vault = useVault();\n const config = useConfig();\n const resource = useAppResource();\n const configsToShow = configs.filter((c) => c.type === \"external-manifest-preview\");\n const { isOpen, buttonProps, itemProps } = useDropdownMenu(configsToShow.length);\n\n if (configsToShow.length === 0) {\n return <ButtonEmpty>Preview not available</ButtonEmpty>;\n }\n\n return (\n <>\n {downloadEnabled ? (\n <div className=\"mr-4\">\n <DownloadButton\n fileName={fileName || \"manifest.json\"}\n label=\"Download manifest\"\n getData={() => {\n if (config.export && config.export.version === 2) {\n return JSON.stringify(vault.toPresentation2(resource as any), null, 2);\n }\n return JSON.stringify(vault.toPresentation3(resource as any), null, 2);\n }}\n />\n </div>\n ) : null}\n <ButtonContainer>\n <ButtonMain\n onClick={() => {\n if (!selected) {\n const defaultPreviewId = config.defaultPreview;\n if (defaultPreviewId) {\n const found = configs.find((c) => c.id === defaultPreviewId);\n if (found) {\n actions.selectPreview(found.id);\n return;\n }\n }\n\n actions.selectPreview(configs[0]!.id);\n }\n actions.updatePreviews();\n }}\n >\n Preview\n </ButtonMain>\n <ButtonChange $open={isOpen} {...buttonProps}>\n <DownIcon />\n </ButtonChange>\n\n <MenuContainer $open={isOpen}>\n {configsToShow.map((config, key) => {\n const inactive = active.indexOf(config.id) === -1;\n return (\n <MenuItem key={config.id} {...(itemProps[key] as any)}>\n <MenuItemStatus $status={inactive ? \"available\" : config.id === selected ? \"active\" : \"configured\"} />\n <MenuItemLabel\n onClick={() => {\n actions.selectPreview(config.id);\n }}\n >\n {config.label}\n </MenuItemLabel>\n {!inactive ? (\n <MenuItemClose onClick={() => actions.deletePreview(config.id)}>\n <CloseIcon />\n </MenuItemClose>\n ) : null}\n </MenuItem>\n );\n })}\n </MenuContainer>\n </ButtonContainer>\n </>\n );\n}\n","import { toRef } from \"@iiif/parser\";\nimport type {\n EditingStackActionCreators,\n EditingStackState,\n} from \"./EditingStack.types\";\n\nexport function editingStackReducer(\n state: EditingStackState,\n action: EditingStackActionCreators,\n): EditingStackState {\n switch (action.type) {\n case \"setStack\": {\n return {\n ...state,\n stack: action.payload.resources,\n current: action.payload.resources[0] || null,\n };\n }\n\n case \"edit\": {\n let reset = action.payload.reset;\n if (\n action.payload.resource?.resource.source?.type === \"Manifest\" ||\n action.payload.resource?.resource.source?.type === \"Canvas\"\n ) {\n reset = true;\n }\n\n if (\n state.current?.resource.source.id ===\n action.payload.resource?.resource.source.id\n ) {\n return {\n ...state,\n current: action.payload.resource,\n };\n }\n\n return {\n ...state,\n current: action.payload.resource,\n stack: reset\n ? []\n : state.current\n ? [state.current, ...state.stack]\n : state.stack,\n };\n }\n case \"syncRemoval\": {\n const item = toRef(action.payload.resource.resource);\n if (!item) {\n return state;\n }\n const found = state.stack.find((r) => toRef(r.resource)?.id === item.id);\n\n if (!found) {\n return state;\n }\n\n const newCurrent =\n state.current?.resource.id === item.id ? null : state.current;\n const newStack = filterStack(\n state.stack.filter((r) => toRef(r.resource)?.id !== item.id),\n newCurrent,\n );\n\n return {\n ...state,\n stack: newStack,\n current: newCurrent,\n };\n }\n case \"updateCurrent\": {\n return {\n ...state,\n current: action.payload.resource,\n };\n }\n\n case \"back\": {\n const newCurrent = state.stack[0];\n return {\n ...state,\n stack: state.stack.slice(1),\n current: newCurrent || null,\n };\n }\n\n case \"close\": {\n return {\n ...state,\n stack: [], // @todo maybe not right?\n current: null,\n };\n }\n\n case \"create\": {\n if (action.payload.resource === null) {\n return { ...state, create: null };\n }\n\n return {\n ...state,\n create: action.payload as any,\n };\n }\n }\n\n return state;\n}\n\nfunction filterStack(\n newStackWithDuplicates: EditingStackState[\"stack\"],\n current: EditingStackState[\"current\"],\n): EditingStackState[\"stack\"] {\n const newStack = [];\n let prev = null;\n for (const stackItem of newStackWithDuplicates) {\n if (prev?.resource.id === stackItem.resource.id) {\n continue;\n }\n newStack.push(stackItem);\n prev = stackItem;\n }\n\n if (prev && prev.resource.id === current?.resource.id) {\n return newStack.slice(0, newStack.length - 1);\n }\n\n return newStack;\n}\n","import { toRef } from \"@iiif/parser\";\nimport type { Reference, SpecificResource } from \"@iiif/presentation-3\";\nimport { EditorInstance } from \"@manifest-editor/editor-api\";\nimport { createContext, useCallback, useContext, useEffect, useMemo, useReducer } from \"react\";\nimport { flushSync } from \"react-dom\";\nimport { useResourceContext, useVault } from \"react-iiif-vault\";\nimport invariant from \"tiny-invariant\";\nimport { useAppInstance } from \"../AppContext/AppContext\";\nimport { editingStackReducer } from \"./EditingStack.reducer\";\nimport type { EditableResource, EditingStackActions, EditingStackState } from \"./EditingStack.types\";\n\nconst defaultState: EditingStackState = { stack: [], current: null, create: null };\nexport const EditingStackContext = createContext<EditingStackState>(defaultState);\nconst EditingStackActionsContext = createContext<EditingStackActions>({\n edit() {},\n close() {},\n back() {},\n setStack() {},\n updateCurrent() {},\n create() {\n return () => {};\n },\n});\n\nexport function useEditingStack() {\n return useContext(EditingStackActionsContext);\n}\n\nexport function useEditingResource() {\n return useContext(EditingStackContext).current;\n}\n\nexport function useEditingResourceStack() {\n return useContext(EditingStackContext).stack;\n}\n\nexport function useCreatingResource() {\n return useContext(EditingStackContext).create;\n}\n\nexport function useManifestEditor() {\n const { manifest } = useResourceContext();\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n invariant(manifest, \"Manifest not found\");\n\n const editor = useMemo(() => {\n return new EditorInstance({\n reference: { id: manifest, type: \"Manifest\" },\n vault,\n });\n }, [manifest, vault]);\n\n useEffect(() => {\n return editor.observe.start(invalidate);\n }, [editor]);\n\n editor.observe.key = `${key}`;\n editor.observe.reset();\n\n return editor;\n}\n\nexport function useCollectionEditor() {\n const { collection } = useResourceContext();\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n invariant(collection, \"Collection not found\");\n\n const editor = useMemo(() => {\n return new EditorInstance({\n reference: { id: collection, type: \"Collection\" },\n vault,\n });\n }, [collection, vault]);\n\n useEffect(() => {\n return editor.observe.start(invalidate);\n }, [editor]);\n\n editor.observe.key = `${key}`;\n editor.observe.reset();\n\n return editor;\n}\n\nexport function useGenericEditor(\n ref: Reference<any> | SpecificResource | undefined,\n ctx: { parent?: Reference; parentProperty?: string; index?: number; allowNull?: boolean } = {},\n) {\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n !ctx.allowNull && invariant(ref, \"Resource not found\");\n\n const editor = useMemo(() => {\n if (ctx.allowNull && !ref) {\n return null as any as EditorInstance<{}>;\n }\n\n return new EditorInstance({\n reference: toRef(ref) as any,\n vault,\n context: { resource: ref!, parent: ctx.parent, index: ctx.index, parentProperty: ctx.parentProperty },\n });\n }, [ref, vault]);\n\n useEffect(() => {\n return editor?.observe.start(invalidate);\n }, [editor]);\n\n if (editor) {\n editor.observe.key = `${key}`;\n editor.observe.reset();\n }\n\n return editor!;\n}\n\nexport function useAnnotationPageEditor() {\n const { annotationPage } = useResourceContext();\n\n invariant(annotationPage, \"Annotation page not found\");\n\n return useGenericEditor({ id: annotationPage, type: \"AnnotationPage\" });\n}\n\nexport function useEditor() {\n const resource = useEditingResource();\n const vault = useVault();\n const [key, invalidate] = useReducer((i: number) => i + 1, 0);\n\n invariant(resource, \"No resource selected\");\n\n const editor = useMemo(() => {\n return new EditorInstance({\n reference: resource.resource.source || resource.resource,\n vault,\n });\n }, [resource, vault]);\n\n useEffect(() => {\n return editor.observe.start(invalidate);\n }, [editor]);\n\n editor.observe.key = `${key}`;\n editor.observe.reset();\n\n return editor;\n}\n\nfunction useInternalEditingStackActions(defaultState: EditingStackState) {\n const vault = useVault();\n const [state, _dispatch] = useReducer(editingStackReducer, defaultState);\n\n const dispatch = useCallback((action: any) => {\n _dispatch(action);\n // (() => flushSync(() => _dispatch(action)))();\n }, []);\n\n useEffect(() => {\n return vault.on(\"@iiif/REMOVE_REFERENCE\", (payload: any) => {\n const action = payload.action;\n const parent = { id: action.payload.id, type: action.payload.type };\n const resource = action.payload.reference;\n _dispatch({ type: \"syncRemoval\", payload: { resource: { parent, resource } } });\n });\n }, [vault]);\n\n const edit = useCallback(\n (resource: EditableResource, reset = false) => dispatch({ type: \"edit\", payload: { resource, reset } }),\n [],\n );\n\n const setStack = useCallback(\n (resources: EditableResource[]) => dispatch({ type: \"setStack\", payload: { resources } }),\n [],\n );\n\n const updateCurrent = useCallback(\n (resource: EditableResource) => dispatch({ type: \"updateCurrent\", payload: { resource } }),\n [],\n );\n\n const close = useCallback(() => dispatch({ type: \"close\" }), []);\n\n const back = useCallback(() => dispatch({ type: \"back\" }), []);\n\n const create = useCallback<EditingStackActions[\"create\"]>((resource, options) => {\n dispatch({ type: \"create\", payload: { resource, options } });\n\n // Returns function when complete.\n return () => {\n dispatch({ type: \"create\", payload: { resource: null } });\n };\n }, []);\n\n const actions: EditingStackActions = useMemo(() => {\n return { edit, updateCurrent, close, back, create, setStack };\n }, []);\n\n return [state, actions] as const;\n}\n\nexport function EditingStack(props: {\n children?: any;\n initialState?: EditingStackState;\n editing?: { id: string; type: string };\n}) {\n const { instanceId } = useAppInstance();\n const [state, actions] = useInternalEditingStackActions(props.initialState || defaultState);\n\n return (\n <EditingStackActionsContext.Provider value={actions} key={instanceId}>\n <EditingStackContext.Provider value={state}>{props.children}</EditingStackContext.Provider>\n </EditingStackActionsContext.Provider>\n );\n}\n\nexport function InlineEditingStack({\n resource,\n children,\n}: {\n resource: { id: string; type: string };\n children?: React.ReactNode;\n}) {\n const { instanceId } = useAppInstance();\n const initialState = useMemo(() => {\n return {\n create: null,\n stack: [],\n current: {\n resource: {\n type: \"SpecificResource\",\n source: {\n id: resource.id,\n type: resource.type,\n },\n },\n },\n } as EditingStackState;\n }, []);\n const [state, actions] = useInternalEditingStackActions(initialState);\n\n return (\n <EditingStackActionsContext.Provider value={actions} key={instanceId}>\n <EditingStackContext.Provider value={state}>{children}</EditingStackContext.Provider>\n </EditingStackActionsContext.Provider>\n );\n}\n","import { createContext, useContext, useMemo } from \"react\";\nimport {\n LayoutActions,\n LayoutProviderProps,\n LayoutState,\n} from \"./Layout.types\";\nimport { useApp } from \"../AppContext/AppContext\";\n\nexport const LayoutActionsReactContext = createContext<LayoutActions>(\n null as any,\n);\nexport const LayoutStateReactContext = createContext<LayoutState>(null as any);\nexport const LayoutModeReactContext = createContext<\"default\" | \"focused\">(\n \"default\",\n);\n\nexport function useLayoutState() {\n return useContext(LayoutStateReactContext);\n}\n\nexport function useLayoutActions() {\n return useContext(LayoutActionsReactContext);\n}\n\nexport function useLayoutMode() {\n return useContext(LayoutModeReactContext);\n}\n\nexport function useAvailableLayouts() {\n const app = useApp();\n return app.layout;\n}\n\nexport function useLayoutProvider(): LayoutProviderProps & {\n loading?: true;\n actions: LayoutActions;\n state: LayoutState;\n} {\n const app = useApp();\n const layout = app.layout;\n const actions = useContext(LayoutActionsReactContext);\n const state = useContext(LayoutStateReactContext);\n\n return useMemo(() => {\n return { actions, state, ...layout };\n\n // The actions have a fully stable identity.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [app, state]);\n}\n","import type { Vault } from \"@iiif/helpers/vault\";\nimport { type CSSProperties, type SVGProps, useMemo } from \"react\";\nimport { useVault, useVaultSelector } from \"react-iiif-vault\";\n\nexport const TAGS_META_NAMESPACE = \"@manifest-editor/tags\";\nexport const TAGS_META_KEY = \"tags\";\n\nexport interface ManifestEditorTag {\n type: string;\n id: string;\n label: string;\n backgroundColor: string;\n textColor: string;\n icon?: string;\n}\n\nexport type ManifestEditorTagResource =\n | string\n | {\n id: string;\n type?: string;\n }\n | null\n | undefined;\n\nexport interface ManifestEditorTagGroupRow {\n key: string;\n type: string;\n id: string;\n tag: ManifestEditorTag;\n canvasIds: string[];\n canvasCount: number;\n}\n\nexport interface ManifestEditorTagGroup {\n key: string;\n type: string;\n rows: ManifestEditorTagGroupRow[];\n canvasIds: string[];\n canvasCount: number;\n tagCount: number;\n}\n\nexport const FLAG_TAG: ManifestEditorTag = {\n type: \"flag\",\n id: \"flag\",\n label: \"Flag\",\n backgroundColor: \"#b91c1c\",\n textColor: \"#ffffff\",\n icon: \"flag\",\n};\n\nconst EMPTY_TAGS: ManifestEditorTag[] = [];\n\nfunction getResourceId(resource: ManifestEditorTagResource) {\n return typeof resource === \"string\" ? resource : resource?.id || null;\n}\n\nfunction getTagType(tag: Pick<ManifestEditorTag, \"type\" | \"id\">) {\n return tag.type || tag.id;\n}\n\nfunction getTagKey(tag: Pick<ManifestEditorTag, \"type\" | \"id\">) {\n return `${tag.type}:${tag.id}`;\n}\n\nfunction normaliseTags(tags: ManifestEditorTag[] | undefined | null): ManifestEditorTag[] {\n if (!Array.isArray(tags)) {\n return EMPTY_TAGS;\n }\n\n const byType = new Map<string, ManifestEditorTag>();\n for (const tag of tags) {\n if (!tag?.id) {\n continue;\n }\n const type = getTagType(tag);\n byType.set(type, { ...tag, type });\n }\n\n return Array.from(byType.values());\n}\n\nfunction getTagLabel(tag: Pick<ManifestEditorTag, \"label\" | \"id\" | \"type\">) {\n return tag.label || tag.id || tag.type;\n}\n\nfunction isFlagTag(type: string, id?: string) {\n return type === FLAG_TAG.type && (!id || id === FLAG_TAG.id);\n}\n\nfunction compareTagRows(a: ManifestEditorTagGroupRow, b: ManifestEditorTagGroupRow) {\n if (isFlagTag(a.type, a.id)) return -1;\n if (isFlagTag(b.type, b.id)) return 1;\n return (\n getTagLabel(a.tag).localeCompare(getTagLabel(b.tag)) ||\n a.type.localeCompare(b.type) ||\n a.id.localeCompare(b.id)\n );\n}\n\nfunction compareTagGroups(a: ManifestEditorTagGroup, b: ManifestEditorTagGroup) {\n if (isFlagTag(a.type)) return -1;\n if (isFlagTag(b.type)) return 1;\n return a.type.localeCompare(b.type);\n}\n\nexport function getResourceTags(vault: Vault, resource: ManifestEditorTagResource): ManifestEditorTag[] {\n const id = getResourceId(resource);\n if (!id) {\n return EMPTY_TAGS;\n }\n\n const meta = vault.getResourceMeta(id, TAGS_META_NAMESPACE) as { [TAGS_META_KEY]?: ManifestEditorTag[] } | undefined;\n return normaliseTags(meta?.[TAGS_META_KEY]);\n}\n\nexport function getResourceTagsFromState(state: any, resource: ManifestEditorTagResource): ManifestEditorTag[] {\n const id = getResourceId(resource);\n if (!id) {\n return EMPTY_TAGS;\n }\n\n return normaliseTags(state?.iiif?.meta?.[id]?.[TAGS_META_NAMESPACE]?.[TAGS_META_KEY]);\n}\n\nexport function setResourceTags(\n vault: Vault,\n resource: ManifestEditorTagResource,\n tags: ManifestEditorTag[],\n): ManifestEditorTag[] {\n const id = getResourceId(resource);\n if (!id) {\n return EMPTY_TAGS;\n }\n\n const nextTags = normaliseTags(tags);\n vault.setMetaValue([id, TAGS_META_NAMESPACE, TAGS_META_KEY], nextTags);\n return nextTags;\n}\n\nexport function addResourceTag(\n vault: Vault,\n resource: ManifestEditorTagResource,\n tag: ManifestEditorTag,\n): ManifestEditorTag[] {\n return setResourceTags(vault, resource, [...getResourceTags(vault, resource), tag]);\n}\n\nexport function getResourceTag(\n vault: Vault,\n resource: ManifestEditorTagResource,\n tagType: string,\n): ManifestEditorTag | undefined {\n return getResourceTags(vault, resource).find((tag) => tag.type === tagType);\n}\n\nexport function removeResourceTag(\n vault: Vault,\n resource: ManifestEditorTagResource,\n tagType: string,\n tagId?: string,\n): ManifestEditorTag[] {\n return setResourceTags(\n vault,\n resource,\n getResourceTags(vault, resource).filter((tag) => tag.type !== tagType || (tagId ? tag.id !== tagId : false)),\n );\n}\n\nexport function getResourceTagGroups(\n vault: Vault,\n resources: ManifestEditorTagResource[],\n): ManifestEditorTagGroup[] {\n const groups = new Map<string, ManifestEditorTagGroup>();\n\n for (const resource of resources) {\n const resourceId = getResourceId(resource);\n if (!resourceId) {\n continue;\n }\n\n for (const tag of getResourceTags(vault, resource)) {\n const groupKey = tag.type;\n const rowKey = getTagKey(tag);\n let group = groups.get(groupKey);\n\n if (!group) {\n group = {\n key: groupKey,\n type: tag.type,\n rows: [],\n canvasIds: [],\n canvasCount: 0,\n tagCount: 0,\n };\n groups.set(groupKey, group);\n }\n\n let row = group.rows.find((item) => item.key === rowKey);\n if (!row) {\n row = {\n key: rowKey,\n type: tag.type,\n id: tag.id,\n tag,\n canvasIds: [],\n canvasCount: 0,\n };\n group.rows.push(row);\n }\n\n row.canvasIds.push(resourceId);\n row.canvasCount = row.canvasIds.length;\n group.tagCount += 1;\n }\n }\n\n for (const group of groups.values()) {\n group.rows.sort(compareTagRows);\n group.canvasIds = Array.from(new Set(group.rows.flatMap((row) => row.canvasIds)));\n group.canvasCount = group.canvasIds.length;\n }\n\n return Array.from(groups.values()).sort(compareTagGroups);\n}\n\nexport function hasResourceTag(\n vault: Vault,\n resource: ManifestEditorTagResource,\n tagType: string,\n tagId?: string,\n): boolean {\n const tag = getResourceTag(vault, resource, tagType);\n return tagId ? tag?.id === tagId : !!tag;\n}\n\nexport function toggleResourceTag(\n vault: Vault,\n resource: ManifestEditorTagResource,\n tag: ManifestEditorTag,\n): ManifestEditorTag[] {\n return hasResourceTag(vault, resource, tag.type, tag.id)\n ? removeResourceTag(vault, resource, tag.type)\n : addResourceTag(vault, resource, tag);\n}\n\nexport interface ManifestEditorTagsApi {\n getTags(resource: ManifestEditorTagResource): ManifestEditorTag[];\n setTags(resource: ManifestEditorTagResource, tags: ManifestEditorTag[]): ManifestEditorTag[];\n addTag(resource: ManifestEditorTagResource, tag: ManifestEditorTag): ManifestEditorTag[];\n upsertTag(resource: ManifestEditorTagResource, tag: ManifestEditorTag): ManifestEditorTag[];\n getTag(resource: ManifestEditorTagResource, tagType: string): ManifestEditorTag | undefined;\n removeTag(resource: ManifestEditorTagResource, tagType: string, tagId?: string): ManifestEditorTag[];\n hasTag(resource: ManifestEditorTagResource, tagType: string, tagId?: string): boolean;\n toggleTag(resource: ManifestEditorTagResource, tag: ManifestEditorTag): ManifestEditorTag[];\n}\n\nexport function createManifestEditorTagsApi(vault: Vault): ManifestEditorTagsApi {\n return {\n getTags(resource) {\n return getResourceTags(vault, resource);\n },\n setTags(resource, tags) {\n return setResourceTags(vault, resource, tags);\n },\n addTag(resource, tag) {\n return addResourceTag(vault, resource, tag);\n },\n upsertTag(resource, tag) {\n return addResourceTag(vault, resource, tag);\n },\n getTag(resource, tagType) {\n return getResourceTag(vault, resource, tagType);\n },\n removeTag(resource, tagType, tagId) {\n return removeResourceTag(vault, resource, tagType, tagId);\n },\n hasTag(resource, tagType, tagId) {\n return hasResourceTag(vault, resource, tagType, tagId);\n },\n toggleTag(resource, tag) {\n return toggleResourceTag(vault, resource, tag);\n },\n };\n}\n\nexport function useResourceTags(resource: ManifestEditorTagResource): ManifestEditorTag[] {\n const resourceId = getResourceId(resource);\n\n return useVaultSelector((state) => {\n if (!resourceId) {\n return EMPTY_TAGS;\n }\n return getResourceTagsFromState(state, resourceId);\n }, [resourceId]);\n}\n\nexport function useResourceTagActions(resource: ManifestEditorTagResource) {\n const vault = useVault();\n const resourceId = getResourceId(resource);\n const tagActions = useMemo(() => createManifestEditorTagsApi(vault), [vault]);\n\n return useMemo(\n () => ({\n setTags(tags: ManifestEditorTag[]) {\n return tagActions.setTags(resourceId, tags);\n },\n addTag(tag: ManifestEditorTag) {\n return tagActions.addTag(resourceId, tag);\n },\n getTag(tagType: string) {\n return tagActions.getTag(resourceId, tagType);\n },\n removeTag(tagType: string, tagId?: string) {\n return tagActions.removeTag(resourceId, tagType, tagId);\n },\n toggleTag(tag: ManifestEditorTag) {\n return tagActions.toggleTag(resourceId, tag);\n },\n hasTag(tagType: string, tagId?: string) {\n return tagActions.hasTag(resourceId, tagType, tagId);\n },\n }),\n [tagActions, resourceId],\n );\n}\n\nexport function ManifestEditorTagIcon({\n icon,\n title,\n ...props\n}: SVGProps<SVGSVGElement> & { icon?: string; title?: string }) {\n if (icon !== \"flag\") {\n return null;\n }\n\n return (\n <svg viewBox=\"0 0 24 24\" width=\"1em\" height=\"1em\" aria-hidden={title ? undefined : true} {...props}>\n {title ? <title>{title}</title> : null}\n <path\n fill=\"currentColor\"\n d=\"M5 21a1 1 0 0 1-1-1V5.6c0-.42.26-.8.65-.94C6.7 3.9 8.65 4 10.5 4.7c1.55.58 3.05.7 4.5.36l3.75-.88A1 1 0 0 1 20 5.15v9.25c0 .46-.31.86-.75.97l-3.79.9c-1.85.43-3.76.28-5.66-.43-1.28-.48-2.55-.59-3.8-.33V20a1 1 0 0 1-1 1Z\"\n />\n </svg>\n );\n}\n\nexport function ManifestEditorTagBadge({\n tag,\n showIcon = true,\n className,\n style,\n}: {\n tag: ManifestEditorTag;\n showIcon?: boolean;\n className?: string;\n style?: CSSProperties;\n}) {\n return (\n <span\n className={`inline-flex max-w-full items-center gap-0.5 rounded px-1 py-0.5 font-medium shadow-sm ${className || \"\"}`}\n style={{\n backgroundColor: tag.backgroundColor || \"#e5e7eb\",\n color: tag.textColor || \"#111827\",\n fontSize: 9,\n lineHeight: \"11px\",\n ...style,\n }}\n >\n {showIcon && tag.icon ? <ManifestEditorTagIcon icon={tag.icon} className=\"h-2.5 w-2.5 flex-shrink-0\" /> : null}\n <span className=\"min-w-0 truncate\">{getTagLabel(tag)}</span>\n </span>\n );\n}\n\nexport function ManifestEditorTagOverlay({\n resource,\n tags,\n className,\n}: {\n resource?: ManifestEditorTagResource;\n tags?: ManifestEditorTag[];\n className?: string;\n}) {\n if (tags) {\n return <ManifestEditorTagOverlayContent tags={tags} className={className} />;\n }\n\n return <ManifestEditorResourceTagOverlay resource={resource} className={className} />;\n}\n\nfunction ManifestEditorResourceTagOverlay({\n resource,\n className,\n}: {\n resource?: ManifestEditorTagResource;\n className?: string;\n}) {\n const tags = useResourceTags(resource);\n\n return <ManifestEditorTagOverlayContent tags={tags} className={className} />;\n}\n\nfunction ManifestEditorTagOverlayContent({ tags, className }: { tags: ManifestEditorTag[]; className?: string }) {\n const resolvedTags = tags;\n\n if (!resolvedTags.length) {\n return null;\n }\n\n return (\n <div\n className={`pointer-events-none absolute bottom-1 right-1 z-10 flex max-w-full flex-wrap justify-end gap-0.5 ${className || \"\"}`}\n >\n {resolvedTags.map((tag) => (\n <ManifestEditorTagBadge key={tag.type} tag={tag} />\n ))}\n </div>\n );\n}\n","import {\n ToastRegion,\n type ToastContent as ComponentToastContent,\n type ToastVariant as ComponentToastVariant,\n} from \"@manifest-editor/components\";\nimport { useToastState, type ToastOptions } from \"@react-stately/toast\";\nimport { createContext, type ReactNode, useContext, useMemo } from \"react\";\n\nexport type ToastVariant = ComponentToastVariant;\n\nexport type ToastContent = ComponentToastContent;\n\nexport interface ToastApi {\n add(content: ToastContent, options?: ToastOptions): string;\n info(content: ToastContent, options?: ToastOptions): string;\n success(content: ToastContent, options?: ToastOptions): string;\n warning(content: ToastContent, options?: ToastOptions): string;\n error(content: ToastContent, options?: ToastOptions): string;\n close(key: string): void;\n}\n\ninterface ToastProviderProps {\n children: ReactNode;\n maxVisibleToasts?: number;\n}\n\nconst DEFAULT_TOAST_TIMEOUT = 5000;\nconst ERROR_TOAST_TIMEOUT = 8000;\n\nconst ToastReactContext = createContext<ToastApi | null>(null);\n\nfunction getDefaultTimeout(variant?: ToastVariant) {\n return variant === \"error\" ? ERROR_TOAST_TIMEOUT : DEFAULT_TOAST_TIMEOUT;\n}\n\nexport function ToastProvider({ children, maxVisibleToasts = 3 }: ToastProviderProps) {\n const state = useToastState<ToastContent>({ maxVisibleToasts });\n\n const api = useMemo<ToastApi>(() => {\n const add: ToastApi[\"add\"] = (content, options) =>\n state.add(content, {\n ...options,\n timeout: options?.timeout ?? getDefaultTimeout(content.variant),\n });\n\n const addVariant = (variant: ToastVariant, content: ToastContent, options?: ToastOptions) =>\n add({ ...content, variant }, options);\n\n return {\n add,\n info: (content, options) => addVariant(\"info\", content, options),\n success: (content, options) => addVariant(\"success\", content, options),\n warning: (content, options) => addVariant(\"warning\", content, options),\n error: (content, options) => addVariant(\"error\", content, options),\n close: state.close,\n };\n }, [state]);\n\n return (\n <ToastReactContext.Provider value={api}>\n {children}\n <ToastRegion state={state} />\n </ToastReactContext.Provider>\n );\n}\n\nexport function useToasts() {\n const api = useContext(ToastReactContext);\n\n if (!api) {\n throw new Error(\"useToasts must be used within a ToastProvider\");\n }\n\n return api;\n}\n","import type { ToastContent } from \"../Toast/ToastContext\";\nimport type { BackgroundActionDefinition, BackgroundActionInstance } from \"./BackgroundTasks.types\";\n\nexport function getBackgroundActionToastDedupKey(instance: BackgroundActionInstance) {\n if ((instance.status !== \"complete\" && instance.status !== \"error\") || !instance.completedAt) {\n return null;\n }\n\n return `${instance.id}:${instance.status}:${instance.completedAt}`;\n}\n\nexport function getBackgroundActionToastContent(\n definition: BackgroundActionDefinition,\n instance: BackgroundActionInstance,\n onResults?: () => void,\n): ToastContent | null {\n const label = instance.label || definition.label;\n\n if (instance.status === \"complete\") {\n return {\n variant: \"success\",\n title: `${label} complete`,\n description: instance.resultsAvailable ? \"Results are ready.\" : undefined,\n action:\n instance.resultsAvailable && onResults\n ? {\n label: \"Results\",\n onPress: onResults,\n }\n : undefined,\n };\n }\n\n if (instance.status === \"error\") {\n return {\n variant: \"error\",\n title: `${label} failed`,\n description: instance.error?.message || instance.statusText || \"Action failed\",\n };\n }\n\n return null;\n}\n","import {\n BackgroundActionMenuButton,\n BackgroundActionMenuActionButton,\n BackgroundActionMenuDivider,\n BackgroundActionMenuInfoButton,\n BackgroundActionMenuInlineAction,\n BackgroundActionMenuItem,\n BackgroundActionMenuLabel,\n BackgroundActionMenuMeta,\n BackgroundActionMenuPanel,\n BackgroundActionMenuProgressBar,\n BackgroundActionMenuRoot,\n BackgroundActionMenuSection,\n BackgroundActionMenuText,\n BackgroundActionMenuTrigger,\n Modal,\n} from \"@manifest-editor/components\";\nimport { Fragment, useEffect, useMemo, useRef, useState } from \"react\";\nimport useDropdownMenu from \"react-accessible-dropdown-menu-hook\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useConfig } from \"../ConfigContext/ConfigContext\";\nimport { useEditingResource, useEditingResourceStack } from \"../EditingStack/EditingStack\";\nimport { useLayoutActions, useLayoutState } from \"../Layout/Layout.context\";\nimport { createManifestEditorCanvasProgressApi } from \"../CanvasProgress\";\nimport { usePluginRuntimeApi } from \"../PluginContext/PluginContext\";\nimport { createManifestEditorTagsApi } from \"../Tags\";\nimport { useToasts } from \"../Toast/ToastContext\";\nimport { getBackgroundActionToastContent, getBackgroundActionToastDedupKey } from \"./BackgroundActionToasts.helpers\";\nimport {\n getAvailableBackgroundActionGroups,\n runBackgroundAction,\n useBackgroundActionsStore,\n useBackgroundActionsStoreApi,\n} from \"./BackgroundTasksStore\";\nimport type {\n BackgroundActionDefinition,\n BackgroundActionGroup,\n BackgroundActionInstance,\n BackgroundActionContext,\n BackgroundActionSystemContext,\n BackgroundActionTarget,\n} from \"./BackgroundTasks.types\";\n\nfunction toRootTarget(resource: { id: string; type: string }): BackgroundActionTarget {\n return {\n id: resource.id,\n type: resource.type,\n label: resource.type,\n scope: \"root\",\n };\n}\n\nfunction toCanvasTarget(resource: { id?: string; type?: string } | undefined): BackgroundActionTarget | undefined {\n if (!resource || !resource.id || resource.type !== \"Canvas\") {\n return undefined;\n }\n\n return {\n id: resource.id,\n type: \"Canvas\",\n label: \"Current canvas\",\n scope: \"canvas\",\n };\n}\n\nfunction useCurrentCanvasTarget() {\n const current = useEditingResource();\n const stack = useEditingResourceStack();\n\n return useMemo(() => {\n const canvasResource = [current, ...stack].find((item) => item?.resource?.source?.type === \"Canvas\");\n return toCanvasTarget(canvasResource?.resource?.source);\n }, [current, stack]);\n}\n\nfunction useBackgroundActionSystemContext(): BackgroundActionSystemContext {\n const rootResource = useAppResource();\n const currentCanvas = useCurrentCanvasTarget();\n const vault = useVault();\n const tags = useMemo(() => createManifestEditorTagsApi(vault), [vault]);\n const canvasProgress = useMemo(() => createManifestEditorCanvasProgressApi(vault), [vault]);\n const plugins = usePluginRuntimeApi();\n const config = useConfig();\n const layoutState = useLayoutState();\n const layoutActions = useLayoutActions();\n\n return useMemo(\n () => ({\n rootResource,\n currentCanvas,\n vault,\n tags,\n canvasProgress,\n plugins,\n config,\n layoutState,\n layoutActions,\n }),\n [rootResource, currentCanvas, vault, tags, canvasProgress, plugins, config, layoutState, layoutActions],\n );\n}\n\nexport function useAvailableBackgroundActions(): BackgroundActionGroup[] {\n const definitions = useBackgroundActionsStore((state) => state.definitions);\n const instances = useBackgroundActionsStore((state) => state.instances);\n const systemContext = useBackgroundActionSystemContext();\n const rootTarget = useMemo(() => toRootTarget(systemContext.rootResource), [systemContext.rootResource]);\n\n return useMemo(() => {\n const targets = [rootTarget, ...(systemContext.currentCanvas ? [systemContext.currentCanvas] : [])];\n return getAvailableBackgroundActionGroups({\n definitions,\n instances,\n systemContext,\n targets,\n onSupportsError: (definition, error) => {\n console.error(`Background action \"${definition.id}\" failed support check`, error);\n },\n });\n }, [definitions, instances, rootTarget, systemContext]);\n}\n\nexport function BackgroundActionsMount() {\n const store = useBackgroundActionsStoreApi();\n const definitions = useBackgroundActionsStore((state) => state.definitions);\n const instances = useBackgroundActionsStore((state) => state.instances);\n const plans = useBackgroundActionsStore((state) => state.plans);\n const controllers = useBackgroundActionsStore((state) => state.controllers);\n const hasHydrated = useBackgroundActionsStore((state) => state.hasHydrated);\n const systemContext = useBackgroundActionSystemContext();\n const resumedRuns = useRef(new Set<string>());\n\n useEffect(() => {\n if (!hasHydrated) {\n return;\n }\n\n const definitionsById = new Map(definitions.map((definition) => [definition.id, definition]));\n\n for (const [instanceKey, instance] of Object.entries(instances)) {\n const definition = definitionsById.get(instance.actionId);\n const runKey = `${instanceKey}:${instance.runId}`;\n\n if (!definition?.resumable || !isBusy(instance) || !plans[instanceKey] || controllers[instanceKey]) {\n continue;\n }\n\n if (resumedRuns.current.has(runKey)) {\n continue;\n }\n\n resumedRuns.current.add(runKey);\n void runBackgroundAction({\n store,\n resume: true,\n context: {\n ...systemContext,\n definition,\n target: instance.target,\n instanceKey,\n instance,\n },\n });\n }\n }, [controllers, definitions, hasHydrated, instances, plans, store, systemContext]);\n\n return (\n <>\n {definitions.map((definition) => {\n if (!definition.render) {\n return null;\n }\n\n return <Fragment key={definition.id}>{definition.render({ ...systemContext, definition })}</Fragment>;\n })}\n </>\n );\n}\n\nexport function BackgroundActionToasts() {\n const definitions = useBackgroundActionsStore((state) => state.definitions);\n const instances = useBackgroundActionsStore((state) => state.instances);\n const systemContext = useBackgroundActionSystemContext();\n const toasts = useToasts();\n const shownToastKeys = useRef(new Set<string>());\n\n const definitionsById = useMemo(\n () => new Map(definitions.map((definition) => [definition.id, definition])),\n [definitions],\n );\n\n useEffect(() => {\n for (const instance of Object.values(instances)) {\n const dedupKey = getBackgroundActionToastDedupKey(instance);\n if (!dedupKey || shownToastKeys.current.has(dedupKey)) {\n continue;\n }\n\n const definition = definitionsById.get(instance.actionId);\n if (!definition) {\n continue;\n }\n\n const context: BackgroundActionContext = {\n ...systemContext,\n definition,\n target: instance.target,\n instanceKey: instance.id,\n instance,\n };\n const content = getBackgroundActionToastContent(\n definition,\n instance,\n instance.resultsAvailable && definition.onResults\n ? () => {\n void definition.onResults?.(context);\n }\n : undefined,\n );\n\n if (content) {\n toasts.add(content);\n shownToastKeys.current.add(dedupKey);\n }\n }\n }, [definitionsById, instances, systemContext, toasts]);\n\n return null;\n}\n\nfunction isBusy(instance: BackgroundActionInstance | undefined) {\n return instance?.status === \"preparing\" || instance?.status === \"running\";\n}\n\nfunction getActionStatusLabel(instance: BackgroundActionInstance | undefined) {\n if (!instance || instance.status === \"idle\") {\n return \"\";\n }\n\n if (instance.status === \"error\") {\n return instance.error?.message || instance.statusText || \"Error\";\n }\n\n if (instance.status === \"complete\" && instance.resultsAvailable) {\n return \"Results ready\";\n }\n\n if (instance.status === \"cancelled\") {\n return \"Cancelled\";\n }\n\n return instance.statusText || instance.status;\n}\n\nfunction formatTimestamp(value: number | undefined) {\n if (!value) {\n return \"Not recorded\";\n }\n\n return new Date(value).toLocaleString();\n}\n\nfunction formatTime(value: number | undefined) {\n if (!value) return \"--:--:--\";\n return new Date(value).toLocaleTimeString(undefined, { hour: \"2-digit\", minute: \"2-digit\", second: \"2-digit\" });\n}\n\nfunction formatDuration(instance: BackgroundActionInstance) {\n if (!instance.startedAt) {\n return \"Not recorded\";\n }\n\n const end = instance.completedAt || Date.now();\n const seconds = Math.max(0, Math.round((end - instance.startedAt) / 1000));\n const minutes = Math.floor(seconds / 60);\n const remainingSeconds = seconds % 60;\n\n if (minutes) {\n return `${minutes}m ${remainingSeconds}s`;\n }\n\n return `${remainingSeconds}s`;\n}\n\nfunction formatJson(value: unknown) {\n if (typeof value === \"undefined\") {\n return \"\";\n }\n\n if (typeof value === \"string\") {\n return value;\n }\n\n try {\n return JSON.stringify(value, null, 2);\n } catch {\n return String(value);\n }\n}\n\nfunction DetailItem({ label, value }: { label: string; value: string }) {\n return (\n <div className=\"min-w-0\">\n <dt className=\"text-[10px] font-semibold uppercase tracking-widest text-zinc-400\">{label}</dt>\n <dd className=\"mt-1 break-words text-sm text-zinc-800\">{value}</dd>\n </div>\n );\n}\n\nconst logLevelConfig: Record<string, { label: string; className: string }> = {\n debug: { label: \"DBG\", className: \"text-zinc-500\" },\n verbose: { label: \"VRB\", className: \"text-zinc-500\" },\n info: { label: \"INF\", className: \"text-sky-400\" },\n log: { label: \"LOG\", className: \"text-zinc-300\" },\n warn: { label: \"WRN\", className: \"text-amber-400\" },\n warning: { label: \"WRN\", className: \"text-amber-400\" },\n error: { label: \"ERR\", className: \"text-red-400\" },\n};\n\nfunction getLogLevelConfig(level: string) {\n return logLevelConfig[level?.toLowerCase()] ?? { label: level?.toUpperCase().slice(0, 3) ?? \"LOG\", className: \"text-zinc-300\" };\n}\n\nconst milestoneEventBadgeClass: Record<string, string> = {\n error: \"bg-red-100 text-red-700\",\n failed: \"bg-red-100 text-red-700\",\n completed: \"bg-green-100 text-green-700\",\n success: \"bg-green-100 text-green-700\",\n started: \"bg-sky-100 text-sky-700\",\n cancelled: \"bg-zinc-100 text-zinc-600\",\n warning: \"bg-amber-100 text-amber-700\",\n warn: \"bg-amber-100 text-amber-700\",\n};\n\nfunction getMilestoneBadgeClass(type: string) {\n return milestoneEventBadgeClass[type?.toLowerCase()] ?? \"bg-zinc-100 text-zinc-600\";\n}\n\nfunction isMilestoneEvent(type: string) {\n return type?.toLowerCase() in milestoneEventBadgeClass;\n}\n\ntype DetailsTab = \"overview\" | \"logs\";\n\nfunction BackgroundActionDetailsModal({\n definition,\n instance,\n onClose,\n}: {\n definition: BackgroundActionDefinition;\n instance: BackgroundActionInstance;\n onClose: () => void;\n}) {\n const [activeTab, setActiveTab] = useState<DetailsTab>(\"overview\");\n const logEndRef = useRef<HTMLDivElement>(null);\n const logCount = instance.logs.length;\n\n // Auto-scroll log terminal to bottom when switching to logs tab\n useEffect(() => {\n if (activeTab === \"logs\") {\n logEndRef.current?.scrollIntoView({ behavior: \"instant\" });\n }\n }, [activeTab]);\n\n const statusColourMap: Record<string, string> = {\n idle: \"bg-zinc-100 text-zinc-600\",\n preparing: \"bg-orange-100 text-orange-700\",\n running: \"bg-orange-100 text-orange-700\",\n complete: \"bg-green-100 text-green-700\",\n error: \"bg-red-100 text-red-700\",\n cancelled: \"bg-zinc-100 text-zinc-500\",\n };\n\n const milestoneEvents = instance.events.filter((e) => isMilestoneEvent(e.type));\n\n const tabs: Array<{ id: DetailsTab; label: string; count?: number }> = [\n { id: \"overview\", label: \"Overview\" },\n { id: \"logs\", label: \"Logs\", count: logCount },\n ];\n\n return (\n <Modal title={instance.label || definition.label} onClose={onClose} className=\"max-w-3xl\">\n {/* Tab bar — sticky inside the scroll container */}\n <div className=\"sticky top-0 z-10 border-b border-zinc-200 bg-white px-2\">\n <div className=\"flex gap-0.5\">\n {tabs.map((tab) => (\n <button\n key={tab.id}\n type=\"button\"\n onClick={() => setActiveTab(tab.id)}\n className={[\n \"flex items-center gap-1.5 border-b-2 px-3 py-2.5 text-sm transition-colors -mb-px\",\n activeTab === tab.id\n ? \"border-me-primary-500 font-semibold text-me-primary-600\"\n : \"border-transparent text-zinc-500 hover:text-zinc-800\",\n ].join(\" \")}\n >\n {tab.label}\n {tab.count ? (\n <span className=\"rounded-full bg-zinc-100 px-1.5 py-0.5 text-[10px] font-medium text-zinc-500\">\n {tab.count}\n </span>\n ) : null}\n </button>\n ))}\n </div>\n </div>\n\n {/* Overview tab */}\n {activeTab === \"overview\" && (\n <div className=\"flex flex-col gap-5 p-5\">\n {/* Status row */}\n <div className=\"flex flex-wrap items-center gap-2\">\n <span\n className={[\n \"inline-flex items-center gap-1.5 rounded-full px-3 py-1 text-xs font-semibold uppercase tracking-wide\",\n statusColourMap[instance.status] ?? \"bg-zinc-100 text-zinc-600\",\n ].join(\" \")}\n >\n {instance.status}\n </span>\n {instance.statusText ? <span className=\"text-sm text-zinc-500\">{instance.statusText}</span> : null}\n </div>\n\n {/* Details grid */}\n <dl className=\"grid gap-x-6 gap-y-4 sm:grid-cols-2\">\n <DetailItem label=\"Target\" value={`${instance.target.label} (${instance.target.type})`} />\n <DetailItem label=\"Run ID\" value={instance.runId} />\n <DetailItem label=\"Started\" value={formatTimestamp(instance.startedAt)} />\n <DetailItem label=\"Finished\" value={formatTimestamp(instance.completedAt)} />\n <DetailItem label=\"Duration\" value={formatDuration(instance)} />\n {instance.progress ? (\n <DetailItem\n label=\"Progress\"\n value={`${Math.round(instance.progress.percent)}%${instance.progress.label ? ` — ${instance.progress.label}` : \"\"}`}\n />\n ) : null}\n </dl>\n\n {/* Progress bar */}\n {instance.progress ? (\n <div>\n <BackgroundActionMenuProgressBar\n percent={instance.progress.percent}\n label={instance.progress.label || \"Background action progress\"}\n />\n {typeof instance.progress.current === \"number\" && typeof instance.progress.total === \"number\" ? (\n <div className=\"mt-1 text-xs text-zinc-500\">\n {instance.progress.current} of {instance.progress.total} items\n </div>\n ) : null}\n </div>\n ) : null}\n\n {/* Error */}\n {instance.error ? (\n <div className=\"rounded-lg border border-red-200 bg-red-50\">\n <div className=\"border-b border-red-200 px-4 py-2.5\">\n <span className=\"text-xs font-semibold uppercase tracking-widest text-red-600\">Error</span>\n </div>\n <div className=\"p-4\">\n <div className=\"text-sm font-medium text-red-800\">{instance.error.message}</div>\n {instance.error.stack ? (\n <pre className=\"mt-3 max-h-40 overflow-auto rounded bg-red-100 p-3 text-xs text-red-700 leading-relaxed whitespace-pre-wrap\">\n {instance.error.stack}\n </pre>\n ) : null}\n </div>\n </div>\n ) : null}\n\n {/* Key milestones */}\n {milestoneEvents.length > 0 ? (\n <div>\n <h3 className=\"mb-2 text-[10px] font-semibold uppercase tracking-widest text-zinc-400\">Key events</h3>\n <div className=\"divide-y divide-zinc-100 rounded-lg border border-zinc-200\">\n {milestoneEvents.map((event) => (\n <div key={event.id} className=\"flex items-baseline gap-3 px-3 py-2\">\n <span className={[\"shrink-0 rounded px-1.5 py-0.5 text-[10px] font-semibold uppercase tracking-wide\", getMilestoneBadgeClass(event.type)].join(\" \")}>\n {event.type}\n </span>\n <span className=\"min-w-0 flex-1 truncate text-sm text-zinc-700\">{event.message || event.type}</span>\n <time className=\"shrink-0 text-xs text-zinc-400\">{formatTime(event.createdAt)}</time>\n </div>\n ))}\n </div>\n </div>\n ) : null}\n </div>\n )}\n\n {/* Logs tab — terminal style */}\n {activeTab === \"logs\" && (\n <div className=\"p-5\">\n {logCount === 0 ? (\n <div className=\"rounded-lg border border-zinc-200 p-6 text-center text-sm text-zinc-400\">\n No logs recorded.\n </div>\n ) : (\n <div className=\"overflow-hidden rounded-lg bg-zinc-950 shadow-inner\">\n {/* Terminal toolbar */}\n <div className=\"flex items-center gap-1.5 border-b border-white/10 px-3 py-2\">\n <div className=\"h-2.5 w-2.5 rounded-full bg-zinc-700\" />\n <div className=\"h-2.5 w-2.5 rounded-full bg-zinc-700\" />\n <div className=\"h-2.5 w-2.5 rounded-full bg-zinc-700\" />\n <span className=\"ml-2 text-[10px] text-zinc-500 font-mono\">\n {logCount} {logCount === 1 ? \"entry\" : \"entries\"}\n </span>\n </div>\n {/* Log lines */}\n <div className=\"max-h-[50vh] overflow-y-auto p-1 font-mono text-xs\">\n {instance.logs.map((log) => {\n const levelCfg = getLogLevelConfig(log.level);\n return (\n <div\n key={log.id}\n className=\"group flex gap-0 hover:bg-white/5 rounded px-2 py-1 leading-relaxed\"\n >\n {/* Timestamp */}\n <time className=\"w-20 shrink-0 text-zinc-600 select-none pr-2\">{formatTime(log.createdAt)}</time>\n {/* Level badge */}\n <span className={[\"w-10 shrink-0 select-none font-bold pr-2\", levelCfg.className].join(\" \")}>\n {levelCfg.label}\n </span>\n {/* Message + optional data */}\n <span className=\"min-w-0 flex-1 text-zinc-200 break-words\">\n {log.message}\n {typeof log.data !== \"undefined\" ? (\n <span className=\"block mt-0.5 text-zinc-500 whitespace-pre-wrap\">{formatJson(log.data)}</span>\n ) : null}\n </span>\n </div>\n );\n })}\n {/* Anchor for auto-scroll */}\n <div ref={logEndRef} />\n </div>\n </div>\n )}\n </div>\n )}\n </Modal>\n );\n}\n\nexport function BackgroundActionsMenu() {\n const store = useBackgroundActionsStoreApi();\n const groups = useAvailableBackgroundActions();\n const [detailsInstanceKey, setDetailsInstanceKey] = useState<string | null>(null);\n const actionCount = groups.reduce((total, group) => total + group.actions.length, 0);\n const runningCount = groups.reduce(\n (total, group) => total + group.actions.filter((action) => isBusy(action.instance)).length,\n 0,\n );\n const errorCount = groups.reduce(\n (total, group) => total + group.actions.filter((action) => action.instance?.status === \"error\").length,\n 0,\n );\n const { isOpen, buttonProps, itemProps, setIsOpen } = useDropdownMenu(actionCount);\n\n if (!actionCount) {\n return null;\n }\n\n const selectedAction = detailsInstanceKey\n ? groups.flatMap((group) => group.actions).find((action) => action.instanceKey === detailsInstanceKey)\n : undefined;\n let itemIndex = 0;\n\n return (\n <BackgroundActionMenuRoot>\n <BackgroundActionMenuButton active={isOpen} runningCount={runningCount} errorCount={errorCount} aria-label=\"Actions menu\" {...buttonProps} />\n <BackgroundActionMenuPanel open={isOpen} role=\"menu\">\n <div className=\"py-1.5\">\n {groups.map((group, groupIndex) => (\n <Fragment key={group.id}>\n {groupIndex ? <BackgroundActionMenuDivider /> : null}\n <BackgroundActionMenuSection>{group.label}</BackgroundActionMenuSection>\n {group.actions.map((action) => {\n const currentItemProps = itemProps[itemIndex++] || {};\n const { onKeyDown, ...menuItemProps } = currentItemProps as any;\n const statusLabel = getActionStatusLabel(action.instance);\n const busy = isBusy(action.instance);\n const runAction = () => {\n if (!busy) {\n runBackgroundAction({ store, context: action.context });\n setIsOpen(true);\n }\n };\n const cancelAction = () => {\n if (busy) {\n store.getState().cancelAction(action.instanceKey);\n setIsOpen(true);\n }\n };\n\n return (\n <BackgroundActionMenuItem key={action.instanceKey} status={action.instance?.status || \"idle\"}>\n <BackgroundActionMenuTrigger\n running={busy}\n {...menuItemProps}\n aria-label={busy ? `Cancel ${action.definition.label}` : `Run ${action.definition.label}`}\n onMouseDown={(event) => {\n event.preventDefault();\n }}\n onClick={(event) => {\n event.stopPropagation();\n if (busy) {\n cancelAction();\n } else {\n runAction();\n }\n }}\n onKeyDown={(event) => {\n if (event.key === \"Enter\" || event.key === \" \") {\n event.preventDefault();\n event.stopPropagation();\n if (busy) {\n cancelAction();\n } else {\n runAction();\n }\n } else {\n onKeyDown?.(event);\n }\n }}\n >\n <BackgroundActionMenuText>\n <BackgroundActionMenuLabel running={busy}>\n {action.instance?.label || action.definition.label}\n </BackgroundActionMenuLabel>\n {statusLabel ? (\n <BackgroundActionMenuMeta variant={action.instance?.status === \"error\" ? \"error\" : \"default\"}>\n {statusLabel}\n </BackgroundActionMenuMeta>\n ) : null}\n {action.definition.summary && !statusLabel ? (\n <BackgroundActionMenuMeta>\n {action.definition.summary}\n </BackgroundActionMenuMeta>\n ) : null}\n {busy && action.instance?.progress ? (\n <BackgroundActionMenuProgressBar\n percent={action.instance.progress.percent}\n label={action.instance.progress.label || statusLabel || action.definition.label}\n />\n ) : null}\n </BackgroundActionMenuText>\n </BackgroundActionMenuTrigger>\n {action.instance?.resultsAvailable && action.definition.onResults ? (\n <BackgroundActionMenuInlineAction\n onClick={(event) => {\n event.stopPropagation();\n action.definition.onResults?.(action.context);\n }}\n >\n Results\n </BackgroundActionMenuInlineAction>\n ) : null}\n {action.instance ? (\n <BackgroundActionMenuInfoButton\n aria-label={`View ${action.definition.label} details`}\n onClick={(event) => {\n event.preventDefault();\n event.stopPropagation();\n setDetailsInstanceKey(action.instanceKey);\n setIsOpen(true);\n }}\n />\n ) : null}\n </BackgroundActionMenuItem>\n );\n })}\n </Fragment>\n ))}\n </div>\n </BackgroundActionMenuPanel>\n {selectedAction?.instance ? (\n <BackgroundActionDetailsModal\n definition={selectedAction.definition}\n instance={selectedAction.instance}\n onClose={() => setDetailsInstanceKey(null)}\n />\n ) : null}\n </BackgroundActionMenuRoot>\n );\n}\n","import { Logo, Container, Header } from \"./AppHeader.styles\";\nimport { PreviewButton } from \"../PreviewButton/PreviewButton\";\nimport { BackgroundActionsMenu } from \"../BackgroundTasks/BackgroundActions\";\nimport { ManifestEditorLogo } from \"@manifest-editor/components\";\n\nimport { memo } from \"react\";\nimport { useLocalStorage } from \"../hooks/use-local-storage\";\n\ninterface AppHeaderProps {\n onClickLogo?: () => void;\n}\n\nexport const AppHeader = memo(function AppHeader(props: AppHeaderProps) {\n const [isMenuHidden] = useLocalStorage(\"menu-hidden\");\n\n return (\n <Header>\n <Container>\n <Logo onClick={props.onClickLogo}>\n <ManifestEditorLogo />\n </Logo>\n\n <PreviewButton />\n <BackgroundActionsMenu />\n\n {/*<IconButton>•</IconButton>*/}\n </Container>\n {/* {!isMenuHidden ? <ShellOptions /> : null} */}\n </Header>\n );\n});\n","import { createContext, useContext } from \"react\";\n\ntype MenuItem = {\n label: string;\n onClick?: () => void;\n active?: boolean;\n};\n\ninterface AppMenuContext {\n file: {\n new: MenuItem;\n edit: MenuItem;\n open: MenuItem;\n\n newOptions: MenuItem[];\n openOptions: MenuItem[];\n };\n}\n\nconst ReactAppMenuContext = createContext<AppMenuContext | null>(null);\n\nexport function useAppMenu() {\n const ctx = useContext(ReactAppMenuContext);\n\n if (!ctx) {\n return null;\n }\n\n return ctx;\n}\n\nexport function useAppMenuItem<\n Key extends keyof AppMenuContext,\n Name extends keyof AppMenuContext[Key],\n Return extends AppMenuContext[Key][Name],\n>(menu: Key, name: Name): Return | null {\n const ctx = useAppMenu();\n\n if (!ctx) {\n return null;\n }\n\n return ctx[menu][name] as Return;\n}\n\nexport function AppMenuProvider({ children, menu }: { children: React.ReactNode; menu: AppMenuContext }) {\n return <ReactAppMenuContext.Provider value={menu}>{children}</ReactAppMenuContext.Provider>;\n}\n","import { useContext } from \"react\";\nimport { type AtlasStore, AtlasStoreProvider, AtlasStoreReactContext } from \"react-iiif-vault\";\nimport type { StoreApi } from \"zustand\";\n\nexport { AtlasStoreProvider, AtlasStoreReactContext };\n\nexport function useAtlasStore() {\n return useContext(AtlasStoreReactContext) as StoreApi<AtlasStore>;\n}\n","import type { InputShape } from \"polygon-editor\";\n\nexport function polygonToBoundingBox(polygon: InputShape | null) {\n if (!polygon) {\n return null;\n }\n if (polygon.points.length > 2) {\n const x1 = Math.min(...polygon.points.map((p) => p[0]));\n const y1 = Math.min(...polygon.points.map((p) => p[1]));\n const x2 = Math.max(0, ...polygon.points.map((p) => p[0]));\n const y2 = Math.max(0, ...polygon.points.map((p) => p[1]));\n return {\n x: x1,\n y: y1,\n width: x2 - x1,\n height: y2 - y1,\n };\n }\n return null;\n}\n","import { getValue } from \"@iiif/helpers\";\nimport * as IIIFVault from \"@iiif/helpers/vault\";\n\n// This is from the ts version\n// Create an image in the DOM to measure height and width\nconst getImage = async (src: string): Promise<HTMLImageElement> => {\n return new Promise((resolve, reject) => {\n const $img = document.createElement(\"img\");\n $img.onload = () => resolve($img);\n $img.onerror = () => reject();\n $img.src = src;\n if ($img.complete) {\n resolve($img); // cached.\n }\n });\n};\n\nconst getAudioVideo = async (src: string) => {\n return new Promise<HTMLVideoElement>((resolve, reject) => {\n // Video tag accepts both.\n const $media = document.createElement(\"video\");\n $media.onloadedmetadata = () => resolve($media);\n $media.onerror = () => reject();\n $media.preload = \"metadata\";\n $media.src = src;\n });\n};\n\n// use the hints from the user (if any), plus defaults, to get the order\n// in which to try various analysis\nfunction makeTryList(suppliedExpectedTypes: string[]) {\n const defaults = [\"Image\", \"ImageService\", \"ManifestOrCollection\", \"ContentState\"];\n let tryList: string[] = [];\n if (!suppliedExpectedTypes || suppliedExpectedTypes.length === 0) {\n tryList = defaults;\n }\n mergeList(suppliedExpectedTypes, tryList);\n mergeList(defaults, tryList);\n return tryList;\n}\n\nfunction mergeList(inputList: string[], outputList: string[]) {\n inputList.map((t: string) => {\n if (t === \"Image\" && !outputList.includes(\"Image\")) {\n outputList.push(\"Image\");\n }\n if (t === \"ImageService\" && !outputList.includes(\"ImageService\")) {\n outputList.push(\"ImageService\");\n }\n if (t === \"Manifest\" && !outputList.includes(\"ManifestOrCollection\")) {\n outputList.push(\"ManifestOrCollection\");\n }\n if (t === \"Collection\" && !outputList.includes(\"ManifestOrCollection\")) {\n outputList.push(\"ManifestOrCollection\");\n }\n if (t === \"ManifestOrCollection\" && !outputList.includes(\"ManifestOrCollection\")) {\n outputList.push(\"ManifestOrCollection\");\n }\n if (t === \"ContentState\" && !outputList.includes(\"ContentState\")) {\n outputList.push(\"ContentState\");\n }\n });\n}\n\nexport async function detectMedia() {\n //\n}\n\nexport async function analyse(url: string, ...expectedTypes: string[]) {\n // const tryList = makeTryList(expectedTypes);\n\n if (!url) {\n return;\n }\n\n // 2 new options:\n // - Audio\n // - Video\n // Only support them if they end in mp3 or mp4\n if (url.endsWith(\".mp3\") || url.endsWith(\".mp4\") || url.endsWith(\".m4a\") || url.endsWith(\".m4v\")) {\n try {\n const av = await getAudioVideo(url);\n if (av) {\n const isAudio = av.videoWidth === 0;\n return {\n id: url,\n type: av.videoWidth === 0 ? \"Sound\" : \"Video\",\n width: av.videoWidth || undefined, // naturalWidth\n height: av.videoHeight || undefined, // naturalHeight\n duration: av.duration,\n format: isAudio ? \"audio/mp4\" : \"video/mp4\",\n };\n }\n } catch (e) {\n // fall through..\n }\n }\n\n // This doesn't use the tryList order yet.\n // One advantage of doing a fetch first _even if we expect an image_ is that\n // we might capture the content type, if the image is CORS-enabled.\n let response = null;\n try {\n // Try head request, if that works...\n // await fetch(url, { method: \"HEAD\" });\n\n // then fetch the full resource.\n response = await fetch(url);\n } catch {\n // can handle the error better, but maybe CORS error happened so:\n return handleNonFetchableUrl(url);\n }\n\n if (!response.ok) {\n response = await fetch(url + \"/info.json\");\n if (!response.ok) {\n return handleNonFetchableUrl(url);\n }\n }\n\n // but... it might have been a CORS-enabled image, or an image from an image service.\n // In this scenario we can capture the content type right here.\n const contentTypeHeader = response.headers.get(\"Content-Type\");\n if (contentTypeHeader?.includes(\"image/\")) {\n return handleNonFetchableUrl(url, contentTypeHeader);\n }\n\n // OK, it's probably NOT an image, and we have an OK response, so can we get JSON from it?\n let data = null;\n try {\n data = await response.json();\n } catch {\n return null;\n }\n\n return await analyseJson(data, url);\n}\n\nfunction asImageService(data: any) {\n if (data.protocol && data.protocol === \"http://iiif.io/api/image\") {\n if (!data.type) {\n data.type = \"ImageService\";\n }\n // NB this will be ImageService3 if it's a v3 img service\n return data;\n }\n return null;\n}\n\nexport async function analyseJson(data: any, url: string) {\n // Is it an image service?\n const testImageService = asImageService(data);\n if (testImageService) {\n return testImageService;\n }\n\n // does it have an ID?\n const dataId = data.id || data[\"@id\"];\n if (!dataId) {\n return null;\n }\n const vault = new IIIFVault.Vault();\n const vaultData = await vault.load(url, data); // we could use dataId here, but just in case it's wrong...\n if (!vaultData) {\n return;\n }\n // @ts-expect-error\n if ((vaultData && vaultData?.type === \"Manifest\") || vaultData?.type === \"Collection\") {\n return {\n id: url,\n // @ts-expect-error\n type: vaultData.type,\n // @ts-expect-error\n label: getValue(vaultData.label),\n };\n }\n}\n\nasync function handleNonFetchableUrl(url: string, capturedContentType?: string) {\n // it *is* an image... but is it an image from an image service?\n // In its current form this should be tried before any fetch happens\n // that is, does it match:\n // http<s>://<any.org>/<any-prefix>/region/size/rotation/format.quality ?\n // This should really call Stephen's IIIF Image API parser, and if it's a success, we know it's\n // probably an image service\n // https://github.com/atlas-viewer/iiif-image-api\n // https://github.com/atlas-viewer/iiif-image-api/blob/main/src/utility/parse-image-service-request.ts\n const parts = url.split(\"/\");\n if (parts.length >= 8) {\n // might be an image service\n const iiifParts = parts.slice(-4);\n // need to do more than this but the parser can do the hard work\n if (iiifParts[3]!.split(\".\").length === 2) {\n // This is not reliable! parse it properly!\n if (iiifParts[2]![0] === \"!\" || iiifParts[2] === iiifParts[2]) {\n // rotation param is numeric\n // this is worth trying as an image service\n const serviceUrl = parts.slice(0, parts.length - 4).join(\"/\") + \"/info.json\";\n // assume this is a low cost thing to try\n const imgService = await getImageService(serviceUrl);\n if (imgService && imgService?.type && imgService?.type?.startsWith(\"ImageService\")) {\n return imgService;\n }\n }\n }\n }\n\n // OK we didn't find an image service behind that image URL. So now it's time to use the DOM.\n\n try {\n const image = (await getImage(url)) as any;\n const data = {\n id: url,\n type: \"Image\",\n width: image.width, // naturalWidth\n height: image.height, // naturalHeight\n format: await getFormat(url, capturedContentType),\n };\n return data;\n } catch { }\n\n return null;\n}\n\nasync function getImageService(url: string) {\n try {\n const response = await fetch(url);\n if (response.ok) {\n const data = await response.json();\n return await analyseJson(data, url);\n }\n return null;\n } catch (e: any) {\n console.log(e);\n return null;\n }\n}\n\nexport async function getFormat(url: string, capturedContentType?: string) {\n if (capturedContentType) {\n // we managed to learn this earlier, the image had CORS\n return capturedContentType;\n }\n try {\n // a HEAD request doesn't have CORS issues... well it didn't used to...\n const response = await fetch(url, { method: \"HEAD\", mode: \"no-cors\" });\n const ct = response.headers.get(\"Content-type\");\n if (ct) {\n return ct;\n }\n } catch (e) {\n // ignore.\n }\n\n // if the above still fails, we could fall back to guessing\n // content-type from the URL (.jpg etc).\n const test = url.toLowerCase();\n if (test.endsWith(\"jpg\") || test.endsWith(\"jpeg\")) {\n return \"image/jpeg\";\n }\n if (test.endsWith(\"png\")) {\n return \"image/png\";\n }\n // Just a default.\n return \"image/jpeg\";\n}\n\nexport async function getImageDimensions(url: string) {\n try {\n const image = await getImage(url);\n if (image) {\n return {\n width: image.naturalWidth || image.width,\n height: image.naturalHeight || image.height,\n };\n }\n } catch (e) {\n return null;\n }\n return null;\n}\n","import { create } from \"zustand\";\nimport { useEffect, useMemo } from \"react\";\nimport { randomId } from \"./helpers\";\n\ntype Projection = {\n x: number;\n y: number;\n width: number;\n height: number;\n};\n\ninterface HighlightedImageResources {\n regions: Record<string, Projection | null>;\n resources: string[];\n setRegion: (id: string, region?: Projection | null) => void;\n setHighlight: (id: string | string[]) => void;\n highlight: (id: string) => void;\n clearHighlight: (id: string) => void;\n}\n\nexport const useHighlightedImageResource = create<HighlightedImageResources>((set) => ({\n regions: {},\n resources: [],\n setRegion: (id, region) => {\n set((ex) => ({ ...ex.regions, regions: { [id]: region || null } }));\n },\n setHighlight: (id: string | string[]) => {\n set({ resources: Array.isArray(id) ? id : [id] });\n },\n highlight: (id) => {\n set((s) => {\n if (s.resources.indexOf(id) !== -1) {\n return s;\n }\n return { resources: [...s.resources, id] };\n });\n },\n clearHighlight: (id) => {\n set((s) => ({ resources: s.resources.filter((item) => item !== id) }));\n },\n}));\n\nexport function useTemporaryHighlight(newValue?: Projection | null) {\n const id = useMemo(() => randomId(), []);\n const value = useHighlightedImageResource((s) => s.regions[id]);\n const setRegion = useHighlightedImageResource((s) => s.setRegion);\n\n useEffect(() => {\n if (value && newValue) {\n if (\n value !== newValue &&\n (value.x !== newValue.x ||\n value.y !== newValue.y ||\n value.width !== newValue.width ||\n value.height !== newValue.height)\n ) {\n setRegion(id, newValue || null);\n }\n } else {\n setRegion(id, newValue || null);\n }\n }, [value]);\n\n useEffect(() => {\n return () => setRegion(id, null);\n }, []);\n}\n\nexport function useHoverHighlightImageResource(id?: string) {\n const highlight = useHighlightedImageResource((s) => s.highlight);\n const clear = useHighlightedImageResource((s) => s.clearHighlight);\n\n useEffect(() => {\n return () => {\n if (id) {\n clear(id);\n }\n };\n }, [clear, id]);\n\n return useMemo(() => {\n return {\n onMouseEnter() {\n if (id) {\n highlight(id);\n }\n },\n onMouseLeave() {\n if (id) {\n clear(id);\n }\n },\n };\n }, [id, highlight, clear]);\n}\n","import * as React from \"react\";\nimport { SVGProps } from \"react\";\n\nexport const StarIcon = (props: SVGProps<SVGSVGElement>) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"1em\" width=\"1em\" viewBox=\"0 0 24 24\" {...props}>\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path\n d=\"M12 17.27 18.18 21l-1.64-7.03L22 9.24l-7.19-.61L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21z\"\n fill=\"currentColor\"\n />\n </svg>\n);\n","export const BackIcon: React.FC<{ style?: any }> = ({ style }) => (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"1rem\" viewBox=\"0 0 24 24\" width=\"1rem\" fill=\"#000000\" style={style}>\n <path d=\"M0 0h24v24H0z\" fill=\"none\" />\n <path d=\"M20 11H7.83l5.59-5.59L12 4l-8 8 8 8 1.41-1.41L7.83 13H20v-2z\" />\n </svg>\n);\n","import { ErrorMessage, PaddedSidebarContainer } from \"@manifest-editor/components\";\nimport { Button, CalltoButton } from \"@manifest-editor/ui/atoms/Button\";\nimport { ExperimentalMessage } from \"@manifest-editor/ui/madoc/components/callouts/ExperimentalMessage\";\nimport { WarningMessage } from \"@manifest-editor/ui/madoc/components/callouts/WarningMessage\";\nimport { ExperimentalIcon } from \"@manifest-editor/ui/madoc/components/icons/ExperimentalIcon\";\n// import { LimitationError } from \"../../../helpers/limitation\";\n// import { FixMeError } from \"@/helpers/fix-me\";\nimport { useState } from \"react\";\n\nexport function PanelError(props: { error: Error; resetErrorBoundary: () => void }) {\n const error = props.error.toString();\n const [isFixing, setIsFixing] = useState(false);\n\n // @todo come back to.\n // if (props.error instanceof FixMeError) {\n // const errorObject = props.error;\n\n // return (\n // <PaddedSidebarContainer>\n // <WarningMessage $banner>\n // <ExperimentalIcon style={{ fontSize: \"2.2em\", margin: \"0 0.3em 0 0\" }} />\n // <div>\n // <h4 style={{ margin: 0 }}>There is a fixable error</h4>\n // <p>{errorObject.message}</p>\n // <Button\n // disabled={isFixing}\n // onClick={async () => {\n // setIsFixing(true);\n // await errorObject.fix();\n // props.resetErrorBoundary();\n // setIsFixing(false);\n // }}\n // >\n // Fix error\n // </Button>\n // </div>\n // </WarningMessage>\n // </PaddedSidebarContainer>\n // );\n // }\n\n // @todo come back to.\n // if (props.error instanceof LimitationError) {\n // error = props.error.message;\n\n // return (\n // <PaddedSidebarContainer>\n // <ExperimentalMessage $banner>\n // <ExperimentalIcon style={{ fontSize: \"2.2em\", margin: \"0 0.3em 0 0\" }} />\n // <div>\n // <h4 style={{ margin: 0 }}>The manifest editor is still in development</h4>\n // <p>{error}</p>\n // </div>\n // </ExperimentalMessage>\n // </PaddedSidebarContainer>\n // );\n // }\n\n return (\n <PaddedSidebarContainer>\n <ErrorMessage className=\"mb-2\">{error}</ErrorMessage>\n <CalltoButton onClick={props.resetErrorBoundary}>Try again</CalltoButton>\n </PaddedSidebarContainer>\n );\n}\n","import { PinnablePanelState } from \"./Layout.types\";\nimport { createElement, ReactNode } from \"react\";\n\nexport function isPinnableState(t: unknown): t is PinnablePanelState {\n return t && (t as any).pinnable;\n}\n\nexport function panelSizing({\n initial,\n\n fallback,\n options = {},\n}: {\n initial?: number;\n fallback: number;\n options?: { minWidth?: number; maxWidth?: number };\n}) {\n // panel min width\n // panel max width\n // default width\n // fallback width\n return Math.max(options.minWidth || 0, Math.min(options.maxWidth || Infinity, initial || fallback));\n}\n\nexport function renderHelper(htmlOrReact: string | ReactNode): ReactNode {\n if (typeof htmlOrReact === \"string\") {\n return createElement(\"div\", { dangerouslySetInnerHTML: { __html: htmlOrReact } });\n }\n return htmlOrReact;\n}\n","import styled, { css } from \"styled-components\";\nimport { Button } from \"./Button\";\n\nexport const Dropdown = styled.div`\n position: relative;\n display: inline-block;\n`;\n\nexport const DropdownContent = styled.div`\n display: flex;\n flex-direction: column;\n position: absolute;\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n color: ${(props: any) => props.theme.color.black || \" black\"};\n font-size: 0.75rem;\n min-width: 160px;\n box-shadow: 0px 8px 16px 0px rgba(0, 0, 0, 0.2);\n z-index: 150;\n button {\n &:hover {\n background-color: ${(props: any) => props.theme.color.lightgrey || \"lightgrey\"};\n }\n }\n`;\n\nexport const DropdownItem = styled.button<{ $active?: boolean }>`\n padding: 0 ${(props: any) => props.theme.padding.small || \"0.5rem\"};\n color: ${(props: any) => props.theme.color.main || \"none\"};\n background-color: ${(props: any) => props.theme.color.white || \"white\"};\n border-radius: 0;\n border: none;\n cursor: pointer;\n display: flex;\n padding: 0.65em 1em;\n align-items: center;\n :disabled {\n opacity: 0.65;\n cursor: not-allowed;\n }\n\n &:hover {\n background-color: ${(props: any) => props.theme.color.lightgrey || \"lightgrey\"};\n }\n\n ${(props) =>\n props.$active &&\n css`\n background: #b84c74;\n color: #fff;\n &:hover {\n background: #b84c74;\n color: #fff;\n }\n `}\n`;\n\nexport const DropdownMenu = styled.div<{ $open?: boolean; $center?: boolean }>`\n display: none;\n flex-direction: column;\n position: absolute;\n background: #fff;\n color: ${(props: any) => props.theme.color.black || \" black\"};\n font-size: 0.75rem;\n min-width: 190px;\n top: calc(100% + 0.5em);\n box-shadow:\n 0 4px 15px 0 rgba(0, 0, 0, 0.18),\n 0 0px 0px 1px rgba(0, 0, 0, 0.15),\n inset 0 0 0 1px rgba(255, 255, 255, 0.2);\n border-radius: 3px;\n z-index: 150;\n overflow: hidden;\n padding-bottom: 3px;\n\n ${Button} {\n &:hover {\n background-color: ${(props: any) => props.theme.color.lightgrey || \"lightgrey\"};\n }\n }\n\n ${(props) =>\n props.$open &&\n css`\n display: flex;\n `}\n`;\n\nexport const DropdownLabel = styled.div`\n color: #999;\n text-transform: uppercase;\n font-weight: 600;\n padding: 0.7em;\n font-size: 0.875em;\n`;\n\nexport const DropdownDivider = styled.div`\n height: 1px;\n margin: 0 0.5em;\n background: #eee;\n`;\n","import { TransitionStatus } from \"react-transition-group\";\nimport { LayoutPanel, PanelActions, PanelState, PinnablePanelActions, PinnablePanelState } from \"../Layout.types\";\nimport styled, { css } from \"styled-components\";\nimport { StarIcon } from \"@manifest-editor/ui/icons/StarIcon\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { BackIcon } from \"@manifest-editor/ui/icons/BackIcon\";\nimport { useLayoutProvider } from \"../Layout.context\";\nimport { ErrorBoundary } from \"react-error-boundary\";\nimport { createContext, useCallback, useContext, useEffect, useMemo, useRef, useState } from \"react\";\nimport { PanelError } from \"./PanelError\";\nimport { renderHelper } from \"../Layout.helpers\";\nimport { ReactVaultContext } from \"react-iiif-vault\";\nimport {\n DropdownDivider,\n DropdownLabel,\n DropdownMenu,\n Dropdown,\n DropdownItem,\n} from \"@manifest-editor/ui/atoms/Dropdown\";\nimport useDropdownMenu from \"react-accessible-dropdown-menu-hook\";\nimport { useAppState } from \"../../AppContext/AppContext\";\n\nconst OverrideScrollbar = 'OverrideScrollbar';\n\ninterface ModularPanelProps {\n panel?: LayoutPanel;\n isLeft?: boolean;\n state: PinnablePanelState | PanelState;\n actions: PanelActions;\n pinActions?: PinnablePanelActions;\n transition?: TransitionStatus;\n noHeader?: boolean;\n close?: () => void;\n available?: LayoutPanel[];\n style?: any;\n}\n\nconst LayoutTitleReactContext = createContext<(title: string) => void>(null as any);\n\nexport function useSetCustomTitle() {\n return useContext(LayoutTitleReactContext);\n}\n\nconst ModularPanelWrapper = styled.div<{ $floating?: boolean; $state?: TransitionStatus; $flipped?: boolean }>`\n display: flex;\n flex-direction: column;\n position: relative;\n height: 100%;\n overflow: hidden;\n transition: transform 300ms;\n\n &[data-header=\"false\"] {\n border-top: 1px solid #e4e7f0;\n }\n\n &[data-floating=\"true\"] {\n margin: 10px;\n border-radius: 5px;\n overflow: hidden;\n background: #fff;\n }\n\n &[data-state=\"entering\"],\n &[data-state=\"entered\"] {\n transform: translateX(0);\n }\n\n &[data-state=\"exiting\"],\n &[data-state=\"exited\"] {\n transform: translateX(100%);\n }\n\n &[data-state=\"exiting\"][data-flipped=\"true\"],\n &[data-state=\"exited\"][data-flipped=\"true\"] {\n transform: translateX(0);\n }\n\n &[data-state=\"exiting\"][data-flipped=\"false\"],\n &[data-state=\"exited\"][data-flipped=\"false\"] {\n transform: translateX(100%);\n }\n\n &[data-state=\"entering\"][data-flipped=\"true\"],\n &[data-state=\"entered\"][data-flipped=\"true\"] {\n transform: translateX(0);\n }\n\n &[data-state=\"entering\"][data-flipped=\"false\"],\n &[data-state=\"entered\"][data-flipped=\"false\"] {\n transform: translateX(100%);\n }\n\n &[data-state=\"unmounted\"] {\n transform: translateX(100%);\n }\n`;\n\nexport const ModularPanelHeader = styled.div<{ $tabs?: boolean; $error?: boolean }>`\n background: #fff;\n display: flex;\n height: 2.8em;\n align-items: center;\n z-index: 2;\n\n &[data-tabs=\"true\"] {\n box-shadow: inset 0 1px 0 0 rgba(0, 0, 0, 0.17);\n }\n\n &[data-tabs=\"false\"] {\n box-shadow:\n inset 0 -1px 0 0 rgba(0, 0, 0, 0.17),\n inset 0 1px 0 0 rgba(0, 0, 0, 0.17);\n }\n\n &[data-error=\"true\"] {\n color: #b61717;\n background: #ffc2d2;\n box-shadow: inset 0 -5px 10px 0 rgba(255, 255, 255, 0.5);\n }\n`;\n\nexport const ModulePanelButton = styled.button`\n border: none;\n background: transparent;\n padding: 0 0.4em;\n margin: 0.3em;\n border-radius: 3px;\n &:hover {\n background: #eee;\n }\n svg {\n font-size: 1.2em;\n }\n`;\n\nconst ModulePanelSpacer = styled.div`\n flex: 1 1 0px;\n`;\n\nconst ModularPanelLabel = styled.div`\n font-size: 0.875em;\n flex: 1 1 0px;\n padding-left: 1em;\n text-align: center;\n align-self: center;\n`;\n\nconst ModularPanelContent = styled.div`\n flex: 1 1 0px;\n display: flex;\n\n min-height: 0;\n overflow-y: auto;\n overflow-x: hidden;\n\n > * {\n min-width: 0;\n }\n`;\n\nexport function ModularPanel({\n panel,\n state,\n actions,\n isLeft,\n pinActions = actions as any,\n transition,\n close,\n available = [],\n style,\n noHeader,\n}: ModularPanelProps) {\n const vault = useContext(ReactVaultContext) || null;\n const [didError, setDidError] = useState(false);\n const appState = useAppState();\n const layout = useLayoutProvider();\n const { tabs, pinnable, hideHeader } = panel?.options || {};\n const resetKeys = [appState.state.canvasId, panel?.id];\n const switchablePanels = useMemo(() => {\n return (available || []).filter((p) => !p.requiresState);\n }, [available]);\n const { itemProps, isOpen, setIsOpen } = useDropdownMenu(switchablePanels.length);\n const [customTitle, setCustomTitle] = useState(\"\");\n const setCustomTitleRef = useRef<((title: string) => void) | undefined>(undefined);\n\n useEffect(() => setDidError(false), resetKeys);\n\n useEffect(() => setCustomTitle(\"\"), [panel]);\n\n useEffect(() => {\n setCustomTitleRef.current = setCustomTitle;\n return () => {\n setCustomTitleRef.current = undefined;\n };\n }, []);\n\n const _setCustomTitle = useCallback((title: string) => {\n if (setCustomTitleRef.current) {\n setCustomTitleRef.current(title);\n }\n }, []);\n\n const backAction = useCallback(\n (e?: React.MouseEvent) => {\n const originalCallback = panel\n ? state.stack.length\n ? actions.popStack\n : panel.backAction\n ? () => panel && panel.backAction && panel.backAction(state, { ...layout, current: actions }, appState)\n : null\n : null;\n\n if (e && (!originalCallback || e.metaKey) && switchablePanels.length) {\n e.preventDefault();\n setIsOpen(true);\n } else {\n originalCallback && originalCallback();\n }\n },\n [actions, appState, layout, panel, setIsOpen, state, switchablePanels.length]\n );\n\n const menuHandler = (newPanel: LayoutPanel) => {\n actions.change({\n id: newPanel.id,\n state: newPanel.defaultState,\n stacked: !!(state.stack.length || panel?.backAction),\n });\n };\n\n if (!panel || !state.current) {\n return null;\n }\n\n const backButton =\n panel.backAction || state.stack.length ? (\n <ModulePanelButton onClick={backAction}>\n <BackIcon />\n </ModulePanelButton>\n ) : null;\n\n const closeButton = (\n <ModulePanelButton onClick={close || actions.close}>\n <CloseIcon />\n </ModulePanelButton>\n );\n\n return (\n <LayoutTitleReactContext.Provider value={_setCustomTitle}>\n <ModularPanelWrapper data-state={transition} data-flipped={isLeft} style={style} data-header={!noHeader}>\n {noHeader ? null : (\n <ModularPanelHeader data-tabs={!!tabs} data-error={didError}>\n <Dropdown style={{ display: \"flex\", height: \"100%\" }}>\n {panel.renderBackAction ? panel.renderBackAction({ backAction, fallback: backButton }) : backButton}\n {switchablePanels.length ? (\n <DropdownMenu $open={isOpen} style={{ left: \"0.5em\" }}>\n <DropdownLabel>All panels</DropdownLabel>\n <DropdownDivider />\n {switchablePanels.map((newPanel, i) => (\n <DropdownItem\n key={i}\n {...(itemProps as any)[i]}\n onClick={() => menuHandler(newPanel)}\n $active={panel.id === newPanel.id}\n >\n {newPanel.label}\n </DropdownItem>\n ))}\n </DropdownMenu>\n ) : null}\n </Dropdown>\n\n {customTitle ? (\n <ModularPanelLabel>{customTitle}</ModularPanelLabel>\n ) : hideHeader ? (\n <ModulePanelSpacer />\n ) : (\n <ModularPanelLabel>{panel.label}</ModularPanelLabel>\n )}\n {pinnable ? (\n (state as PinnablePanelState).pinned ? (\n <ModulePanelButton onClick={pinActions.unpin}>\n <StarIcon fill=\"orange\" />\n </ModulePanelButton>\n ) : (\n <ModulePanelButton onClick={() => pinActions.pin({ id: panel.id, state: state.state })}>\n <StarIcon fill=\"#ddd\" />\n </ModulePanelButton>\n )\n ) : null}\n {panel.renderCloseAction\n ? panel.renderCloseAction({ closeAction: close || actions.close, fallback: closeButton })\n : closeButton}\n </ModularPanelHeader>\n )}\n <ModularPanelContent className={OverrideScrollbar}>\n <ErrorBoundary\n // onResetKeysChange={() => setDidError(false)}\n onError={() => setDidError(true)}\n FallbackComponent={PanelError}\n resetKeys={resetKeys}\n onReset={() => setDidError(false)}\n >\n {renderHelper(\n panel.render(\n state.state || panel.defaultState || {},\n { ...layout, current: actions, vault: vault as any, transition },\n appState\n )\n )}\n </ErrorBoundary>\n </ModularPanelContent>\n </ModularPanelWrapper>\n </LayoutTitleReactContext.Provider>\n );\n}\n","import { Vault } from \"@iiif/helpers/vault\";\nimport {\n addReference,\n batchActions,\n modifyEntityField,\n reorderEntityField,\n requestResource,\n} from \"@iiif/helpers/vault/actions\";\nimport { actionListFromResource } from \"@iiif/helpers/vault/utility\";\n\nexport function createPreviewVault(homepageCollectionId = \"vault://homepage-collection.json\") {\n const vault = new Vault();\n\n // 1st - ensure that our \"default\" collection exists OR import one.\n const previewCollection = window.localStorage.getItem(\"preview-vault-collection\");\n let didImport = false;\n if (previewCollection) {\n try {\n const previewState = JSON.parse(previewCollection);\n if (previewState.id && previewState.id === homepageCollectionId) {\n vault.dispatch(requestResource({ id: previewState.id }));\n const toDispatch: any = actionListFromResource(previewState.id, previewState);\n vault.dispatch(batchActions({ actions: toDispatch }));\n didImport = true;\n }\n } catch (e) {\n //\n }\n }\n\n if (!didImport) {\n const toDispatch: any = actionListFromResource(homepageCollectionId, {\n \"@context\": \"http://iiif.io/api/presentation/3/context.json\",\n id: homepageCollectionId,\n type: \"Collection\",\n label: { en: [\"Recent items\"] },\n items: [],\n });\n vault.dispatch(requestResource({ id: homepageCollectionId }));\n vault.dispatch(batchActions({ actions: toDispatch }));\n }\n\n const clearHistory = () => {\n vault.dispatch(modifyEntityField({ id: homepageCollectionId, type: \"Collection\", key: \"items\", value: [] }));\n window.localStorage.setItem(\n \"preview-vault-collection\",\n JSON.stringify(vault.toPresentation3({ id: homepageCollectionId, type: \"Collection\" }))\n );\n };\n\n const addHistory = (id: string, type: string) => {\n const state = vault.getState();\n if (id && type && (type === \"Collection\" || type === \"Manifest\")) {\n const existingCollection = state.iiif.entities.Collection[homepageCollectionId];\n // This shouldn't happen... but it could.\n if (existingCollection) {\n const alreadyExists = existingCollection.items.findIndex((t) => t.id === id);\n if (alreadyExists === -1) {\n vault.dispatch(\n addReference({\n id: homepageCollectionId,\n type: \"Collection\",\n reference: { id, type },\n key: \"items\",\n index: 0,\n })\n );\n } else {\n vault.dispatch(\n reorderEntityField({\n id: homepageCollectionId,\n type: \"Collection\",\n key: \"items\",\n startIndex: alreadyExists,\n endIndex: 0,\n })\n );\n }\n\n window.localStorage.setItem(\n \"preview-vault-collection\",\n JSON.stringify(vault.toPresentation3({ id: homepageCollectionId, type: \"Collection\" }))\n );\n }\n }\n };\n\n const unsubscribe2 = vault.on(\"after:@iiif/REMOVE_REFERENCE\", (ctx) => {\n if (ctx.action.payload.id === homepageCollectionId) {\n window.localStorage.setItem(\n \"preview-vault-collection\",\n JSON.stringify(vault.toPresentation3({ id: homepageCollectionId, type: \"Collection\" }))\n );\n }\n });\n\n const unsubscribe = () => {\n // This isn't working, because React.\n // unsubscribe1();\n // unsubscribe2();\n };\n\n return { vault, unsubscribe, addHistory, clearHistory } as const;\n}\n","import { createContext, useContext, useEffect, useMemo } from \"react\";\nimport { Vault } from \"@iiif/helpers/vault\";\nimport { VaultProvider } from \"react-iiif-vault\";\nimport { createPreviewVault } from \"./create-preview-vault\";\n\nexport function usePreviewVault() {\n return useContext(PreviewVaultReactContext);\n}\n\nconst PreviewVaultReactContext = createContext<Vault>(new Vault());\n\nconst PreviewVaultAddHistory = createContext({\n addHistory: (id: string, type: string) => {},\n clearHistory: () => {},\n});\n\nexport const HOMEPAGE_COLLECTION = \"manifest-editor://homepage-collection.json\";\n\nexport function usePreviewHistory() {\n return useContext(PreviewVaultAddHistory);\n}\n\nexport function PreviewVaultContext(props: { children: any }) {\n const { vault, unsubscribe, addHistory, clearHistory } = useMemo(() => {\n return createPreviewVault(HOMEPAGE_COLLECTION);\n }, []);\n\n useEffect(() => {\n return unsubscribe;\n }, []);\n\n return (\n <PreviewVaultAddHistory.Provider value={{ addHistory, clearHistory }}>\n <PreviewVaultReactContext.Provider value={vault}>{props.children}</PreviewVaultReactContext.Provider>\n </PreviewVaultAddHistory.Provider>\n );\n}\n\nexport function PreviewVaultBoundary({ children }: { children: any }) {\n const vault = usePreviewVault();\n\n return <VaultProvider vault={vault}>{children}</VaultProvider>;\n}\n","import { toRef } from \"@iiif/parser\";\nimport type { Reference } from \"@iiif/presentation-3\";\nimport { Creator, matchBasedOnResource } from \"@manifest-editor/creator-api\";\nimport { useCallback, useMemo } from \"react\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { createActionIdentity } from \"../helpers\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { usePreviewVault } from \"../PreviewVault/PreviewVault\";\n\nexport function useCreator(\n parent: any,\n property: string,\n type: string,\n target?: Reference,\n options?: { isPainting?: boolean; onlyReference?: boolean },\n) {\n const vault = useVault();\n const app = useApp();\n const { create, edit } = useLayoutActions();\n const supported = useMemo(\n () => matchBasedOnResource({ type, parent, index: 0, property }, app.layout.creators || [], { vault }),\n [parent, property, app.layout.creators, type, vault],\n );\n const canCreate = parent && supported.length !== 0;\n\n const wrappedCreate = useCallback(\n (index?: number, initialData?: any) => {\n if (parent) {\n return create({\n type,\n parent: toRef(parent),\n property,\n index,\n target,\n initialData,\n ...(options || {}),\n });\n }\n },\n [create, parent, property, type, options, target],\n );\n\n const wrappedFilteredCreate = useCallback(\n (filter: string, index?: number, initialData?: any) => {\n if (parent) {\n return create({\n type,\n filter,\n parent: toRef(parent),\n property,\n index,\n target,\n initialData,\n ...(options || {}),\n });\n }\n },\n [create, parent, property, type, options, target],\n );\n\n const wrappedEdit = useCallback(\n (resource: any, index?: number) => {\n edit(resource, parent ? { parent: toRef(parent), property, index } : undefined);\n },\n [edit, parent, property],\n );\n\n const wrappedCreator = useCallback(\n (initialCreator: string, initialData?: any) => {\n if (parent) {\n return create({\n type,\n initialCreator,\n parent: toRef(parent),\n property,\n target,\n initialData,\n ...(options || {}),\n });\n }\n },\n [type, property, parent, target, create, options],\n );\n\n const buttonProps = useMemo(() => {\n return {\n \"data-action-id\": createActionIdentity(type, property, parent),\n };\n }, [type, property, parent]);\n\n return [\n canCreate,\n {\n create: wrappedCreate,\n edit: wrappedEdit,\n createFiltered: wrappedFilteredCreate,\n creator: wrappedCreator,\n buttonProps,\n },\n ] as const;\n}\n\nexport function useInlineCreator() {\n const vault = useVault();\n const previewVault = usePreviewVault();\n const app = useApp();\n return useMemo(() => {\n return new Creator(vault, app.layout.creators || [], previewVault);\n }, [app.layout.creators, vault]);\n}\n","import { createContext, useContext, useMemo } from \"react\";\n\nconst CreatorInitialDataReactContext = createContext<Record<string, unknown>>({});\n\nexport function useInitialData<T = unknown>(id: string): T | {} {\n const context = useContext(CreatorInitialDataReactContext);\n return context[id] || {};\n}\n\nexport function CreatorInitialData<T extends Record<string, unknown>>(props: { id: string; children: React.ReactNode; data: T }) {\n const existingContext = useContext(CreatorInitialDataReactContext);\n const newContext = useMemo(\n () => ({ ...existingContext, [props.id]: props.data }),\n [existingContext, props.id, props.data],\n );\n return (\n <CreatorInitialDataReactContext.Provider value={newContext}>\n {props.children}\n </CreatorInitialDataReactContext.Provider>\n );\n}\n","import { toRef } from \"@iiif/parser\";\nimport {\n ActionButton,\n BackIcon,\n CreatorGrid,\n EmptyState,\n ErrorMessage,\n GridIcon,\n IconButton,\n ModalBackSlot,\n Spinner,\n} from \"@manifest-editor/components\";\nimport {\n type CreatableResource,\n type CreatorDefinition,\n type CreatorOptions,\n matchBasedOnResource,\n} from \"@manifest-editor/creator-api\";\nimport { Button } from \"@manifest-editor/ui/atoms/Button\";\nimport { memo, Suspense, useEffect, useMemo, useRef, useState } from \"react\";\nimport { useVault } from \"react-iiif-vault\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { useTemporaryHighlight } from \"../highlighted-image-resources\";\nimport { ModulePanelButton, useSetCustomTitle } from \"../Layout/components/ModularPanel\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { useInlineCreator } from \"./BaseCreator.hooks\";\nimport { useInitialData } from \"./CreatorInitialData\";\n\ninterface BaseCreatorProps {\n resource: CreatableResource;\n}\n\nexport const RenderCreator = memo(function RenderCreator(props: {\n resource: CreatableResource;\n creator: CreatorDefinition;\n onCreate?: () => void;\n skipEditingOnCreate?: boolean;\n}) {\n const vault = useVault();\n const { edit, modal } = useLayoutActions();\n const [isCreating, setIsCreating] = useState(false);\n const [error, setError] = useState<string | null>(null);\n const creator = useInlineCreator();\n const isCreatingRef = useRef(false);\n\n const canvasSelector = props.resource.initialData?.selector;\n useTemporaryHighlight(canvasSelector);\n\n const initialData = useInitialData<Record<string, unknown>>(props.creator.id);\n\n const options: CreatorOptions = {\n targetType: props.resource.type,\n parent: props.resource.parent\n ? {\n property: props.resource.property as string,\n atIndex: props.resource.index,\n resource: props.resource.parent,\n }\n : undefined,\n target: props.resource.target,\n initialData: { ...initialData, ...(props.resource.initialData || {}) },\n };\n\n const runCreate = (payload: any) => {\n try {\n if (isCreating || isCreatingRef.current) return;\n setIsCreating(true);\n isCreatingRef.current = true;\n creator\n .create(props.creator.id, payload, options)\n .catch((err) => {\n setError(err?.message || \"Unknown error\");\n return null;\n })\n .then(async (ref) => {\n props.onCreate?.();\n if (props.resource.initialData?.skipEditingOnCreate) {\n setIsCreating(false);\n modal.popStack();\n modal.close();\n return;\n }\n if (props.skipEditingOnCreate) return;\n if (!ref) return;\n const singleRef = Array.isArray(ref) ? ref[0] : ref;\n setIsCreating(false);\n modal.popStack();\n modal.close();\n // Ref might be an array?\n if (singleRef) {\n edit(singleRef!, {\n parent: toRef(props.resource.parent),\n property: props.resource.property,\n index: props.resource.index,\n });\n }\n });\n } catch (err: any) {\n setError(err?.message || \"Unknown error\");\n }\n };\n\n const validate = async () => {\n return true;\n };\n\n useEffect(() => {\n if (props.resource.initialData?.showEmptyForm) {\n return;\n }\n\n if (!props.creator.render && !isCreating) {\n runCreate({});\n }\n }, [props.creator]);\n\n if (error) {\n return (\n <div className=\"flex flex-col items-center p-4\">\n <ErrorMessage>{error}</ErrorMessage>\n </div>\n );\n }\n\n const spinner = (\n <div className=\"flex flex-col items-center py-8\">\n <div className=\"flex gap-2 items-center\">\n <Spinner /> <span>Loading</span>\n </div>\n </div>\n );\n\n if (isCreating) {\n return spinner;\n }\n\n if (!props.creator.render) {\n return (\n <>\n <EmptyState>No options available</EmptyState>\n <ActionButton primary onPress={() => runCreate({})}>\n {props.creator.actionButton || \"Create\"}\n </ActionButton>\n </>\n );\n }\n\n return (\n <>\n <Suspense fallback={spinner}>\n {props.creator.render({\n vault,\n runCreate,\n validate,\n options,\n })}\n </Suspense>\n </>\n );\n});\n\nexport function BaseCreator(props: BaseCreatorProps) {\n const app = useApp();\n const vault = useVault();\n const [currentId, setCurrentId] = useState(props.resource.initialCreator || \"\");\n const set = useSetCustomTitle();\n const supported = useMemo(\n () =>\n matchBasedOnResource(props.resource, app.layout.creators || [], {\n vault,\n }),\n [props.resource, app.layout.creators, vault],\n );\n if (supported.length === 1 && !currentId) {\n setCurrentId(supported[0]!.id);\n }\n\n const current = supported.find((t) => t.id === currentId);\n\n useEffect(() => {\n if (current) {\n set?.(current.label);\n }\n });\n\n if (supported.length === 0) {\n return <EmptyState>Not currently supported</EmptyState>;\n }\n\n const backButton = (\n <ModalBackSlot>\n <IconButton\n root={document.getElementById(\"headlessui-portal-root\") || undefined}\n label=\"Back to Add content options\"\n className=\"group\"\n placement=\"right\"\n onPress={() => setCurrentId(\"\")}\n >\n <GridIcon className=\"text-2xl opacity-50 group-hover:opacity-70\" />\n </IconButton>\n </ModalBackSlot>\n );\n\n if (current) {\n const shouldHideModal = current.hiddenModal;\n\n if (shouldHideModal) {\n return (\n <>\n {backButton}\n <RenderCreator creator={current} resource={props.resource} />\n </>\n );\n }\n\n return (\n <div>\n {backButton}\n <div className={\"p-2 py-6\"}>\n <RenderCreator creator={current} resource={props.resource} />\n </div>\n </div>\n );\n }\n\n return (\n <CreatorGrid\n label=\"Select a type\"\n items={supported.map((item) => ({\n id: item.id,\n title: item.label,\n description: item.summary || \"\",\n icon: item.icon,\n onClick: () => setCurrentId(item.id),\n }))}\n />\n );\n}\n","import type { CreatableResource } from \"@manifest-editor/creator-api\";\nimport type { LayoutPanel } from \"../Layout/Layout.types\";\nimport { BaseCreator } from \"./BaseCreator\";\n\nexport const baseCreator: LayoutPanel = {\n id: \"@manifest-editor/creator\",\n label: \"Add content\",\n options: { hideHeader: true, tabs: false },\n render(state: CreatableResource) {\n return <BaseCreator resource={state} />;\n },\n};\n","export const defaultTheme = {\n color: {\n main: \"#B84C74\",\n mainHover: \"#4a89ff\",\n logoPink: \"#E94581\",\n white: \"white\",\n grey: \"grey\",\n black: \"black\",\n lightgrey: \"#F8F9FA\",\n mediumgrey: \"#dddddd\",\n danger: \"#a90e21\",\n warning: \"#e38627\",\n lightdanger: \"#ffeaea\",\n lightsuccess: \"#c5e8c5\",\n success: \"#6ccd55\",\n greyOverlay: \"rgba(0, 0, 0, 0.2)\",\n highlight: \"#faeed7\",\n },\n iiifColor: {\n manifest: \"rgba(0, 0, 0, 0.2)\",\n canvas: \"rgba(255, 222, 219, 0.8)\",\n service: \"rgba(13, 110, 253, 0.8)\",\n annotation: \"rgba(247, 226, 173, 0.8)\",\n contentResource: \"rgba(207, 247, 255, 0.8)\",\n ranges: \"rgba(144, 213, 157, 0.8)\",\n },\n padding: {\n xs: \"0.25rem\",\n small: \"0.5rem\",\n medium: \"1rem\",\n large: \"2rem\",\n },\n device: {\n mobile: \"375px\",\n tablet: \"768px\",\n laptop: \"992px\",\n desktop: \"1200px\",\n },\n shadows: {\n standard: \"rgba(0, 0, 0, 0.1) 0px 1px 3px 0px, rgba(0, 0, 0, 0.05) 0px 5px 15px 0px\",\n bottom: \"rgba(0, 0, 0, 0.1) 0px 4px 2px -2px\",\n },\n};\n","import { useVault } from \"react-iiif-vault\";\nimport { useMemo } from \"react\";\nimport {\n type CreatableResource,\n matchBasedOnResource,\n} from \"@manifest-editor/creator-api\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { Tab, TabList, TabPanel, Tabs } from \"@manifest-editor/components\";\nimport { RenderCreator } from \"./BaseCreator\";\nimport { ThemeProvider } from \"styled-components\";\nimport { defaultTheme } from \"../ShellContext/default-theme\";\n\ninterface BaseAnnotationCreatorProps {\n resource: CreatableResource;\n onCreate: () => void;\n}\n\nexport function BaseAnnotationCreator(props: BaseAnnotationCreatorProps) {\n const {} = props;\n const vault = useVault();\n const app = useApp();\n const supported = useMemo(\n () =>\n matchBasedOnResource(props.resource, app.layout.creators || [], {\n vault,\n }),\n [props.resource, app.layout.creators, vault],\n );\n\n if (supported.length === 0) {\n return <div>No supported creators found</div>;\n }\n\n return (\n <div>\n <Tabs className=\"w-full flex-1 overflow-hidden flex flex-col\">\n <TabList\n className=\"flex-1 overflow-hidden w-full flex text-sm whitespace-nowrap\"\n items={supported}\n >\n {(item) => <Tab id={item.id}>{item.label}</Tab>}\n </TabList>\n {supported.map((item) => {\n return (\n <TabPanel key={item.id} id={item.id} className=\"p-2\">\n <ThemeProvider theme={defaultTheme}>\n <RenderCreator\n creator={item}\n resource={props.resource}\n onCreate={props.onCreate}\n skipEditingOnCreate\n />\n </ThemeProvider>\n </TabPanel>\n );\n })}\n </Tabs>\n </div>\n );\n}\n","import type { Vault } from \"@iiif/helpers\";\nimport { SidebarTabs } from \"@manifest-editor/components\";\nimport { BackIcon } from \"@manifest-editor/ui/icons/BackIcon\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { type ReactNode, useContext, useEffect, useMemo } from \"react\";\nimport { ResourceReactContext, useVault } from \"react-iiif-vault\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { type EditorConfig, useConfig } from \"../ConfigContext/ConfigContext\";\nimport { useEditingResource, useEditingResourceStack, useEditingStack } from \"../EditingStack/EditingStack\";\nimport type { EditableResource } from \"../EditingStack/EditingStack.types\";\nimport { ModulePanelButton, useSetCustomTitle } from \"../Layout/components/ModularPanel\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport type { EditorDefinition, ResourceDefinition } from \"../Layout/Layout.types\";\n\nexport function BaseEditorBackButton({ fallback, backAction }: any) {\n const stack = useEditingResourceStack();\n const { back } = useEditingStack();\n\n if (stack.length) {\n return (\n <ModulePanelButton onClick={back}>\n <BackIcon />\n </ModulePanelButton>\n );\n }\n\n return fallback;\n}\n\nexport function BaseEditorCloseButton({ closeAction, fallback }: any) {\n const stack = useEditingResourceStack();\n const current = useEditingResource();\n\n if (current || stack.length) {\n return (\n <ModulePanelButton\n onClick={() => {\n closeAction();\n }}\n >\n <CloseIcon />\n </ModulePanelButton>\n );\n }\n\n return fallback;\n}\n\nexport function editBasedOnResource(\n resource: EditableResource,\n list: ResourceDefinition[],\n options: { edit?: boolean; vault: Vault },\n config: EditorConfig,\n): ResourceDefinition | null {\n const filteredList = list.filter((l) => l.resourceType === resource.resource.source.type);\n\n if (filteredList.length === 0) {\n return null;\n }\n\n for (const item of filteredList) {\n // Check for a match in order.\n const sortKeys: string[] = [];\n const sortKeyFallbacks: Record<string, EditorDefinition> = {};\n // 1. Filter out the\n const editors = (item.editors || []).filter((editor) => {\n if (config.hideTabs && config.hideTabs.includes(editor.id)) {\n return false;\n }\n if (config.onlyTabs && !config.onlyTabs.includes(editor.id)) {\n return false;\n }\n if (editor.supports.sortKey) {\n if (sortKeys.includes(editor.supports.sortKey)) {\n return false;\n }\n if (editor.supports.sortFallback) {\n sortKeyFallbacks[editor.supports.sortKey] = editor;\n }\n }\n\n // Does this editor support the input resource.\n if (options.edit && !editor.supports.edit) {\n return false;\n }\n\n if (editor.supports.custom ? editor.supports.custom(resource, options.vault) === false : false) {\n return false;\n }\n\n // @todo more logic here, including \"custom\" supports check.\n\n if (editor.supports.sortKey) {\n sortKeys.push(editor.supports.sortKey);\n }\n\n return true;\n });\n\n const missingKeys = Object.keys(sortKeyFallbacks);\n for (const missingKey of missingKeys) {\n if (\n !sortKeys.includes(missingKey) &&\n sortKeyFallbacks[missingKey] &&\n !editors.includes(sortKeyFallbacks[missingKey]!)\n ) {\n editors.push(sortKeyFallbacks[missingKey]!);\n }\n }\n\n if (editors.length) {\n return {\n ...item,\n editors,\n };\n }\n }\n\n return null;\n}\n\nexport function BaseEditor({ currentTab = undefined }: { currentTab?: string }) {\n const resource = useEditingResource();\n const currentResourceContext = useContext(ResourceReactContext);\n const app = useApp();\n const rootResource = useAppResource();\n const vault = useVault();\n const { change } = useLayoutActions();\n const set = useSetCustomTitle();\n const { editorConfig } = useConfig();\n const resourceId = resource?.resource.source?.id;\n let resourceType = resource?.resource.source?.type;\n // Could use this is for later.\n const isNested = resourceId !== rootResource.id;\n if (resourceId && isNested && rootResource.type === \"Collection\" && resourceType === \"Collection\") {\n resourceType = \"EmbeddedCollection\";\n }\n\n const resourceConfig: EditorConfig = (resourceType ? (editorConfig as any)[resourceType] : editorConfig.All) || {};\n\n const newResourceContext = useMemo(() => {\n const newCtx = { ...currentResourceContext };\n const id = resource?.resource.source.id;\n const type = resource?.resource.source.type;\n const mapping = {\n Collection: \"collection\",\n Manifest: \"manifest\",\n Range: \"range\",\n Canvas: \"canvas\",\n Annotation: \"annotation\",\n AnnotationPage: \"annotationPage\",\n };\n\n if (type && (mapping as any)[type]) {\n (newCtx as any)[(mapping as any)[type]] = id;\n }\n return newCtx;\n }, [resource, currentResourceContext]);\n\n function wrap(children: ReactNode) {\n if (!resource) {\n return children;\n }\n\n return <ResourceReactContext.Provider value={newResourceContext}>{children}</ResourceReactContext.Provider>;\n }\n\n const match = useMemo(() => {\n if (!resource) {\n return null;\n }\n\n const editors = app.layout.editors || [];\n const resources = app.layout.resources || [];\n const mappedResources: ResourceDefinition[] = resources.map((resource: string | ResourceDefinition) => {\n if (typeof resource === \"string\") {\n return {\n id: \"@default/\" + resource,\n label: resource,\n resourceType: resource,\n auto: true,\n editors: editors.filter((e: any) => e.supports.resourceTypes.includes(resource)),\n };\n }\n return resource;\n });\n\n return editBasedOnResource(resource, mappedResources, { edit: true, vault }, resourceConfig);\n }, [resource, app]);\n\n useEffect(() => {\n set(match?.label || \"\");\n }, [match]);\n\n useEffect(() => {\n const availableKeys = match?.editors.map((editor) => editor.id) || [];\n const currentKey = availableKeys.find((key) => key === currentTab);\n if (!currentKey) {\n change(\"@manifest-editor/editor\", { currentTab: availableKeys[0] });\n }\n }, [match?.editors, currentTab, change]);\n\n // Memoize the tab menu to prevent React Aria's collection items from receiving new\n // inline function props on every parent re-render, which causes an infinite\n // setProps → queueUpdate → re-render loop in Next.js SSR collection mode.\n const sidebarMenu = useMemo(\n () =>\n (match?.editors || []).map((editor) => ({\n id: editor.id,\n label: editor.label,\n renderComponent: () => editor.component(resourceConfig),\n })),\n // eslint-disable-next-line react-hooks/exhaustive-deps\n [match?.editors, resourceConfig],\n );\n\n // Problems to solve:\n // - Subscribing to updates to the reference\n // - Keeping track of changes to the item, by checking it's index\n // - If the items change - ensure we have the same index by doing an equality check on the reference?\n\n if (!resource || !match) {\n return null;\n }\n\n if (resourceConfig.singleTab) {\n const first = (match?.editors || []).find((editor) => editor.id === resourceConfig.singleTab);\n if (first) {\n return wrap(\n <div key={resource.resource.source?.id} className=\"w-full\">\n {first.component(resourceConfig)}\n </div>,\n );\n }\n }\n\n return wrap(\n <SidebarTabs\n isNested={isNested}\n rootResource={rootResource}\n key={resource.resource.source?.id}\n menuId={resource.resource.source.id}\n menu={sidebarMenu}\n selectedKey={currentTab}\n onSelectionChange={(p: any) => {\n change(\"@manifest-editor/editor\", { currentTab: p });\n }}\n />,\n );\n}\n","import type { LayoutPanel } from \"../Layout/Layout.types\";\nimport {\n BaseEditor,\n BaseEditorBackButton,\n BaseEditorCloseButton,\n} from \"./BaseEditor\";\n\nexport const baseEditor: LayoutPanel = {\n id: \"@manifest-editor/editor\",\n label: \"Editor\",\n options: { hideHeader: true, tabs: true, minWidth: 400 },\n renderBackAction: ({ backAction, fallback }) => (\n <BaseEditorBackButton backAction={backAction} fallback={fallback} />\n ),\n renderCloseAction: ({ closeAction, fallback }) => (\n <BaseEditorCloseButton closeAction={closeAction} fallback={fallback} />\n ),\n render({ currentTab }) {\n return <BaseEditor currentTab={currentTab} />;\n },\n};\n","import { useMemo, useRef, useState } from \"react\";\n\nexport function useDecayState(time: number) {\n const [active, _setActive] = useState(false);\n const lastTimeout = useRef<any>(null);\n const focusCount = useRef<any>(0);\n\n function clear(existing?: boolean) {\n focusCount.current--;\n\n if (existing && focusCount.current !== 0) {\n return;\n }\n\n if (lastTimeout.current) {\n clearTimeout(lastTimeout.current);\n lastTimeout.current = 0;\n }\n lastTimeout.current = setTimeout(() => {\n _setActive(false);\n }, time);\n }\n\n function set() {\n focusCount.current++;\n if (lastTimeout.current) {\n clearTimeout(lastTimeout.current);\n }\n _setActive(true);\n }\n\n return useMemo(() => [active, { set, clear }] as const, [active]);\n}\n","import { CheckIcon, Modal } from \"@manifest-editor/components\";\nimport { useContext, useEffect, useMemo, useState } from \"react\";\nimport { useApp, useAppInstance } from \"../AppContext/AppContext\";\nimport { useConfig, useSaveConfig } from \"../ConfigContext/ConfigContext\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { PluginGlobalConfigReactContext, usePluginActions, usePluginConfigApi, usePlugins } from \"./PluginContext\";\nimport {\n disablePluginInConfig,\n enablePluginAndDependenciesInConfig,\n getEnabledPluginsForApp,\n getPluginCompatibilityReason,\n getPluginSelectionSource,\n isPluginCompatible,\n isPluginSelected,\n resetPluginInConfig,\n} from \"./PluginContext.helpers\";\nimport type {\n MappedPlugin,\n PluginAppConfig,\n PluginConfigScope,\n PluginSettingsField,\n PluginSettingsValue,\n} from \"./PluginContext.types\";\n\nfunction getImage(image: MappedPlugin[\"metadata\"][\"image\"]) {\n if (!image) return null;\n return typeof image === \"string\" ? { src: image, alt: \"\" } : image;\n}\n\nfunction getAuthor(author: MappedPlugin[\"metadata\"][\"author\"]) {\n if (!author) return null;\n return typeof author === \"string\" ? author : author.name;\n}\n\nfunction getPluginEntryPoint(plugin: MappedPlugin) {\n const extension = plugin.extension;\n const panel =\n extension.leftPanels?.[0] ||\n extension.centerPanels?.[0] ||\n extension.rightPanels?.[0] ||\n extension.modalPanels?.[0];\n\n if (!panel) return null;\n\n return {\n id: panel.id,\n label: panel.label || \"Open plugin\",\n modal: extension.modalPanels?.some((item) => item.id === panel.id) || false,\n };\n}\n\nfunction getErrorMessage(error: unknown) {\n return error instanceof Error ? error.message : \"Plugin configuration could not be saved.\";\n}\n\nfunction ConfigureIcon(props: React.SVGProps<SVGSVGElement>) {\n return (\n <svg\n xmlns=\"http://www.w3.org/2000/svg\"\n width=\"1em\"\n height=\"1em\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n strokeWidth=\"2\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n {...props}\n >\n <path d=\"M12.22 2h-.44a2 2 0 0 0-2 2v.18a2 2 0 0 1-1 1.73l-.43.25a2 2 0 0 1-2 0l-.15-.08a2 2 0 0 0-2.73.73l-.22.38a2 2 0 0 0 .73 2.73l.15.1a2 2 0 0 1 1 1.72v.51a2 2 0 0 1-1 1.74l-.15.09a2 2 0 0 0-.73 2.73l.22.38a2 2 0 0 0 2.73.73l.15-.08a2 2 0 0 1 2 0l.43.25a2 2 0 0 1 1 1.73V20a2 2 0 0 0 2 2h.44a2 2 0 0 0 2-2v-.18a2 2 0 0 1 1-1.73l.43-.25a2 2 0 0 1 2 0l.15.08a2 2 0 0 0 2.73-.73l.22-.39a2 2 0 0 0-.73-2.73l-.15-.08a2 2 0 0 1-1-1.74v-.5a2 2 0 0 1 1-1.74l.15-.09a2 2 0 0 0 .73-2.73l-.22-.38a2 2 0 0 0-2.73-.73l-.15.08a2 2 0 0 1-2 0l-.43-.25a2 2 0 0 1-1-1.73V4a2 2 0 0 0-2-2z\" />\n <circle cx=\"12\" cy=\"12\" r=\"3\" />\n </svg>\n );\n}\n\nfunction OpenArrowIcon(props: React.SVGProps<SVGSVGElement>) {\n return (\n <svg\n xmlns=\"http://www.w3.org/2000/svg\"\n width=\"1em\"\n height=\"1em\"\n viewBox=\"0 0 24 24\"\n fill=\"none\"\n stroke=\"currentColor\"\n strokeWidth=\"2\"\n strokeLinecap=\"round\"\n strokeLinejoin=\"round\"\n {...props}\n >\n <path d=\"M7 7h10v10\" />\n <path d=\"M7 17 17 7\" />\n </svg>\n );\n}\n\nexport function PluginManager() {\n const app = useApp();\n const { appId } = useAppInstance();\n const config = useConfig();\n const saveConfig = useSaveConfig();\n const pluginState = usePlugins();\n const actions = usePluginActions();\n const layoutActions = useLayoutActions();\n const { saveGlobalPluginConfig } = useContext(PluginGlobalConfigReactContext);\n const [showAll, setShowAll] = useState(false);\n const [query, setQuery] = useState(\"\");\n const [selectedPluginId, setSelectedPluginId] = useState<string | null>(null);\n const [savingKey, setSavingKey] = useState<string | null>(null);\n const [error, setError] = useState<string | null>(null);\n\n const activePluginIds = useMemo(\n () => new Set(getEnabledPluginsForApp(pluginState, app, appId).map((plugin) => plugin.metadata.id)),\n [pluginState, app, appId],\n );\n\n const filteredPlugins = useMemo(() => {\n const normalisedQuery = query.trim().toLowerCase();\n\n return pluginState.plugins.filter((plugin) => {\n const compatible = isPluginCompatible(plugin, app, appId);\n if (!showAll && !compatible) return false;\n\n if (!normalisedQuery) return true;\n\n const haystack = [\n plugin.metadata.label,\n plugin.metadata.id,\n plugin.metadata.description,\n getAuthor(plugin.metadata.author),\n ...(plugin.metadata.tags || []),\n ]\n .filter(Boolean)\n .join(\" \")\n .toLowerCase();\n\n return haystack.includes(normalisedQuery);\n });\n }, [app, appId, pluginState.plugins, query, showAll]);\n\n const selectedPlugin = selectedPluginId\n ? pluginState.plugins.find((plugin) => plugin.metadata.id === selectedPluginId) || null\n : null;\n\n if (!pluginState.plugins.length) {\n return null;\n }\n\n function persistWorkspaceAppConfig(nextAppConfig: PluginAppConfig) {\n actions.setAppConfig(appId, nextAppConfig);\n saveConfig({\n plugins: {\n ...(config.plugins || {}),\n apps: {\n ...(config.plugins?.apps || {}),\n [appId]: nextAppConfig,\n },\n },\n });\n }\n\n async function persistGlobalAppConfig(nextAppConfig: PluginAppConfig) {\n if (!saveGlobalPluginConfig) {\n setError(\"Global plugin settings are not available in this host.\");\n return;\n }\n\n const previousAppConfig = pluginState.globalApps[appId] || {};\n const nextGlobalConfig = {\n apps: {\n ...pluginState.globalApps,\n [appId]: nextAppConfig,\n },\n };\n\n actions.setGlobalAppConfig(appId, nextAppConfig);\n\n try {\n await saveGlobalPluginConfig(nextGlobalConfig);\n } catch (error) {\n actions.setGlobalAppConfig(appId, previousAppConfig);\n setError(getErrorMessage(error));\n }\n }\n\n async function setPluginEnabled(plugin: MappedPlugin, enabled: boolean, scope: PluginConfigScope) {\n setError(null);\n setSavingKey(`${scope}:${plugin.metadata.id}`);\n\n const current = scope === \"global\" ? pluginState.globalApps[appId] || {} : pluginState.apps[appId] || {};\n const nextAppConfig = enabled\n ? enablePluginAndDependenciesInConfig(current, pluginState, plugin, app, appId)\n : { config: disablePluginInConfig(current, plugin.metadata.id), blocked: [] };\n\n if (nextAppConfig.blocked.length) {\n setSavingKey(null);\n setError(`Cannot enable ${plugin.metadata.label}: ${nextAppConfig.blocked.join(\", \")}.`);\n return;\n }\n\n if (scope === \"global\") {\n await persistGlobalAppConfig(nextAppConfig.config);\n } else {\n persistWorkspaceAppConfig(nextAppConfig.config);\n }\n\n setSavingKey(null);\n }\n\n function openPlugin(plugin: MappedPlugin) {\n const entryPoint = getPluginEntryPoint(plugin);\n if (!entryPoint) return;\n\n if (entryPoint.modal) {\n layoutActions.modal.open({ id: entryPoint.id });\n return;\n }\n\n layoutActions.open(entryPoint.id);\n }\n\n return (\n <section className=\"flex flex-col gap-3 border-t border-gray-200 pt-4 mt-4\">\n <div className=\"flex items-center gap-2\">\n <div className=\"min-w-0 flex-1\">\n <h3 className=\"font-semibold text-sm text-gray-900\">Plugins</h3>\n </div>\n <button\n type=\"button\"\n className=\"rounded border border-gray-200 bg-white px-2 py-1 text-xs text-gray-500 hover:text-gray-700 hover:border-gray-300 transition-colors\"\n onClick={() => setShowAll((value) => !value)}\n >\n {showAll ? \"Compatible only\" : \"Show all\"}\n </button>\n </div>\n\n <input\n className=\"rounded border border-gray-200 px-2.5 py-1.5 text-xs focus:border-me-primary-500 focus:ring-2 focus:ring-me-primary-500/20 focus:outline-none\"\n type=\"search\"\n placeholder=\"Search plugins…\"\n value={query}\n onChange={(event) => setQuery(event.currentTarget.value)}\n />\n\n {error ? (\n <div className=\"rounded border border-red-200 bg-red-50 px-3 py-2 text-xs text-red-700\">{error}</div>\n ) : null}\n\n <div className=\"flex flex-col gap-2\">\n {filteredPlugins.map((plugin) => {\n const selected = isPluginSelected(plugin, pluginState, appId);\n const active = activePluginIds.has(plugin.metadata.id);\n const loading = selected && plugin.loadStatus === \"loading\";\n const loadError = selected && plugin.loadStatus === \"error\" ? plugin.loadError : null;\n const image = getImage(plugin.metadata.image);\n const blocked = selected && !active && !loading && !loadError;\n const compatible = isPluginCompatible(plugin, app, appId);\n const compatibilityReason = getPluginCompatibilityReason(plugin, app, appId);\n const entryPoint = getPluginEntryPoint(plugin);\n const canConfigure = !!plugin.settings;\n const isSaving = savingKey === `workspace:${plugin.metadata.id}`;\n\n return (\n <article\n key={plugin.metadata.id}\n className={`flex gap-2.5 rounded-lg border bg-white p-3 text-sm transition-colors ${\n active ? \"border-gray-200\" : \"border-gray-100 opacity-60\"\n } ${!compatible ? \"opacity-40\" : \"\"}`}\n >\n {image ? (\n <img\n className=\"h-9 w-9 rounded object-cover flex-none mt-0.5\"\n src={image.src}\n alt={image.alt || plugin.metadata.label}\n />\n ) : (\n <div\n className={`h-9 w-9 rounded flex items-center justify-center flex-none mt-0.5 text-lg ${\n active ? \"bg-me-primary-50 text-me-primary-500\" : \"bg-gray-100 text-gray-400\"\n }`}\n >\n <ConfigureIcon className=\"w-4 h-4\" />\n </div>\n )}\n\n <div className=\"flex min-w-0 flex-1 flex-col gap-1\">\n <div className=\"flex items-start justify-between gap-1\">\n <div className=\"flex flex-wrap items-center gap-1.5 min-w-0\">\n <span className=\"font-medium text-gray-900 text-xs\">{plugin.metadata.label}</span>\n {plugin.metadata.official ? (\n <span className=\"rounded-full text-me-primary-500 px-1.5 py-0 text-[9px] font-bold inline-flex items-center gap-1\">\n <CheckIcon className=\"w-3 h-3\" /> Verified\n </span>\n ) : null}\n {plugin.metadata.version ? (\n <span className=\"text-[10px] text-gray-400\">{plugin.metadata.version}</span>\n ) : null}\n </div>\n\n <div className=\"flex items-center gap-1 flex-none\">\n {canConfigure ? (\n <button\n type=\"button\"\n title=\"Configure plugin\"\n className=\"rounded p-1 text-gray-400 hover:text-gray-700 hover:bg-gray-100 transition-colors\"\n onClick={() => setSelectedPluginId(plugin.metadata.id)}\n >\n <ConfigureIcon className=\"w-3.5 h-3.5\" />\n </button>\n ) : null}\n {active && entryPoint ? (\n <button\n type=\"button\"\n title={`Open ${entryPoint.label}`}\n className=\"rounded p-1 text-me-primary-500 hover:bg-me-primary-50 transition-colors\"\n onClick={() => openPlugin(plugin)}\n >\n <OpenArrowIcon className=\"w-3.5 h-3.5\" />\n </button>\n ) : null}\n <button\n type=\"button\"\n disabled={!compatible || isSaving}\n onClick={() => setPluginEnabled(plugin, !selected, \"workspace\")}\n className={`relative inline-flex h-5 w-9 flex-none items-center rounded-full transition-colors disabled:opacity-40 focus:outline-none focus:ring-2 focus:ring-me-primary-500/30 ${\n selected ? \"bg-me-primary-500\" : \"bg-gray-200\"\n }`}\n title={selected ? \"Disable plugin\" : \"Enable plugin\"}\n aria-label={selected ? \"Disable plugin\" : \"Enable plugin\"}\n >\n <span\n className={`inline-block h-3.5 w-3.5 transform rounded-full bg-white shadow transition-transform ${\n selected ? \"translate-x-4\" : \"translate-x-0.5\"\n }`}\n />\n </button>\n </div>\n </div>\n\n {plugin.metadata.description ? (\n <p className=\"text-xs text-gray-500 leading-relaxed\">{plugin.metadata.description}</p>\n ) : null}\n\n {loading ? <span className=\"text-xs text-gray-500\">Loading plugin…</span> : null}\n {loadError ? <span className=\"text-xs text-red-600\">{loadError}</span> : null}\n {blocked ? <span className=\"text-xs text-amber-600\">Waiting for required dependencies</span> : null}\n {!compatible && compatibilityReason ? (\n <span className=\"text-xs text-gray-400\">{compatibilityReason}</span>\n ) : null}\n </div>\n </article>\n );\n })}\n </div>\n\n {!filteredPlugins.length ? (\n <div className=\"rounded-lg border border-gray-100 bg-gray-50 p-4 text-center text-xs text-gray-500\">\n No plugins found.\n </div>\n ) : null}\n\n {selectedPlugin ? (\n <Modal\n title={`Configure ${selectedPlugin.metadata.label}`}\n onClose={() => setSelectedPluginId(null)}\n width=\"560px\"\n >\n <PluginSettingsEditor\n plugin={selectedPlugin}\n onClose={() => setSelectedPluginId(null)}\n canSaveGlobal={!!saveGlobalPluginConfig}\n />\n </Modal>\n ) : null}\n </section>\n );\n}\n\nfunction PluginSettingsEditor({\n plugin,\n onClose,\n canSaveGlobal,\n}: {\n plugin: MappedPlugin;\n onClose: () => void;\n canSaveGlobal?: boolean;\n}) {\n const api = usePluginConfigApi(plugin.metadata.id);\n const [scope, setScope] = useState<PluginConfigScope>(\"workspace\");\n const [draft, setDraft] = useState<PluginSettingsValue>({});\n const [saving, setSaving] = useState(false);\n const [saved, setSaved] = useState(false);\n const [error, setError] = useState<string | null>(null);\n const sourceValue = scope === \"global\" ? api.global : api.workspace;\n\n useEffect(() => {\n setDraft({ ...sourceValue });\n setError(null);\n setSaved(false);\n }, [plugin.metadata.id, scope]);\n\n async function save() {\n const validation = plugin.settings?.validate?.(draft);\n if (validation) {\n setError(validation);\n return;\n }\n\n setSaving(true);\n setError(null);\n try {\n if (scope === \"global\") {\n await api.setGlobalSettings(draft);\n } else {\n api.setWorkspaceSettings(draft);\n }\n setSaved(true);\n setTimeout(() => setSaved(false), 2000);\n } catch (error) {\n setError(getErrorMessage(error));\n } finally {\n setSaving(false);\n }\n }\n\n async function reset() {\n setSaving(true);\n setError(null);\n try {\n if (scope === \"global\") {\n await api.resetGlobalSettings();\n } else {\n api.resetWorkspaceSettings();\n }\n setDraft({});\n } catch (error) {\n setError(getErrorMessage(error));\n } finally {\n setSaving(false);\n }\n }\n\n const showGlobal = canSaveGlobal && api.canSaveGlobal;\n\n return (\n <div className=\"flex flex-col flex-1 min-h-0\">\n {showGlobal ? (\n <div className=\"flex items-center gap-1 px-5 pt-4 pb-3 border-b border-gray-100\">\n <span className=\"text-xs text-gray-500 mr-2\">Scope:</span>\n <button\n type=\"button\"\n className={`rounded-full px-3 py-1 text-xs font-medium transition-colors ${\n scope === \"workspace\" ? \"bg-me-primary-500 text-white\" : \"bg-gray-100 text-gray-600 hover:bg-gray-200\"\n }`}\n onClick={() => setScope(\"workspace\")}\n >\n This workspace\n </button>\n <button\n type=\"button\"\n className={`rounded-full px-3 py-1 text-xs font-medium transition-colors ${\n scope === \"global\" ? \"bg-me-primary-500 text-white\" : \"bg-gray-100 text-gray-600 hover:bg-gray-200\"\n }`}\n onClick={() => setScope(\"global\")}\n >\n All workspaces\n </button>\n </div>\n ) : null}\n\n {error ? (\n <div className=\"mx-5 mt-4 rounded-lg border border-red-200 bg-red-50 px-3 py-2 text-xs text-red-700\">\n {error}\n </div>\n ) : null}\n\n <div className=\"flex-1 overflow-y-auto p-5\">\n <div className=\"flex flex-col gap-3\">\n {plugin.settings?.render ? (\n plugin.settings.render({\n plugin,\n appId: api.appId,\n scope,\n value: draft,\n defaults: api.defaults,\n effective: api.effective,\n onChange: setDraft,\n })\n ) : plugin.settings?.fields?.length ? (\n plugin.settings.fields.map((field) => (\n <PluginSettingsFieldControl key={field.id} field={field} draft={draft} setDraft={setDraft} />\n ))\n ) : (\n <div className=\"rounded-lg border border-gray-100 bg-gray-50 p-4 text-center text-sm text-gray-500\">\n This plugin has no configurable settings.\n </div>\n )}\n </div>\n </div>\n\n <div className=\"flex items-center justify-between gap-3 border-t border-gray-100 px-5 py-4\">\n <button\n type=\"button\"\n className=\"text-xs text-gray-400 hover:text-gray-600 transition-colors disabled:opacity-40\"\n disabled={saving}\n onClick={reset}\n >\n Reset to defaults\n </button>\n <div className=\"flex items-center gap-2\">\n {saved ? <span className=\"text-xs text-green-600\">✓ Saved</span> : null}\n <button\n type=\"button\"\n className=\"rounded-lg bg-me-primary-500 px-4 py-2 text-sm font-medium text-white hover:bg-me-primary-600 disabled:opacity-50 transition-colors\"\n disabled={saving}\n onClick={save}\n >\n {saving ? \"Saving…\" : `Save ${scope}`}\n </button>\n </div>\n </div>\n </div>\n );\n}\n\nfunction PluginSettingsFieldControl({\n field,\n draft,\n setDraft,\n}: {\n field: PluginSettingsField;\n draft: PluginSettingsValue;\n setDraft: (value: PluginSettingsValue) => void;\n}) {\n const value = draft[field.id];\n const id = `plugin-setting-${field.id}`;\n\n function update(nextValue: unknown) {\n setDraft({\n ...draft,\n [field.id]: nextValue,\n });\n }\n\n const label = (\n <label className=\"text-sm font-medium text-gray-900\" htmlFor={id}>\n {field.label}\n </label>\n );\n\n const inputClasses =\n \"rounded-lg border border-gray-200 bg-white px-3 py-2 text-sm focus:border-me-primary-500 focus:ring-2 focus:ring-me-primary-500/20 focus:outline-none\";\n\n if (field.type === \"boolean\") {\n return (\n <div className=\"flex items-center justify-between rounded-lg border border-gray-100 bg-white px-4 py-3\">\n <div className=\"flex flex-col gap-0.5\">\n {label}\n {field.description ? <span className=\"text-xs text-gray-500\">{field.description}</span> : null}\n </div>\n <input\n id={id}\n type=\"checkbox\"\n checked={value === true}\n onChange={(event) => update(event.currentTarget.checked)}\n className=\"h-4 w-4 rounded border-gray-300 text-me-primary-500 focus:ring-me-primary-500\"\n />\n </div>\n );\n }\n\n if (field.type === \"textarea\") {\n return (\n <div className=\"flex flex-col gap-2 rounded-lg border border-gray-100 bg-white px-4 py-3\">\n {label}\n {field.description ? <span className=\"text-xs text-gray-500\">{field.description}</span> : null}\n <textarea\n id={id}\n className={`${inputClasses} min-h-24 resize-y`}\n value={typeof value === \"string\" ? value : \"\"}\n placeholder={field.placeholder}\n onChange={(event) => update(event.currentTarget.value)}\n />\n </div>\n );\n }\n\n if (field.type === \"select\") {\n return (\n <div className=\"flex flex-col gap-2 rounded-lg border border-gray-100 bg-white px-4 py-3\">\n {label}\n {field.description ? <span className=\"text-xs text-gray-500\">{field.description}</span> : null}\n <select\n id={id}\n className={inputClasses}\n value={typeof value === \"undefined\" ? \"\" : String(value)}\n onChange={(event) => {\n const option = field.options?.find((item) => String(item.value) === event.currentTarget.value);\n update(option ? option.value : event.currentTarget.value);\n }}\n >\n <option value=\"\">Default</option>\n {(field.options || []).map((option) => (\n <option key={String(option.value)} value={String(option.value)}>\n {option.label}\n </option>\n ))}\n </select>\n </div>\n );\n }\n\n return (\n <div className=\"flex flex-col gap-2 rounded-lg border border-gray-100 bg-white px-4 py-3\">\n {label}\n {field.description ? <span className=\"text-xs text-gray-500\">{field.description}</span> : null}\n <input\n id={id}\n className={inputClasses}\n type={field.type === \"number\" ? \"number\" : \"text\"}\n value={typeof value === \"string\" || typeof value === \"number\" ? value : \"\"}\n placeholder={field.placeholder}\n onChange={(event) => {\n update(field.type === \"number\" ? Number(event.currentTarget.value) : event.currentTarget.value);\n }}\n />\n </div>\n );\n}\n","import { ActionButton, Form, Sidebar, SidebarContent, SidebarHeader } from \"@manifest-editor/components\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport { useDecayState } from \"../hooks/use-decay-state\";\nimport { PluginManager } from \"../PluginContext/PluginManager\";\nimport { usePreviewContext, usePreviews } from \"../PreviewContext/PreviewContext\";\nimport { type Config, useConfig, useSaveConfig } from \"./ConfigContext\";\n\nexport function ConfigEditor() {\n const previews = usePreviewContext();\n const resource = useAppResource();\n const config = useConfig();\n const setConfig = useSaveConfig();\n const [isSaved, saveState] = useDecayState(2000);\n\n function onSubmit(e: React.FormEvent) {\n e.preventDefault();\n const formValues = new FormData(e.target as HTMLFormElement);\n\n const newConfig: Partial<Config> = {\n defaultPreview: formValues.get(\"defaultPreview\") as string,\n i18n: {\n ...(config.i18n || ({} as any)),\n advancedLanguageMode: formValues.get(\"advancedLanguageMode\") === \"on\",\n availableLanguages: ((formValues.get(\"availableLanguages\") as string) || \"\")\n .split(\",\")\n .map((t: string) => t.trim()),\n defaultLanguage: formValues.get(\"defaultLanguage\") as string,\n },\n export: {\n ...(config.export || ({} as any)),\n version: formValues.get(\"isVersion2\") === \"on\" ? 2 : 3,\n baseIdentifier: (formValues.get(\"base\") as string) || null,\n },\n plugins: config.plugins,\n editorFeatureFlags: {\n ...(config.editorFeatureFlags || ({} as any)),\n rememberCanvasId: formValues.get(\"rememberCanvasId\") === \"on\",\n rememberLeftPanelId: formValues.get(\"rememberLeftPanelId\") === \"on\",\n annotationPopups: formValues.get(\"annotationPopups\") === \"on\",\n manifestGridOptions: formValues.get(\"manifestGridOptions\") === \"on\",\n enableMultiImageCanvases: formValues.get(\"enableMultiImageCanvases\") === \"on\",\n enableMultiMediaCanvases: formValues.get(\"enableMultiMediaCanvases\") === \"on\",\n },\n };\n\n setConfig(newConfig);\n saveState.set();\n saveState.clear();\n }\n\n return (\n <Sidebar>\n <SidebarHeader title=\"Workspace configuration\" />\n {isSaved ? <div className=\"bg-me-primary-500 text-white p-3 text-sm\">Changes saved</div> : null}\n <SidebarContent className=\"p-4\">\n <Form.Form onSubmit={onSubmit} className=\"flex flex-col gap-3\">\n <Form.InputContainer>\n <Form.Label htmlFor=\"defaultLanguage\">Default Language</Form.Label>\n <Form.Input\n type=\"text\"\n name=\"defaultLanguage\"\n id=\"defaultLanguage\"\n defaultValue={config.i18n?.defaultLanguage || \"\"}\n />\n </Form.InputContainer>\n\n <Form.InputContainer>\n <Form.Label htmlFor=\"availableLanguages\">Available Languages</Form.Label>\n <Form.Input\n type=\"text\"\n name=\"availableLanguages\"\n id=\"availableLanguages\"\n defaultValue={(config.i18n?.availableLanguages || []).join(\", \")}\n />\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"advancedLanguageMode\"\n id=\"advancedLanguageMode\"\n defaultChecked={config.i18n?.advancedLanguageMode || false}\n />\n <Form.Label htmlFor=\"advancedLanguageMode\">Advanced Language Mode</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"textGranularityEnabled\"\n id=\"textGranularityEnabled\"\n defaultChecked={config.i18n?.textGranularityEnabled || false}\n />\n <Form.Label htmlFor=\"textGranularityEnabled\">Enable text granularity</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"rememberCanvasId\"\n id=\"rememberCanvasId\"\n defaultChecked={config.editorFeatureFlags?.rememberCanvasId || false}\n />\n <Form.Label htmlFor=\"rememberCanvasId\">Remember Canvas ID</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"rememberLeftPanelId\"\n id=\"rememberLeftPanelId\"\n defaultChecked={config.editorFeatureFlags?.rememberLeftPanelId || false}\n />\n <Form.Label htmlFor=\"rememberLeftPanelId\">Remember Left panel</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"manifestGridOptions\"\n id=\"manifestGridOptions\"\n defaultChecked={config.editorFeatureFlags?.manifestGridOptions || false}\n />\n <Form.Label htmlFor=\"manifestGridOptions\">Manifest Grid Options</Form.Label>\n </Form.InputContainer>\n\n <Form.InputContainer horizontal className=\"my-3\">\n <Form.Input\n type=\"checkbox\"\n name=\"isVersion2\"\n id=\"isVersion2\"\n defaultChecked={config.export?.version === 2}\n />\n <Form.Label htmlFor=\"isVersion2\">Export Presentation 2 {resource.type}s</Form.Label>\n </Form.InputContainer>\n\n {/* <Form.InputContainer>\n <Form.Label htmlFor=\"base\">Base Identifier</Form.Label>\n <Form.Input\n type=\"text\"\n name=\"base\"\n id=\"base\"\n autoComplete=\"none\"\n defaultValue={config.export?.baseIdentifier || \"\"}\n />\n </Form.InputContainer> */}\n\n <Form.InputContainer>\n <Form.Label htmlFor=\"defaultPreview\">Default preview</Form.Label>\n <div>\n {previews.configs.map((preview, key) => {\n if (preview.type === \"iiif-preview-service\") {\n return null;\n }\n return (\n <Form.InputContainer key={preview.id} horizontal>\n <Form.Input\n type=\"radio\"\n id={preview.id}\n name=\"defaultPreview\"\n value={preview.id}\n defaultChecked={!config.defaultPreview ? key === 0 : config.defaultPreview === preview.id}\n />\n <label htmlFor={preview.id}>{preview.label}</label>\n </Form.InputContainer>\n );\n })}\n </div>\n </Form.InputContainer>\n {resource.type === \"Manifest\" ? (\n <a\n className=\"text-sm text-me-primary-500 hover:underline hover:text-me-primary-600\"\n href={\n window.location.pathname.includes(\"/exhibition\")\n ? window.location.pathname.replace(\"/exhibition\", \"\") || \"/\"\n : `${window.location.pathname}/exhibition`\n }\n >\n {window.location.pathname.includes(\"/exhibition\")\n ? \"Return to Manifest Editor\"\n : \"Go to Exhibition Editor\"}\n </a>\n ) : null}\n\n <PluginManager />\n\n <div className=\"mt-5\">\n <ActionButton type=\"submit\">{\"Save changes\"}</ActionButton>\n </div>\n </Form.Form>\n </SidebarContent>\n </Sidebar>\n );\n}\n","import { createContext, useContext, useEffect, useMemo } from \"react\";\nimport { createStore, type StoreApi, useStore } from \"zustand\";\nimport { randomId } from \"../helpers\";\n\nexport type ContextMenuItem = {\n id: string;\n label: string;\n onAction: (options: { position: { x: number; y: number }; resource: { id: string; type: string } }) => void;\n disabled?: boolean;\n enabled?: boolean;\n enabledFunction?: (options: { resource: { id: string; type: string } }) => boolean;\n order?: number;\n};\n\nexport type ContextMenuRequest = {\n resource?: { id?: string; type: string };\n sectionTitle?: string;\n items: Array<ContextMenuItem>;\n};\n\ntype ContextMenuStore = {\n specificMenus: Record<\n string,\n {\n menus: Record<\n string,\n | {\n sectionTitle?: string;\n items: Array<ContextMenuItem>;\n }\n | undefined\n >;\n }\n >;\n\n resourceMenus: Record<\n string,\n {\n menus: Record<\n string,\n | {\n sectionTitle?: string;\n items: Array<ContextMenuItem>;\n }\n | undefined\n >;\n }\n >;\n\n hookMenuItem(req: ContextMenuRequest): () => void;\n};\n\nfunction createContextMenuStore() {\n return createStore<ContextMenuStore>((set, get) => ({\n specificMenus: {},\n resourceMenus: {},\n hookMenuItem(req: ContextMenuRequest) {\n const requestId = randomId();\n const resourceId = req.resource?.id || \"\";\n const resourceType = req.resource?.type;\n if (!resourceType) return () => {};\n\n if (resourceId) {\n set((prev) => {\n return {\n specificMenus: {\n ...prev.specificMenus,\n [resourceId]: {\n ...(prev.specificMenus[resourceId] || {}),\n menus: {\n ...(prev.specificMenus[resourceId]?.menus || {}),\n [requestId]: {\n sectionTitle: req.sectionTitle,\n items: req.items,\n },\n },\n },\n },\n };\n });\n\n return () => {\n set((prev) => {\n return {\n specificMenus: {\n ...prev.specificMenus,\n [resourceId]: {\n ...(prev.specificMenus[resourceId] || {}),\n menus: {\n ...(prev.specificMenus[resourceId]?.menus || {}),\n [requestId]: undefined,\n },\n },\n },\n };\n });\n };\n }\n set((prev) => {\n return {\n resourceMenus: {\n ...prev.resourceMenus,\n [resourceType]: {\n ...(prev.resourceMenus[resourceType] || {}),\n menus: {\n ...(prev.resourceMenus[resourceType]?.menus || {}),\n [requestId]: {\n sectionTitle: req.sectionTitle,\n items: req.items,\n },\n },\n },\n },\n };\n });\n\n return () => {\n set((prev) => {\n return {\n resourceMenus: {\n ...prev.resourceMenus,\n [resourceType]: {\n ...(prev.resourceMenus[resourceType] || {}),\n menus: {\n ...(prev.resourceMenus[resourceType]?.menus || {}),\n [requestId]: undefined,\n },\n },\n },\n };\n });\n };\n },\n }));\n}\n\nexport const ContextMenuReactContext = createContext<StoreApi<ContextMenuStore> | null>(null);\n\nexport function ContextMenuProvider({ children }: { children: React.ReactNode }) {\n const store = useMemo(() => {\n return createContextMenuStore();\n }, []);\n\n return <ContextMenuReactContext.Provider value={store}>{children}</ContextMenuReactContext.Provider>;\n}\n\nfunction useContextMenuStore() {\n const ctx = useContext(ContextMenuReactContext);\n if (!ctx) {\n throw new Error(\"useContextMenuStore must be used within a ContextMenuProvider\");\n }\n return ctx;\n}\n\nexport function useResourceContextMenuItems(req: { id?: string; type: string }) {\n const store = useContextMenuStore();\n const resourceMenus = useStore(store, (s) => s.resourceMenus);\n const specificMenus = useStore(store, (s) => s.specificMenus);\n\n return useMemo(() => {\n const specificRequests = specificMenus[req.id || \"\"]?.menus || {};\n const resourceRequests = resourceMenus[req.type]?.menus || {};\n\n const specificItems = Object.values(specificRequests).flat();\n const resourceItems = Object.values(resourceRequests).flat();\n\n const items = [...resourceItems, ...specificItems].filter((t) => typeof t !== \"undefined\");\n const seenIds: string[] = [];\n const returnSections = [];\n\n for (const section of items) {\n const sectionItems = [];\n for (const sectionItem of section.items || []) {\n if (sectionItem.id && seenIds.includes(sectionItem.id)) continue;\n seenIds.push(sectionItem.id);\n sectionItems.push(sectionItem);\n }\n if (sectionItems.length) {\n returnSections.push({\n ...section,\n items: sectionItems,\n });\n }\n }\n\n return mergeSectionsWithTheSameTitle(returnSections);\n }, [specificMenus, resourceMenus, req.id, req.type]);\n}\n\nfunction mergeSectionsWithTheSameTitle(sections: Array<{ sectionTitle?: string; items: Array<ContextMenuItem> }>) {\n const sectionMap: Record<string, ContextMenuItem[]> = {};\n const emptySections: ContextMenuItem[] = [];\n\n sections.forEach((section) => {\n if (!section) return;\n const title = section.sectionTitle;\n if (!title) {\n emptySections.push(...(section.items || []));\n return;\n }\n if (!sectionMap[title]) {\n sectionMap[title] = [];\n }\n sectionMap[title].push(...section.items);\n });\n\n const returnSections: Array<{ sectionTitle?: string; items: Array<ContextMenuItem> }> = Object.entries(\n sectionMap,\n ).map(([title, items]) => ({\n sectionTitle: title,\n items,\n }));\n\n if (emptySections.length) {\n returnSections.push({ items: emptySections });\n }\n\n return returnSections;\n}\n\nexport function useCustomContextMenu(req: ContextMenuRequest, deps: any[] = []) {\n const store = useContextMenuStore();\n const hookMenuItem = useStore(store, (s) => s.hookMenuItem);\n\n useEffect(() => {\n return hookMenuItem(req);\n }, [hookMenuItem, req.resource?.id, req.resource?.type, ...deps]);\n}\n",".CenterPanelContainer {\n display: flex;\n flex-direction: column;\n flex: 1;\n overflow: hidden;\n background: #fff;\n margin: 1.2rem;\n padding: 1em;\n border-radius: 10px;\n box-shadow:\n 0 4px 15px 0 rgba(0, 0, 0, 0.18),\n 0 0px 0px 1px rgba(0, 0, 0, 0.15),\n inset 0 0 0 1px rgba(255, 255, 255, 0.2);\n}\n\n.CenterPanelHeader {\n height: 3em;\n display: flex;\n align-items: center;\n margin-bottom: 1em;\n}\n\n.CenterPanelClose {\n margin-left: auto;\n align-self: center;\n}\n\n.CenterPanelTitle {\n margin: 0;\n}\n","import { ReactNode } from \"react\";\nimport $ from \"./CenterPanelContainer.module.css\";\nimport { Button } from \"../../atoms/Button\";\nimport { CloseIcon } from \"../../icons/CloseIcon\";\n\ninterface CenterPanelContainerProps {\n close?: () => void;\n title?: string;\n children: ReactNode;\n}\n\nexport function CenterPanelContainer(props: CenterPanelContainerProps) {\n return (\n <div className={$.CenterPanelContainer}>\n {props.title || props.close ? (\n <div className={$.CenterPanelHeader}>\n {props.title ? <h2 className={$.CenterPanelTitle}>{props.title}</h2> : null}\n {props.close ? (\n <Button className={$.CenterPanelClose} onClick={props.close}>\n <CloseIcon />\n </Button>\n ) : null}\n </div>\n ) : null}\n {props.children}\n </div>\n );\n}\n","import styled from \"styled-components\";\nimport {\n createRef,\n forwardRef,\n KeyboardEventHandler,\n ReactNode,\n RefObject,\n UIEventHandler,\n useEffect,\n useImperativeHandle,\n useMemo,\n useRef,\n useState,\n} from \"react\";\nimport { DownIcon } from \"../icons/DownIcon\";\n\nexport const AccordionContainer = styled.div`\n flex: 1;\n display: flex;\n width: 100%;\n flex-direction: column;\n position: relative;\n`;\n\nconst ItemRow = styled.div`\n background: #fff;\n position: relative;\n border-bottom: 1px solid #d0d0d0;\n border-top: 1px solid #d0d0d0;\n\n & ~ & {\n border-top: none;\n }\n\n &[data-large=\"true\"] {\n background: #f7f7f7;\n border: none;\n margin-bottom: 1em;\n //display: flex;\n //flex-direction: column;\n //justify-content: center;\n }\n`;\n\nconst ItemDescription = styled.p`\n font-size: 0.9em;\n color: #777;\n font-weight: 400;\n`;\n\nconst ItemLabel = styled.button`\n color: inherit;\n text-rendering: geometricPrecision;\n border: none;\n text-align: left;\n background: transparent;\n font: inherit;\n text-transform: uppercase;\n padding: 0.6em 1.2em;\n flex: 1;\n font-size: 0.8em;\n font-weight: 600;\n white-space: nowrap;\n text-overflow: ellipsis;\n min-width: 0;\n overflow: hidden;\n\n &:focus {\n outline: none;\n }\n\n p {\n display: none;\n }\n\n [data-large=\"true\"] & {\n //padding: 1.5em;\n padding: 0.85em 1.25em;\n display: block;\n text-transform: initial;\n font-size: 1em;\n margin-bottom: 0;\n color: #000;\n\n p {\n display: block;\n color: #999;\n font-size: 0.9em;\n margin: 0;\n margin-top: 0.5em;\n }\n }\n`;\n\nconst ItemCollapse = styled.div`\n font-size: 1.4em;\n padding-right: 0.3em;\n display: flex;\n align-items: center;\n\n [data-large=\"true\"] & {\n font-size: 2em;\n }\n`;\n\nconst ItemIcon = styled.div`\n width: 2em;\n align-items: center;\n //padding-top: 0.5em;\n display: flex;\n justify-content: center;\n margin-left: 1.5em;\n svg {\n width: 1.75em;\n height: 1.75em;\n fill: #999;\n color: #999;\n }\n`;\n\nconst ItemBodyInner = styled.div<{ $full?: boolean }>`\n min-height: 0;\n overflow: visible;\n display: flex;\n`;\n\nconst ItemBodyPadding = styled.div<{ $full?: boolean; $max?: boolean }>`\n min-height: 0;\n overflow: visible;\n flex: 1;\n padding: 1em 1em 1.5em;\n\n &[data-full=\"true\"] {\n margin: 0;\n }\n\n &[data-max-height=\"true\"] {\n overflow-y: auto;\n }\n`;\n\nconst ItemBody = styled.section<{\n $initial?: boolean;\n $scrolled?: boolean;\n}>`\n display: grid;\n grid-template-rows: 0fr;\n overflow: hidden;\n opacity: 0;\n visibility: hidden;\n\n [data-open=\"true\"] & {\n opacity: 1;\n grid-template-rows: 1fr;\n visibility: visible;\n &[data-overflow=\"true\"] {\n overflow: visible;\n }\n }\n\n transition:\n all 0.4s,\n visibility 0.8s;\n\n &[data-has-icon=\"true\"] {\n padding-left: 4em;\n }\n\n box-shadow: inset 0px 2px 0px 0 rgba(0, 0, 0, 0);\n &[data-scrolled=\"true\"] {\n box-shadow: inset 0px 2px 0px 0 rgba(0, 0, 0, 0.1);\n }\n`;\n\nconst ItemHeading = styled.div<{ $open?: boolean }>`\n position: sticky;\n display: flex;\n top: 0;\n background: #fff;\n min-width: 0;\n width: 100%;\n color: #757575;\n z-index: 1;\n &:hover {\n color: #333;\n }\n\n [data-large=\"true\"] & {\n border: 1px solid #d0d0d0;\n &:after {\n display: none;\n }\n }\n\n [data-large=\"true\"]:focus-within & {\n border-color: #3579f6;\n }\n\n [data-open=\"true\"] & {\n color: #333;\n &:after {\n content: \"\";\n height: 1px;\n background: #eee;\n position: absolute;\n top: 100%;\n left: 0.5em;\n right: 0.5em;\n }\n }\n`;\n\ninterface AccordionItemProps {\n label: string | ReactNode;\n description?: string | ReactNode;\n icon?: ReactNode;\n children: ReactNode;\n initialOpen?: boolean;\n maxHeight?: number | false;\n fullWidth?: boolean;\n overflow?: boolean;\n onChange?: (value: boolean) => void;\n large?: boolean;\n}\n\nexport interface AccordionItemRef {\n open(): void;\n close(): void;\n toggle(): void;\n focus(): void;\n button?: RefObject<HTMLButtonElement | null>;\n}\n\nconst noop = (() => void 0) as any;\n\nlet keyIdIndex = 0;\nfunction useId() {\n return useMemo(() => keyIdIndex++, []);\n}\n\nexport function useAccordionItems(itemsLength: number, singleMode = false) {\n const [elRefs, setElRefs] = useState<RefObject<AccordionItemRef | null>[]>([]);\n const current = useRef(-1);\n\n const onKeyDown: KeyboardEventHandler<HTMLDivElement> = (e) => {\n const currentEl = document.activeElement;\n const currentIndex = elRefs.findIndex((r) => r.current?.button?.current === currentEl);\n if (currentIndex === -1) {\n return;\n }\n\n switch (e.code) {\n case \"Home\": {\n const next = 0;\n if (elRefs[next]) {\n elRefs[next].current?.focus();\n }\n break;\n }\n case \"End\": {\n const next = itemsLength - 1;\n if (elRefs[next]) {\n elRefs[next]!.current?.focus();\n }\n break;\n }\n\n case \"ArrowDown\": {\n if (currentIndex !== itemsLength - 1) {\n const next = currentIndex + 1;\n if (elRefs[next]) {\n elRefs[next]!.current?.focus();\n }\n }\n break;\n }\n // Focus previous\n case \"ArrowUp\": {\n if (currentIndex !== 0) {\n const next = currentIndex - 1;\n if (elRefs[next]) {\n elRefs[next]!.current?.focus();\n }\n }\n break;\n }\n // Focus next\n case \"ArrowLeft\": {\n // Close current\n const el = elRefs[currentIndex];\n if (el && el.current) {\n el.current.close();\n }\n break;\n }\n // Open current\n case \"ArrowRight\": {\n // Close current\n const el = elRefs[currentIndex];\n if (el && el.current) {\n el.current.open();\n }\n break;\n }\n }\n };\n\n const onChange = (key: number, isOpen: boolean) => {\n if (singleMode && isOpen && key !== current.current) {\n current.current = key;\n for (let i = 0; i < elRefs.length; i++) {\n const ref = elRefs[i];\n if (i === key) {\n continue;\n }\n ref!.current?.close();\n }\n }\n };\n\n useEffect(() => {\n // add or remove refs\n setElRefs((elRefs_) =>\n Array(itemsLength)\n .fill(0)\n .map((_, i) => elRefs_[i] || createRef())\n );\n }, [itemsLength]);\n\n const getItemProps = (key: number) => {\n return {\n ref: elRefs[key],\n onChange: (isOpen: boolean) => onChange(key, isOpen),\n };\n };\n\n const open = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.open();\n }\n };\n\n const close = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.close();\n }\n };\n\n const toggle = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.toggle();\n }\n };\n\n const focus = (key: number) => {\n const el = elRefs[key];\n if (el && el.current) {\n el.current.focus();\n }\n };\n\n const openAll = () => {\n for (let i = 0; i < elRefs.length; i++) {\n const ref = elRefs[i]!;\n ref.current?.open();\n }\n };\n\n const closeAll = () => {\n for (let i = 0; i < elRefs.length; i++) {\n const ref = elRefs[i]!;\n ref.current?.close();\n }\n };\n\n return {\n open,\n close,\n toggle,\n focus,\n openAll,\n closeAll,\n onKeyDown,\n getItemProps,\n };\n}\n\nexport const AccordionItem = forwardRef<AccordionItemRef, AccordionItemProps>(function AccordionItem(props, ref) {\n const content = useRef<HTMLDivElement>(null);\n const btn = useRef<HTMLButtonElement>(null);\n const id = useId();\n\n const [open, setIsOpen] = useState<boolean>(props.initialOpen || false);\n const onChange = props.onChange || noop;\n const toggle = () => {\n onChange(!open);\n setIsOpen((o) => !o);\n };\n const maxHeight = props.maxHeight;\n const [scrolled, setScrolled] = useState(false);\n\n useImperativeHandle(ref, () => ({\n open() {\n onChange(true);\n setIsOpen(true);\n },\n close() {\n onChange(false);\n setIsOpen(false);\n },\n toggle() {\n toggle();\n },\n focus() {\n if (btn.current) {\n btn.current.focus();\n }\n },\n button: btn,\n }));\n\n const onScroll: UIEventHandler<HTMLDivElement> = (e) => {\n if ((e.target as HTMLDivElement).scrollTop > 0) {\n setScrolled(true);\n } else {\n setScrolled(false);\n }\n };\n\n return (\n <ItemRow data-large={props.large} data-open={open}>\n <ItemHeading data-open={open}>\n {props.icon ? <ItemIcon onClick={toggle}>{props.icon}</ItemIcon> : null}\n <ItemLabel ref={btn} onClick={toggle} aria-expanded={open} aria-controls={`accordion-${id}`}>\n {props.label}\n {props.description ? <ItemDescription>{props.description}</ItemDescription> : null}\n </ItemLabel>\n <ItemCollapse onClick={toggle}>\n <DownIcon width=\"1em\" height=\"1em\" rotate={open ? 0 : 180} />\n </ItemCollapse>\n </ItemHeading>\n <ItemBody\n aria-labelledby={`accordion-${id}`}\n aria-hidden={!open}\n data-overflow={!!props.overflow}\n data-has-icon={!!props.icon}\n onScroll={onScroll}\n ref={content}\n $initial={!open}\n data-scrolled={scrolled}\n hidden={!open}\n >\n <ItemBodyInner>\n <ItemBodyPadding\n data-max-height={!!maxHeight}\n data-full={props.fullWidth}\n style={{ maxHeight: maxHeight || undefined }}\n >\n {props.children}\n </ItemBodyPadding>\n </ItemBodyInner>\n </ItemBody>\n </ItemRow>\n );\n});\n\ninterface AccordionProps {\n singleMode?: boolean;\n items: Array<AccordionItemProps>;\n maxHeight?: number | false;\n overflow?: boolean;\n}\n\nexport function Accordion(props: AccordionProps) {\n const { getItemProps, onKeyDown } = useAccordionItems(props.items.length, props.singleMode);\n\n return (\n <AccordionContainer onKeyDown={onKeyDown}>\n {props.items.map((item, key) => (\n <AccordionItem overflow={props.overflow} maxHeight={props.maxHeight} key={key} {...item} {...getItemProps(key)}>\n {item.children}\n </AccordionItem>\n ))}\n </AccordionContainer>\n );\n}\n","export function DownloadIcon() {\n return (\n <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"48\" viewBox=\"0 -960 960 960\" width=\"48\">\n <path d=\"M220-160q-24 0-42-18t-18-42v-143h60v143h520v-143h60v143q0 24-18 42t-42 18H220Zm260-153L287-506l43-43 120 120v-371h60v371l120-120 43 43-193 193Z\" />\n </svg>\n );\n}\n","import styled from \"styled-components\";\n\nexport const ButtonRow = styled.div`\n padding: 0.3em;\n\n display: flex;\n background: #e4e7ef;\n border-radius: 3px;\n margin: 0.3em 0;\n gap: 0.3em;\n\n button,\n a {\n //\n\n & ~ & {\n margin-left: 0.3em;\n }\n }\n\n &[data-sticky=\"true\"] {\n position: sticky;\n bottom: 0;\n }\n`;\n","import { Button } from \"@manifest-editor/ui/atoms/Button\";\nimport { useMemo } from \"react\";\nimport { useManifest, useVault } from \"react-iiif-vault\";\nimport { useLayoutActions } from \"../Layout/Layout.context\";\nimport { CenterPanelContainer } from \"@manifest-editor/ui/CenterPanelContainer\";\nimport { Accordion } from \"@manifest-editor/ui/atoms/Accordion\";\nimport { copyToClipboard, createDownload } from \"../helpers\";\nimport { DownloadIcon } from \"@manifest-editor/ui/icons/DownloadIcon\";\nimport { ButtonRow } from \"@manifest-editor/ui/atoms/ButtonRow\";\n\nexport interface ExportPanelProps {\n // We could limit versions / download options etc.\n initialVersion?: 2 | 3;\n versions?: Array<2 | 3>;\n}\n\nexport function ExportPanel(props: ExportPanelProps) {\n const manifest = useManifest();\n const vault = useVault();\n const actions = useLayoutActions();\n\n const version3 = useMemo(() => {\n return JSON.stringify(vault.toPresentation3(manifest as any), null, 2);\n }, [manifest, vault]);\n\n const version2 = useMemo(() => {\n return JSON.stringify(vault.toPresentation2(manifest as any), null, 2);\n }, [manifest, vault]);\n\n return (\n <CenterPanelContainer title=\"Export manifest\" close={actions.centerPanel.popStack}>\n <div style={{ flex: 1, overflowY: \"auto\" }}>\n <Accordion\n items={[\n {\n label: \"Presentation 3\",\n description: 'Download this version by clicking the \"Download\" button.',\n maxHeight: 400,\n large: true,\n initialOpen: true,\n overflow: true,\n icon: (\n <Button onClick={() => createDownload(version3, \"manifest.json\")}>\n <DownloadIcon />\n </Button>\n ),\n children: (\n <div style={{ maxWidth: \"100%\" }}>\n <pre style={{ whiteSpace: \"pre-wrap\" }}>\n {JSON.stringify(vault.toPresentation3(manifest as any), null, 2)}\n </pre>\n <ButtonRow data-sticky=\"true\">\n <Button onClick={() => copyToClipboard(version3)}>Copy to clipboard</Button>\n <Button onClick={() => createDownload(version3, \"manifest.json\")}>Download</Button>\n </ButtonRow>\n </div>\n ),\n },\n {\n label: \"Presentation 2\",\n description: 'Download this version by clicking the \"Download\" button.',\n maxHeight: 400,\n large: true,\n icon: (\n <Button onClick={() => createDownload(version2, \"manifest.json\")}>\n <DownloadIcon />\n </Button>\n ),\n children: (\n <div style={{ maxWidth: \"100%\" }}>\n <pre style={{ whiteSpace: \"pre-wrap\" }}>\n {JSON.stringify(vault.toPresentation2(manifest as any), null, 2)}\n </pre>\n <ButtonRow data-sticky=\"true\">\n <Button onClick={() => copyToClipboard(version2)}>Copy to clipboard</Button>\n <Button onClick={() => createDownload(version2, \"manifest.json\")}>Download</Button>\n </ButtonRow>\n </div>\n ),\n },\n ]}\n />\n </div>\n </CenterPanelContainer>\n );\n}\n","import { useCallback, useState } from \"react\";\nimport { useCurrentAnnotationMetadata } from \"react-iiif-vault\";\n\nexport function useAnnotationCreatorState<Type = any>({ key, initialValue, requestId, getInitialValue }: {\n key: string,\n initialValue?: Type,\n requestId?: string;\n getInitialValue?: (metadata: any) => (Type | null)\n}) {\n const [metadata, setMetadata] = useCurrentAnnotationMetadata({ requestId });\n const [reactState, reactSetState] = useState<Type>(getInitialValue && getInitialValue(metadata) || (metadata[key] || initialValue));\n\n const setState = useCallback((newValue: Type) => {\n setMetadata({ [key]: newValue });\n reactSetState(newValue);\n }, []);\n\n return [\n reactState,\n setState,\n ] as const;\n}\n","import type { Emitter } from \"mitt\";\nimport mitt from \"mitt\";\nimport { createContext, useContext, useEffect } from \"react\";\n\nconst events = mitt();\n\nexport const ReactEmitterContext = createContext<Emitter<any>>(events);\n\nexport function EventEmitterProvider({\n children,\n emitter,\n}: { children: React.ReactNode; emitter: Emitter<any> }) {\n return (\n <ReactEmitterContext.Provider value={emitter}>\n {children}\n </ReactEmitterContext.Provider>\n );\n}\n\nexport function useEmitter<\n Event extends Record<string | symbol, unknown>,\n>(): Emitter<Event> {\n return useContext(ReactEmitterContext);\n}\n\nexport function useEvent<\n Event extends Record<string | symbol, unknown>,\n Key extends keyof Event,\n>(key: Key, listener: (data: Event[Key]) => void, deps: any[] = []) {\n const emitter = useContext(ReactEmitterContext);\n useEffect(() => {\n const handler = (data: Event[Key]) => {\n listener(data);\n };\n emitter.on(key as any, handler);\n return () => {\n emitter.off(key as any, handler);\n };\n }, [emitter, key, ...deps]);\n}\n","// MIT License\n//\n// Copyright (c) 2020 Jepser Bernardino\n//\n// Permission is hereby granted, free of charge, to any person obtaining a copy\n// of this software and associated documentation files (the \"Software\"), to deal\n// in the Software without restriction, including without limitation the rights\n// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n// copies of the Software, and to permit persons to whom the Software is\n// furnished to do so, subject to the following conditions:\n//\n// The above copyright notice and this permission notice shall be included in all\n// copies or substantial portions of the Software.\n//\n// THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n// SOFTWARE.\n//\n// Source: https://github.com/jepser/use-match-media\n\nimport { useState, useLayoutEffect } from \"react\";\n\ntype IMediaQuery = Array<string>;\n\ntype IMatchedMedia = Array<boolean>;\n\nexport function useMatchMedia(queries: IMediaQuery, defaultValues: IMatchedMedia = []): IMatchedMedia {\n const initialValues = defaultValues.length ? defaultValues : Array(queries.length).fill(false);\n\n if (typeof window === \"undefined\") return initialValues;\n\n const mediaQueryLists = queries.map((q) => window.matchMedia(q));\n const getValue = (): IMatchedMedia => {\n // Return the value for the given queries\n const matchedQueries = mediaQueryLists.map((mql) => mql.matches);\n\n return matchedQueries;\n };\n\n // State and setter for matched value\n const [value, setValue] = useState(getValue);\n\n useLayoutEffect(() => {\n // Event listener callback\n // Note: By defining getValue outside of useEffect we ensure that it has ...\n // ... current values of hook args (as this hook only runs on mount/dismount).\n const handler = (): void => setValue(getValue);\n // Set a listener for each media query with above handler as callback.\n mediaQueryLists.forEach((mql) => mql.addListener(handler));\n // Remove listeners on cleanup\n return (): void => mediaQueryLists.forEach((mql) => mql.removeListener(handler));\n }, []);\n\n return value;\n}\n","import { Vault } from \"@iiif/helpers\";\nimport { useEffect } from \"react\";\nimport { useDebounce } from \"tiny-use-debounce\";\n\nexport function useSaveVault(vault: Vault, saveChanges: () => void, saveInterval: number, enabled = true) {\n const debounceSaveChanges = useDebounce(saveChanges, saveInterval);\n\n useEffect(() => {\n if (typeof window === \"undefined\") {\n return () => void 0;\n }\n window.addEventListener(\"beforeunload\", saveChanges, false);\n\n return () => {\n saveChanges();\n window.removeEventListener(\"beforeunload\", saveChanges);\n };\n }, [saveChanges]);\n\n useEffect(() => {\n if (vault && enabled) {\n return vault.subscribe(debounceSaveChanges, true);\n }\n }, [debounceSaveChanges, vault, enabled]);\n}\n","import { useMemo } from \"react\";\nimport { useAtlasStore } from \"react-iiif-vault\";\nimport { useStore } from \"zustand\";\n\nexport function useSvgTools() {\n const store = useAtlasStore();\n const switchTool = useStore(store, (s) => s.switchTool);\n const currentTool = useStore(store, (s) => s.polygonState.currentTool);\n const selectedStamp = useStore(store, (s) => s.polygonState.selectedStamp);\n const showBoundingBox = useStore(store, (s) => s.polygonState.showBoundingBox);\n\n return useMemo(\n () => ({\n currentTool,\n selectedStamp,\n // Draw tool.\n draw: {\n active: currentTool === \"pencil\",\n enable: switchTool.draw,\n },\n\n // Polygon.\n polygon: {\n active: currentTool === \"pen\",\n enable: switchTool.pen,\n },\n\n // Line\n line: {\n active: currentTool === \"line\",\n enable: switchTool.line,\n },\n\n // Line box.\n lineBox: {\n active: currentTool === \"lineBox\",\n enable: switchTool.lineBox,\n },\n\n // Square.\n square: {\n active: currentTool === \"box\",\n enable: switchTool.box,\n },\n\n // Triangle.\n triangle: {\n active: selectedStamp?.id === \"triangle\",\n enable: switchTool.triangle,\n },\n\n // Hexagon.\n hexagon: {\n active: selectedStamp?.id === \"hexagon\",\n enable: switchTool.hexagon,\n },\n\n // Circle\n circle: {\n active: selectedStamp?.id === \"circle\",\n enable: switchTool.circle,\n },\n\n // Delete\n remove: {\n active: showBoundingBox,\n enable: switchTool.remove,\n },\n }),\n [showBoundingBox, selectedStamp, currentTool, switchTool],\n );\n}\n","import { useState } from \"react\";\nimport {\n DefaultTooltipContent,\n IconHandle,\n ResetIcon,\n ResizeHandle,\n Tooltip,\n TooltipTrigger,\n} from \"@manifest-editor/components\";\nimport { ButtonReset } from \"@manifest-editor/ui/atoms/Button\";\nimport { CloseIcon } from \"@manifest-editor/ui/icons/CloseIcon\";\nimport { DownIcon } from \"@manifest-editor/ui/icons/DownIcon\";\nimport { forwardRef } from \"react\";\nimport type { TransitionStatus } from \"react-transition-group\";\nimport styled, { css } from \"styled-components\";\nimport type { PanelActions } from \"../Layout.types\";\n\nexport const HandleContainer = styled.div`\n position: relative;\n width: 1px;\n background: rgba(0, 0, 0, 0.2);\n z-index: 50;\n`;\n\nconst HandleControl = styled(ButtonReset)`\n transition:\n opacity 300ms,\n transform 300ms;\n margin-block-start: 0.2em;\n margin-block-end: 0.2em;\n user-select: none;\n opacity: 0;\n transform: scaleY(70%);\n &:focus {\n outline: 2px solid salmon;\n }\n`;\n\nconst IconControl = styled(HandleControl)`\n background: #fff;\n width: 30px;\n height: 30px;\n border-radius: 50%;\n display: flex;\n justify-content: center;\n align-items: center;\n box-shadow: 0 2px 4px 0 rgba(0, 0, 0, 0.2);\n cursor: default;\n\n svg {\n fill: #9999;\n }\n`;\n\nconst OpenControl = styled(HandleControl)<{ $dir: \"left\" | \"right\" }>`\n position: relative;\n display: flex;\n opacity: 1;\n background: #fff;\n height: 55px;\n pointer-events: visible;\n width: 21px;\n margin-bottom: auto;\n margin-top: 4.5em;\n cursor: pointer;\n border-radius: ${(props) => (props.$dir === \"right\" ? \"5px 0 0 5px\" : \"0 5px 5px 0\")};\n\n align-items: center;\n justify-content: center;\n box-shadow: 0 2px 3px 0 rgba(0, 0, 0, 0.2);\n transform: scaleX(100%);\n transform-origin: ${(props) => (props.$dir === \"right\" ? \"right\" : \"left\")};\n\n &:hover {\n background: #f9f9f9;\n transform: scaleX(125%);\n }\n\n svg {\n font-size: 1.5em;\n }\n`;\n\nconst InnerHandleContainer = styled.div<{ $open: boolean; $dir: \"left\" | \"right\" }>`\n background: rgba(0, 0, 0, 0);\n position: absolute;\n width: 16px;\n left: ${(props) => (props.$dir === \"left\" ? 0 : \"1px\")};\n top: 0;\n bottom: 0;\n z-index: 50; // This will always be quite high.\n transition:\n background-color 300ms,\n transform 300ms;\n transform: scaleX(70%);\n\n cursor: ${(props) => (props.$open ? \"col-resize\" : \"pointer\")};\n\n display: flex;\n flex-direction: column;\n align-items: center;\n justify-content: center;\n\n &:hover {\n transform: scaleX(100%);\n background: rgba(0, 0, 0, 0.1);\n ${HandleControl} {\n transform: scaleX(100%);\n opacity: 1;\n }\n }\n`;\n\nconst UnscaledContainer = styled.div<{ $open: boolean; $dir: \"left\" | \"right\" }>`\n background: rgba(0, 0, 0, 0);\n position: absolute;\n pointer-events: none;\n width: 16px;\n left: ${(props) => (props.$dir === \"left\" ? 0 : \"-16px\")};\n top: 0;\n bottom: 0;\n z-index: 51; // This will always be quite high.\n`;\n\nexport const HandleControls = forwardRef<\n HTMLDivElement,\n {\n dir: \"left\" | \"right\";\n open: boolean;\n actions: PanelActions;\n transition?: TransitionStatus;\n reset?: () => void;\n }\n>(function HandleControls({ dir, open, actions, reset }, ref) {\n const [showDragTooltip, setShowDragToolTip] = useState(true);\n const dragTooltipMt = \"mt-[calc(50vh+8px)]\";\n const dragTooltipClasses = dir === \"left\" ? `${dragTooltipMt} ml-[13px]` : `${dragTooltipMt} ml-[3px]`;\n return (\n <HandleContainer onClick={() => actions.open()}>\n <UnscaledContainer $open={open} $dir={dir} className=\"group\">\n {!open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger as={OpenControl} $dir={dir} onClick={(e) => actions.open()}>\n <DownIcon className=\"text-2xl\" rotate={dir === \"right\" ? 90 : 270} />\n </TooltipTrigger>\n <DefaultTooltipContent>Open</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n </UnscaledContainer>\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger aria-label=\"Resize panel\" asChild>\n <div>\n <InnerHandleContainer ref={ref} $open={open} $dir={dir} className=\"group\">\n {open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger as={IconHandle} onPress={() => actions.close()}>\n <div\n onMouseOut={() => {\n setShowDragToolTip(true);\n }}\n onMouseOver={() => {\n setShowDragToolTip(false);\n }}\n >\n <CloseIcon />\n </div>\n </TooltipTrigger>\n <DefaultTooltipContent>Close</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n {reset && open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger as={IconHandle} onPress={() => reset()}>\n <div\n onMouseOut={() => {\n setShowDragToolTip(true);\n }}\n onMouseOver={() => {\n setShowDragToolTip(false);\n }}\n >\n <ResetIcon />\n </div>\n </TooltipTrigger>\n <DefaultTooltipContent>Reset</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n {open ? (\n <Tooltip placement={dir === \"left\" ? \"right\" : \"left\"}>\n <TooltipTrigger asChild aria-label=\"Resize panel\">\n <div\n onMouseOut={() => {\n setShowDragToolTip(true);\n }}\n onMouseOver={() => {\n setShowDragToolTip(false);\n }}\n >\n <ResizeHandle aria-label=\"Resize panel\" />\n </div>\n </TooltipTrigger>\n <DefaultTooltipContent>Resize panel</DefaultTooltipContent>\n </Tooltip>\n ) : null}\n </InnerHandleContainer>\n </div>\n </TooltipTrigger>\n {showDragTooltip && <DefaultTooltipContent className={dragTooltipClasses}>Resize panel</DefaultTooltipContent>}\n </Tooltip>\n </HandleContainer>\n );\n});\n","import type * as React from \"react\";\n\nexport function Spinner(props: React.SVGProps<SVGSVGElement>) {\n return (\n <svg\n width=\"1em\"\n height=\"1em\"\n viewBox=\"0 0 42 42\"\n xmlns=\"http://www.w3.org/2000/svg\"\n stroke=\"currentColor\"\n {...props}\n >\n <g transform=\"translate(2 2)\" strokeWidth={5} fill=\"none\" fillRule=\"evenodd\">\n <circle strokeOpacity={0.5} cx={18} cy={18} r={18} />\n <path d=\"M36 18c0-9.94-8.06-18-18-18\">\n <animateTransform\n attributeName=\"transform\"\n type=\"rotate\"\n from=\"0 18 18\"\n to=\"360 18 18\"\n dur=\"1s\"\n repeatCount=\"indefinite\"\n />\n </path>\n </g>\n </svg>\n );\n}\n",".ghostLoadingBlock[data-header=\"true\"] {\n box-shadow:\n inset 0 -1px 0 0 rgba(0, 0, 0, 0.17),\n inset 0 1px 0 0 rgba(0, 0, 0, 0.17);\n}\n\n.ghostLoadingBlock {\n display: block;\n width: 100%;\n height: 2.8em;\n margin-bottom: 1em;\n background-color: #e4e7f0;\n animation: ghost-loading 2s infinite ease-in-out;\n}\n\n@keyframes ghost-loading {\n 0% {\n opacity: 0.4;\n }\n 50% {\n opacity: 0.8;\n }\n 100% {\n opacity: 0.4;\n }\n}\n\n.ghostBlockList {\n padding: 1em;\n display: flex;\n flex-direction: column;\n}\n","import $ from \"./GhostBlocks.module.css\";\nexport function GhostBlocks() {\n return (\n <>\n <div data-header=\"true\" className={$.ghostLoadingBlock} />\n <div className={$.ghostBlockList}>\n <div className={$.ghostLoadingBlock} />\n <div className={$.ghostLoadingBlock} />\n <div className={$.ghostLoadingBlock} />\n <div className={$.ghostLoadingBlock} />\n </div>\n </>\n );\n}\n","import { useLayoutEffect } from \"react\";\n\nexport function useEventHandler(ref: any, name: string, callback: (e: any) => void, deps: any[] = []) {\n useLayoutEffect(() => {\n const current = ref.current;\n if (current) {\n current.addEventListener(name, callback);\n\n return () => {\n current.removeEventListener(name, callback);\n };\n }\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [name, ...deps]);\n}\n","import { useEventHandler } from \"@manifest-editor/ui/madoc/use-event-handler\";\nimport { useEffect, useRef, useState } from \"react\";\nimport { useLocalStorage } from \"../../hooks/use-local-storage\";\nimport { panelSizing } from \"../Layout.helpers\";\n\nfunction distance(x1: number, y1: number, x2: number, y2: number) {\n return Math.sqrt(Math.abs(x2 - x1) ** 2 + Math.abs(y2 - y1) ** 2);\n}\n\nfunction getMaxWidthPct(container: number, defaultMaxWidthPct: number, maxWidthPct?: number, maxWidthPixel?: number) {\n if (maxWidthPct) {\n return maxWidthPct;\n }\n\n if (maxWidthPixel) {\n return maxWidthPixel / container;\n }\n\n return defaultMaxWidthPct;\n}\n\nexport function useResizeLayout(\n name: string,\n options: {\n left?: boolean;\n widthA?: any;\n marginLeft?: number;\n widthB?: any;\n maxWidthPx?: number;\n maxWidthPct?: number;\n minWidthPx?: number;\n minWidthPct?: number;\n onDragEnd?: () => void;\n loading?: boolean;\n } = {},\n) {\n const container = useRef<HTMLDivElement | null>(null);\n const resizableDiv = useRef<HTMLDivElement | null>(null);\n const otherDiv = useRef<HTMLDivElement | null>(null);\n const resizer = useRef<HTMLDivElement | null>(null);\n const newPct = useRef(0.5);\n const [isDragging, setIsDragging] = useState(false);\n const isEventDragging = useRef(false);\n const isEventTimeout = useRef<number>(0);\n const startPos = useRef({ x: 0, y: 0 });\n const [{ widthA, widthB }, setWidths] = useLocalStorage(`resize-layout/${name}`, {\n widthA: \"auto\",\n widthB: `${panelSizing({\n initial: options.widthA,\n fallback: 320,\n options: { minWidth: options.minWidthPx, maxWidth: options.maxWidthPx },\n })}px`,\n });\n const { loading = false } = options;\n\n useEventHandler(\n resizer,\n \"mousedown\",\n (e) => {\n startPos.current.x = e.pageX;\n startPos.current.y = e.pageY;\n\n if (isEventTimeout.current) {\n clearTimeout(isEventTimeout.current);\n isEventTimeout.current = 0;\n }\n isEventTimeout.current = setTimeout(() => {\n setIsDragging(true);\n isEventDragging.current = true;\n }, 350) as any;\n },\n [loading],\n );\n\n useEventHandler(\n { current: typeof window !== \"undefined\" ? window : undefined },\n \"mouseup\",\n () => {\n const current = container.current;\n if (current && isEventDragging.current) {\n const { x, width } = current.getBoundingClientRect();\n\n const ml = options.marginLeft || 0;\n const maxWidthPct = getMaxWidthPct(width, 0.8, options.maxWidthPct, options.maxWidthPx) * width;\n const minWidthPct = getMaxWidthPct(width, 0.2, options.minWidthPct, options.minWidthPx) * width;\n\n if (options.left) {\n const newWidthB = (newPct.current * width) - ml;\n\n setWidths({\n widthA: `${((1 - newPct.current) * width) - ml}`,\n widthB: `${newWidthB > maxWidthPct ? maxWidthPct : newWidthB < minWidthPct ? minWidthPct : newWidthB}px`,\n });\n } else {\n const newWidthA = 1 - (newPct.current * width) - ml;\n\n setWidths({\n widthA: `${newWidthA > maxWidthPct ? maxWidthPct : newWidthA < minWidthPct ? minWidthPct : newWidthA}px`,\n widthB: `${(newPct.current * width) - ml}px`,\n });\n }\n\n setIsDragging(false);\n isEventDragging.current = false;\n if (options.onDragEnd) {\n options.onDragEnd();\n }\n }\n\n clearTimeout(isEventTimeout.current);\n isEventTimeout.current = 0;\n },\n [loading],\n );\n\n useEventHandler(\n container,\n \"mousemove\",\n (e) => {\n if (!isEventDragging.current && isEventTimeout.current) {\n if (distance(startPos.current.x, startPos.current.y, e.pageX, e.pageY) > 20) {\n setIsDragging(true);\n isEventDragging.current = true;\n clearTimeout(isEventTimeout.current);\n isEventTimeout.current = 0;\n }\n }\n\n if (isEventDragging.current && resizableDiv.current) {\n const current = container.current;\n if (current) {\n const { x, width } = current.getBoundingClientRect();\n\n const ml = options.marginLeft || 0;\n const isLeft = options.left || false;\n\n const maxWidthPct = getMaxWidthPct(width, 0.8, options.maxWidthPct, options.maxWidthPx);\n const minWidthPct = getMaxWidthPct(width, 0.2, options.minWidthPct, options.minWidthPx);\n\n newPct.current = (width + x - e.pageX - 5) / width;\n if (isLeft) {\n newPct.current = 1 - newPct.current;\n }\n newPct.current = newPct.current < minWidthPct ? minWidthPct : newPct.current;\n newPct.current = newPct.current > maxWidthPct ? maxWidthPct : newPct.current;\n\n resizableDiv.current.style.width = `${(newPct.current * width) - ml}px`;\n }\n }\n },\n [isDragging, loading],\n );\n\n return {\n refs: {\n container,\n resizer,\n resizableDiv,\n otherDiv,\n },\n setWidths,\n isDragging,\n widthA,\n widthB,\n };\n}\n","import type { LayoutPanel, LayoutPanelSupportContext } from \"./Layout.types\";\n\nexport function filterSupportedPanels(\n panels: LayoutPanel[],\n ctx: LayoutPanelSupportContext,\n onSupportsError?: (panel: LayoutPanel, error: unknown) => void,\n) {\n return panels.filter((panel) => {\n if (!panel.supports) {\n return true;\n }\n\n try {\n return panel.supports(ctx);\n } catch (error) {\n onSupportsError?.(panel, error);\n return false;\n }\n });\n}\n\nexport function getSupportedPanelFallback(\n panels: LayoutPanel[],\n currentId: string | null,\n) {\n if (!currentId) {\n return null;\n }\n if (panels.some((panel) => panel.id === currentId)) {\n return currentId;\n }\n return panels[0]?.id || null;\n}\n\nexport function panelIds(panels: LayoutPanel[]) {\n return panels.map((panel) => panel.id).join(\",\");\n}\n","import styled, { css } from \"styled-components\";\nimport {\n ModularPanelHeader,\n ModulePanelButton,\n} from \"./components/ModularPanel\";\n\nconst focusedExhibition = \".manifest-editor.exhibition-focused &\";\nconst darkFocusedExhibition = `[data-exhibition-theme=\"dark\"] ${focusedExhibition}`;\n\nconst exhibitionColours = {\n pink: \"#b84c74\",\n pinkHover: \"#9f3f64\",\n lightApp: \"#f4f1ec\",\n lightStage: \"#dfdbd4\",\n lightPanel: \"#fff\",\n lightPanelSoft: \"#f8f6f3\",\n lightBorder: \"#dcd5ce\",\n lightPanelBorder: \"#ddd5ce\",\n lightText: \"#25211f\",\n lightMuted: \"#6a625c\",\n darkApp: \"#18161d\",\n darkStage: \"#0e0d12\",\n darkPanel: \"#28222d\",\n darkPanelSoft: \"#2f2934\",\n darkPanelHeader: \"#25222b\",\n darkHover: \"#312c34\",\n darkSelected: \"#3a3440\",\n darkText: \"#f6f1f4\",\n darkMuted: \"#c8c0c6\",\n darkSubtle: \"#999088\",\n darkLabel: \"#d9d1da\",\n darkWarning: \"#4a2636\",\n darkWarningBorder: \"#7a3f59\",\n darkBorder: \"rgba(246, 241, 244, 0.16)\",\n darkBorderSoft: \"rgba(246, 241, 244, 0.14)\",\n};\n\nexport const Main = styled.div`\n display: flex;\n flex: 1 1 0;\n min-height: 0;\n position: relative;\n overflow: hidden;\n\n ${focusedExhibition} {\n background: ${exhibitionColours.lightApp};\n }\n\n ${darkFocusedExhibition} {\n background: ${exhibitionColours.darkApp};\n }\n`;\n\nexport const CenterPanel = styled.div`\n flex: 1 1 0;\n min-width: 0;\n min-height: 0;\n display: flex;\n background: #e3e7f0;\n padding-top: 1px;\n overflow: hidden;\n\n ${focusedExhibition} {\n background: ${exhibitionColours.lightApp};\n }\n\n ${darkFocusedExhibition} {\n background: ${exhibitionColours.darkApp};\n }\n\n > * {\n min-width: 0;\n }\n\n ${focusedExhibition} > .delft-exhibition {\n background: ${exhibitionColours.lightStage};\n color: ${exhibitionColours.lightText};\n }\n\n ${focusedExhibition} .atlas-container {\n --atlas-background: ${exhibitionColours.lightStage} !important;\n background: ${exhibitionColours.lightStage} !important;\n }\n\n ${focusedExhibition} .atlas-canvas {\n background: ${exhibitionColours.lightStage} !important;\n }\n\n ${darkFocusedExhibition} > .delft-exhibition {\n background: ${exhibitionColours.darkStage};\n color: ${exhibitionColours.darkText};\n }\n\n ${darkFocusedExhibition} .atlas-container {\n --atlas-background: ${exhibitionColours.darkStage} !important;\n background: ${exhibitionColours.darkStage} !important;\n }\n\n ${darkFocusedExhibition} .atlas-canvas {\n background: ${exhibitionColours.darkStage} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"CanvasContainer\"],\n ${darkFocusedExhibition} [class*=\"ViewerContainer\"] {\n background: ${exhibitionColours.darkStage} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-workbench,\n ${darkFocusedExhibition} .exhibition-slideshow-current-canvas {\n background: ${exhibitionColours.darkApp} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-current-viewport,\n ${darkFocusedExhibition} .exhibition-slideshow-preview-frame {\n background: ${exhibitionColours.darkStage} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-heading {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-muted {\n color: ${exhibitionColours.darkMuted} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-preview-card,\n ${darkFocusedExhibition} .exhibition-slideshow-slide-strip,\n ${darkFocusedExhibition} .exhibition-slideshow-slide-card,\n ${darkFocusedExhibition} .exhibition-slideshow-content-item,\n ${darkFocusedExhibition} .exhibition-slideshow-content-empty,\n ${darkFocusedExhibition} .exhibition-slideshow-navigation,\n ${darkFocusedExhibition} .exhibition-slideshow-current-preview {\n background: ${exhibitionColours.darkPanel} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-content-item-selected {\n background: ${exhibitionColours.darkSelected} !important;\n border-color: ${exhibitionColours.pink} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-toolbar,\n ${darkFocusedExhibition} .exhibition-slideshow-current-toolbar {\n background: ${exhibitionColours.darkPanelHeader} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-navigation button,\n ${darkFocusedExhibition} .exhibition-slideshow-navigation-current,\n ${darkFocusedExhibition} .exhibition-slideshow-toolbar button,\n ${darkFocusedExhibition} .exhibition-slideshow-slide-card button,\n ${darkFocusedExhibition} .exhibition-slideshow-content-item button,\n ${darkFocusedExhibition} .exhibition-slideshow-current-control {\n background: ${exhibitionColours.darkPanelSoft} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-slideshow-navigation button:not(:disabled):hover,\n ${darkFocusedExhibition} .exhibition-slideshow-toolbar button:not(:disabled):hover,\n ${darkFocusedExhibition} .exhibition-slideshow-slide-card button:not(:disabled):hover,\n ${darkFocusedExhibition} .exhibition-slideshow-content-item button:not(:disabled):hover,\n ${darkFocusedExhibition} .exhibition-slideshow-current-control:not(:disabled):hover {\n background: ${exhibitionColours.darkHover} !important;\n color: #fff !important;\n }\n`;\n\nexport const LoadingCenter = styled.div`\n display: flex;\n flex: 1;\n justify-content: center;\n align-items: center;\n`;\n\nexport const PanelSwitcher = styled.div<{ $side: \"left\" | \"right\" }>`\n position: absolute;\n top: 3rem;\n z-index: 40;\n display: flex;\n flex-direction: column;\n gap: 0.25rem;\n padding: 0.25rem;\n border: 1px solid rgba(15, 23, 42, 0.16);\n border-radius: 6px;\n background: rgba(255, 255, 255, 0.94);\n box-shadow: 0 8px 22px rgba(15, 23, 42, 0.12);\n\n ${focusedExhibition} {\n border-color: ${exhibitionColours.lightBorder};\n background: rgba(255, 255, 255, 0.96);\n box-shadow: 0 8px 22px rgba(38, 33, 42, 0.12);\n }\n\n ${darkFocusedExhibition} {\n border-color: ${exhibitionColours.darkBorder};\n background: rgba(38, 33, 42, 0.94);\n box-shadow: 0 12px 28px rgba(0, 0, 0, 0.36);\n }\n\n ${(props) =>\n props.$side === \"left\"\n ? css`\n left: 1rem;\n `\n : css`\n right: 1rem;\n `}\n`;\n\nexport const PanelSwitchButton = styled.button`\n width: 2.35rem;\n height: 2.35rem;\n border: 0;\n border-radius: 4px;\n background: transparent;\n color: #555;\n display: flex;\n align-items: center;\n justify-content: center;\n font-size: 1.2rem;\n cursor: pointer;\n\n &:hover {\n background: #f2f3f6;\n color: #111827;\n }\n\n &[data-selected=\"true\"] {\n background: ${exhibitionColours.pink};\n color: #fff;\n }\n\n ${focusedExhibition} {\n color: ${exhibitionColours.lightMuted};\n }\n\n ${focusedExhibition}:hover {\n background: #f5eaf0;\n color: ${exhibitionColours.lightText};\n }\n\n ${focusedExhibition}[data-selected=\"true\"] {\n background: ${exhibitionColours.pink};\n color: #fff;\n }\n\n ${darkFocusedExhibition} {\n color: #efe8ed;\n }\n\n ${darkFocusedExhibition}:hover {\n background: rgba(255, 255, 255, 0.1);\n color: #fff;\n }\n\n ${darkFocusedExhibition}[data-selected=\"true\"] {\n background: ${exhibitionColours.pink};\n color: #fff;\n }\n\n svg {\n width: 1.25em;\n height: 1.25em;\n }\n`;\n\nexport const PanelSwitchGroup = styled.div`\n display: flex;\n flex-direction: column;\n gap: 0.25rem;\n`;\n\nexport const PanelSwitchDivider = styled.div`\n width: 100%;\n height: 1px;\n margin: 0.25rem 0;\n background: rgba(15, 23, 42, 0.14);\n`;\n\nexport const FloatingPanel = styled.aside<{\n $side: \"left\" | \"right\";\n $open: boolean;\n}>`\n position: absolute;\n top: 3rem;\n bottom: 1rem;\n z-index: 35;\n display: flex;\n min-width: min(320px, calc(100vw - 2rem));\n max-width: min(720px, calc(100vw - 2rem));\n background: #fff;\n border: 1px solid rgba(15, 23, 42, 0.16);\n border-radius: 6px;\n box-shadow: 0 16px 40px rgba(15, 23, 42, 0.18);\n overflow: hidden;\n opacity: ${(props) => (props.$open ? 1 : 0)};\n pointer-events: ${(props) => (props.$open ? \"auto\" : \"none\")};\n transition:\n opacity 180ms ease,\n transform 180ms ease;\n\n ${focusedExhibition} {\n background: ${exhibitionColours.lightPanel};\n border-color: ${exhibitionColours.lightPanelBorder};\n border-radius: 10px;\n color: ${exhibitionColours.lightText};\n box-shadow: 0 18px 42px rgba(38, 33, 42, 0.14);\n }\n\n ${focusedExhibition} [class~=\"bg-white\"] {\n background-color: ${exhibitionColours.lightPanel} !important;\n }\n\n ${focusedExhibition} [class*=\"bg-[#f8f6f3]\"] {\n background-color: ${exhibitionColours.lightPanelSoft} !important;\n }\n\n ${focusedExhibition} [class*=\"border-[#dcd5ce]\"] {\n border-color: ${exhibitionColours.lightBorder} !important;\n }\n\n ${darkFocusedExhibition} {\n --exhibition-primary: ${exhibitionColours.pink};\n --exhibition-field-bg: ${exhibitionColours.darkPanelSoft};\n --exhibition-field-border: ${exhibitionColours.darkBorder};\n --exhibition-text: ${exhibitionColours.darkText};\n --exhibition-muted: ${exhibitionColours.darkMuted};\n --exhibition-button-bg: ${exhibitionColours.darkPanelSoft};\n --exhibition-button-text: #fff;\n --exhibition-inactive-button-text: ${exhibitionColours.darkText};\n\n background: ${exhibitionColours.darkPanel};\n border-color: ${exhibitionColours.darkBorderSoft};\n color: ${exhibitionColours.darkText};\n box-shadow: 0 20px 50px rgba(0, 0, 0, 0.42);\n }\n\n ${darkFocusedExhibition} ${ModularPanelHeader} {\n background: ${exhibitionColours.darkPanelHeader} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n box-shadow:\n inset 0 -1px 0 0 ${exhibitionColours.darkBorder},\n inset 0 1px 0 0 ${exhibitionColours.darkBorder} !important;\n }\n\n ${darkFocusedExhibition} ${ModulePanelButton} {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} ${ModulePanelButton}:hover {\n background: ${exhibitionColours.darkHover} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [class~=\"bg-white\"],\n ${darkFocusedExhibition} [class*=\"bg-[#f8f6f3]\"] {\n background-color: ${exhibitionColours.darkPanelSoft} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"bg-gray-200\"],\n ${darkFocusedExhibition} [class*=\"bg-gray-100\"],\n ${darkFocusedExhibition} [class*=\"bg-me-gray-100\"] {\n background-color: ${exhibitionColours.darkPanelHeader} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"hover:bg-gray-100\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-gray-200\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-gray-300\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-gray-100\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-gray-300\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-50\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-100\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-primary-50\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-primary-100\"]:hover {\n background-color: ${exhibitionColours.darkHover} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [class*=\"hover:text-black\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:text-gray-\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:text-me-\"]:hover {\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} label {\n background-color: transparent !important;\n color: ${exhibitionColours.darkLabel} !important;\n }\n\n ${focusedExhibition} .exhibition-workbench-muted {\n color: ${exhibitionColours.lightMuted} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-workbench-muted {\n color: ${exhibitionColours.darkMuted} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-workbench-tab[class*=\"text-me-primary\"] {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} fieldset {\n background-color: ${exhibitionColours.darkPanelSoft} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"bg-me-50\"],\n ${darkFocusedExhibition} [class*=\"bg-me-100\"],\n ${darkFocusedExhibition} [class*=\"bg-me-primary-50\"],\n ${darkFocusedExhibition} [class*=\"bg-me-primary-100\"] {\n background-color: ${exhibitionColours.darkSelected} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"text-me-700\"],\n ${darkFocusedExhibition} [class*=\"text-me-500\"],\n ${darkFocusedExhibition} [class*=\"text-me-primary-500\"],\n ${darkFocusedExhibition} [class*=\"text-me-primary-600\"],\n ${darkFocusedExhibition} [class*=\"text-me-primary-700\"] {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"bg-me-gray-100\"] {\n background-color: ${exhibitionColours.darkPanelHeader} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"border-b-me-gray-300\"] {\n border-bottom-color: ${exhibitionColours.darkSelected} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"hover:bg-me-gray-300\"]:hover,\n ${darkFocusedExhibition} [class*=\"bg-me-gray-300\"] {\n background-color: ${exhibitionColours.darkHover} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [data-active],\n ${darkFocusedExhibition} [data-selected],\n ${darkFocusedExhibition} [aria-selected=\"true\"],\n ${darkFocusedExhibition} [data-canvas-selected=\"true\"] {\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [data-active=\"true\"],\n ${darkFocusedExhibition} [data-selected=\"true\"],\n ${darkFocusedExhibition} [aria-selected=\"true\"] {\n background-color: ${exhibitionColours.pink} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"bg-me-primary-500\"],\n ${darkFocusedExhibition} [class*=\"bg-me-500\"],\n ${darkFocusedExhibition} [class*=\"bg-me-700\"] {\n background-color: ${exhibitionColours.pink} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [class*=\"hover:bg-me-primary-500\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-primary-600\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-600\"]:hover,\n ${darkFocusedExhibition} [class*=\"hover:bg-me-800\"]:hover {\n background-color: ${exhibitionColours.pinkHover} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [class*=\"text-[#25211f]\"],\n ${darkFocusedExhibition} [class*=\"text-black\"] {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"text-black/40\"],\n ${darkFocusedExhibition} [class*=\"text-black/50\"],\n ${darkFocusedExhibition} [class*=\"text-black/60\"] {\n color: ${exhibitionColours.darkMuted} !important;\n }\n\n ${darkFocusedExhibition} [class*=\"border-[#dcd5ce]\"],\n ${darkFocusedExhibition} [class*=\"border-[#e4ddd6]\"],\n ${darkFocusedExhibition} .border,\n ${darkFocusedExhibition} .border-b {\n border-color: ${exhibitionColours.darkBorder} !important;\n }\n\n ${darkFocusedExhibition} select,\n ${darkFocusedExhibition} input,\n ${darkFocusedExhibition} textarea {\n background-color: ${exhibitionColours.darkPanelSoft} !important;\n border-color: rgba(246, 241, 244, 0.18) !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} input::placeholder,\n ${darkFocusedExhibition} textarea::placeholder {\n color: ${exhibitionColours.darkSubtle} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-tour-step-card {\n background-color: ${exhibitionColours.darkPanelSoft} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-tour-step-body,\n ${darkFocusedExhibition} .exhibition-tour-step-body * {\n background-color: transparent !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} a,\n ${darkFocusedExhibition} button {\n color: inherit;\n }\n\n ${darkFocusedExhibition} .exhibition-aspect-warning {\n background-color: ${exhibitionColours.darkWarning} !important;\n border-color: ${exhibitionColours.darkWarningBorder} !important;\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} .exhibition-aspect-warning [class*=\"text-me-\"],\n ${darkFocusedExhibition} .exhibition-aspect-warning [class*=\"text-black\"] {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} fieldset button {\n color: ${exhibitionColours.darkText} !important;\n }\n\n ${darkFocusedExhibition} fieldset button:hover {\n background-color: ${exhibitionColours.darkHover} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} fieldset button[data-active=\"true\"] {\n background-color: ${exhibitionColours.pink} !important;\n color: #fff !important;\n }\n\n ${darkFocusedExhibition} [role=\"menu\"],\n ${darkFocusedExhibition} [class*=\"DropdownMenu\"],\n ${darkFocusedExhibition} [class*=\"DropdownContent\"] {\n background-color: ${exhibitionColours.darkPanelHeader} !important;\n color: ${exhibitionColours.darkText} !important;\n border-color: ${exhibitionColours.darkBorder} !important;\n }\n\n ${(props) =>\n props.$side === \"left\"\n ? css`\n left: 4.5rem;\n transform: translateX(${props.$open ? \"0\" : \"-0.75rem\"});\n `\n : css`\n right: 4.5rem;\n transform: translateX(${props.$open ? \"0\" : \"0.75rem\"});\n `}\n\n @media (max-width: 760px) {\n top: 4.25rem;\n bottom: 1rem;\n left: 1rem;\n right: 1rem;\n width: auto !important;\n max-width: none;\n min-width: 0;\n transform: translateY(${(props) => (props.$open ? \"0\" : \"0.75rem\")});\n }\n`;\n\nexport const FloatingPanelBody = styled.div`\n display: flex;\n flex: 1;\n min-width: 0;\n height: 100%;\n overflow: hidden;\n`;\n","import styled, { css, keyframes } from \"styled-components\";\nimport { MenuPositions } from \"./Layout.types\";\nimport { TransitionStatus } from \"react-transition-group\";\n\nexport const OuterWrapper = styled.div`\n display: flex;\n flex-direction: column;\n flex: 1;\n min-height: 0;\n\n max-width: 100%;\n min-width: 0;\n overflow: hidden;\n`;\n\nexport const Header = styled.header`\n //box-shadow: 0 3px 2px 0 rgba(0, 0, 0, 0.04), 0 1px 0 0 rgba(0, 0, 0, 0.17);\n z-index: 200;\n`;\n\nexport const Footer = styled.div`\n background: #fff;\n`;\n\nexport const Main = styled.div`\n display: flex;\n flex: 1 1 0;\n min-height: 0;\n`;\n\nexport const LeftPanel = styled.div<{ $state?: TransitionStatus; $width: string; $motion?: boolean }>`\n background: #fff;\n display: flex;\n flex-direction: column;\n overflow: hidden;\n max-width: 720px;\n align-items: flex-end;\n\n ${(props) =>\n props.$motion\n ? css`\n transition: max-width 400ms;\n `\n : \"\"}\n\n ${(props) => {\n switch (props.$state) {\n case \"entering\":\n return css`\n max-width: ${props.$width};\n `;\n case \"exiting\":\n return css`\n max-width: 0;\n `;\n case \"unmounted\":\n case \"exited\":\n return css`\n max-width: 0;\n `;\n }\n }}\n`;\n\nexport const CenterPanel = styled.div`\n flex: 1 1 0;\n background: #e3e7f0;\n // background: #efefef;\n // box-shadow:\n // inset 0 3px 2px 0 rgba(0, 0, 0, 0.04),\n // inset 0 1px 0 0 rgba(0, 0, 0, 0.14);\n padding-top: 1px;\n // background: linear-gradient(0deg, rgba(251, 242, 237, 1) 0%, rgba(240, 229, 245, 1) 50%, rgba(236, 245, 255, 1) 100%);\n\n min-width: 320px;\n display: flex;\n\n min-height: 0;\n overflow: hidden;\n\n > * {\n min-width: 0;\n }\n`;\n\nexport const RightPanel = styled.div<{ $state?: TransitionStatus; $width: string; $motion?: boolean }>`\n background: #fff;\n display: flex;\n flex-direction: column;\n overflow: hidden;\n max-width: 720px;\n\n ${(props) => (props.$motion ? \"transition: max-width 400ms;\" : \"\")}\n\n ${(props) => {\n switch (props.$state) {\n case \"entering\":\n return css`\n max-width: ${props.$width};\n `;\n case \"exiting\":\n return css`\n max-width: 0;\n `;\n case \"unmounted\":\n case \"exited\":\n return css`\n max-width: 0;\n `;\n }\n }}\n`;\n\nexport const PanelContainer = styled.div<{ $menu?: MenuPositions }>`\n display: flex;\n flex: 1;\n height: 100%;\n min-width: 50px;\n transition: min-width 400ms;\n overflow: hidden;\n\n ${(props) => {\n switch (props.$menu) {\n case \"top\":\n return css`\n flex-direction: column;\n ${PanelMenu} {\n flex-direction: column;\n }\n `;\n case \"left\":\n return css`\n flex-direction: row;\n ${PanelMenu} {\n flex-direction: row;\n }\n `;\n default:\n case \"bottom\":\n return css`\n flex-direction: column-reverse;\n ${PanelMenu} {\n flex-direction: column;\n }\n `;\n case \"right\":\n return css`\n flex-direction: row-reverse;\n ${PanelMenu} {\n flex-direction: row;\n }\n `;\n }\n }}\n`;\n\nexport const PanelSideMenu = styled.div`\n background: #fff;\n border-top: 1px solid #e3e7f0;\n border-right: 1px solid #e3e7f0;\n display: flex;\n flex-direction: column;\n width: 3em;\n /* width: 3.35em;\n padding: 0.3em;\n gap: 0.3em; */\n`;\n\nexport const PanelSideMenuItem = styled.button`\n cursor: pointer;\n aspect-ratio: 1;\n width: 3em;\n height: 3em;\n display: flex;\n justify-content: center;\n align-items: center;\n &:hover {\n background: #fff6f9;\n }\n\n &:hover svg {\n color: #000;\n }\n\n &[data-selected=\"true\"] {\n background: #b84c74;\n svg {\n color: #ffffff;\n }\n }\n\n & svg {\n font-size: 1.5em;\n color: #999;\n }\n`;\n\nexport const PanelMenu = styled.div<{ $position: \"bottom\" | \"top\" | \"left\" | \"right\"; $open: boolean }>`\n display: flex;\n box-shadow:\n 0 -3px 2px 0 rgba(0, 0, 0, 0.04),\n 0 -1px 0 0 rgba(0, 0, 0, 0.17);\n\n ${(props) =>\n !props.$open && (props.$position === \"top\" || props.$position === \"bottom\")\n ? css`\n display: none;\n `\n : \"\"}\n`;\n\nexport const PanelContent = styled.div`\n display: flex;\n flex-direction: column;\n flex: 1;\n min-width: 0;\n overflow: hidden;\n`;\n","import {\n DefaultTooltipContent,\n Modal,\n Tooltip,\n TooltipTrigger,\n} from \"@manifest-editor/components\";\nimport { Spinner } from \"@manifest-editor/ui/madoc/components/icons/Spinner\";\nimport { GhostBlocks } from \"@manifest-editor/ui/ui/GhostBlocks/GhostBlocks\";\nimport {\n type CSSProperties,\n Fragment,\n memo,\n useContext,\n useLayoutEffect,\n useMemo,\n} from \"react\";\nimport { ErrorBoundary } from \"react-error-boundary\";\nimport { ReactVaultContext, useVaultSelector } from \"react-iiif-vault\";\nimport equal from \"shallowequal\";\nimport { useApp, useAppState } from \"../AppContext/AppContext\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport {\n BackgroundActionsMount,\n BackgroundActionToasts,\n} from \"../BackgroundTasks/BackgroundActions\";\nimport { useEvent } from \"../hooks/use-event\";\nimport { ModularPanel } from \"./components/ModularPanel\";\nimport { PanelError } from \"./components/PanelError\";\nimport { LayoutModeReactContext, useLayoutProvider } from \"./Layout.context\";\nimport { panelSizing, renderHelper } from \"./Layout.helpers\";\nimport {\n filterSupportedPanels,\n getSupportedPanelFallback,\n panelIds,\n} from \"./Layout.supports\";\nimport type { LayoutPanel } from \"./Layout.types\";\nimport type { LayoutRenderProps } from \"./Layout\";\nimport * as F from \"./Layout.focused.styles\";\nimport * as L from \"./Layout.styles\";\n\nfunction getEditedResourceType(data: unknown) {\n const resource = (data as any)?.resource;\n return resource?.source?.type || resource?.type || null;\n}\n\nexport const FocusedLayout = memo(function FocusedLayout(\n props: LayoutRenderProps,\n) {\n const app = useApp();\n const appState = useAppState();\n const rootResource = useAppResource();\n const layout = useLayoutProvider();\n const { vault: _vault } = useContext(ReactVaultContext);\n const vault = _vault || undefined;\n const vaultState = useVaultSelector((state) => state.iiif);\n const {\n loading,\n state,\n leftPanels: configuredLeftPanels,\n centerPanels: configuredCenterPanels,\n rightPanels: configuredRightPanels,\n modals: configuredModals = [],\n actions,\n } = layout;\n const isLoading = props.isLoading || false;\n\n const supportContext = useMemo(\n () => ({\n rootResource,\n vault,\n app,\n layoutState: state,\n appState,\n }),\n [rootResource, vault, app, state, appState, vaultState],\n );\n\n const leftPanels = useMemo(\n () =>\n filterSupportedPanels(\n configuredLeftPanels,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ).filter((panel) => !panel.focusedMode?.hide),\n [configuredLeftPanels, supportContext],\n );\n const centerPanels = useMemo(\n () =>\n filterSupportedPanels(\n configuredCenterPanels,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ),\n [configuredCenterPanels, supportContext],\n );\n const rightPanels = useMemo(\n () =>\n filterSupportedPanels(\n configuredRightPanels,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ).filter((panel) => !panel.focusedMode?.hide),\n [configuredRightPanels, supportContext],\n );\n const modals = useMemo(\n () =>\n filterSupportedPanels(\n configuredModals,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ),\n [configuredModals, supportContext],\n );\n\n const supportedLayout = useMemo(\n () => ({\n ...layout,\n leftPanels,\n centerPanels,\n rightPanels,\n modals,\n }),\n [layout, leftPanels, centerPanels, rightPanels, modals],\n );\n\n const leftPanel = leftPanels.find(\n (panel) => panel.id === state.leftPanel.current,\n );\n const rightPanel = rightPanels.find(\n (panel) => panel.id === state.rightPanel.current,\n );\n const centerPanel = centerPanels.find(\n (panel) => panel.id === state.centerPanel.current,\n );\n const modalToRender = modals.find(\n (panel) => panel.id === state.modal.current,\n );\n const pinnedRightPanel = state.pinnedRightPanel.pinned\n ? rightPanels.find((panel) => panel.id === state.pinnedRightPanel.current)\n : undefined;\n const showRightPanel =\n rightPanel &&\n (pinnedRightPanel?.id !== rightPanel.id ||\n !equal(state.pinnedRightPanel.state, state.rightPanel.state));\n const focusedPanelContext = useMemo(\n () => ({\n rootResource,\n vault,\n app,\n layoutState: state,\n appState,\n actions,\n }),\n [rootResource, vault, app, state, appState, actions],\n );\n const handleFocusedPanelSelect = (panel: LayoutPanel) => {\n panel.focusedMode?.onSelect?.(focusedPanelContext);\n };\n const closeLeftPanelOnMainPanelClick =\n !leftPanel || leftPanel.focusedMode?.closeOnMainPanelClick !== false;\n\n const backgroundItems = useMemo(() => {\n return (layout.background || []).map((bg, key) => {\n return <Fragment key={key}>{bg.render()}</Fragment>;\n });\n }, [layout.background]);\n\n useLayoutEffect(() => {\n rightPanels.length && actions.rightPanel.change({ id: rightPanels[0]!.id });\n leftPanels.length && actions.leftPanel.change({ id: leftPanels[0]!.id });\n centerPanels.length &&\n actions.centerPanel.change({ id: centerPanels[0]!.id });\n actions.leftPanel.close();\n actions.rightPanel.close();\n\n // actions are stable.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n useLayoutEffect(() => {\n if (centerPanel && centerPanel.onMount) {\n return centerPanel.onMount(\n state.centerPanel.state || centerPanel.defaultState || {},\n {\n ...supportedLayout,\n current: actions.centerPanel,\n vault: vault as any,\n },\n appState,\n );\n }\n }, [state.centerPanel.current, centerPanel?.id]);\n\n useLayoutEffect(() => {\n if (!state.leftPanel.open || !state.leftPanel.current) {\n return;\n }\n\n const selectedLeftPanel = leftPanels.find(\n (panel) => panel.id === state.leftPanel.current,\n );\n if (selectedLeftPanel?.focusedMode?.onSelect) {\n handleFocusedPanelSelect(selectedLeftPanel);\n }\n }, [state.leftPanel.open, state.leftPanel.current, panelIds(leftPanels)]);\n\n useLayoutEffect(() => {\n if (state.leftPanel.current && !leftPanel) {\n const fallback = getSupportedPanelFallback(\n leftPanels,\n state.leftPanel.current,\n );\n if (fallback) {\n actions.leftPanel.change({ id: fallback });\n } else {\n actions.leftPanel.close();\n }\n }\n\n if (state.centerPanel.current && !centerPanel) {\n const fallback = getSupportedPanelFallback(\n centerPanels,\n state.centerPanel.current,\n );\n if (fallback) {\n actions.centerPanel.change({ id: fallback });\n } else {\n actions.centerPanel.close();\n }\n }\n\n if (state.rightPanel.current && !rightPanel) {\n const fallback = getSupportedPanelFallback(\n rightPanels,\n state.rightPanel.current,\n );\n if (fallback) {\n actions.rightPanel.change({ id: fallback });\n } else {\n actions.rightPanel.close();\n }\n }\n\n if (state.modal.current && !modalToRender) {\n const fallback = getSupportedPanelFallback(modals, state.modal.current);\n if (fallback) {\n actions.modal.change({ id: fallback });\n } else {\n actions.modal.close();\n }\n }\n }, [\n state.leftPanel.current,\n state.centerPanel.current,\n state.rightPanel.current,\n state.modal.current,\n leftPanel?.id,\n centerPanel?.id,\n rightPanel?.id,\n modalToRender?.id,\n panelIds(leftPanels),\n panelIds(centerPanels),\n panelIds(rightPanels),\n panelIds(modals),\n ]);\n\n useEvent<{ \"layout.edit\": unknown }, \"layout.edit\">(\n \"layout.edit\",\n (data) => {\n if (getEditedResourceType(data) === \"Canvas\" && !state.rightPanel.open) {\n return;\n }\n\n if (rightPanels.find((panel) => panel.id === \"@manifest-editor/editor\")) {\n actions.rightPanel.open({\n id: \"@manifest-editor/editor\",\n stacked: true,\n });\n } else if (rightPanel) {\n actions.rightPanel.open();\n }\n },\n [panelIds(rightPanels), rightPanel?.id, state.rightPanel.open],\n );\n\n const sidebarSmall = \"4.5rem\";\n const leftPanelWidth = `${panelSizing({\n options: leftPanel?.options,\n fallback: 340,\n })}px`;\n const rightPanelWidth = `${panelSizing({\n options: rightPanel?.options,\n fallback: 420,\n })}px`;\n const layoutVariables = {\n \"--manifest-editor-layout-left-sidebar-small\": sidebarSmall,\n \"--manifest-editor-layout-left-sidebar-large\": state.leftPanel.open\n ? `calc(${sidebarSmall} + ${leftPanelWidth})`\n : sidebarSmall,\n \"--manifest-editor-layout-right-sidebar-small\": sidebarSmall,\n \"--manifest-editor-layout-right-sidebar-large\": state.rightPanel.open\n ? `calc(${sidebarSmall} + ${rightPanelWidth})`\n : sidebarSmall,\n } as CSSProperties & Record<string, string>;\n\n useLayoutEffect(() => {\n if (typeof document === \"undefined\") {\n return;\n }\n\n const root = document.documentElement;\n const previousValues: Array<[string, string]> = Object.keys(\n layoutVariables,\n ).map((key) => [key, root.style.getPropertyValue(key)]);\n\n for (const [key, value] of Object.entries(layoutVariables)) {\n root.style.setProperty(key, value);\n }\n\n return () => {\n for (const [key, value] of previousValues) {\n if (value) {\n root.style.setProperty(key, value);\n } else {\n root.style.removeProperty(key);\n }\n }\n };\n }, [\n leftPanelWidth,\n rightPanelWidth,\n state.leftPanel.open,\n state.rightPanel.open,\n ]);\n\n if (loading) {\n return null;\n }\n\n const renderSidePanelSwitcher = (\n side: \"left\" | \"right\",\n panels: LayoutPanel[],\n current: string | null,\n ) => {\n if (!panels.length) {\n return null;\n }\n\n const panelActions =\n side === \"left\" ? actions.leftPanel : actions.rightPanel;\n\n return (\n <F.PanelSwitcher $side={side} aria-label={`${side} panels`}>\n {panels.map((panel) => (\n <Tooltip\n placement={side === \"left\" ? \"right\" : \"left\"}\n key={panel.id}\n >\n <TooltipTrigger asChild>\n <F.PanelSwitchButton\n type=\"button\"\n aria-label={panel.label}\n data-selected={current === panel.id}\n onClick={() => {\n if (current === panel.id) {\n panelActions.toggle();\n } else {\n panelActions.open({ id: panel.id });\n }\n }}\n >\n {panel.icon || panel.label.slice(0, 1)}\n </F.PanelSwitchButton>\n </TooltipTrigger>\n <DefaultTooltipContent>{panel.label}</DefaultTooltipContent>\n </Tooltip>\n ))}\n </F.PanelSwitcher>\n );\n };\n\n const renderFocusedLeftSwitcher = () => {\n if (!centerPanels.length && !leftPanels.length) {\n return null;\n }\n\n return (\n <F.PanelSwitcher $side=\"left\" aria-label=\"Main and left panels\">\n {centerPanels.length ? (\n <F.PanelSwitchGroup aria-label=\"Main panels\">\n {centerPanels\n .filter((panel) => !panel.focusedMode?.hide)\n .map((panel) => (\n <Tooltip placement=\"right\" key={panel.id}>\n <TooltipTrigger asChild>\n <F.PanelSwitchButton\n type=\"button\"\n aria-label={panel.label}\n data-selected={state.centerPanel.current === panel.id}\n onClick={() => {\n actions.centerPanel.open({ id: panel.id });\n actions.leftPanel.close();\n actions.rightPanel.close();\n handleFocusedPanelSelect(panel);\n }}\n >\n {panel.icon || panel.label.slice(0, 1)}\n </F.PanelSwitchButton>\n </TooltipTrigger>\n <DefaultTooltipContent>{panel.label}</DefaultTooltipContent>\n </Tooltip>\n ))}\n </F.PanelSwitchGroup>\n ) : null}\n {centerPanels.length && leftPanels.length ? (\n <F.PanelSwitchDivider />\n ) : null}\n {leftPanels.length ? (\n <F.PanelSwitchGroup aria-label=\"Left panels\">\n {leftPanels.map((panel) => (\n <Tooltip placement=\"right\" key={panel.id}>\n <TooltipTrigger asChild>\n <F.PanelSwitchButton\n type=\"button\"\n aria-label={panel.label}\n data-selected={state.leftPanel.current === panel.id}\n onClick={() => {\n if (state.leftPanel.current === panel.id) {\n actions.leftPanel.toggle();\n } else {\n actions.leftPanel.open({ id: panel.id });\n }\n }}\n >\n {panel.icon || panel.label.slice(0, 1)}\n </F.PanelSwitchButton>\n </TooltipTrigger>\n <DefaultTooltipContent>{panel.label}</DefaultTooltipContent>\n </Tooltip>\n ))}\n </F.PanelSwitchGroup>\n ) : null}\n </F.PanelSwitcher>\n );\n };\n\n const renderModal = () => {\n if (!modalToRender || state.modal.open === false) {\n return null;\n }\n\n return (\n <Modal title={modalToRender.label} onClose={() => actions.modal.close()}>\n {renderHelper(\n modalToRender.render(\n state.modal.state || modalToRender.defaultState || {},\n { ...supportedLayout, current: actions.modal, vault: vault },\n appState,\n ),\n )}\n </Modal>\n );\n };\n\n const renderCenterPanel = () => (\n <L.PanelContainer $menu={props.centerPanelMenuPosition || \"top\"}>\n {props.centerPanelMenu ? (\n <L.PanelMenu\n $open={state.centerPanel.open}\n $position={props.centerPanelMenuPosition || \"top\"}\n >\n {props.centerPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n <ErrorBoundary\n resetKeys={[centerPanel?.id]}\n FallbackComponent={PanelError}\n >\n {isLoading ? (\n <F.LoadingCenter>\n <Spinner stroke=\"rgba(0,0,0,.3)\" fontSize={\"2em\"} />\n </F.LoadingCenter>\n ) : state.centerPanel.open ? (\n centerPanel ? (\n renderHelper(\n centerPanel.render(\n state.centerPanel.state || centerPanel.defaultState || {},\n {\n ...supportedLayout,\n current: actions.centerPanel,\n vault: vault,\n },\n appState,\n ),\n )\n ) : null\n ) : null}\n </ErrorBoundary>\n </L.PanelContent>\n </L.PanelContainer>\n );\n\n const renderLeftPanel = () => (\n <F.FloatingPanelBody>\n {isLoading ? (\n <L.PanelContent>\n <GhostBlocks />\n </L.PanelContent>\n ) : (\n <>\n {props.leftPanelMenu ? (\n <L.PanelMenu\n $open={state.leftPanel.open}\n $position={props.leftPanelMenuPosition || \"bottom\"}\n >\n {props.leftPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n {leftPanel ? (\n <ModularPanel\n isLeft\n panel={leftPanel}\n state={state.leftPanel}\n actions={actions.leftPanel}\n />\n ) : null}\n </L.PanelContent>\n </>\n )}\n </F.FloatingPanelBody>\n );\n\n const renderRightPanel = () => (\n <F.FloatingPanelBody>\n {isLoading ? (\n <L.PanelContent>\n <GhostBlocks />\n </L.PanelContent>\n ) : (\n <>\n {props.rightPanelMenu ? (\n <L.PanelMenu\n $open={state.rightPanel.open}\n $position={props.rightPanelMenuPosition || \"bottom\"}\n >\n {props.rightPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n {showRightPanel ? (\n <ModularPanel\n panel={rightPanel}\n state={state.rightPanel}\n actions={actions.rightPanel}\n pinActions={actions.pinnedRightPanel}\n available={rightPanels}\n />\n ) : null}\n\n {pinnedRightPanel ? (\n <ModularPanel\n panel={pinnedRightPanel}\n state={state.pinnedRightPanel}\n actions={actions.pinnedRightPanel}\n close={actions.rightPanel.close}\n />\n ) : null}\n </L.PanelContent>\n </>\n )}\n </F.FloatingPanelBody>\n );\n\n return (\n <LayoutModeReactContext.Provider value=\"focused\">\n <L.OuterWrapper\n id={props.htmlId || \"manifest-editor-container\"}\n className={`manifest-editor ${props.className || \"\"}`}\n data-layout-mode=\"focused\"\n style={layoutVariables}\n >\n {props.hideHeader ? null : (\n <L.Header>\n {props.header || null}\n {props.menu ? <menu>{props.menu}</menu> : null}\n </L.Header>\n )}\n <F.Main>\n <F.CenterPanel\n onClick={() => {\n if (closeLeftPanelOnMainPanelClick) {\n actions.leftPanel.close();\n }\n }}\n >\n {renderCenterPanel()}\n </F.CenterPanel>\n\n {renderFocusedLeftSwitcher()}\n {renderSidePanelSwitcher(\n \"right\",\n rightPanels,\n state.rightPanel.current,\n )}\n\n {leftPanels.length > 0 ? (\n <F.FloatingPanel\n $side=\"left\"\n $open={state.leftPanel.open}\n style={{\n width: leftPanelWidth,\n minWidth: leftPanel?.options?.minWidth,\n maxWidth: leftPanel?.options?.maxWidth,\n }}\n >\n {renderLeftPanel()}\n </F.FloatingPanel>\n ) : null}\n\n {rightPanels.length > 0 ? (\n <F.FloatingPanel\n $side=\"right\"\n $open={state.rightPanel.open}\n style={{\n width: rightPanelWidth,\n minWidth: rightPanel?.options?.minWidth,\n maxWidth: rightPanel?.options?.maxWidth,\n }}\n >\n {renderRightPanel()}\n </F.FloatingPanel>\n ) : null}\n </F.Main>\n <L.Footer>{props.footer || null}</L.Footer>\n\n <div className=\"hidden\">{backgroundItems}</div>\n <BackgroundActionsMount />\n <BackgroundActionToasts />\n\n <>{renderModal()}</>\n </L.OuterWrapper>\n </LayoutModeReactContext.Provider>\n );\n});\n","import styled, { css } from \"styled-components\";\nimport { ModularPanelHeader } from \"../Layout/components/ModularPanel\";\n\nexport const Container = styled.div`\n position: relative;\n display: flex;\n flex: 1;\n overflow: hidden;\n flex-direction: column;\n`;\n\nexport const CenterPanel = styled.div`\n flex: 1;\n position: relative;\n z-index: 7;\n`;\n\nexport const MobileBar = styled.div`\n display: flex;\n justify-content: space-around;\n width: 100%;\n background: #fff;\n border-top: 1px solid #cbcbcb;\n padding: 0.5em;\n height: 3.4rem;\n`;\n\nexport const LeftBarButton = styled.button`\n //background: red;\n padding: 0.5em 1em;\n width: 32%;\n\n border-radius: 5px;\n border: none;\n background: #ffffff;\n`;\n\nexport const PreviewBarButton = styled.button`\n padding: 0.5em 1em;\n width: 32%;\n\n border-radius: 5px;\n\n background: #5e59c2;\n border: 1px solid rgba(0, 0, 0, 0.21);\n color: #ffffff;\n`;\n\nexport const DrawerContainer = styled.div`\n position: relative;\n width: 32%;\n margin: 0 0.75em;\n z-index: 9;\n`;\n\nexport const DrawerButton = styled.button`\n padding: 0.4em 1em 0.65em;\n position: absolute;\n width: 100%;\n bottom: 1em;\n background: #ffffff;\n box-shadow: 0 3px 18px 0 rgba(0, 0, 0, 0.04);\n border-radius: 5px;\n border: 1px solid #979797;\n letter-spacing: -0.46px;\n white-space: nowrap;\n overflow: hidden;\n text-overflow: ellipsis;\n\n svg {\n display: block;\n margin: auto;\n font-size: 1.8em;\n }\n`;\n\nexport const DrawerBody = styled.div<{ $open?: boolean }>`\n background: #fff;\n display: flex;\n position: absolute;\n transform: translateY(100%);\n overflow-y: auto;\n left: 0;\n right: 0;\n top: 7em;\n z-index: 10;\n box-shadow:\n 0 -5px 15px 0 rgba(0, 0, 0, 0),\n 0 -3px 5px 0 rgba(0, 0, 0, 0);\n bottom: 0;\n transition:\n 0.3s transform ease-in-out,\n 0.3s box-shadow;\n ${(props) =>\n props.$open &&\n css`\n box-shadow:\n 0 -5px 15px 0 rgba(0, 0, 0, 0.1),\n 0 -3px 5px 0 rgba(0, 0, 0, 0.1);\n transform: translateY(0);\n `}\n\n ${ModularPanelHeader} {\n box-shadow: none;\n padding-left: 0.5em;\n padding-right: 0.5em;\n font-size: 1.1em;\n }\n`;\n\nexport const LeftPanel = styled.div<{ $open?: boolean }>`\n position: absolute;\n transform: translateX(-100%);\n background: #fff;\n left: 0;\n top: 0;\n bottom: 0;\n z-index: 10;\n overflow-y: auto;\n transition: 0.5s transform;\n ${(props) =>\n props.$open &&\n css`\n transform: translateX(0);\n `}\n`;\n\nexport const Lightbox = styled.div<{ $open?: boolean }>`\n background: rgba(0, 0, 0, 0.4);\n pointer-events: none;\n position: absolute;\n z-index: 8;\n top: 0;\n left: 0;\n right: 0;\n bottom: 0;\n opacity: 0;\n transition: opacity 0.5s;\n\n ${(props) =>\n props.$open &&\n css`\n pointer-events: visible;\n opacity: 1;\n `}\n`;\n","import { Modal, PanelSideMenu } from \"@manifest-editor/components\";\n// import { LayoutProps } from \"./Layout.types\";\nimport { DownIcon } from \"@manifest-editor/ui/icons/DownIcon\";\nimport { StarIcon } from \"@manifest-editor/ui/icons/StarIcon\";\nimport { Spinner } from \"@manifest-editor/ui/madoc/components/icons/Spinner\";\nimport { GhostBlocks } from \"@manifest-editor/ui/ui/GhostBlocks/GhostBlocks\";\nimport {\n Fragment,\n memo,\n useContext,\n useLayoutEffect,\n useMemo,\n useRef,\n} from \"react\";\nimport { ErrorBoundary } from \"react-error-boundary\";\nimport { ReactVaultContext, useVaultSelector } from \"react-iiif-vault\";\nimport { Transition, type TransitionStatus } from \"react-transition-group\";\nimport equal from \"shallowequal\";\nimport { useApp, useAppState } from \"../AppContext/AppContext\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport {\n BackgroundActionsMount,\n BackgroundActionToasts,\n} from \"../BackgroundTasks/BackgroundActions\";\nimport { useMatchMedia } from \"../hooks/use-match-media\";\nimport { HandleControls } from \"./components/HandleControls\";\nimport { ModularPanel } from \"./components/ModularPanel\";\nimport { PanelError } from \"./components/PanelError\";\nimport { useResizeLayout } from \"./components/use-resize-layouts\";\nimport { FocusedLayout } from \"./Layout.focused\";\nimport { useLayoutProvider } from \"./Layout.context\";\nimport { panelSizing, renderHelper } from \"./Layout.helpers\";\nimport {\n filterSupportedPanels,\n getSupportedPanelFallback,\n panelIds,\n} from \"./Layout.supports\";\nimport * as M from \"./Layout.mobile\";\nimport * as L from \"./Layout.styles\";\n\nexport interface LayoutRenderProps {\n header?: React.ReactNode;\n footer?: React.ReactNode;\n menu?: React.ReactNode;\n leftPanelMenu?: React.ReactNode;\n rightPanelMenu?: React.ReactNode;\n centerPanelMenu?: React.ReactNode;\n leftPanelMenuPosition?: \"top\" | \"bottom\";\n rightPanelMenuPosition?: \"top\" | \"bottom\";\n hideHeader?: boolean;\n isLoading?: boolean;\n className?: string;\n htmlId?: string;\n centerPanelMenuPosition?: \"top\" | \"bottom\";\n disableSideEffects?: string[];\n layoutMode?: \"default\" | \"focused\";\n}\n\nexport const Layout = memo(function Layout(props: LayoutRenderProps) {\n if (props.layoutMode === \"focused\") {\n return <FocusedLayout {...props} />;\n }\n\n const app = useApp();\n const appState = useAppState();\n const rootResource = useAppResource();\n const layout = useLayoutProvider();\n const { vault: _vault } = useContext(ReactVaultContext);\n const vault = _vault || undefined;\n const vaultState = useVaultSelector((state) => state.iiif);\n const leftPanelRef = useRef<HTMLDivElement | null>(null);\n const rightPanelRef = useRef<HTMLDivElement | null>(null);\n const {\n loading,\n state,\n leftPanels: configuredLeftPanels,\n centerPanels: configuredCenterPanels,\n rightPanels: configuredRightPanels,\n modals: configuredModals = [],\n actions,\n } = layout;\n const supportContext = useMemo(\n () => ({\n rootResource,\n vault,\n app,\n layoutState: state,\n appState,\n }),\n [rootResource, vault, app, state, appState, vaultState],\n );\n const leftPanels = useMemo(\n () =>\n filterSupportedPanels(\n configuredLeftPanels,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ),\n [configuredLeftPanels, supportContext],\n );\n const centerPanels = useMemo(\n () =>\n filterSupportedPanels(\n configuredCenterPanels,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ),\n [configuredCenterPanels, supportContext],\n );\n const rightPanels = useMemo(\n () =>\n filterSupportedPanels(\n configuredRightPanels,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ),\n [configuredRightPanels, supportContext],\n );\n const modals = useMemo(\n () =>\n filterSupportedPanels(\n configuredModals,\n supportContext,\n (panel, error) => {\n console.error(\n `Layout panel \"${panel.id}\" failed support check`,\n error,\n );\n },\n ),\n [configuredModals, supportContext],\n );\n const supportedLayout = useMemo(\n () => ({\n ...layout,\n leftPanels,\n centerPanels,\n rightPanels,\n modals,\n }),\n [layout, leftPanels, centerPanels, rightPanels, modals],\n );\n const leftPanel = leftPanels.find(\n (panel) => panel.id === state.leftPanel.current,\n );\n const rightPanel = rightPanels.find(\n (panel) => panel.id === state.rightPanel.current,\n );\n const centerPanel = centerPanels.find(\n (panel) => panel.id === state.centerPanel.current,\n );\n const modalToRender = modals.find(\n (panel) => panel.id === state.modal.current,\n );\n const enableMotion = true;\n const pinnedRightPanel = state.pinnedRightPanel.pinned\n ? rightPanels.find((panel) => panel.id === state.pinnedRightPanel.current)\n : undefined;\n const [mobile] = useMatchMedia([\"(max-width: 1020px)\"]);\n\n const isLoading = props.isLoading || false;\n const backgroundItems = useMemo(() => {\n return (layout.background || []).map((bg, key) => {\n return <Fragment key={key}>{bg.render()}</Fragment>;\n });\n }, [layout.background]);\n\n // Resizers\n const leftPanelResizer = useResizeLayout(`left-panel/${leftPanel?.id}`, {\n left: true,\n marginLeft: 60,\n minWidthPx: leftPanel?.options?.minWidth || 200,\n maxWidthPx: leftPanel?.options?.maxWidth || 720,\n loading,\n });\n const rightPanelResizer = useResizeLayout(`right-panel/${rightPanel?.id}`, {\n left: false,\n minWidthPx: rightPanel?.options?.minWidth || 320,\n maxWidthPx: rightPanel?.options?.maxWidth || 720,\n loading,\n });\n\n // Pinned state\n const showRightPanel =\n rightPanel &&\n (pinnedRightPanel?.id !== rightPanel.id ||\n !equal(state.pinnedRightPanel.state, state.rightPanel.state));\n const resetLeftPanel =\n leftPanelResizer.widthB !== \"auto\"\n ? () =>\n leftPanelResizer.setWidths({\n widthA: \"auto\",\n widthB: panelSizing({\n options: leftPanel?.options,\n fallback: 320,\n }),\n } as any)\n : undefined;\n const resetRightPanel =\n rightPanelResizer.widthB !== \"auto\"\n ? () =>\n rightPanelResizer.setWidths({\n widthA: \"auto\",\n widthB: panelSizing({\n options: rightPanel?.options,\n fallback: 320,\n }),\n } as any)\n : undefined;\n\n // Remove dynamic layouts for now.\n // useEffect(() => {\n // // @todo to enable dynamic layouts, we need this effect to run IF the props change.\n // actions.setAvailable(props);\n // props.rightPanels.length && actions.rightPanel.change({ id: props.rightPanels[0]!.id });\n // props.leftPanels.length && actions.leftPanel.change({ id: props.leftPanels[0]!.id });\n // props.centerPanels.length && actions.centerPanel.change({ id: props.centerPanels[0]!.id });\n\n // // actions are stable.\n // // eslint-disable-next-line react-hooks/exhaustive-deps\n // }, []);\n\n useLayoutEffect(() => {\n if (mobile && state.leftPanel.open && state.rightPanel.open) {\n actions.leftPanel.close();\n actions.rightPanel.close();\n }\n }, [mobile]);\n\n useLayoutEffect(() => {\n if (centerPanel && centerPanel.onMount) {\n return centerPanel.onMount(\n state.centerPanel.state || centerPanel.defaultState || {},\n {\n ...supportedLayout,\n current: actions.centerPanel,\n vault: vault as any,\n },\n appState,\n );\n }\n }, [state.centerPanel.current, centerPanel?.id]);\n\n useLayoutEffect(() => {\n if (state.leftPanel.current && !leftPanel) {\n const fallback = getSupportedPanelFallback(\n leftPanels,\n state.leftPanel.current,\n );\n if (fallback) {\n actions.leftPanel.change({ id: fallback });\n } else {\n actions.leftPanel.close();\n }\n }\n\n if (state.centerPanel.current && !centerPanel) {\n const fallback = getSupportedPanelFallback(\n centerPanels,\n state.centerPanel.current,\n );\n if (fallback) {\n actions.centerPanel.change({ id: fallback });\n } else {\n actions.centerPanel.close();\n }\n }\n\n if (state.rightPanel.current && !rightPanel) {\n const fallback = getSupportedPanelFallback(\n rightPanels,\n state.rightPanel.current,\n );\n if (fallback) {\n actions.rightPanel.change({ id: fallback });\n } else {\n actions.rightPanel.close();\n }\n }\n\n if (state.modal.current && !modalToRender) {\n const fallback = getSupportedPanelFallback(modals, state.modal.current);\n if (fallback) {\n actions.modal.change({ id: fallback });\n } else {\n actions.modal.close();\n }\n }\n }, [\n state.leftPanel.current,\n state.centerPanel.current,\n state.rightPanel.current,\n state.modal.current,\n leftPanel?.id,\n centerPanel?.id,\n rightPanel?.id,\n modalToRender?.id,\n panelIds(leftPanels),\n panelIds(centerPanels),\n panelIds(rightPanels),\n panelIds(modals),\n ]);\n\n useLayoutEffect(() => {\n // @todo to enable dynamic layouts, we need this effect to run IF the props change.\n // actions.setAvailable(props);\n rightPanels.length && actions.rightPanel.change({ id: rightPanels[0]!.id });\n leftPanels.length && actions.leftPanel.change({ id: leftPanels[0]!.id });\n centerPanels.length &&\n actions.centerPanel.change({ id: centerPanels[0]!.id });\n\n // actions are stable.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, []);\n\n if (loading) {\n // It will render as soon as possible, downside of hoisting the layout provider\n // Unlikely this will be hit because of flushSync, but best to check.\n return null;\n }\n\n // Build our panels here.\n\n const renderLeftPanel = (transition?: TransitionStatus) => (\n <L.PanelContainer\n $menu={props.leftPanelMenuPosition || \"bottom\"}\n ref={leftPanelResizer.refs.resizableDiv}\n className={[\n \"manifest-editor\",\n transition && enableMotion ? `transition transition-${transition}` : \"\",\n ].join(\" \")}\n style={{\n width:\n state.leftPanel.open || transition !== \"exited\"\n ? leftPanelResizer.widthB\n : undefined,\n minWidth: leftPanel?.options?.minWidth,\n }}\n >\n {isLoading ? (\n <L.PanelContent>\n <GhostBlocks />\n </L.PanelContent>\n ) : (\n <>\n {props.leftPanelMenu ? (\n <L.PanelMenu\n $open={state.leftPanel.open && transition !== \"exited\"}\n $position={props.leftPanelMenuPosition || \"bottom\"}\n >\n {props.leftPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n {state.leftPanel.open || transition !== \"exited\" ? (\n <>\n {leftPanel ? (\n <ModularPanel\n isLeft\n noHeader\n transition={transition}\n panel={leftPanel}\n state={state.leftPanel}\n actions={actions.leftPanel}\n />\n ) : null}\n </>\n ) : null}\n </L.PanelContent>\n </>\n )}\n </L.PanelContainer>\n );\n\n const renderModal = () => {\n if (!modalToRender || state.modal.open === false) {\n return null;\n }\n\n return (\n <Modal title={modalToRender.label} onClose={() => actions.modal.close()}>\n {renderHelper(\n modalToRender.render(\n state.modal.state || modalToRender.defaultState || {},\n { ...supportedLayout, current: actions.modal, vault: vault },\n appState,\n ),\n )}\n </Modal>\n );\n };\n\n const renderCenterPanel = () => (\n <L.PanelContainer $menu={props.centerPanelMenuPosition || \"top\"}>\n {props.centerPanelMenu ? (\n <L.PanelMenu\n $open={state.centerPanel.open}\n $position={props.centerPanelMenuPosition || \"top\"}\n >\n {props.centerPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n <ErrorBoundary\n resetKeys={[centerPanel?.id]}\n FallbackComponent={PanelError}\n >\n {isLoading ? (\n <div\n style={{\n display: \"flex\",\n flex: 1,\n justifyContent: \"center\",\n alignItems: \"center\",\n }}\n >\n <Spinner stroke=\"rgba(0,0,0,.3)\" fontSize={\"2em\"} />\n </div>\n ) : state.centerPanel.open ? (\n centerPanel ? (\n renderHelper(\n centerPanel.render(\n state.centerPanel.state || centerPanel.defaultState || {},\n {\n ...supportedLayout,\n current: actions.centerPanel,\n vault: vault,\n },\n appState,\n ),\n )\n ) : null\n ) : null}\n </ErrorBoundary>\n </L.PanelContent>\n </L.PanelContainer>\n );\n\n const renderRightPanel = (transition?: TransitionStatus) => (\n <L.PanelContainer\n $menu={props.rightPanelMenuPosition || \"bottom\"}\n ref={rightPanelResizer.refs.resizableDiv}\n className={\n transition && enableMotion ? `transition transition-${transition}` : \"\"\n }\n style={{\n width:\n state.rightPanel.open || transition !== \"exited\"\n ? rightPanelResizer.widthB\n : undefined,\n minWidth: rightPanel?.options?.minWidth,\n }}\n >\n {isLoading ? (\n <L.PanelContent>\n <GhostBlocks />\n </L.PanelContent>\n ) : (\n <>\n {props.rightPanelMenu ? (\n <L.PanelMenu\n $open={state.rightPanel.open}\n $position={props.rightPanelMenuPosition || \"bottom\"}\n >\n {props.rightPanelMenu}\n </L.PanelMenu>\n ) : null}\n <L.PanelContent>\n {state.rightPanel.open || transition !== \"exited\" ? (\n <>\n {showRightPanel ? (\n <ModularPanel\n panel={rightPanel}\n state={state.rightPanel}\n actions={actions.rightPanel}\n pinActions={actions.pinnedRightPanel}\n available={rightPanels}\n />\n ) : null}\n\n {pinnedRightPanel ? (\n <ModularPanel\n panel={pinnedRightPanel}\n state={state.pinnedRightPanel}\n actions={actions.pinnedRightPanel}\n close={actions.rightPanel.close}\n />\n ) : null}\n </>\n ) : null}\n </L.PanelContent>\n </>\n )}\n </L.PanelContainer>\n );\n\n if (mobile) {\n return (\n <L.OuterWrapper>\n {props.hideHeader ? null : (\n <L.Header>\n {props.header || null}\n {props.menu ? <menu>{props.menu}</menu> : null}\n </L.Header>\n )}\n <L.Main>\n <M.Container>\n <M.CenterPanel>{renderCenterPanel()}</M.CenterPanel>\n <M.MobileBar>\n {leftPanels.length > 0 ? (\n <M.LeftBarButton onClick={actions.leftPanel.toggle}>\n {leftPanel?.label}\n </M.LeftBarButton>\n ) : null}\n {rightPanels.length > 0 ? (\n <M.DrawerContainer>\n <M.DrawerButton onClick={actions.rightPanel.toggle}>\n <DownIcon rotate={180} />\n {rightPanel?.label}\n </M.DrawerButton>\n </M.DrawerContainer>\n ) : null}\n <M.PreviewBarButton>Preview</M.PreviewBarButton>\n </M.MobileBar>\n {rightPanels.length > 0 ? (\n <M.DrawerBody $open={state.rightPanel.open}>\n {renderRightPanel()}\n </M.DrawerBody>\n ) : null}\n {leftPanels.length > 0 ? (\n <M.LeftPanel $open={state.leftPanel.open}>\n {renderLeftPanel()}\n </M.LeftPanel>\n ) : null}\n {leftPanels.length > 0 || rightPanels.length > 0 ? (\n <M.Lightbox\n $open={state.leftPanel.open || state.rightPanel.open}\n onClick={() => {\n actions.leftPanel.close();\n actions.rightPanel.close();\n }}\n />\n ) : null}\n </M.Container>\n </L.Main>\n </L.OuterWrapper>\n );\n }\n\n // This is a big ol' work in progress.\n return (\n <L.OuterWrapper\n id={props.htmlId || \"manifest-editor-container\"}\n className={`manifest-editor ${props.className || \"\"}`}\n >\n {props.hideHeader ? null : (\n <L.Header>\n {props.header || null}\n {props.menu ? <menu>{props.menu}</menu> : null}\n </L.Header>\n )}\n <L.Main\n ref={(div) => {\n leftPanelResizer.refs.container.current = div;\n rightPanelResizer.refs.container.current = div;\n }}\n >\n {leftPanels.length > 0 ? (\n <PanelSideMenu\n current={state.leftPanel.current}\n items={leftPanels.map((panel) => ({\n id: panel.id,\n label: panel.label,\n icon: panel.icon,\n divide: panel.divide,\n separator: panel.separator,\n onClick: () => {\n if (state.leftPanel.current === panel.id) {\n actions.leftPanel.toggle();\n } else {\n actions.leftPanel.change({ id: panel.id });\n }\n },\n }))}\n open={state.leftPanel.open}\n />\n ) : null}\n\n {leftPanels.length > 0 ? (\n <Transition\n nodeRef={leftPanelRef}\n in={state.leftPanel.open}\n timeout={enableMotion ? 400 : 0}\n unmountOnExit={false}\n >\n {(transition) => (\n <>\n <L.LeftPanel\n ref={leftPanelRef}\n $width={leftPanelResizer.widthB}\n $state={transition}\n $motion={enableMotion}\n >\n {renderLeftPanel(transition)}\n </L.LeftPanel>\n <HandleControls\n ref={leftPanelResizer.refs.resizer}\n reset={resetLeftPanel}\n dir=\"left\"\n transition={transition}\n open={state.leftPanel.open || transition !== \"exited\"}\n actions={actions.leftPanel}\n />\n </>\n )}\n </Transition>\n ) : null}\n <L.CenterPanel>{renderCenterPanel()}</L.CenterPanel>\n {rightPanels.length > 0 ? (\n <Transition\n nodeRef={rightPanelRef}\n in={state.rightPanel.open}\n timeout={enableMotion ? 400 : 0}\n unmountOnExit={false}\n >\n {(transition) => (\n <>\n <HandleControls\n ref={rightPanelResizer.refs.resizer}\n dir=\"right\"\n reset={resetRightPanel}\n open={state.rightPanel.open}\n actions={actions.rightPanel}\n />\n <L.RightPanel\n ref={rightPanelRef}\n $width={rightPanelResizer.widthB}\n $state={transition}\n $motion={enableMotion}\n >\n {renderRightPanel(transition)}\n </L.RightPanel>\n </>\n )}\n </Transition>\n ) : null}\n </L.Main>\n <L.Footer>{props.footer || null}</L.Footer>\n\n <div className=\"hidden\">{backgroundItems}</div>\n <BackgroundActionsMount />\n <BackgroundActionToasts />\n\n <>{renderModal()}</>\n </L.OuterWrapper>\n );\n});\n","import { LayoutState, PanelActions, PanelActionType, PinnablePanelActions } from \"./Layout.types\";\nimport { Dispatch, useMemo } from \"react\";\nexport function usePanelActions(\n panel: keyof LayoutState,\n dispatch: Dispatch<PanelActionType>\n): PanelActions | PinnablePanelActions {\n function popStack() {\n dispatch({ type: \"popStack\", panel, payload: undefined });\n }\n function change(payload: { id: string; state?: any; stacked?: boolean }) {\n // flushSync(() => {\n dispatch({ type: \"change\", panel, payload });\n // });\n }\n function open(payload?: { id: string; state?: any; stacked?: boolean }) {\n // flushSync(() => {\n dispatch({ type: \"open\", panel, payload });\n // });\n }\n function close() {\n dispatch({ type: \"close\", panel, payload: undefined });\n }\n function toggle() {\n dispatch({ type: \"toggle\", panel, payload: undefined });\n }\n function minimise() {\n dispatch({ type: \"minimise\", panel, payload: undefined });\n }\n function maximise(payload?: { id: string; state?: any }) {\n dispatch({ type: \"maximise\", panel, payload });\n }\n function setCustomWidth(payload: number) {\n dispatch({ type: \"setCustomWidth\", panel, payload });\n }\n function resetSize() {\n dispatch({ type: \"resetSize\", panel, payload: undefined });\n }\n function pin(payload: { id: string; state?: any }) {\n dispatch({ type: \"pin\", panel, payload });\n }\n function unpin() {\n dispatch({ type: \"unpin\", panel, payload: undefined });\n }\n\n return useMemo(\n () => ({\n popStack,\n change,\n open,\n close,\n toggle,\n minimise,\n maximise,\n setCustomWidth,\n resetSize,\n pin,\n unpin,\n }),\n // Dispatch is stable here.\n // eslint-disable-next-line react-hooks/exhaustive-deps\n []\n );\n}\n","import { produce, Draft, original } from \"immer\";\nimport { LayoutState, PanelActionType, PanelState, PinnablePanelState } from \"./Layout.types\";\nimport { isPinnableState } from \"./Layout.helpers\";\n\nfunction pushStack<T>(\n state: Draft<PinnablePanelState | PanelState>,\n action: T extends { payload: { stacked?: boolean; unique?: boolean } } ? T : never\n) {\n if (action.payload && action.payload.stacked) {\n if (state.current) {\n const latest = state.stack[state.stack.length - 1];\n if (latest && latest.id === state.current) {\n return;\n }\n\n if (action.payload.unique) {\n state.stack = state.stack.filter((i) => i.id !== state.current);\n }\n\n state.stack.push({\n id: state.current,\n state: state.state ? { ...original(state.state) } : {},\n });\n }\n } else {\n state.stack = [];\n }\n}\n\nfunction panelReducer(state: Draft<PinnablePanelState | PanelState>, action: PanelActionType) {\n switch (action.type) {\n case \"popStack\": {\n if (state.stack.length) {\n const latest = state.stack[state.stack.length - 1];\n if (latest) {\n state.current = latest.id;\n state.state = latest.state;\n }\n state.stack = state.stack.slice(0, -1);\n }\n break;\n }\n\n case \"change\": {\n if (action.payload.id !== state.current) {\n pushStack(state, action);\n }\n state.state = action.payload.state;\n state.current = action.payload.id;\n break;\n }\n case \"close\": {\n state.open = false;\n break;\n }\n case \"open\": {\n state.open = true;\n if (action.payload) {\n if (action.payload.id !== state.current) {\n pushStack<any>(state, action);\n }\n state.state = action.payload.state;\n state.current = action.payload.id;\n }\n break;\n }\n case \"toggle\": {\n state.open = !state.open;\n break;\n }\n case \"maximise\": {\n state.minimised = false;\n if (action.payload) {\n state.state = action.payload.state;\n state.current = action.payload.id;\n }\n break;\n }\n case \"minimise\": {\n state.minimised = true;\n break;\n }\n case \"setCustomWidth\": {\n state.customWidth = action.payload;\n break;\n }\n case \"resetSize\": {\n state.customWidth = undefined;\n }\n }\n\n if (isPinnableState(state)) {\n switch (action.type) {\n case \"pin\": {\n state.pinned = true;\n state.state = action.payload.state;\n state.current = action.payload.id;\n break;\n }\n case \"unpin\": {\n state.pinned = false;\n state.state = undefined;\n break;\n }\n }\n }\n}\n\nexport const layoutReducer = produce<LayoutState, [PanelActionType]>((state, action: PanelActionType) => {\n switch (action.panel) {\n case \"centerPanel\": {\n panelReducer(state.centerPanel, action);\n break;\n }\n case \"leftPanel\": {\n panelReducer(state.leftPanel, action);\n break;\n }\n case \"rightPanel\": {\n panelReducer(state.rightPanel, action);\n break;\n }\n case \"modal\": {\n panelReducer(state.modal, action);\n break;\n }\n case \"pinnedRightPanel\": {\n panelReducer(state.pinnedRightPanel, action);\n break;\n }\n }\n});\n\nexport function getDefaultPanelState(): PanelState {\n return {\n customWidth: undefined,\n minimised: false,\n open: true,\n current: null,\n state: null,\n stack: [],\n };\n}\n\nexport function getDefaultLayoutState(): LayoutState {\n return {\n leftPanel: getDefaultPanelState(),\n centerPanel: getDefaultPanelState(),\n rightPanel: getDefaultPanelState(),\n modal: getDefaultPanelState(),\n pinnedRightPanel: {\n ...getDefaultPanelState(),\n pinnable: true,\n pinned: false,\n },\n };\n}\n","import { getValue } from \"@iiif/helpers\";\nimport type { Reference } from \"@iiif/presentation-3\";\nimport { ArrowRightIcon, BackIcon } from \"@manifest-editor/components\";\nimport type { ReactNode, SVGProps } from \"react\";\nimport { useMemo } from \"react\";\nimport { useManifest, useVault } from \"react-iiif-vault\";\nimport { useEditingResource, useEditingResourceStack } from \"./EditingStack/EditingStack\";\nimport { useLayoutActions } from \"./Layout/Layout.context\";\n\nexport interface ManifestPaginationNavigationProps {\n className?: string;\n variant?: \"light\" | \"dark\";\n}\n\ntype CanvasOption = {\n id: string;\n pageNumber: number;\n labelText: string;\n};\n\nexport function ManifestPaginationNavigation({ className, variant = \"light\" }: ManifestPaginationNavigationProps) {\n const manifest = useManifest();\n const vault = useVault();\n const { edit } = useLayoutActions();\n const currentEditingResource = useEditingResource();\n const editingStack = useEditingResourceStack();\n\n const items = manifest?.items || [];\n const isRev = manifest?.viewingDirection === \"right-to-left\" || manifest?.viewingDirection === \"bottom-to-top\";\n const isVert = manifest?.viewingDirection === \"top-to-bottom\" || manifest?.viewingDirection === \"bottom-to-top\";\n\n const currentCanvasId =\n findCanvasId(currentEditingResource) || editingStack.map(findCanvasId).find(Boolean) || items[0]?.id || \"\";\n const currentIndex = Math.max(\n 0,\n items.findIndex((item) => item.id === currentCanvasId),\n );\n const selectedCanvasId = items[currentIndex]?.id || \"\";\n const currentPage = currentIndex + 1;\n\n const canvasOptions = useMemo<CanvasOption[]>(() => {\n return items.map((item, index) => {\n const canvas = vault.get({ id: item.id, type: \"Canvas\" });\n return {\n id: item.id,\n pageNumber: index + 1,\n labelText: getValue(canvas?.label as any) || `Page ${index + 1}`,\n };\n });\n }, [items, vault]);\n\n const goToCanvas = (canvasId: string) => {\n const index = items.findIndex((item) => item.id === canvasId);\n const canvas = items[index];\n\n if (!canvas || !manifest) {\n return;\n }\n\n edit(\n { id: canvas.id, type: \"Canvas\" },\n {\n parent: { id: manifest.id, type: \"Manifest\" },\n property: \"items\",\n index,\n },\n { forceOpen: false },\n );\n };\n\n if (!manifest || items.length < 2) {\n return <div />;\n }\n\n const previousCanvas = items[currentIndex - 1];\n const nextCanvas = items[currentIndex + 1];\n const dark = variant === \"dark\";\n\n return (\n <nav\n aria-label=\"Manifest pagination\"\n className={cx(\n \"inline-flex shrink-0 items-center gap-1 rounded-full border px-1.5 py-1\",\n \"focus-within:ring-2 focus-within:ring-me-primary-500/40\",\n isRev && \"flex-row-reverse\",\n dark ? \"border-white/20 bg-white/10 text-white\" : \"border-me-gray-300 bg-white text-me-gray-900\",\n className,\n )}\n >\n <NavigationButton\n ariaLabel=\"Previous canvas\"\n disabled={!previousCanvas}\n onClick={() => previousCanvas && goToCanvas(previousCanvas.id)}\n dark={dark}\n >\n <DirectionIcon reverse={isRev} vertical={isVert} />\n </NavigationButton>\n\n <label\n htmlFor=\"manifest-pagination-page-select\"\n aria-label={`Page ${currentPage} of ${items.length}`}\n className={cx(\n \"relative inline-flex min-h-8 cursor-pointer select-none items-center gap-0.5\",\n \"whitespace-nowrap rounded-full border px-2.5 text-xs font-semibold leading-none\",\n \"focus-within:outline-none focus-within:ring-2 focus-within:ring-me-primary-500/40\",\n dark\n ? \"border-white/20 bg-white/10 text-white hover:bg-white/15\"\n : \"border-me-gray-300 bg-me-gray-100 text-me-gray-900 hover:bg-me-primary-50\",\n )}\n >\n <span>\n {currentPage} / {items.length}\n </span>\n <ArrowDownIcon className={cx(\"shrink-0 text-base\", dark ? \"text-white/60\" : \"text-me-gray-500\")} />\n <select\n id=\"manifest-pagination-page-select\"\n aria-label=\"Jump to canvas\"\n value={selectedCanvasId}\n onChange={(event) => goToCanvas(event.target.value)}\n className=\"absolute inset-0 cursor-pointer appearance-none border-0 bg-white opacity-0\"\n >\n {canvasOptions.map((canvas) => (\n <option key={canvas.id} value={canvas.id}>\n Page {canvas.pageNumber} - {canvas.labelText}\n </option>\n ))}\n </select>\n </label>\n\n <NavigationButton\n ariaLabel=\"Next canvas\"\n disabled={!nextCanvas}\n onClick={() => nextCanvas && goToCanvas(nextCanvas.id)}\n dark={dark}\n >\n <DirectionIcon reverse={!isRev} vertical={isVert} />\n </NavigationButton>\n </nav>\n );\n}\n\nfunction findCanvasId(\n resource:\n | {\n resource?: {\n source?: Reference;\n };\n }\n | null\n | undefined,\n) {\n const source = resource?.resource?.source;\n return source?.type === \"Canvas\" ? source.id : null;\n}\n\nfunction NavigationButton({\n ariaLabel,\n children,\n dark,\n disabled,\n onClick,\n}: {\n ariaLabel: string;\n children: ReactNode;\n dark: boolean;\n disabled?: boolean;\n onClick: () => void;\n}) {\n return (\n <button\n type=\"button\"\n aria-label={ariaLabel}\n disabled={disabled}\n onClick={onClick}\n className={cx(\n \"inline-flex h-8 w-8 items-center justify-center rounded-full border-0 bg-transparent p-0\",\n \"text-lg transition-colors focus:outline-none focus-visible:ring-2 focus-visible:ring-me-primary-500/50\",\n dark\n ? \"text-white hover:bg-white/15 disabled:text-white/40 disabled:hover:bg-transparent\"\n : \"text-me-gray-900 hover:bg-me-primary-50 disabled:text-me-gray-500 disabled:hover:bg-transparent\",\n \"disabled:cursor-not-allowed\",\n )}\n >\n {children}\n </button>\n );\n}\n\nfunction DirectionIcon({ reverse, vertical }: { reverse: boolean; vertical: boolean }) {\n const Icon = reverse ? ArrowRightIcon : BackIcon;\n\n return <Icon aria-hidden className={cx(\"block\", vertical && \"rotate-90\")} />;\n}\n\nfunction ArrowDownIcon(props: SVGProps<SVGSVGElement>) {\n return (\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"1em\" height=\"1em\" viewBox=\"0 0 24 24\" aria-hidden {...props}>\n <path fill=\"currentColor\" d=\"m7 10l5 5l5-5z\" />\n </svg>\n );\n}\n\nfunction cx(...classes: Array<string | false | null | undefined>) {\n return classes.filter(Boolean).join(\" \");\n}\n","import type { AllActions, Vault } from \"@iiif/helpers/vault\";\nimport type { BatchAction } from \"@iiif/helpers/vault/actions\";\nimport type { RemoteVaultAction, RemoteVaultClientMessage } from \"@manifest-editor/client-vault\";\nimport { randomId } from \"../helpers\";\n\ntype BridgeTarget = {\n port: MessagePort;\n lastActionId: string;\n};\n\nexport type VaultBridgeRegistry = {\n originalDispatch: Vault[\"dispatch\"];\n patchedDispatch: Vault[\"dispatch\"];\n targets: Set<BridgeTarget>;\n};\n\nconst registries = new WeakMap<Vault, VaultBridgeRegistry>();\n\nexport function createIframeVaultBridge(vault: Vault, port: MessagePort) {\n const target: BridgeTarget = {\n port,\n lastActionId: \"@genesis\",\n };\n const registry = getVaultBridgeRegistry(vault);\n\n function send(message: unknown) {\n port.postMessage(typeof message === \"string\" ? message : JSON.stringify(message));\n }\n\n function sendInitResponse() {\n send({\n _id: randomId(),\n _type: \"init-response\",\n _lastActionId: target.lastActionId,\n data: vault.getState(),\n });\n }\n\n function sendRejection(actionId: string) {\n send({\n _id: actionId,\n _type: \"vault-action-rejection\",\n _lastActionId: target.lastActionId,\n action: actionId,\n });\n }\n\n function handleMessage(event: MessageEvent) {\n const parsed = parseMessage(event.data);\n if (!parsed) return;\n\n if (parsed._type === \"init-request\") {\n sendInitResponse();\n return;\n }\n\n if (parsed._type === \"vault-action\") {\n sendRejection(parsed._id);\n }\n }\n\n registry.targets.add(target);\n port.addEventListener(\"message\", handleMessage);\n port.start();\n\n return () => {\n port.removeEventListener(\"message\", handleMessage);\n registry.targets.delete(target);\n if (registry.targets.size === 0 && vault.dispatch === registry.patchedDispatch) {\n vault.dispatch = registry.originalDispatch;\n registries.delete(vault);\n }\n port.close();\n };\n}\n\nfunction getVaultBridgeRegistry(vault: Vault): VaultBridgeRegistry {\n const existing = registries.get(vault);\n if (existing) {\n return existing;\n }\n\n const originalDispatch = vault.dispatch.bind(vault) as Vault[\"dispatch\"];\n const targets = new Set<BridgeTarget>();\n const patchedDispatch = ((action: AllActions | BatchAction) => {\n const result = originalDispatch(action);\n for (const target of targets) {\n mirrorAction(target, action);\n }\n return result;\n }) as typeof vault.dispatch;\n const registry = { originalDispatch, patchedDispatch, targets };\n\n vault.dispatch = patchedDispatch;\n registries.set(vault, registry);\n\n return registry;\n}\n\nfunction mirrorAction(target: BridgeTarget, action: AllActions | BatchAction) {\n const wrapped: RemoteVaultAction = {\n _id: randomId(),\n _type: \"vault-action\",\n _lastActionId: target.lastActionId,\n action,\n };\n target.lastActionId = wrapped._id;\n target.port.postMessage(JSON.stringify(wrapped));\n}\n\nfunction parseMessage(data: unknown): RemoteVaultClientMessage | null {\n try {\n if (typeof data === \"string\") {\n return JSON.parse(data);\n }\n if (typeof data === \"object\" && data) {\n return data as RemoteVaultClientMessage;\n }\n } catch {\n return null;\n }\n\n return null;\n}\n","import type { Reference } from \"@iiif/presentation-3\";\nimport { createContext, type ReactNode, useContext, useMemo } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { useVault, useVaultSelector } from \"react-iiif-vault\";\n\ninterface ResourceEditingContext {\n resource: Reference<any> | null;\n}\n\nexport const ResourceEditingReactContext =\n createContext<ResourceEditingContext>({\n resource: null,\n });\n\nexport function useEditingContext() {\n return useContext(ResourceEditingReactContext);\n}\n\n/**\n * useResource\n *\n * Only use this if you KNOW that there is a resource (e.g. in a panel)\n */\nexport function useResource<T = Record<string, never>>(): T & Reference<any> {\n const vault = useVault();\n const { resource } = useEditingContext();\n\n invariant(resource, \"Nothing selected\");\n\n const { id, type } = resource;\n\n const fullResource = useVaultSelector(() => {\n return vault.get({ id, type });\n }, [id, type]);\n\n return fullResource as T & Reference<any>;\n}\n\n/**\n * useOptionalResource\n *\n * Use in components where you don't know if something is editing. (e.g. canvas listing)\n */\nexport function useOptionalResource() {\n const { resource } = useEditingContext();\n\n return resource;\n}\n\nexport function ResourceEditingProvider({\n resource,\n children,\n}: {\n resource: { id: string; type: string } | null | undefined;\n children: ReactNode;\n}) {\n const { id, type } = resource || {};\n\n return (\n <ResourceEditingReactContext.Provider\n value={useMemo(\n () => ({\n // Current resource.\n resource: id && type ? { id, type } : null,\n }),\n [id, type],\n )}\n >\n {children}\n </ResourceEditingReactContext.Provider>\n );\n}\n","import React, { Component, ErrorInfo, ReactNode } from \"react\";\n\ninterface Props {\n children: ReactNode;\n}\n\ninterface State {\n hasError: boolean;\n}\n\nexport class ErrorBoundary extends Component<Props, State> {\n public state: State = {\n hasError: false,\n };\n\n public static getDerivedStateFromError(_: Error): State {\n console.error(_);\n // Update state so the next render will show the fallback UI.\n return { hasError: true };\n }\n\n public componentDidCatch(error: Error, errorInfo: ErrorInfo) {\n console.error(\"Uncaught error:\", error, errorInfo);\n }\n\n public render() {\n if (this.state.hasError) {\n return <h1>Sorry.. there was an error</h1>;\n }\n\n return this.props.children;\n }\n}\n","import { isSpecificResource } from \"@iiif/parser\";\nimport type { Reference, SpecificResource } from \"@iiif/presentation-3\";\nimport type { CreatableResource } from \"@manifest-editor/creator-api\";\nimport { type ReactNode, memo, useMemo, useReducer } from \"react\";\nimport invariant from \"tiny-invariant\";\nimport { useApp } from \"../AppContext/AppContext\";\nimport { useEditingStack } from \"../EditingStack/EditingStack\";\nimport type { EditableResource } from \"../EditingStack/EditingStack.types\";\nimport {\n LayoutActionsReactContext,\n LayoutStateReactContext,\n} from \"./Layout.context\";\nimport { usePanelActions } from \"./Layout.hooks\";\nimport { getDefaultLayoutState, layoutReducer } from \"./Layout.reducer\";\nimport type { PinnablePanelActions } from \"./Layout.types\";\nimport { useEmitter } from \"../hooks/use-event\";\n\nfunction parse(\n args: string | { id: string; state?: any; stacked?: boolean },\n _state?: any,\n): any {\n if (typeof args === \"string\") {\n return { id: args, state: _state };\n }\n return args;\n}\n\nexport const LayoutProvider = memo(function LayoutProvider(props: {\n children: ReactNode;\n}) {\n const app = useApp();\n const emitter = useEmitter();\n const available = app.layout;\n\n const [state, dispatch] = useReducer(\n layoutReducer,\n undefined,\n getDefaultLayoutState,\n );\n const actions = {\n centerPanel: usePanelActions(\"centerPanel\", dispatch),\n leftPanel: usePanelActions(\"leftPanel\", dispatch),\n rightPanel: usePanelActions(\"rightPanel\", dispatch),\n pinnedRightPanel: usePanelActions(\n \"pinnedRightPanel\",\n dispatch,\n ) as PinnablePanelActions,\n modal: usePanelActions(\"modal\", dispatch),\n editingStack: useEditingStack(),\n };\n\n function find(id: any) {\n const right = available.rightPanels.find((r) => r.id === id);\n if (right) {\n return [right, actions.rightPanel, actions.pinnedRightPanel] as const;\n }\n\n const center = available.centerPanels.find((r) => r.id === id);\n if (center) {\n return [center, actions.centerPanel] as const;\n }\n\n const left = available.leftPanels.find((r) => r.id === id);\n if (left) {\n return [left, actions.leftPanel] as const;\n }\n\n invariant(false, `Was not able to find panel with id \"${id}\"`);\n }\n\n function open(\n args: string | { id: string; state?: any; stacked?: boolean },\n _state?: any,\n ): void {\n const { id, state, stacked } = parse(args, _state);\n const [found, actions, pinnable] = find(id);\n\n if (pinnable && found.options?.openPinned) {\n pinnable.pin({\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n });\n } else {\n const openData = {\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n stacked,\n };\n\n emitter.emit(\"layout.open\", openData);\n actions.open(openData);\n }\n }\n\n function stack(\n args: string | { id: string; state?: any },\n _state?: any,\n ): void {\n const { id, state } = parse(args, _state);\n const [found, actions] = find(id);\n\n const openData = {\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n stacked: true,\n };\n\n emitter.emit(\"layout.open\", openData);\n actions.open(openData);\n }\n\n function change(\n args: string | { id: string; state?: any; stacked?: boolean },\n _state?: any,\n ): void {\n const { id, state, stacked } = parse(args, _state);\n const [found, actions] = find(id);\n const changeData = {\n id,\n state: { ...(found.defaultState || {}), ...(state || {}) },\n stacked,\n };\n\n emitter.emit(\"layout.change\", changeData);\n actions.change(changeData);\n }\n\n function close(\n args: string | { id: string; state?: any },\n _state?: any,\n ): void {\n const { id } = parse(args, _state);\n const [, actions] = find(id);\n\n emitter.emit(\"layout.close\", { id });\n actions.close();\n }\n\n function toggle(\n args: string | { id: string; state?: any },\n _state?: any,\n ): void {\n const { id } = parse(args, _state);\n const [, actions] = find(id);\n\n emitter.emit(\"layout.toggle\", { id });\n actions.toggle();\n }\n\n function edit(\n resource: Reference | SpecificResource,\n context: Omit<EditableResource, \"resource\"> = {},\n {\n reset,\n property,\n stacked,\n forceOpen,\n selectedTab,\n }: {\n reset?: boolean;\n property?: string;\n stacked?: boolean | undefined;\n forceOpen?: boolean;\n selectedTab?: string;\n } = {},\n ) {\n const toEdit: EditableResource = {\n resource: isSpecificResource(resource)\n ? resource\n : {\n type: \"SpecificResource\",\n source: resource,\n },\n ...context,\n };\n\n emitter.emit(\"layout.edit\", toEdit);\n actions.editingStack.edit(toEdit, reset);\n\n if (available.rightPanels.find((e) => e.id === \"@manifest-editor/editor\")) {\n if (forceOpen) {\n actions.rightPanel.open({\n id: \"@manifest-editor/editor\",\n stacked: stacked !== false,\n state: { property, currentTab: selectedTab },\n unique: true,\n });\n } else {\n actions.rightPanel.change({\n id: \"@manifest-editor/editor\",\n stacked: stacked !== false,\n state: { property, currentTab: selectedTab },\n unique: true,\n });\n }\n }\n }\n\n async function create(resource: CreatableResource) {\n actions.editingStack.create(resource, {});\n emitter.emit(\"layout.create\", resource);\n if (available.modals?.find((e) => e.id === \"@manifest-editor/creator\")) {\n actions.modal.open({\n id: \"@manifest-editor/creator\",\n stacked: true,\n unique: true,\n state: resource,\n });\n } else if (\n available.rightPanels.find((e) => e.id === \"@manifest-editor/creator\")\n ) {\n actions.rightPanel.open({\n id: \"@manifest-editor/creator\",\n stacked: true,\n unique: true,\n state: resource,\n });\n }\n }\n\n const otherActions = {\n open,\n change,\n close,\n toggle,\n stack,\n edit,\n create,\n };\n\n return (\n <LayoutActionsReactContext.Provider\n // biome-ignore lint/correctness/useExhaustiveDependencies: actions do not change\n value={useMemo(() => ({ ...actions, ...otherActions }), [available])}\n >\n <LayoutStateReactContext.Provider value={state}>\n {props.children}\n </LayoutStateReactContext.Provider>\n </LayoutActionsReactContext.Provider>\n );\n});\n","import { ImageServiceLoader } from \"@atlas-viewer/iiif-image-api\";\nimport { ErrorBoundary } from \"@manifest-editor/ui/atoms/ErrorBoundary\";\nimport { type ReactNode, useMemo } from \"react\";\nimport { AtlasStoreProvider, ImageServiceLoaderContext } from \"react-iiif-vault\";\nimport { ThemeProvider } from \"styled-components\";\nimport { useAppInstance } from \"../AppContext/AppContext\";\nimport { AppResourceProvider, type Resource } from \"../AppResourceProvider/AppResourceProvider\";\nimport type { BackgroundActionPersistence } from \"../BackgroundTasks/BackgroundTasks.types\";\nimport { BackgroundActionsProvider } from \"../BackgroundTasks/BackgroundTasksStore\";\nimport { type Config, ConfigProvider, mergeConfig, useConfig } from \"../ConfigContext/ConfigContext\";\nimport { ContextMenuProvider } from \"../ContextMenu/ContextMenuContext\";\nimport { EditingStack } from \"../EditingStack/EditingStack\";\nimport { LayoutProvider } from \"../Layout/Layout.context-internal\";\nimport { PluginConfigBridge } from \"../PluginContext/PluginContext\";\nimport { PreviewProvider } from \"../PreviewContext/PreviewContext\";\nimport type { Preview, PreviewConfiguration } from \"../PreviewContext/PreviewContext.types\";\nimport { PreviewVaultContext } from \"../PreviewVault/PreviewVault\";\nimport { ToastProvider } from \"../Toast/ToastContext\";\nimport { defaultTheme } from \"./default-theme\";\n\nconst previewConfigs: PreviewConfiguration[] = [\n {\n id: \"universal-viewer\",\n config: {\n url: \"https://universalviewer.dev/#?iiifManifestId={manifestId}\",\n },\n type: \"external-manifest-preview\",\n label: \"Universal viewer\",\n },\n {\n id: \"mirador-3\",\n type: \"external-manifest-preview\",\n label: \"Mirador 3\",\n config: {\n url: \"https://tomcrane.github.io/scratch/mirador3/?iiif-content={manifestId}\",\n },\n },\n {\n id: \"annona\",\n type: \"external-manifest-preview\",\n label: \"Annona\",\n config: {\n url: \"https://ncsu-libraries.github.io/annona/tools/#/display?url={manifestId}&viewtype=iiif-storyboard&settings=%7B%22fullpage%22%3Atrue%7D\",\n },\n },\n {\n id: \"iiif-preview\",\n config: { url: \"https://iiif-preview.digirati.services/store\" },\n type: \"iiif-preview-service\",\n label: \"IIIF Preview\",\n },\n];\n\nconst imageServiceLoader = new ImageServiceLoader({\n approximateServices: true,\n verificationsRequired: 8,\n enableFetching: true,\n});\n\nexport function ShellProvider({\n config,\n saveConfig,\n children,\n theme,\n previews,\n resource,\n editing,\n backgroundActionPersistence,\n}: {\n resource: Resource;\n config?: Partial<Config>;\n saveConfig?: (config: Partial<Config>) => void;\n children: ReactNode;\n theme?: any;\n previews?: Preview[];\n editing?: { id: string; type: string };\n backgroundActionPersistence?: BackgroundActionPersistence | false | null;\n}) {\n const app = useAppInstance();\n const existingConfig = useConfig();\n const mergedConfig = useMemo(() => {\n const resolvedPreviews =\n config?.previews || (existingConfig.previews?.length ? existingConfig.previews : previewConfigs);\n return mergeConfig(\n existingConfig,\n {\n previews: resolvedPreviews,\n },\n config,\n );\n }, [existingConfig, config]);\n const backgroundActionPersistenceKey = useMemo(\n () => ({\n appId: app.appId,\n instanceId: app.instanceId,\n rootResource: {\n id: resource.id,\n type: resource.type,\n },\n }),\n [app.appId, app.instanceId, resource.id, resource.type],\n );\n\n return (\n <ErrorBoundary>\n <ImageServiceLoaderContext.Provider value={imageServiceLoader}>\n <AppResourceProvider resource={resource}>\n <PreviewVaultContext>\n <ThemeProvider theme={theme || defaultTheme}>\n <ConfigProvider config={mergedConfig} saveConfig={saveConfig}>\n <PluginConfigBridge config={mergedConfig} />\n <EditingStack>\n <LayoutProvider>\n <BackgroundActionsProvider\n persistence={backgroundActionPersistence}\n persistenceKey={backgroundActionPersistenceKey}\n >\n <ContextMenuProvider>\n <ToastProvider>\n {/* @todo swap these out for (config?.previews || []) */}\n <PreviewProvider previews={previews || []} configs={mergedConfig.previews}>\n <AtlasStoreProvider>{children}</AtlasStoreProvider>\n </PreviewProvider>\n </ToastProvider>\n </ContextMenuProvider>\n </BackgroundActionsProvider>\n </LayoutProvider>\n </EditingStack>\n </ConfigProvider>\n </ThemeProvider>\n </PreviewVaultContext>\n </AppResourceProvider>\n </ImageServiceLoaderContext.Provider>\n </ErrorBoundary>\n );\n}\n","import type { Vault } from \"@iiif/helpers/vault\";\nimport type { Reference } from \"@iiif/presentation-3\";\nimport type {\n ManifestEditorSpecification,\n SpecificationEditorTarget,\n SpecificationEntityType,\n SpecificationJsonValue,\n SpecificationPropertyPath,\n SpecificationPropertyPolicy,\n SpecificationReport,\n SpecificationReportItem,\n SpecificationReportStatus,\n SpecificationRule,\n SpecificationTextValue,\n} from \"./SpecificationContext.types\";\n\nconst entityTypes = new Set<SpecificationEntityType>([\n \"Collection\",\n \"Manifest\",\n \"Canvas\",\n \"Range\",\n \"AnnotationPage\",\n \"Annotation\",\n \"ContentResource\",\n \"Agent\",\n]);\n\nconst emptyCounts: Record<SpecificationReportStatus, number> = {\n satisfied: 0,\n missing: 0,\n invalid: 0,\n disallowed: 0,\n \"not-applicable\": 0,\n};\n\nconst descriptiveProperties = new Set([\n \"label\",\n \"summary\",\n \"language\",\n \"navDate\",\n \"provider\",\n \"requiredStatement\",\n \"rights\",\n \"thumbnail\",\n]);\n\ntype CollectedResource = {\n ref: Reference;\n resource: any;\n};\n\nexport function normaliseSpecificationPath(\n path: SpecificationPropertyPath | string | undefined,\n): SpecificationPropertyPath {\n if (!path) return [];\n return Array.isArray(path)\n ? path.filter(Boolean)\n : path.split(\".\").filter(Boolean);\n}\n\nexport function specificationPathEquals(\n a: SpecificationPropertyPath | string | undefined,\n b: SpecificationPropertyPath | string | undefined,\n) {\n const pathA = normaliseSpecificationPath(a);\n const pathB = normaliseSpecificationPath(b);\n return (\n pathA.length === pathB.length &&\n pathA.every((part, index) => part === pathB[index])\n );\n}\n\nexport function getValueAtPath(\n resource: any,\n path: SpecificationPropertyPath | string | undefined,\n): unknown {\n let current = resource;\n for (const part of normaliseSpecificationPath(path)) {\n if (current == null) {\n return undefined;\n }\n current = current[part as keyof typeof current];\n }\n return current;\n}\n\nexport function setValueAtPath(\n resource: any,\n path: SpecificationPropertyPath | string,\n value: unknown,\n): any {\n const parts = normaliseSpecificationPath(path);\n if (!parts.length) return value;\n\n const next = Array.isArray(resource)\n ? [...resource]\n : { ...(resource || {}) };\n let cursor = next;\n\n parts.forEach((part, index) => {\n if (index === parts.length - 1) {\n cursor[part] = value;\n return;\n }\n\n const existing = cursor[part];\n cursor[part] = Array.isArray(existing)\n ? [...existing]\n : { ...(existing || {}) };\n cursor = cursor[part];\n });\n\n return next;\n}\n\nexport function hasMeaningfulValue(value: unknown): boolean {\n if (value == null) return false;\n if (typeof value === \"string\") return value.trim().length > 0;\n if (typeof value === \"number\" || typeof value === \"boolean\") return true;\n if (Array.isArray(value))\n return value.some((item) => hasMeaningfulValue(item));\n if (typeof value !== \"object\") return false;\n\n const entries = Object.entries(value as Record<string, unknown>);\n if (!entries.length) return false;\n\n const looksLikeLanguageMap = entries.every(([, item]) => {\n return (\n typeof item === \"string\" ||\n (Array.isArray(item) && item.every((value) => typeof value === \"string\"))\n );\n });\n\n if (looksLikeLanguageMap) {\n return entries.some(([, item]) => hasMeaningfulValue(item));\n }\n\n return true;\n}\n\nexport function normaliseJsonValue(value: unknown): unknown {\n if (Array.isArray(value)) {\n return value.map(normaliseJsonValue);\n }\n\n if (value && typeof value === \"object\") {\n return Object.keys(value as Record<string, unknown>)\n .sort()\n .reduce<Record<string, unknown>>((acc, key) => {\n acc[key] = normaliseJsonValue((value as Record<string, unknown>)[key]);\n return acc;\n }, {});\n }\n\n return value;\n}\n\nexport function specificationJsonEquals(a: unknown, b: unknown): boolean {\n return (\n JSON.stringify(normaliseJsonValue(a)) ===\n JSON.stringify(normaliseJsonValue(b))\n );\n}\n\nexport function getTerminologyLabel(\n specifications: ManifestEditorSpecification[] | undefined,\n entityType: SpecificationEntityType | string | undefined,\n path: SpecificationPropertyPath | string | undefined,\n fallback?: string,\n): string {\n const normalisedPath = normaliseSpecificationPath(path);\n\n for (const specification of specifications || []) {\n for (const item of specification.terminology?.properties || []) {\n if (item.entityType && item.entityType !== entityType) continue;\n if (specificationPathEquals(item.path, normalisedPath)) {\n return item.label;\n }\n }\n }\n\n return fallback || humanisePath(normalisedPath);\n}\n\nexport function getPropertyPolicy(\n specifications: ManifestEditorSpecification[] | undefined,\n resource: Reference | null | undefined,\n path: SpecificationPropertyPath | string,\n): SpecificationPropertyPolicy {\n const normalisedPath = normaliseSpecificationPath(path);\n const rules: SpecificationRule[] = [];\n let fixedValue: SpecificationJsonValue | undefined;\n let fixedValueRule: SpecificationPropertyPolicy[\"fixedValueRule\"];\n let disallowed = false;\n let required = false;\n\n if (!resource || !entityTypes.has(resource.type as SpecificationEntityType)) {\n return {\n entityType: resource?.type as SpecificationEntityType | undefined,\n path: normalisedPath,\n label: getTerminologyLabel(\n specifications,\n resource?.type,\n normalisedPath,\n ),\n disallowed: false,\n required: false,\n rules,\n };\n }\n\n for (const specification of specifications || []) {\n for (const rule of specification.rules || []) {\n if (!(\"entityType\" in rule) || !(\"path\" in rule)) continue;\n if (rule.entityType !== resource.type) continue;\n if (!specificationPathEquals(rule.path, normalisedPath)) continue;\n\n rules.push(rule);\n\n if (rule.type === \"disallow-property\") {\n disallowed = true;\n }\n\n if (rule.type === \"require-non-empty\") {\n required = true;\n }\n\n if (rule.type === \"fixed-value\" && !fixedValueRule) {\n fixedValue = rule.value;\n fixedValueRule = rule;\n required = true;\n }\n }\n }\n\n return {\n entityType: resource.type as SpecificationEntityType,\n path: normalisedPath,\n label: getTerminologyLabel(specifications, resource.type, normalisedPath),\n disallowed,\n required,\n fixedValue,\n fixedValueRule,\n rules,\n };\n}\n\nexport function evaluateSpecifications(\n specifications: ManifestEditorSpecification[] | undefined,\n vault: Vault,\n rootRef: Reference,\n): SpecificationReport {\n const resolvedSpecifications = specifications || [];\n const resources = collectSpecificationResources(vault, rootRef);\n const results: SpecificationReportItem[] = [];\n\n for (const specification of resolvedSpecifications) {\n for (const [ruleIndex, rule] of (specification.rules || []).entries()) {\n results.push(\n ...evaluateRule(specification, rule, ruleIndex, resources, vault),\n );\n }\n }\n\n return {\n specifications: resolvedSpecifications,\n results,\n counts: countResults(results),\n };\n}\n\nexport function collectSpecificationResources(\n vault: Vault,\n rootRef: Reference,\n): CollectedResource[] {\n const collected: CollectedResource[] = [];\n const seen = new Set<string>();\n\n function addResource(input: unknown) {\n const ref = toReference(input);\n if (!ref) return;\n\n if (ref.type === \"SpecificResource\") {\n addResource((input as any)?.source);\n return;\n }\n\n const resource =\n resolveResource(vault, input) || resolveResource(vault, ref);\n if (!resource || !resource.type) return;\n\n const key = `${resource.type}:${resource.id || JSON.stringify(ref)}`;\n if (seen.has(key)) return;\n seen.add(key);\n\n if (entityTypes.has(resource.type)) {\n collected.push({\n ref: { id: resource.id, type: resource.type },\n resource,\n });\n }\n\n for (const child of getResourceChildren(resource)) {\n addResource(child);\n }\n }\n\n addResource(rootRef);\n\n return collected;\n}\n\nfunction evaluateRule(\n specification: ManifestEditorSpecification,\n rule: SpecificationRule,\n ruleIndex: number,\n resources: CollectedResource[],\n vault: Vault,\n): SpecificationReportItem[] {\n switch (rule.type) {\n case \"disallow-property\":\n case \"require-non-empty\":\n case \"fixed-value\":\n return evaluatePropertyRule(specification, rule, ruleIndex, resources);\n case \"iiif:canvas-with-image-service\":\n return [\n evaluateCanvasWithImageService(\n specification,\n rule,\n ruleIndex,\n resources,\n vault,\n ),\n ];\n case \"iiif:thumbnail-from-body-service\":\n return evaluateThumbnailFromBodyService(\n specification,\n rule,\n ruleIndex,\n resources,\n vault,\n );\n case \"iiif:valid-rights\":\n return evaluateValidRights(specification, rule, ruleIndex, resources);\n case \"iiif:required-statement\":\n return evaluateRequiredStatement(\n specification,\n rule,\n ruleIndex,\n resources,\n );\n case \"iiif:metadata-template\":\n return evaluateMetadataTemplate(\n specification,\n rule,\n ruleIndex,\n resources,\n );\n default:\n return [];\n }\n}\n\nfunction evaluatePropertyRule(\n specification: ManifestEditorSpecification,\n rule: Extract<\n SpecificationRule,\n { entityType: SpecificationEntityType; path: SpecificationPropertyPath }\n >,\n ruleIndex: number,\n resources: CollectedResource[],\n): SpecificationReportItem[] {\n const targets = resources.filter((item) => item.ref.type === rule.entityType);\n const displayLabel = getTerminologyLabel(\n specification ? [specification] : [],\n rule.entityType,\n rule.path,\n );\n\n if (!targets.length) {\n return [\n createReportItem(specification, rule, ruleIndex, {\n status: \"not-applicable\",\n displayLabel,\n message: `No ${rule.entityType} resources were found for ${displayLabel}.`,\n path: rule.path,\n }),\n ];\n }\n\n return targets.map(({ ref, resource }) => {\n const value = getValueAtPath(resource, rule.path);\n const hasValue = hasMeaningfulValue(value);\n\n if (rule.type === \"disallow-property\") {\n return createReportItem(specification, rule, ruleIndex, {\n target: ref,\n path: rule.path,\n status: hasValue ? \"disallowed\" : \"satisfied\",\n displayLabel,\n actual: value,\n message: hasValue\n ? `${displayLabel} is present but is not allowed.`\n : `${displayLabel} is not present.`,\n editorTarget: createEditorTarget(ref, rule.path),\n });\n }\n\n if (rule.type === \"require-non-empty\") {\n return createReportItem(specification, rule, ruleIndex, {\n target: ref,\n path: rule.path,\n status: hasValue ? \"satisfied\" : \"missing\",\n displayLabel,\n actual: value,\n message: hasValue\n ? `${displayLabel} has a value.`\n : `${displayLabel} must be filled in.`,\n editorTarget: createEditorTarget(ref, rule.path),\n });\n }\n\n const matches = specificationJsonEquals(value, rule.value);\n return createReportItem(specification, rule, ruleIndex, {\n target: ref,\n path: rule.path,\n status: matches ? \"satisfied\" : hasValue ? \"invalid\" : \"missing\",\n displayLabel,\n expected: rule.value,\n actual: value,\n message: matches\n ? `${displayLabel} matches the required value.`\n : hasValue\n ? `${displayLabel} does not match the required value.`\n : `${displayLabel} must use the required value.`,\n editorTarget: createEditorTarget(ref, rule.path),\n });\n });\n}\n\nfunction evaluateCanvasWithImageService(\n specification: ManifestEditorSpecification,\n rule: Extract<SpecificationRule, { type: \"iiif:canvas-with-image-service\" }>,\n ruleIndex: number,\n resources: CollectedResource[],\n vault: Vault,\n): SpecificationReportItem {\n const canvases = resources.filter((item) => item.ref.type === \"Canvas\");\n const expected = getExpectedServiceIds(rule);\n const matchingCanvas = canvases.find(({ resource }) => {\n const serviceIds = getCanvasPaintingServiceIds(resource, vault);\n return serviceMatches(serviceIds, expected);\n });\n\n return createReportItem(specification, rule, ruleIndex, {\n target: matchingCanvas?.ref,\n status: matchingCanvas ? \"satisfied\" : \"missing\",\n displayLabel: rule.label || \"Canvas image service\",\n expected,\n message: matchingCanvas\n ? \"A canvas contains the required image service.\"\n : expected.length\n ? `A canvas must contain one of the required image services: ${expected.join(\", \")}.`\n : \"A canvas must contain a painting body with an image service.\",\n editorTarget: matchingCanvas\n ? createEditorTarget(matchingCanvas.ref, [\"items\"])\n : undefined,\n });\n}\n\nfunction evaluateThumbnailFromBodyService(\n specification: ManifestEditorSpecification,\n rule: Extract<\n SpecificationRule,\n { type: \"iiif:thumbnail-from-body-service\" }\n >,\n ruleIndex: number,\n resources: CollectedResource[],\n vault: Vault,\n): SpecificationReportItem[] {\n const entityType = rule.entityType || \"Canvas\";\n const targets = resources.filter((item) => item.ref.type === entityType);\n\n if (!targets.length) {\n return [\n createReportItem(specification, rule, ruleIndex, {\n status: \"not-applicable\",\n displayLabel: \"Thumbnail\",\n message: `No ${entityType} resources were found for thumbnail checks.`,\n }),\n ];\n }\n\n return targets.map(({ ref, resource }) => {\n const bodyServiceIds =\n entityType === \"Manifest\"\n ? resources\n .filter((item) => item.ref.type === \"Canvas\")\n .flatMap((item) =>\n getCanvasPaintingServiceIds(item.resource, vault),\n )\n : getCanvasPaintingServiceIds(resource, vault);\n const thumbnailMatches = thumbnailUsesBodyService(\n resource,\n bodyServiceIds,\n vault,\n );\n const hasThumbnail = hasMeaningfulValue(resource.thumbnail);\n\n return createReportItem(specification, rule, ruleIndex, {\n target: ref,\n path: [\"thumbnail\"],\n status: thumbnailMatches\n ? \"satisfied\"\n : !bodyServiceIds.length\n ? \"not-applicable\"\n : hasThumbnail\n ? \"invalid\"\n : rule.requireThumbnail === false\n ? \"not-applicable\"\n : \"missing\",\n displayLabel: getTerminologyLabel(\n [specification],\n ref.type,\n [\"thumbnail\"],\n \"Thumbnail\",\n ),\n expected: bodyServiceIds,\n actual: resource.thumbnail,\n message: thumbnailMatches\n ? \"Thumbnail uses the same image service as the painting content.\"\n : !bodyServiceIds.length\n ? \"No painting image service was found to compare against.\"\n : hasThumbnail\n ? \"Thumbnail does not use the same image service as the painting content.\"\n : \"Thumbnail must be created from the painting image service.\",\n editorTarget: createEditorTarget(ref, [\"thumbnail\"]),\n });\n });\n}\n\nfunction evaluateValidRights(\n specification: ManifestEditorSpecification,\n rule: Extract<SpecificationRule, { type: \"iiif:valid-rights\" }>,\n ruleIndex: number,\n resources: CollectedResource[],\n): SpecificationReportItem[] {\n const entityType = rule.entityType || \"Manifest\";\n const targets = resources.filter((item) => item.ref.type === entityType);\n const allowed = rule.allowed || [];\n\n return targets.map(({ ref, resource }) => {\n const value = resource.rights;\n const hasValue = hasMeaningfulValue(value);\n const valid =\n typeof value === \"string\" &&\n allowed.map(normaliseRights).includes(normaliseRights(value));\n\n return createReportItem(specification, rule, ruleIndex, {\n target: ref,\n path: [\"rights\"],\n status: valid\n ? \"satisfied\"\n : !hasValue && rule.required !== false\n ? \"missing\"\n : \"invalid\",\n displayLabel: getTerminologyLabel(\n [specification],\n ref.type,\n [\"rights\"],\n \"Rights\",\n ),\n expected: allowed,\n actual: value,\n message: valid\n ? \"Rights uses an allowed URI.\"\n : !hasValue && rule.required !== false\n ? \"Rights must use an allowed URI.\"\n : \"Rights is not one of the allowed URIs.\",\n editorTarget: createEditorTarget(ref, [\"rights\"]),\n });\n });\n}\n\nfunction evaluateRequiredStatement(\n specification: ManifestEditorSpecification,\n rule: Extract<SpecificationRule, { type: \"iiif:required-statement\" }>,\n ruleIndex: number,\n resources: CollectedResource[],\n): SpecificationReportItem[] {\n const entityType = rule.entityType || \"Manifest\";\n const targets = resources.filter((item) => item.ref.type === entityType);\n\n return targets.map(({ ref, resource }) => {\n const requiredStatement = resource.requiredStatement;\n const labelMatches = rule.label\n ? textValueMatches(requiredStatement?.label, rule.label)\n : hasMeaningfulValue(requiredStatement?.label);\n const mustHaveValue = rule.value || rule.valueRequired !== false;\n const valueMatches = rule.value\n ? textValueMatches(requiredStatement?.value, rule.value)\n : !mustHaveValue || hasMeaningfulValue(requiredStatement?.value);\n const hasStatement = hasMeaningfulValue(requiredStatement);\n\n return createReportItem(specification, rule, ruleIndex, {\n target: ref,\n path: [\"requiredStatement\"],\n status:\n labelMatches && valueMatches\n ? \"satisfied\"\n : hasStatement\n ? \"invalid\"\n : \"missing\",\n displayLabel: getTerminologyLabel(\n [specification],\n ref.type,\n [\"requiredStatement\"],\n \"Required statement\",\n ),\n expected: rule.value || rule.label,\n actual: requiredStatement,\n message:\n labelMatches && valueMatches\n ? \"Required statement is complete.\"\n : hasStatement\n ? \"Required statement does not match the specification.\"\n : \"Required statement must be filled in.\",\n editorTarget: createEditorTarget(ref, [\"requiredStatement\"]),\n });\n });\n}\n\nfunction evaluateMetadataTemplate(\n specification: ManifestEditorSpecification,\n rule: Extract<SpecificationRule, { type: \"iiif:metadata-template\" }>,\n ruleIndex: number,\n resources: CollectedResource[],\n): SpecificationReportItem[] {\n const entityType = rule.entityType || \"Manifest\";\n const targets = resources.filter((item) => item.ref.type === entityType);\n const results: SpecificationReportItem[] = [];\n\n for (const { ref, resource } of targets) {\n const metadata = Array.isArray(resource.metadata) ? resource.metadata : [];\n\n rule.items.forEach((template, itemIndex) => {\n const matchingItem = metadata.find((item: any) =>\n textValueMatches(item?.label, template.label),\n );\n const hasRequiredValue = template.value\n ? textValueMatches(matchingItem?.value, template.value)\n : template.valueRequired\n ? hasMeaningfulValue(matchingItem?.value)\n : true;\n const status: SpecificationReportStatus =\n matchingItem && hasRequiredValue\n ? \"satisfied\"\n : matchingItem && template.value\n ? \"invalid\"\n : \"missing\";\n const label = textValueToDisplay(template.label);\n\n results.push(\n createReportItem(specification, rule, ruleIndex, {\n idSuffix: `metadata-${itemIndex}`,\n target: ref,\n path: [\"metadata\"],\n status,\n displayLabel: label || \"Metadata\",\n expected: template.value || template.label,\n actual: matchingItem,\n message:\n matchingItem && hasRequiredValue\n ? `${label || \"Metadata\"} is present.`\n : matchingItem\n ? `${label || \"Metadata\"} needs a value.`\n : `${label || \"Metadata\"} metadata must be added.`,\n editorTarget: createEditorTarget(ref, [\"metadata\"]),\n }),\n );\n });\n }\n\n return results;\n}\n\nfunction createReportItem(\n specification: ManifestEditorSpecification,\n rule: SpecificationRule,\n ruleIndex: number,\n options: {\n idSuffix?: string;\n target?: Reference;\n path?: SpecificationPropertyPath;\n status: SpecificationReportStatus;\n displayLabel: string;\n message: string;\n expected?: SpecificationReportItem[\"expected\"];\n actual?: unknown;\n editorTarget?: SpecificationEditorTarget;\n },\n): SpecificationReportItem {\n const ruleId = rule.id || `${rule.type}-${ruleIndex}`;\n const suffix = options.idSuffix ? `-${options.idSuffix}` : \"\";\n\n return {\n id: `${specification.id}-${ruleId}-${options.target?.type || \"root\"}-${options.target?.id || \"none\"}${suffix}`,\n specificationId: specification.id,\n specificationLabel: specification.label,\n ruleId,\n ruleType: rule.type,\n ruleLabel: rule.label || options.displayLabel,\n ruleIndex,\n target: options.target,\n path: options.path,\n status: options.status,\n displayLabel: options.displayLabel,\n message: rule.message || options.message,\n expected: options.expected,\n actual: options.actual,\n editorTarget: options.editorTarget,\n };\n}\n\nfunction createEditorTarget(\n resource: Reference,\n propertyPath: SpecificationPropertyPath,\n): SpecificationEditorTarget {\n const firstProperty = propertyPath[0];\n return {\n resource,\n propertyPath,\n selectedTab:\n firstProperty === \"metadata\"\n ? \"@manifest-editor/metadata\"\n : firstProperty && descriptiveProperties.has(firstProperty)\n ? \"@manifest-editor/descriptive-properties\"\n : undefined,\n };\n}\n\nfunction countResults(\n results: SpecificationReportItem[],\n): Record<SpecificationReportStatus, number> {\n const counts = { ...emptyCounts };\n for (const result of results) {\n counts[result.status] += 1;\n }\n return counts;\n}\n\nfunction resolveResource(vault: Vault, input: any) {\n const ref = toReference(input);\n if (!ref) return input;\n\n try {\n return vault.get(ref as any, { skipSelfReturn: false } as any) || input;\n } catch {\n try {\n return vault.get(ref as any) || input;\n } catch {\n return input;\n }\n }\n}\n\nfunction toReference(input: any): Reference | null {\n if (!input || typeof input !== \"object\") return null;\n if (input.type === \"SpecificResource\")\n return {\n id: input.id || input.source?.id || \"\",\n type: \"SpecificResource\" as any,\n };\n if (typeof input.id === \"string\" && typeof input.type === \"string\") {\n return { id: input.id, type: input.type };\n }\n return null;\n}\n\nfunction getResourceChildren(resource: any): unknown[] {\n if (!resource || typeof resource !== \"object\") return [];\n\n const children: unknown[] = [];\n for (const key of [\n \"items\",\n \"structures\",\n \"annotations\",\n \"thumbnail\",\n \"provider\",\n \"homepage\",\n \"rendering\",\n \"seeAlso\",\n \"body\",\n \"target\",\n \"source\",\n ]) {\n const value = resource[key];\n if (Array.isArray(value)) {\n children.push(...value);\n } else if (value) {\n children.push(value);\n }\n }\n\n return children;\n}\n\nfunction getExpectedServiceIds(rule: {\n serviceId?: string;\n serviceIds?: string[];\n}) {\n return [\n ...(rule.serviceIds || []),\n ...(rule.serviceId ? [rule.serviceId] : []),\n ].filter(Boolean);\n}\n\nfunction serviceMatches(actual: string[], expected: string[]) {\n const actualSet = new Set(actual.filter(Boolean));\n if (!expected.length) return actualSet.size > 0;\n return expected.some((serviceId) => actualSet.has(serviceId));\n}\n\nfunction getCanvasPaintingServiceIds(canvas: any, vault: Vault): string[] {\n const pages = resolveReferenceList(vault, canvas?.items);\n const serviceIds: string[] = [];\n\n for (const page of pages) {\n const annotations = resolveReferenceList(vault, page?.items);\n for (const annotation of annotations) {\n const motivation = Array.isArray(annotation?.motivation)\n ? annotation.motivation\n : [annotation?.motivation];\n if (!motivation.includes(\"painting\")) continue;\n for (const body of normaliseBodies(annotation?.body, vault)) {\n serviceIds.push(...getImageServiceIds(body));\n }\n }\n }\n\n return Array.from(new Set(serviceIds));\n}\n\nfunction thumbnailUsesBodyService(\n resource: any,\n bodyServiceIds: string[],\n vault: Vault,\n) {\n const thumbnails = resolveReferenceList(vault, resource?.thumbnail);\n if (!thumbnails.length || !bodyServiceIds.length) return false;\n\n for (const thumbnail of thumbnails) {\n const thumbnailServiceIds = getImageServiceIds(thumbnail);\n const thumbnailId = typeof thumbnail?.id === \"string\" ? thumbnail.id : \"\";\n\n if (\n thumbnailServiceIds.some((serviceId) =>\n bodyServiceIds.includes(serviceId),\n )\n ) {\n return true;\n }\n\n if (bodyServiceIds.some((serviceId) => thumbnailId.startsWith(serviceId))) {\n return true;\n }\n }\n\n return false;\n}\n\nfunction normaliseBodies(body: any, vault: Vault): any[] {\n const resolved = resolveResource(vault, body);\n if (!resolved) return [];\n if (Array.isArray(resolved))\n return resolved.flatMap((item) => normaliseBodies(item, vault));\n if (resolved.type === \"SpecificResource\")\n return normaliseBodies(resolved.source, vault);\n if (resolved.type === \"Choice\")\n return (\n resolved.items?.flatMap((item: any) => normaliseBodies(item, vault)) || []\n );\n return [resolved];\n}\n\nfunction getImageServiceIds(resource: any): string[] {\n const service = resource?.service || resource?.services;\n const services = Array.isArray(service) ? service : service ? [service] : [];\n const ids: string[] = [];\n\n for (const item of services) {\n const id = typeof item === \"string\" ? item : item?.id || item?.[\"@id\"];\n if (typeof id === \"string\" && id) {\n ids.push(id);\n }\n }\n\n return Array.from(new Set(ids));\n}\n\nfunction resolveReferenceList(vault: Vault, value: any): any[] {\n if (!value) return [];\n const list = Array.isArray(value) ? value : [value];\n\n try {\n const resolved = vault.get(list as any);\n if (Array.isArray(resolved)) {\n return resolved.filter(Boolean);\n }\n } catch {\n // Fall through to resolving each item.\n }\n\n return list.map((item) => resolveResource(vault, item)).filter(Boolean);\n}\n\nfunction normaliseRights(value: string) {\n return value.replace(/^https:/, \"http:\").replace(/\\/?$/, \"/\");\n}\n\nfunction textValueMatches(\n actual: unknown,\n expected: SpecificationTextValue,\n): boolean {\n if (typeof expected === \"string\") {\n return textValues(actual).some((value) => value === expected);\n }\n return specificationJsonEquals(actual, expected);\n}\n\nfunction textValues(value: unknown): string[] {\n if (!value) return [];\n if (typeof value === \"string\") return [value.trim()].filter(Boolean);\n if (Array.isArray(value)) {\n return value.flatMap(textValues);\n }\n if (typeof value === \"object\") {\n return Object.values(value as Record<string, unknown>).flatMap(textValues);\n }\n return [];\n}\n\nfunction textValueToDisplay(value: SpecificationTextValue) {\n if (typeof value === \"string\") return value;\n return textValues(value)[0] || \"\";\n}\n\nfunction humanisePath(path: SpecificationPropertyPath) {\n const value = path[path.length - 1] || \"Property\";\n return value\n .replace(/([A-Z])/g, \" $1\")\n .replace(/[-_]/g, \" \")\n .replace(/^./, (letter) => letter.toUpperCase());\n}\n","import { createContext, type ReactNode, useContext, useMemo } from \"react\";\nimport { useVaultSelector } from \"react-iiif-vault\";\nimport { useAppResource } from \"../AppResourceProvider/AppResourceProvider\";\nimport {\n evaluateSpecifications,\n getPropertyPolicy,\n getTerminologyLabel,\n} from \"./SpecificationContext.helpers\";\nimport type {\n ManifestEditorSpecification,\n SpecificationPropertyPath,\n} from \"./SpecificationContext.types\";\nimport type { Reference } from \"@iiif/presentation-3\";\n\nconst SpecificationReactContext = createContext<ManifestEditorSpecification[]>(\n [],\n);\n\nexport function SpecificationProvider({\n children,\n specifications,\n}: {\n children: ReactNode;\n specifications?: ManifestEditorSpecification[];\n}) {\n const value = useMemo(() => specifications || [], [specifications]);\n\n return (\n <SpecificationReactContext.Provider value={value}>\n {children}\n </SpecificationReactContext.Provider>\n );\n}\n\nexport function useSpecifications() {\n return useContext(SpecificationReactContext);\n}\n\nexport function useSpecificationReport(rootRef?: Reference) {\n const appResource = useAppResource();\n const specifications = useSpecifications();\n const resolvedRootRef = rootRef || appResource;\n\n return useVaultSelector(\n (_state, vault) =>\n evaluateSpecifications(specifications, vault, resolvedRootRef),\n [specifications, resolvedRootRef.id, resolvedRootRef.type],\n );\n}\n\nexport function useSpecificationTerminology() {\n const specifications = useSpecifications();\n\n return useMemo(\n () => ({\n getLabel(\n entityType: string | undefined,\n path: SpecificationPropertyPath | string | undefined,\n fallback?: string,\n ) {\n return getTerminologyLabel(specifications, entityType, path, fallback);\n },\n }),\n [specifications],\n );\n}\n\nexport function useSpecificationPropertyPolicy(\n resourceRef: Reference | null | undefined,\n propertyPath: SpecificationPropertyPath | string,\n) {\n const specifications = useSpecifications();\n\n return useMemo(\n () => getPropertyPolicy(specifications, resourceRef, propertyPath),\n [\n specifications,\n resourceRef?.id,\n resourceRef?.type,\n JSON.stringify(propertyPath),\n ],\n );\n}\n","// TaskBridge.\nimport mitt, { Emitter } from \"mitt\";\nimport { createContext, ReactNode, useCallback, useContext, useEffect, useMemo, useReducer } from \"react\";\n\ninterface Task<Req = any, Res = any> {\n name: string;\n status: \"idle\" | \"running\" | \"complete\" | \"error\";\n emitter: Emitter<any>;\n promise: Promise<any>;\n abort: AbortController;\n resolve: (value?: any) => void;\n reject: (reason?: any) => void;\n error?: string;\n request?: Req;\n response?: Res;\n}\n\nconst tempGlobalState: Record<string, Record<string, Task>> = {};\n\nconst DispatchReactContext = createContext<string>(\"global\");\n\nfunction useCurrentDispatchId() {\n return useContext(DispatchReactContext);\n}\n\nfunction createDeferred() {\n let res: (value: any) => void = undefined as any;\n let rej: (reason?: any) => void = undefined as any;\n const promise = new Promise((resolve, reject) => {\n res = resolve;\n rej = reject;\n });\n\n return { promise, resolve: res, reject: rej };\n}\n\nexport function useTask(name: string) {\n const id = useCurrentDispatchId();\n const [, invalidate] = useReducer((r) => r + 1, 0);\n const task = useMemo(() => {\n if (!tempGlobalState[id]) {\n tempGlobalState[id] = {};\n }\n if (!tempGlobalState[id]![name]) {\n tempGlobalState[id]![name] = {\n name,\n emitter: mitt(),\n status: \"idle\",\n promise: Promise.resolve(),\n abort: new AbortController(),\n reject: () => void 0,\n resolve: () => void 0,\n };\n }\n\n return tempGlobalState[id]![name]!;\n }, [id, name]);\n\n useTaskEvent(task, \"abort\", invalidate);\n useTaskEvent(task, \"error\", invalidate);\n useTaskEvent(task, \"complete\", invalidate);\n useTaskEvent(task, \"running\", invalidate);\n\n return task;\n}\n\nexport function useTaskEvent<Req = any, Res = any>(\n task: Task<Req, Res>,\n name: string,\n _cb: (task: Task<Req, Res>) => any\n) {\n const cb = useCallback(() => _cb(task), [_cb]);\n useEffect(() => {\n const em = task.emitter;\n em.on(name, cb);\n return () => em.off(name, cb);\n }, [name, cb, task.emitter]);\n}\n\nconst noop = () => void 0;\n\nexport function useTaskDispatch<Req = any, Res = any>(\n name: string,\n onComplete?: (task: Task<Req, Res>) => void | Promise<void>\n) {\n const taskDetails = useTask(name);\n\n useTaskEvent(taskDetails, \"complete\", onComplete ? onComplete : noop);\n\n const runTask = (request?: any) => {\n // Abort running tasks.\n if (taskDetails.status === \"running\") {\n taskDetails.abort.abort();\n taskDetails.emitter.emit(\"abort\");\n }\n\n // Error clearing.\n if (taskDetails.error) {\n taskDetails.error = \"\";\n }\n\n // Creating new task.\n const d = createDeferred();\n d.promise.then(() => taskDetails.emitter.emit(\"complete\")).catch(() => taskDetails.emitter.emit(\"error\"));\n taskDetails.status = \"running\";\n taskDetails.request = request;\n taskDetails.promise = d.promise;\n taskDetails.resolve = d.resolve;\n taskDetails.reject = d.reject;\n taskDetails.emitter.emit(\"running\");\n };\n\n return [runTask, taskDetails] as const;\n}\n\nexport function useTaskRunner<Req = any, Res = any>(\n name: string,\n onRun: (task: Task<Req, Res>) => void | Promise<void>\n) {\n const taskDetails = useTask(name);\n\n useTaskEvent(taskDetails, \"running\", onRun);\n\n const completeTask = (response?: any) => {\n if (taskDetails.status === \"running\") {\n taskDetails.response = response;\n taskDetails.status = \"complete\";\n taskDetails.resolve();\n }\n //\n };\n\n const rejectTask = (reason?: any, error?: any) => {\n if (taskDetails.status === \"running\") {\n taskDetails.error = error || reason;\n taskDetails.status = \"error\";\n taskDetails.reject(reason);\n }\n };\n\n return [completeTask, taskDetails, rejectTask] as const;\n}\n\nexport function TaskBridge({ children }: { children?: ReactNode }) {\n return (\n <DispatchReactContext.Provider value={useMemo(() => `id-${Date.now()}`, [])}>\n {children}\n </DispatchReactContext.Provider>\n );\n}\n","import { HTMLAttributes, useCallback, useMemo } from \"react\";\nimport { UniversalCopyPasteProps } from \"./UniversalCopyPaste.types\";\n\n// @todo\nfunction analyse(t: any) {\n return false;\n}\n\nexport function UniversalCopyTarget<T>({\n as,\n reference: _ref,\n onReference,\n onLink,\n onAnalysis,\n onDropReference: _onDropReference,\n onDropLink: _onDropLink,\n onDropAnalysis: _onDropAnalysis,\n onPasteReference: _onPasteReference,\n onPasteLink: _onPasteLink,\n onPasteAnalysis: _onPasteAnalysis,\n ...props\n}: Partial<HTMLAttributes<HTMLElement>> & UniversalCopyPasteProps<T> & T) {\n // const vault = useVault();\n const Component = (as || \"div\") as any;\n\n const onDropReference = _onDropReference || onReference;\n const onDropLink = _onDropLink || onLink;\n const onDropAnalysis = _onDropAnalysis || onAnalysis;\n const onPasteReference = _onPasteReference || onReference;\n const onPasteLink = _onPasteLink || onLink;\n const onPasteAnalysis = _onPasteAnalysis || onAnalysis;\n\n const reference = useMemo(() => {\n return _ref;\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [_ref?.id, _ref?.type]);\n\n const onCopy = useCallback(\n function onCopy(e: ClipboardEvent) {\n if (e.defaultPrevented) {\n return;\n }\n e.preventDefault();\n if (e.clipboardData) {\n if (reference && reference.id && reference.type) {\n // const full = vault.get(reference);\n // if (full) {\n // e.clipboardData.setData(\"application/json\", JSON.stringify(vault.toPresentation3(vault.get(reference))));\n // }\n\n e.clipboardData.setData(\n \"application/json+vault\",\n JSON.stringify({\n id: reference.id,\n type: reference.type,\n })\n );\n }\n }\n },\n [reference]\n );\n\n const onPaste = useCallback(async function onPaste(e: ClipboardEvent) {\n if (e.defaultPrevented) {\n return;\n }\n e.preventDefault();\n if (e.clipboardData) {\n if (props.onLoading) {\n props.onLoading();\n }\n\n if (onPasteReference) {\n const data = e.clipboardData.getData(\"application/json+vault\");\n if (data) {\n try {\n const dataAsJson = JSON.parse(data);\n if (dataAsJson && dataAsJson.id && dataAsJson.type) {\n onPasteReference(dataAsJson);\n }\n } catch (e) {\n // ignore.\n }\n }\n }\n\n if (onPasteLink || onPasteAnalysis) {\n const data = e.clipboardData.getData(\"text\");\n if (data.startsWith(\"http\")) {\n const allLinks = data.split(\"\\n\");\n for (const link of allLinks) {\n if (onPasteAnalysis) {\n try {\n const result = await analyse(link);\n if (result) {\n onPasteAnalysis(result);\n continue;\n }\n } catch (e) {\n // let it fallback to onPasteLink\n }\n }\n if (onPasteLink) {\n onPasteLink(link);\n }\n }\n }\n }\n if (props.onComplete) {\n props.onComplete();\n }\n }\n }, []);\n\n // @todo not working..\n const onDragStart = useCallback(function onPaste(e: DragEvent) {\n if (e.defaultPrevented) {\n return;\n }\n e.preventDefault();\n if (e.dataTransfer && props.draggable) {\n e.dataTransfer.effectAllowed = \"all\";\n\n if (reference && reference.id && reference.type) {\n e.dataTransfer.setData(\n \"application/json+vault\",\n JSON.stringify({\n id: reference.id,\n type: reference.type,\n })\n );\n }\n }\n }, []);\n\n const onDrop = useCallback(async function onDrop(e: DragEvent) {\n e.preventDefault();\n if (e.dataTransfer) {\n if (onDropReference) {\n const data = e.dataTransfer.getData(\"application/json+vault\");\n if (data) {\n try {\n const dataAsJson = JSON.parse(data);\n if (dataAsJson && dataAsJson.id && dataAsJson.type) {\n onDropReference(dataAsJson, e);\n }\n } catch (e) {\n // ignore.\n return;\n }\n }\n }\n const json = e.dataTransfer.getData(\"application/json\");\n if (json) {\n const parsed = JSON.parse(json);\n // @todo this could be raw JSON or a Content State.\n return;\n }\n const link = e.dataTransfer.getData(\"text/plain\");\n if (link) {\n // console.log(\"link\", link);\n return;\n }\n }\n }, []);\n\n const onDragOver = useCallback((e: DragEvent) => {\n e.preventDefault();\n if (e.dataTransfer) {\n e.dataTransfer.dropEffect = \"copy\";\n }\n }, []);\n\n return (\n <Component\n onCopy={onCopy}\n onPaste={onPaste}\n onDrop={onDrop}\n onDragOver={onDragOver}\n onDragStart={onDragStart}\n tabIndex={-1}\n {...props}\n />\n );\n}\n"],"x_google_ignoreList":[0],"mappings":"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"}