asset details (WIP)

This commit is contained in:
bQUARKz 2026-03-19 14:18:23 +00:00
parent b07642f35c
commit 236fa04120
Signed by: bquarkz
SSH Key Fingerprint: SHA256:Z7dgqoglWwoK6j6u4QC87OveEq74WOhFN+gitsxtkf8
4 changed files with 615 additions and 449 deletions

View File

@ -0,0 +1,165 @@
# Palette Management in Studio Agenda
Status: Open
Domain Owner: `docs/studio`
Cross-Domain Impact: `docs/packer`
## Purpose
Define how palettes should be presented, identified, edited, and persisted in Studio without blurring the boundary between Studio UX ownership and packer data ownership.
This agenda is intentionally scoped to the `tile bank` form session.
It does not define a universal Studio pattern for every asset family that may expose previewable inputs.
## Problem
For `tile bank`, each `*.png` file in the asset should be treated as one tile, and each tile brings along a palette extracted during cache construction.
That extracted palette is part of the bank input model even if the developer did not author a separate palette document by hand.
In addition, the developer may add more palettes deliberately, up to a maximum of `64` palettes per bank.
Without a Studio decision for how those palette sources are presented and selected, implementation will guess at least one of the following incorrectly:
- whether extracted tile palettes are first-class selectable resources or only an implementation detail;
- how the user distinguishes tile-derived palettes, favorite palettes, and asset palettes;
- how the `up to 64 palettes` constraint is enforced and explained in the UI;
- whether default color loading means a palette starts as a full `16`-color color-key-backed candidate set and is then curated by the developer;
- whether Studio writes palette changes directly or routes them through packer.
## Context
The current Studio baseline already establishes a few useful constraints:
- the selected-asset view must expose `Inputs / Preview`, and palettes are explicitly listed as previewable materials in [`../specs/4. Assets Workspace Specification.md`](../specs/4.%20Assets%20Workspace%20Specification.md);
- the workspace should help the user inspect real project materials rather than force raw JSON or filesystem inspection;
- Studio should not invent persistence rules locally when packer already owns authoritative asset state and mutation flows.
The product direction discussed so far is more concrete than a generic palette browser:
- every `*.png` input of a `tile bank` is one tile;
- each tile yields one extracted palette during cache construction, replacing the older mental model of standalone `file.palette.json` sidecars;
- each bank may integrate at most `64` palettes;
- each palette contains `16` colors and should load with a default color-key baseline;
- the developer should be able to inspect palettes coming from at least three sources:
- palettes extracted from tiles;
- favorite palettes;
- asset palettes;
- from that combined candidate set, the developer chooses which palettes become part of the bank.
What remains open is not the existence of palette management, but the Studio interaction model around this curation flow.
The current discussion has also converged on a simpler first-wave UI shape:
- the left side should use a `transfer list` with custom palette rendering;
- candidate items should show the palette swatch plus stacked source icons when the same palette matches multiple origins;
- the bank selection must stay within `1..64` selected palettes;
- the right side should expose a compact tile-preview panel with:
- a file/tile selector at the top;
- the tile preview in the middle;
- the applied palette strip at the bottom.
That shape should be treated as `tile bank`-specific.
Other asset families may need different form sessions and different preview/application models.
## Current Code Context
Normative Studio docs already cover shell structure, selected-asset details, and preview expectations, but there is no dedicated Studio decision for palette lifecycle in `tile bank`.
That means the shell can host palette management, but the product model for palette-source aggregation, curation, and bank admission is still open.
## Options
1. Treat extracted tile palettes as implicit data only, and let the bank integrate them automatically without explicit curation.
2. Treat the bank palette set as an asset-scoped curated selection built from multiple palette sources, with Studio orchestrating selection and packer owning persistence.
3. Treat palettes as a fully Studio-owned library/workspace with direct local editing and direct persistence.
## Tradeoffs
1. Automatic integration is cheap, but it removes deliberate bank curation, hides the `64`-palette budget, and makes it harder to reason about favorites, reusable palettes, and intentional bank composition.
2. An asset-scoped curated selection aligns with the concrete bank model: the developer sees candidate palettes from tiles, favorites, and asset-level sources, then chooses which ones enter the bank. The tradeoff is that the Studio must explain source, capacity, and duplicate/conflict behavior clearly.
3. A fully Studio-owned palette workspace may look flexible, but it duplicates persistence rules, risks divergence from packer/cache construction, and creates a second authority for bank composition.
## Recommendation
Adopt the asset-scoped curated-selection model.
Studio should treat palette management as a first-class `tile bank` workflow, but not as a new independent persistence authority.
### Baseline Direction
- the palette admission surface should belong to the `tile bank` asset workflow;
- Studio should aggregate candidate palettes from tile-derived extraction, favorites, and asset palettes into one curation surface;
- the left side should use a custom-rendered `transfer list` to move palettes into or out of the bank selection;
- the user should explicitly choose which palettes enter the bank, with a fixed `1..64` selected range;
- each candidate palette should expose its source and stable identity clearly enough for inspection and deduplication decisions;
- packer should remain authoritative for extraction, identity, validation, and persistence;
- Studio should own the curation UX, including selection state, tile preview state, capacity feedback, and staged mutation review.
### First-Wave Scope Recommendation
The first wave should prioritize a management-oriented bank-composition experience:
- list tile-derived palettes explicitly in the selected `tile bank` asset details;
- allow inspection of each palette's `16` colors with the default color-key baseline visible;
- aggregate candidate palettes from the supported sources into one transfer-list surface;
- render each palette item with:
- stacked source icons when the same palette matches multiple origins;
- a `16`-swatch horizontal palette strip;
- allow the user to move palettes from the candidate side into the bank `selected` side, with a visible `1..64` constraint;
- expose a compact preview panel on the right side with:
- a tile/file combobox at the top;
- a tile preview surface in the middle;
- a palette strip at the bottom representing the palette currently applied in the preview;
- render the chosen tile preview by applying the currently previewed selected palette to the tile's index matrix;
- defer broad standalone palette-authoring workflows until the bank-composition and persistence contract is closed.
### Preview-State Baseline
The first wave should keep preview behavior simple.
The palette transfer list defines the bank's `selected palettes`.
The right-side preview panel should always render one of the selected palettes, with the following baseline:
- when the `selected palettes` set is first created or rebuilt, the first selected palette is used by default in the preview;
- clicking a palette in the `selected` side updates the palette currently shown in the preview;
- changing the previewed palette must not reorder or otherwise mutate the bank selection by itself;
- the preview must always use a palette that belongs to the current `selected palettes` set;
- if the currently previewed palette is removed, the preview falls back to the first remaining selected palette.
### Why This Direction
This keeps the Studio honest about its role.
The Studio should make bank palette composition understandable and operationally safe, but it should not silently become the source of truth for extraction logic or persisted bank data.
It also keeps the Studio honest about family-specific UX.
`Tile bank` has a concrete palette-composition workflow tied to tile index matrices and palette admission limits.
That does not imply that `audio`, `text`, or other asset families should inherit the same transfer-list and active-preview interaction model.
## Open Questions
1. How should Studio detect and present duplicate or near-equivalent palettes across tile-derived, favorite, and asset-level sources?
2. Are favorites project-scoped references to existing palettes, or can they diverge into editable copies before bank admission?
3. What is the canonical user-facing identity of a candidate palette in Studio: source bucket plus logical name, file path, extraction origin tile, stable id, or a combination?
4. Should extracted tile palettes always enter the candidate set automatically, or can the developer suppress some of them before curation?
5. Should clicking a palette on the `selected` side be the only interaction needed to change the previewed palette in the first wave?
6. Which palette operations are read-only in the first wave, and which require staged preview/apply treatment?
7. Which parts of this interaction model should remain explicitly `tile bank`-specific, and which parts are reusable Studio form-session primitives?
8. Does the first release need only an asset-scoped `tile bank` section, or also a project-level palette browser for discovery and favorites management?
## Next Suggested Step
Turn this agenda into a `decision` that closes four points:
1. the palette ownership boundary between Studio and packer;
2. the source model for candidate palettes in `tile bank`;
3. the first-wave asset-scoped `transfer list` UX and `1..64` capacity behavior;
4. the right-side preview-panel behavior for tile/file selection, tile rendering, and palette-strip display;
5. the boundary between `tile bank`-specific form-session behavior and reusable Studio primitives;
6. the minimum mutation model for preview, apply, favorites, and cross-asset visibility.

