Skip to content

Desktop: Fixes #14861: Restore window position and size after relaunch on Windows#15003

Open
gagansokhal-coder wants to merge 1 commit intolaurent22:devfrom
gagansokhal-coder:fix-window-state
Open

Desktop: Fixes #14861: Restore window position and size after relaunch on Windows#15003
gagansokhal-coder wants to merge 1 commit intolaurent22:devfrom
gagansokhal-coder:fix-window-state

Conversation

@gagansokhal-coder
Copy link
Copy Markdown

Fixes #14861

Problem

On Windows, when the Joplin window is snapped (docked) to the left or right, closing and reopening the app resets the window position and size.

Solution

Ensured that the correct window bounds are saved after snap by handling resize and move events and persisting final bounds.

Testing

Tested the following scenarios:

  • Left snap (Win + Left Arrow)
  • Right snap (Win + Right Arrow)
  • Manual resize
  • Maximized window

All cases correctly restore position and size after relaunch.

Notes

This change focuses on Windows behavior and does not affect macOS/Linux.

@github-actions
Copy link
Copy Markdown
Contributor

github-actions bot commented Apr 3, 2026

CLA Assistant Lite bot All contributors have signed the CLA ✍️ ✅

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Apr 3, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 8cca716c-2df6-4db1-b2a0-c7ba324b3bb2

📥 Commits

Reviewing files that changed from the base of the PR and between acd2ef4 and c24d1dd.

📒 Files selected for processing (1)
  • packages/app-desktop/ElectronAppWrapper.ts

📝 Walkthrough

Walkthrough

Added Windows-specific window state persistence logic to ElectronAppWrapper.ts. The change supplements the existing library's window state management by registering additional event listeners for resize, move, and close events that perform debounced saves and ensure immediate persistence before window closure.

Changes

Cohort / File(s) Summary
Window State Persistence
packages/app-desktop/ElectronAppWrapper.ts
Added debounced window state saving on resize/move events and immediate save on close event to ensure snapped window bounds are persisted before app termination, addressing timing issues with the existing library's closed handler.

Suggested labels

bug, desktop, windows


Important

Pre-merge checks failed

Please resolve all errors before merging. Addressing warnings is optional.

❌ Failed checks (1 error)

Check name Status Explanation Resolution
Pr Description Must Follow Guidelines ❌ Error PR description contains required content elements but lacks clearly delineated sections with explicit headers and visual separation. Add explicit section headers such as 'Problem:', 'Solution:', and 'Testing:' to clearly separate each required element into distinct sections.
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately describes the main change: fixing window position and size restoration on Windows after relaunch, which directly addresses the changeset's focus on persisting window state.
Description check ✅ Passed The description is relevant to the changeset, explaining the Windows snapping issue, the solution of handling resize/move events, and listing tested scenarios.
Linked Issues check ✅ Passed The pull request successfully addresses issue #14861 by implementing window state persistence for snapped windows on Windows through additional event listeners and debounced saves.
Out of Scope Changes check ✅ Passed All changes are scoped to the ElectronAppWrapper.ts file and focus solely on fixing Windows window state persistence, with no unrelated modifications detected.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai bot added bug It's a bug desktop All desktop platforms windows labels Apr 3, 2026
@gagansokhal-coder
Copy link
Copy Markdown
Author

I have read the CLA Document and I hereby sign the CLA

github-actions bot added a commit that referenced this pull request Apr 3, 2026
@gagansokhal-coder
Copy link
Copy Markdown
Author

recheck

Comment on lines +580 to +593
this.win_.on('close', () => {
// Cancel any pending debounced save and do a final immediate save
if (snapSaveTimer) {
clearTimeout(snapSaveTimer);
snapSaveTimer = null;
}
try {
if (this.win_ && !this.win_.isDestroyed()) {
windowState.saveState(this.win_);
}
} catch (_e) {
// Window may have been destroyed
}
});
Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is this needed?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This ensures that the final window position and size are saved when the app is closed.

Without this, when the window is snapped (e.g using Win + Arrow keys) the last updated bounds may not be persisted correctly because the debounced save might not execute before the app closes.

By handling the 'close' event, we cancel any pending debounced save and immediately persist the latest window state, ensuring the correct snapped position is restored on next launch.

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Without this, when the window is snapped (e.g using Win + Arrow keys) the last updated bounds may not be persisted correctly because the debounced save might not execute before the app closes.

"may not be" - under what condition that can happen?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This can happen when the window state is updated shortly before the app is closed, while the debounced save is still pending.

For example, when the user snaps the window (Win + Arrow keys), a resize/move event triggers the debounced save. If the user immediately closes the app before the debounce delay completes, the pending save may not run, so the latest bounds are not persisted.

In that case, the previously saved window state (before snapping) would be restored on the next launch instead of the snapped position.

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You mean if the user resize then close the window within 1 second? is it worth the extra code?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're right that this scenario happens only when the window is resized or snapped and then closed very quickly.

I added this to ensure consistency, especially for snap behavior, since users might expect the last visible state to always be restored.

However, I agree that if this is considered too edge-case or adds unnecessary complexity, we can simplify the approach or rely on the existing debounced save.

Happy to adjust or remove this part based on your preference.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug It's a bug desktop All desktop platforms windows

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Doesn't remember last docked location + size after relaunch

2 participants