A proposal. Introduces a focus cursor for code groups and codes on the codebook lens, mirroring the signal-card focus already shipped on Analysis — which is what gives every Codes command a target and makes the menu live again.
The retirement earlier today argued these commands had no target, citing the 29 Aug pin: “selection is single, it lives in the master list … no second place a thing can be ‘current’.” That reasoning was too strong. The pin governs selection — which codebook the detail pane renders. A focus cursor inside that pane is a different axis, and the codebase already models the two separately in two places.
FocusContext, the quote grid. Its own
docstring lists them as separate concerns: “Focus (keyboard cursor): at most one quote focused
at a time” and “Selection (multi-select): zero or more quotes selected for bulk actions”. The
Quotes lens has had both since the React migration, and nobody calls the focused quote a second
selection.AnalysisSignalStore.focusedKey, the signal cards.
A module-level store holding one nullable key, read by the card (bn-selected →
blue wash), the sidebar and the inspector. 40 lines. This proposal is that store again, with
two keys instead of one.One click on a group card’s background focuses it. Same gesture as a signal
card, same bn-selected wash, same clearing rules (click elsewhere, or Escape).
Focus is a cursor, not a mode: every existing direct-manipulation affordance keeps working
untouched.
Menus dim, never hide. Every row below is present in all four; only the enablement changes.
pencil ×4 and trash ×3 as the thinning candidates. Giving these
rows the obvious glyphs takes the app to pencil ×6 and trash ×5 — the menu bar’s two most
repeated symbols, on rows whose labels are already unambiguous. Tier 2 said the payoff of an
icon falls as its repeat count rises; this is that rule applied before the fact rather than
after.| Menu item | Twin on the page | Target | Enabled when |
|---|---|---|---|
| New Code Group | the New Group button | none — creation | floor page open |
| New Code | a group’s + Add code row | focused group | floor + group focused |
| Rename Code Group | click the group title | focused group | floor + group focused |
| Delete Code Group | the ✕ top-right of the card | focused group | floor + group focused |
| Rename Code | click the chip’s name | focused code | floor + code focused |
| Delete Code | hover the chip, click ✕ | focused code | floor + code focused incl. while renaming |
| Browse Codebooks | the Browse Library button | none — navigation | always, on the lens |
| Install / Uninstall Codebook | the page’s own Install ⇄ Uninstall button | the open codebook | detail page open not floor, not Sentiment |
canInstall on both the browse card and the detail page already excludes the
floor and Sentiment (D20). The menu mirrors that predicate rather than restating it..keyboardShortcut installs an NSMenu key equivalent, which is matched
before the responder chain — the same mechanism that forces Edit ▸ Undo to hide itself
while editing. So a ⌫ on Delete Code would steal the keystroke from the rename field the
proposal explicitly wants live. ⌘⌫ is already spent twice in Project. Recommendation: no
shortcuts at all in v1. A shortcut is a speed affordance, so the test
is demand for speed — not how important a command is, nor how advanced. Two
things earn one: often, in the main workflow (edit, delete, bring to
front), or spontaneously needed (Settings, Print — rare, but wanted
now). Nothing here passes either; every row is the twin of a control
already on screen, and nobody is in a hurry to open the codebook library. And
the size of the set is itself the value — a small set stays learnable, so each
addition taxes all of them. A draft gave Browse Codebooks ⇧⌘L,
which was invented, not derived: unclaimed across every Swift file and the web
layer, but free is not earned.focusedGroupId,
focusedTagId and which page is open on the Swift side — a new bridge payload
alongside focusedQuoteId. Per the house rule that is a two-file change plus the
fixture, and it is most of the work: the web half is one 40-line store and three handlers.TagSidebar/TagGroupCard on the Quotes lens and says hide “was
never a third axis here”. That was never a selection argument, so focus does not revive it.
G7/Q11 stay closed.