View File

@ -4,6 +4,7 @@ This directory contains active Studio discussion agendas.
Active agendas: Active agendas:
- [`Palette Management in Studio Agenda.md`](./Palette%20Management%20in%20Studio%20Agenda.md)
- [`Asset Bank Composition Area - Dual List and Capacity Meter Agenda.md`](./Asset%20Bank%20Composition%20Area%20-%20Dual%20List%20and%20Capacity%20Meter%20Agenda.md) - [`Asset Bank Composition Area - Dual List and Capacity Meter Agenda.md`](./Asset%20Bank%20Composition%20Area%20-%20Dual%20List%20and%20Capacity%20Meter%20Agenda.md)
- [`Agenda-01-Asset-Bank-Composition-Snapshot-Transfer-to-Details-DTOs.md`](./Agenda-01-Asset-Bank-Composition-Snapshot-Transfer-to-Details-DTOs.md) - [`Agenda-01-Asset-Bank-Composition-Snapshot-Transfer-to-Details-DTOs.md`](./Agenda-01-Asset-Bank-Composition-Snapshot-Transfer-to-Details-DTOs.md)
- [`Agenda-02-Asset-Bank-Composition-Base-Components.md`](./Agenda-02-Asset-Bank-Composition-Base-Components.md) - [`Agenda-02-Asset-Bank-Composition-Base-Components.md`](./Agenda-02-Asset-Bank-Composition-Base-Components.md)

View File

@ -48,6 +48,171 @@
"message" : "Asset scan started", "message" : "Asset scan started",
"severity" : "INFO", "severity" : "INFO",
"sticky" : false "sticky" : false
}, {
"source" : "Studio",
"message" : "Project ready",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Studio",
"message" : "Project loading started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Studio",
"message" : "Project opened",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan diagnostics updated.",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bla",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bbb2",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan diagnostics updated.",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bla",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bbb2",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan diagnostics updated.",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bla",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bbb2",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, { }, {
"source" : "Assets", "source" : "Assets",
"message" : "7 assets loaded", "message" : "7 assets loaded",
@ -2333,169 +2498,4 @@
"message" : "Discovered asset: ui_atlas", "message" : "Discovered asset: ui_atlas",
"severity" : "INFO", "severity" : "INFO",
"sticky" : false "sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan diagnostics updated.",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bla",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bbb2",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan diagnostics updated.",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bla",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bbb2",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan diagnostics updated.",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bla",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: one-more-atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: bbb2",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: ui_atlas",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Discovered asset: Bigode",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "Asset scan started",
"severity" : "INFO",
"sticky" : false
}, {
"source" : "Assets",
"message" : "7 assets loaded",
"severity" : "SUCCESS",
"sticky" : false
} ] } ]

File diff suppressed because it is too large Load Diff