Conversation
… height of template dropdown to eliminate layout shift when there are less number of items in the list
Contributor
There was a problem hiding this comment.
Pull request overview
This PR adds local session snapshot persistence and a resume/discard modal to avoid losing in-progress editor state, while also improving template browsing UX (skeleton loaders) and tightening a few UI behaviors (auto-save rules, gradient picker safety, sidebar layout).
Changes:
- Added local session snapshot persistence (localStorage) and a
ResumeSessionModalflow, including store support for restoring persisted state. - Improved template library/dropdown loading UX using skeleton placeholders.
- Prevented auto-save from creating new templates when no template is active, and hardened gradient preview parsing against incomplete inputs.
Reviewed changes
Copilot reviewed 14 out of 14 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
| packages/imagekit-editor-dev/src/store.ts | Adds restoreSession action to hydrate resumable editor state into the store. |
| packages/imagekit-editor-dev/src/persistence/editorSessionStorage.ts | Introduces versioned localStorage schema + read/write helpers for session snapshots. |
| packages/imagekit-editor-dev/src/ImageKitEditor.tsx | Detects resumable sessions and renders the resume/discard modal; pauses persistence while modal is open. |
| packages/imagekit-editor-dev/src/hooks/useTemplateSync.ts | Prevents auto-save paths from creating new templates when templateId is null. |
| packages/imagekit-editor-dev/src/hooks/usePersistedEditorSession.ts | Subscribes to editor changes and persists snapshots to localStorage (debounced). |
| packages/imagekit-editor-dev/src/hooks/usePersistedEditorSession.test.tsx | Adds tests for pause/unpause behavior of local session persistence. |
| packages/imagekit-editor-dev/src/components/templates/TemplatesLibraryView.tsx | Replaces spinner-only loading state with a richer skeleton table placeholder. |
| packages/imagekit-editor-dev/src/components/sidebar/sortable-transformation-item.tsx | Adjusts rename layout and reserves action space to reduce layout shift. |
| packages/imagekit-editor-dev/src/components/header/TemplateStatus.test.tsx | Adds coverage to ensure auto-save doesn’t create templates on blank slate. |
| packages/imagekit-editor-dev/src/components/header/TemplatesDropdown.tsx | Adds loading skeleton rows and minor sizing tweaks for dropdown content. |
| packages/imagekit-editor-dev/src/components/editor/ResumeSessionModal.tsx | New modal prompting restore/discard of a detected unsaved session snapshot. |
| packages/imagekit-editor-dev/src/components/editor/layout.tsx | Wires in session persistence hook with a pause flag. |
| packages/imagekit-editor-dev/src/components/editor/index.tsx | Exports ResumeSessionModal. |
| packages/imagekit-editor-dev/src/components/common/GradientPicker.tsx | Makes gradient preview generation resilient to incomplete/invalid hex inputs. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Comment on lines
+139
to
+148
| const [resumeSession, setResumeSession] = | ||
| useState<PersistedEditorSession | null>(null) | ||
|
|
||
| React.useEffect(() => { | ||
| const resumableSession = readEditorSessionFromLocalStorage( | ||
| EDITOR_SESSION_STORAGE_KEY, | ||
| ) | ||
| if (!resumableSession) return | ||
| setResumeSession(resumableSession) | ||
| }, []) |
Comment on lines
+80
to
+93
| function isValidSessionState(x: unknown): x is PersistedEditorSessionState { | ||
| const v = x as Record<string, unknown> | null | ||
| return ( | ||
| !!v && | ||
| typeof v === "object" && | ||
| Array.isArray(v.transformations) && | ||
| typeof v.visibleTransformations === "object" && | ||
| typeof v.templateName === "string" && | ||
| (typeof v.templateId === "string" || v.templateId === null) && | ||
| (typeof v.templateIsPrivate === "boolean" || | ||
| v.templateIsPrivate === null) && | ||
| typeof v.isPristine === "boolean" && | ||
| typeof v.localChangeVersion === "number" && | ||
| typeof v.lastSyncedVersion === "number" |
Comment on lines
+231
to
+235
| minW="14" | ||
| justifyContent="flex-end" | ||
| opacity={isHover && !isRenaming ? 1 : 0} | ||
| pointerEvents={isHover && !isRenaming ? "auto" : "none"} | ||
| transition="opacity 0.15s" |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This pull request introduces a new session resumption flow to the ImageKit Editor, improves the user experience in the template dropdown, and fixes several UI consistency issues. The most significant change is the addition of a modal that prompts users to restore or discard unsaved session data, ensuring that work is not lost unexpectedly. Additionally, the template dropdown now displays skeleton loaders while fetching data, and there are improvements to gradient picker robustness and sidebar UI.
Session persistence and resumption:
ResumeSessionModalcomponent that appears when unsaved editor session data is detected, allowing users to restore their previous session or start a new one. This includes new logic inImageKitEditor.tsxto detect and manage resumable sessions, and updates toEditorLayoutand context providers to pause session persistence while the modal is open. [1] [2] [3] [4] [5] [6] [7] [8]Template dropdown UX improvements:
Editor auto-save and session logic:
Gradient picker robustness:
Sidebar and transformation UI: