docs/target-app-parity.md listed the "Preferences that act" bullet three
times. Two older copies disagreed on Highlight Alternate Glyphs (one said
on by default, the code sets it off in Prefs::default) and still counted
about 14 stored options. The newest copy is kept, now with the Highlight
Alternate Glyphs clause (off by default), and its count names the two
options still stored only: Scratch Disks and the legacy vector clipboard.
The older of the two "Preferences audit (2026-10-30)" bullets, which still
listed five stored-only options, is removed, and the UI chrome summary row
now says 2 options, matching docs/gaps.md G12.
When the desktop portal's process exited while its save dialog was
open, no Response came. The stream that save_file read does not end
while the session bus stays up, so the save waited forever on the
calling thread and rfd's dialog never showed.
save_file now waits with the screen color sampler's Responses, which
moves from linux_screen_color/request.rs to portal_request.rs and is
built on Linux and the BSDs. Before the call it listens for the
Response and for the bus's NameOwnerChanged for the portal's name, so
the wait ends with an error when the connection that replied leaves
the bus, and the caller shows rfd's dialog, as for other portal errors.
When the bus reports the portal gone, the wait first reads the
Responses already queued, so an answer the portal sent before it left
is still the answer. Before, the sampler's wait could take the bus's
report while that answer was queued and end with an error.
The mock portal gains three modes that close its connection after the
reply: 300 ms later without a Response, at once without a Response,
and at once after the Response. The private bus helper of the
sampler's tests moves to portal_request.rs, and the save dialog's
tests use it, so a failing test also stops its bus.
file.newProfiles.edit and file.newProfiles.reset returned the automation
access check and file system errors with the profile file's whole path,
so a client confined to read roots that leave out the preferences folder
learned where the folder is. The errors now go through naming_in_error,
like other paths the client did not give: whole inside the read roots,
otherwise by file name. docs/mcp.md and the params text say so.
vectorcraft_testkit::temp_dir returns a bare path, so every engine test
that wrote into one left the folder in the system temporary folder.
- testkit: TempDir, a test's own folder made through temp_dir (same
private creation and ownership checks) under a tag no other TempDir in
the process uses, removed with its contents when dropped, also when
the test panics.
- Engine unit and integration tests hold a TempDir for the whole test
instead of calling temp_dir: graph, fileio, compare, journal, library,
shortcut set, spelling, store, web export, cancel, containers, build,
color settings, command sweep, font folder, removed font, model-based
and the font search fuzz.
- The DCS and swatch library tests' own helpers and the PDF editing
tests' shared vc-pdfedit-<pid> folder use a TempDir per test too.
- The font and link file search, store, color settings and font folder
helpers no longer delete the private folder temp_dir checked and make
it again with default permissions.
The widget's Constrain button was grayed out in Free Distort, and
neither it nor Shift changed a Free Distort corner drag. Constrain is
now available in Free Transform and Free Distort, and stays unavailable
in Perspective Distort.
With Constrain on, or Shift held, a corner dragged in Free Distort
moves only along the line through the opposite corner, in the box's
own proportions, and the other three corners stay in place. On a
turned box the line runs through the box's own corners. A box with no
size leaves the corner where it is. Cmd/Ctrl+Alt+Shift on a corner
still drags in Perspective Distort. The measurement label shows how
far the corner moved.
A Transform effect whose result would pass the geometry budget (2 million
anchors or 8 million lines drawn) is left out and the art stays where it
was, but the raster effects listed before it still scaled and moved with
it: before a Transform effect that scales the art 1000 times, a Drop
Shadow's offset grew 1000 times and its blur went to the 1000 pt limit
around art that had not moved, and Expand kept those values.
The geometry pass now notes each Transform effect that moves the art once
and that it leaves out, in the Carry it already returns, and
Carry::hide_skipped hides those effects in the list the raster effects
are read from. The canvas (a path's own effects and its fills' and
strokes'), its bounds, bake (SVG and PDF export), shape art, Expand,
Expand Appearance and Outline Stroke use it, and a fill's Transform
effect inside a piece no longer scales the effects before it when the
budget leaves it out. The budget itself is unchanged.
A path drawn as its own art inside a group whose geometry effects run
after its members' own read its object effects whole. The reshaping pass
now notes a Transform effect that no path in the art took past the
budget, and the member's art hides it before its raster effects are read.
The bounds skip the extra geometry pass when no raster effect could
follow a Transform effect, and painted_reach runs it once for both
measurements.
The Live Paint Selection tool always showed the plain arrow. Its cursor
now says what a click at the pointer selects, by the same rules as the
click (Alt, Select Fills, Select Strokes, locked, hidden and isolated
groups): the arrow with a filled square over a face, with a short line
between two anchor marks over an edge, and with an x where a click
selects no face or edge. From a press to the release the cursor keeps
the look it had at the press. Use Precise Cursors shows the crosshair.
- Cursor: LivePaintSelectFace, LivePaintSelectEdge and
LivePaintSelectOutside, with cursors.toml entries and drawn glyphs.
- Tests: live_paint_selection_cursor_shows_what_a_click_selects,
live_paint_selection_shows_the_arrow_with_a_face_edge_or_x_badge, and
the precise-cursor list.
Docs: docs/mcp.md, docs/target-app-parity.md.