icons: cmux custom family (polished)
Closed
LU
7d ago+388+388+012345678901234567890123456789-15-15-01234567890123456789
Summary
a cmux custom icon family behind a new Debug Settings choice, Icons: Family (icons.family, under Shape and Icons), so the team can try it in the app and flip back. the default stays pack, so nothing changes unless someone picks cmux custom.
the family redraws 37 pack names in the agent chat's own recipe: 1.5 line, round caps and joins, 3-unit corners on the 24 grid, line at rest and a filled solid with the details cut out (the chat's eyes, the terminal prompt). the agent chat itself is unchanged. a few that read differently:
- App Store: a shopping bag with the cmux prompt on its front, so it says "store" and "cmux apps", not browser extensions
- folder: Untitled UI's folder (free set), scaled to the same live area
- new chat: the agent bubble with a plus on its shoulder; workspace: an open tray; settings: a toothed gear; diff: a page with ±
how it's wired:
design/icons/source-custom/custom.jsonholds the drawings.build_pack.pybuilds them into an overlay pack next to the shipped one (cmux-icons-custom.jsonnative,cmuxIconsCustom.jsonweb) and fails if an overlay name isn't in the pack.- native:
IconPack.bundledlays the overlay over the shipped pack when the app asks (IconPack.useOverlay). the tunable store loads its file off the main actor, after the first icons draw, soDebugSettingsServicereadsicons.familyfrom the file itself at launch. a change applies after a relaunch. - web:
AgentPaneTunables.documentAttributessetsdata-icon-family="custom", anduseIcons()swaps in the custom pack while it's set. it subscribes to the attribute, so a pooled page that learns it when claimed redraws.
notes for review:
- sidebar toggle and the up/down arrows are drawn too but left out of the overlay here: those names aren't in the pack on this base (the titlebar still draws SF Symbols). a follow-up can add them with the titlebar moving to the pack.
- the shots are crops (3x) from the design playground, which also has separate switches on that aren't in this PR: workspace rows lead with a folder (
sidebar.workspaceIcon, so before shows the chat bubble there) and the New Tab create actions are outlined pills (the Cursor top strip style). what this PR changes is the drawings: the house, the bag with the prompt, the folder glyph, the terminal, browser and chat icons. - Untitled UI's free license allows commercial use and forbids redistributing their icons as a set; one folder inside the app reads as fine, flagging it anyway.
| Before (sidebar, 3x) | After (sidebar, 3x) |
|---|---|
| Before (New Tab create actions, 3x) | After (New Tab create actions, 3x) |
|---|---|
Testing
bun test src/agent-session/acpmux/icons/: 2 pass (pack outputs match the sources, the overlay only redraws names the pack has, the merged pack takes the overlay's drawings)bunx vp checkon the icon files andvite.config.ts: formatting, lint and types passpython3 scripts/icons/build_pack.py --check: up to date./scripts/lint-ios-package-conventions.sh: ok- native: the same change built and ran in a tagged dev build on an older base (the playground), where the custom icons showed in the sidebar, tab strip and New Tab page after a relaunch. this branch's Swift (the
documentAttributeshookup is new here) was not built locally.IconFamilyAttributeTestsandIconFamilyLaunchTestsrun in CI, not run locally. - localization: no user-facing strings; the only new text is the Debug Settings label and choice titles, DEV/NIGHTLY only
Changelog
none
Need help on this PR? Tag @codesmith-bot with what you need.