Skip to content

Restore windows to their macOS Spaces without switching Spaces - #6

Open
jeanmonet wants to merge 8 commits into
openprose:mainfrom
jeanmonet:codex/native-space-restoration-tahoe
Open

jeanmonet wants to merge 8 commits into
openprose:mainfrom
jeanmonet:codex/native-space-restoration-tahoe

Conversation

@jeanmonet

@jeanmonet jeanmonet commented Aug 23, 2026 •

Copy link
Copy Markdown

Summary

Margin's independent windows return to their saved macOS Spaces after a restart, while cold launch leaves the user's current Space active. If no restored window is on the current Space, Margin opens a temporary empty window there. Ordinary Space switching has no observer, polling, hidden-window creation, or activation work.

Display disconnects and resolution changes also preserve the window's preferred frame separately from its temporary fitted frame. For example, a large window moved from an external monitor to a laptop can shrink to fit, then recover its preferred size and display placement when the monitor returns. A smaller window is not enlarged to fill the display. A deliberate drag, live resize, or Zoom establishes a new preference.

Dependency

Depends on #5; merge that PR first. This branch includes its scratchpad/session commit plus seven follow-up commits (2068df2 through 035faeb). Both PRs are based on upstream v0.5.1.

Design and compatibility

  • The native Space backend is restricted to macOS 26, isolates private WindowServer/SkyLight calls in MarginPrivateSupport, verifies moves, and falls back when unavailable. The adapted code and license are credited in NOTICE; there is no supported public API for assigning windows to specific Spaces.
  • Cold launch prepares a current-Space window before promoting the app from accessory to regular activation. Deliberate Dock/Finder reopening uses AppKit's reopen event and follows native macOS activation behavior.
  • Display recovery uses one preferred frame per window group and coalesces physical-display notifications. It makes no activation or private Space-move calls, skips full-screen/minimized/actively resized windows, and does not treat Dock visibility or ordinary Space changes as a physical-display change. A user geometry action cancels pending fitting for that group.
  • Version-2 sessions gain an optional preferredFrame. Existing sessions load using their saved frame; older builds can still read the actual-frame field. Document, scratchpad, and CLI formats are unchanged.
  • User-facing notes remain under Unreleased. The base version remains 0.5.1 (11); the maintainer chooses the next release version.

Verification

For 035faeb, on macOS 26.6.2 / Apple M1 Pro:

  • Production build, signing, and make smoke passed, including CLI inspection/comparison and an isolated app launch.
  • make benchmark-matrix passed all five cases with three warm-ups and ten measured launches each. Worst visible-window p95: 400.330 ms (limit 500 ms). Worst target-ready p95: 1,209.997 ms (limit 1,250 ms). These are local development measurements, not a broad performance claim.
  • A standalone executable compiled against the production placement policy passed 40 synthetic disconnect/reconnect cycles, both notification orders, repeated captures, explicit user overrides, resolution changes, Dock/Space visibility changes, relaunch, and older-session decoding.
  • Added nine focused XCTest placement cases and extended the native tab-group test to cover preference sharing and explicit resize. make test could not run because this machine has Command Line Tools but no XCTest module/full Xcode; source parsing passed.
  • make check-version, signature verification, and git diff --check passed.

Earlier manual validation at 7e7082d covered two windows in separate Spaces, cold-launch placement, and cross-Space Firefox/Margin activation without focus stealing. The new physical unplug/replug behavior has not yet been manually validated; the existing installed app and its open session were left running during development. GitHub's fork workflows require maintainer approval.

Compatibility and safety

  • Ordinary Markdown remains authoritative; this change does not alter document writing.
  • App-only launch work is smoke-tested and measured.
  • CLI output, errors, and exit status are unchanged.
  • The optional session field has compatibility tests and documentation.
  • Generated files, private fixtures, credentials, and raw traces are excluded.
  • Each commit is signed off under the Developer Certificate of Origin.

Documentation

  • User-visible behavior, native activation tradeoff, and release implications are documented.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant