Kickoff: Styling System Overhaul
- Dominant language
- TypeScript
- Stars
- 481
- Forks
- 108
- Avg merge
- 6d 8h
- Merged PRs (30d)
- 5
Description
> [!NOTE]
> **Kickoff — Wayfinder not yet run, no chart yet.** This is the placeholder child of the **Styling System Overhaul** initiative (#2005), holding a brain dump of paths to explore and potential blockers until scoping happens. "Placeholder" means only that there's no chart — the content below is real. Run `/wayfinder` against the initiative to create the map; **this kickoff closes when that map is created**, and the map takes over the scoping route.
## Rough intent
Decide **the future of the Graph Explorer styling system from the user's perspective** — what a style *is*, how users edit one, and where the editing controls live. The eventual destination (a spec to hand off? a locked decision on sidebar-vs-settings? both?) is named when the map is charted.
## Notes
- **Domain:** graph styling — how vertices/edges are visually styled on the Graph View and Schema View canvas.
- **Skills to consult when charting:** `/wayfinder` to chart; `/prototype` for the UI-shape questions; `/domain-modeling` for the style vocabulary.
- **Interrelated:** the *model* determines what the dialogs and sidebar edit, so it likely gates the UI work rather than running beside it.
- **Current style model (start here, don't re-derive it):** a style is raw Cytoscape values stored per type, resolving through a **single user layer** over the app defaults — `{ ...appDefault, ...userCustom.get(type) }`. The multi-source "shared styles" layer was deleted before it shipped (#1974 / #1981), so there are exactly two Sources: **App** (hardcoded) and **User**. #1881 adds a type-less **user default** between them, making it three layers; it is **open**, not shipped.
- **Settled vocabulary (inherit it, don't reopen it):** **Default styles** names the user's type-less tier in the UI; **Clear Customization** is the destructive action in both style dialogs; **Clear All Style Customizations** is the Settings bulk clear. "Default" appears in UI copy only as the subject of the user's tier, never on a destructive control, and the "app" qualifier stays internal. See #1881's Style Vocabulary section.
## Paths to explore
Educated guesses at what needs investigating. Each notes its likely ticket type — the charting session confirms, splits, or drops them.
- **Style model / abstraction layer** *(research + grilling)* — Today a "style" is raw Cytoscape values (a hex color, a border width) stored per type. Should styles instead describe **intent** ("emphasized", "muted", a palette slot, a coordinated theme) with the system computing the Cytoscape values? How does an intent-based model layer onto the **single user style layer** (`{ ...appDefault, ...userCustom }`, soon `{ ...appDefault, ...userDefault, ...userCustom }` via the open #1881), and onto the typed element contract planned in #1891? *(Absorbs the model questions from the superseded #1944.)*
- **Presets** *(grilling)* — what preset vocabulary do we offer (color palettes, coordinated themes, shape sets), and how does a preset interact with per-type overrides and the styling file format?
- **Label options** *(grilling)* — which additional label style options are worth offering (placement, background, size, wrapping), and what do they require from the rendering layer?
- **Migration** *(research)* — how do existing stored styles and saved styles files map into a new model without breaking users? *(Absorbs migration questions from #1944.)*
- **Style dialog redesign** *(prototype)* — the legacy per-type dialog layout is dated. What's the redesigned layout and interaction: how is the live preview presented, how do the Default dialog and per-type dialog relate visually, is the shape catalog curated? *(Absorbs #1885. The dialog can't be finalized until the model is decided — it edits whatever the model defines.)*
- **Style sidebar rethink** *(prototype)* — the current styles sidebar is nearly useless. Redesign it in place, **or** move its options into the **Settings page**? This is the key sidebar-vs-settings decision.
- **Show all styles + quick options / full-page style settings** *(prototype)* — currently only styles for the *current schema's* types are shown. Should we show **all** available styles for all types, with **quick options** for common changes (color, icon, node label, edge label)? A candidate form is a **full-page style-settings view** rather than the current sidebar. Entangled with the sidebar-vs-settings decision above.
- **User-defined default styles** *(grilling)* — let a user define their own default node/edge style as a baseline applied to every type. **Already specified, not yet built:** #1881 (Epic, three-layer cascade) and its slice #1884 (the type-less Default tier), both rewritten for the single-layer model and carrying the settled vocabulary. Scoping should build on these rather than reinvent them, and should treat the Default tier as arriving independently of this initiative.
- **Tokenized label definitions** *(prototype)* — let node/edge labels be defined as templates that interpolate property values (e.g. `{name} ({type})`) rather than picking a single property. What's the token syntax, and what does it need from the rendering layer?
- **Edge weights by property** *(prototype)* — drive an edge's visual weight (thickness, and possibly layout influence) from a numeric property value. A specific case of property-based visual encoding; coordinate with #1785.
## Potential blockers & pitfalls
Educated guesses at what could block the initiative — or block a *particular* way of implementing it. Captured from v3.3 planning so charting doesn't re-derive them.
- **Dependency order (blocks a path):** the model gates the UI. Prototyping dialogs/sidebar before the model is decided risks designing controls for a style shape that then changes. Charting should sequence model-first (or fold model discovery into the first prototype).
- **Migration (first-class risk):** any new model must convert existing stored styles and saved styles files without breaking current users (see the styles file format ADR, and #1881's `defaults` section once it lands).
- **Styles file cross-cut:** a saved styles file must carry whatever the new model produces, and the selective import modal must be able to show it as a before-and-after the user can accept or decline (relates to #1972).
- **Cytoscape rework cross-cut:** the style model should target the typed element contract from the Cytoscape deep-module work (#1891), not fight it.
- **Property-based styling (#1785):** a candidate consumer of the new model — keep in view so the model doesn't preclude it.
## Related / superseded issues
- **Supersedes #1944** (Spike: scope the revamped style system) — its model/presets/label/migration questions are folded into the paths above.
- **Supersedes #1885** (Spike: visual redesign of the style dialogs) — its dialog-redesign questions are folded in.
- Related: #2005 (initiative), #1943 (roadmap), #1881 (Default Styles Epic — three-layer cascade, open), #1884 (the type-less Default tier slice, open), #1883 (style dialog form-schema foundation, open), #1891 (Cytoscape deep module), #1785 (property-based styling).
- Model context: #1974 and #1981 (collapse to a single user style layer — the reason the Source × Scope framing is gone), #1972 (selective style import modal, shipped).
> [!IMPORTANT]
> Internal only — this issue is maintained by the core team and is not accepting external contributions.
Contributor guide
Assessment
This issue has not been assessed yet.