BIG REFACTOR GPT SOL
feat: Refactor Iced panel adapter and introduce build metadata management - Updated Cargo.toml files across multiple crates to use workspace versioning. - Enhanced the `iced-panel-adapter` to include a new `plain_slider` module and updated widget rendering to support theme colors. - Added new theme color utilities for recessed and elevated surfaces in `iced-panel-adapter`. - Introduced a new `hcie-build-info` crate to manage build metadata, including a build ID system. - Created a build script to synchronize build IDs across the workspace. - Added a Makefile for simplified build commands for the Iced application. - Implemented regression tests for vector shape creation history in the engine API. - Added a new script for managing Cargo commands with synchronized build ID increments. - Updated line count report to reflect recent changes in codebase. - Created a visual plan document for future improvements in the Iced history and panel systems.
This commit is contained in:
@@ -0,0 +1,71 @@
|
||||
# Iced History, Panel, Visual, and Slider Improvements
|
||||
|
||||
## Scope And Decisions
|
||||
|
||||
- Target the Iced workspace under `hcie-iced-app/`; use `hcie-egui-app/` only as a behavioral/design reference.
|
||||
- Visual scope: shared design system plus main chrome (title/menu/sidebar/dock/dialogs) and History, Custom Shapes, and Brushes & Tips. Canvas rendering and AI/script plugin internals are out of scope.
|
||||
- Brush filters: `All`, `Drawing`, `Painting`, `Effects`, `Custom`, and `Imported`; combine built-in/default presets, every engine `BrushStyle`, and imported ABR presets. New custom-preset authoring/rename/delete is out of scope.
|
||||
- Slider input: typing a numeric character while hovering enters edit mode; Enter commits, Escape or focus loss cancels. Clicking the value area also enters edit mode.
|
||||
- First shape on a non-vector layer is one atomic `Add Vector Shape` history action; Undo removes the auto-created vector layer and shape together, Redo restores both.
|
||||
- Preserve all current uncommitted work and protected GPU/dirty-region behavior.
|
||||
|
||||
## Implementation Plan
|
||||
|
||||
1. **Make vector creation an atomic engine history operation.**
|
||||
- Temporarily unlock `hcie-document` and `hcie-engine-api` with the repository scripts; relock them after edits.
|
||||
- In `hcie-document/src/lib.rs`, add a documented vector-layer creation path that constructs the final vector layer (including its first shape) before recording history. Record one layer-add action whose captured redo layer is already `LayerType::Vector` and contains the shape; label it `Add Vector Shape`.
|
||||
- In `hcie-engine-api/src/lib.rs::Engine::add_vector_shape`, retain `push_vector_snapshot` for an existing vector layer. Replace the current non-vector path (`add_layer` followed by mutation) with the atomic document operation so no intermediate raster-layer history entry is created.
|
||||
- Ensure undo/redo/jump leave `active_layer` valid after the generated layer is removed/restored; clamp or restore selection through the existing engine history wrapper rather than changing protected compositing caches.
|
||||
- In `hcie-iced-gui/src/app.rs::VectorDrawEnd`, keep the single `add_vector_shape` call, then refresh cached layers/history through the existing composite refresh path. Add a small helper for refreshing `cached_history` if tests show no composite dirty flag after a history-only transition.
|
||||
- Add engine tests for: first shape on raster layer adds exactly one named entry; second shape on existing vector layer adds exactly one entry; undo/redo restores layer count, layer type, and shape count; cancelled/zero-result custom shape creates no entry. Add an Iced update-level regression test confirming `cached_history` exposes the new entry after `VectorDrawEnd`.
|
||||
|
||||
2. **Convert Custom Shapes from a list to a responsive grid.**
|
||||
- Refactor `hcie-iced-gui/src/panels/custom_shapes.rs` to build cards through `iced::widget::responsive`, deriving columns from available width rather than fixing a one-column list.
|
||||
- Use a theme-safe minimum cell width around 72–84 px, 4–6 px gaps, at least two columns when the pane permits, and row chunking that recomputes whenever dock width changes.
|
||||
- Keep SVG preview, readable label, selected accent border, click behavior, refresh button, path hint, and empty state. Truncate/wrap long labels without expanding a cell beyond the grid width.
|
||||
- Extract/test a pure `grid_column_count(available_width, cell_min, gap)` helper for narrow, normal, and wide panes.
|
||||
|
||||
3. **Build a complete, filterable Brushes & Tips catalog.**
|
||||
- Add a public GUI-side `BrushCategory`/filter type and transient `brush_category` state to `HcieIcedApp`, plus `Message::BrushCategorySelected` and `Message::BrushPresetSelected` as needed.
|
||||
- Replace the partial 22-entry `BRUSH_PRESETS` list in `panels/brushes.rs` with a canonical GUI catalog covering every currently exported `BrushStyle` variant, including inactive/missing styles such as Round, Square, Rock, Meadow, Wood, WetPaint, Dirt, Tree, Bristle, Mixer, Blender, and Bitmap.
|
||||
- Initialize built-in runtime presets from `BrushPreset::all_defaults()`, merge `ToolState.imported_brushes`, deduplicate by preset ID, and pass the resulting slices plus active category into `brushes::view` from `dock/view.rs`.
|
||||
- Port egui’s category mapping: Drawing = Basic/Sketch and drawing styles; Painting = Paint/Ink and painting styles; Effects = Texture/Effect/Nature/Mixer and effect styles; Custom matches custom presets; Imported matches Imported and Imported (ABR). Keep all six filter controls visible even when a category is empty.
|
||||
- Make category controls functional and visually selected; show an explicit empty-filter message. Imported ABR completion should switch to or visibly populate `Imported` without dropping existing entries.
|
||||
- Use responsive rows for style/preset cells, cached previews, selected styling, and tooltips. Selecting a preset applies its complete `BrushTip`/style data; selecting a style-only cell updates the style while retaining current size/opacity/hardness unless the egui reference explicitly applies a preset.
|
||||
- Add tests for exhaustive category mapping, imported/custom matching, deduplication, and filter state transitions.
|
||||
|
||||
4. **Introduce a shared Photoshop-inspired surface system.**
|
||||
- Extend `iced-panel-adapter/src/theme.rs::ThemeColors` with explicit recessed/elevated surface and shadow/highlight tokens, or documented derivation helpers, for every theme preset. Do not hard-code dark-only colors; use `is_light` and active theme tokens.
|
||||
- In `panels/styles.rs`, add reusable styles for recessed controls, raised cards/buttons, focused cards, pane headers, menus, and dialogs. Use a restrained 1 px highlight edge, low-contrast lower border, 2–6 px shadow blur, and 2–6 px corner radii; avoid heavy shadows on dense lists.
|
||||
- Apply the shared styles to title/menu/sidebar/dock headers and cards, common dialog surfaces, History rows, Custom Shape cards, and Brush filter/preset cells. Preserve the independent opaque surface layers already required to stay above the custom canvas shader.
|
||||
- Match the supplied Photoshop reference’s hierarchy: darkest workspace, mid-level panels, slightly raised headers/controls, compact typography, clear selected states. The “soft 3D” treatment should come from elevation/highlight/shadow, not large gradients or oversized rounded cards.
|
||||
- Capture before/after screenshots for the full viewport and each changed panel; verify both one dark and one light theme.
|
||||
|
||||
5. **Replace `plain_slider` with an event-aware custom Iced widget.**
|
||||
- Rewrite `hcie-iced-gui/src/widgets/plain_slider.rs` as a documented `iced::advanced::Widget` instead of the deprecated `Component`, because hover-triggered keyboard entry requires direct event/cursor handling.
|
||||
- Store editing/buffer state in the widget tree; support click/drag on the track, step increments in the right spinner area, hover-started numeric typing, click-to-edit, Enter commit, Escape/blur cancel, range clamping, decimal/comma parsing, suffix formatting, normalized percentages, and event capture while editing so global shortcuts do not fire.
|
||||
- Render a 22 px compact progress-bar control modeled on egui: theme-derived recessed track, subtle vertical gradient on the filled accent portion, narrow value handle, centered label/value, right-side up/down spinner, focus/hover border, and lightweight hover shadow. Derive every color from `ThemeColors`.
|
||||
- Preserve a builder/convenience API for label, range, step, suffix, decimals, width, optional logarithmic mapping, and optional snap steps. Keep parent-owned values and emit messages only for committed typing or pointer/spinner changes.
|
||||
- Add focused unit/widget tests for parsing, formatting, clamping, hover-to-edit, Enter/Escape/blur, percentage conversion, drag endpoints, spinner steps, logarithmic mapping, and theme-derived style output.
|
||||
|
||||
6. **Migrate every Iced slider call site.**
|
||||
- Replace existing `plain_slider` calls to pass `ThemeColors` and adopt the new API in dialogs (`new_image`, `confirm`, `adjustments`), properties, filters, layers, tool settings, and any other current users.
|
||||
- Replace direct `iced::widget::slider` calls in `color_picker.rs`, `toolbar.rs`, `tool_options.rs`, `geometry.rs`, `layer_styles.rs`, `brushes.rs`, `text_editor.rs`, and `status_bar.rs`, preserving ranges, steps, units, integer conversions, and compact layout requirements.
|
||||
- Update `iced-panel-adapter/src/lib.rs` so engine-described `WidgetDescription::Slider` also uses the same control and receives active theme colors through its render API.
|
||||
- Use compact labels for RGB/HSL/zoom sliders and avoid duplicated external labels where the new control already displays one. Confirm no raw slider imports/calls remain with a repository grep, except internal implementation details or explicitly documented non-numeric controls.
|
||||
|
||||
7. **Validation and regression protection.**
|
||||
- Run formatting and `git diff --check` without reverting unrelated work.
|
||||
- Run `cargo check -p hcie-iced-gui`, `cargo test -p hcie-iced-gui --tests`, and the relevant document/engine API tests.
|
||||
- Because locked engine crates are touched, run `cargo test -p hcie-engine-api --test visual_regression` and `cargo test -p hcie-engine-api --test performance_stroke_4k -- --nocapture`; confirm no protected pooling, cache, dirty-region, tile, or shader code changed.
|
||||
- Exercise vector creation on raster, vector, and locked-vector starting layers; confirm each successful creation adds one visible History row and Undo/Redo is exact.
|
||||
- Use built-in screenshot flows for `History`, `Custom Shapes`, and `Brushes & Tips`, plus full-viewport/dialog captures. Verify responsive grids at narrow/default/wide dock widths, all six brush filters, imported ABR visibility, dark/light themes, slider typing and dragging, and no transparency regression over the shader canvas.
|
||||
|
||||
## Risks And Guardrails
|
||||
|
||||
- The history fix crosses locked engine boundaries; use the sanctioned unlock/lock scripts and stage only intended files.
|
||||
- Do not emulate atomic vector history solely in the GUI or push a pixel snapshot; that would leave redo with the wrong layer type/content.
|
||||
- Keep brush preview generation cached; generating all style/preset thumbnails every frame would regress panel performance.
|
||||
- Hover typing must only start when the pointer is inside the slider and the text event is numeric; otherwise tool shortcuts remain unaffected.
|
||||
- Maintain the protected Iced shader layering and partial-upload mechanisms. New shadows/surfaces must be ordinary GUI layers above the shader, not changes to `shader_canvas.rs`.
|
||||
- No persisted-data migration is required: brush category and slider edit buffers are transient. Existing settings, imported brush behavior, dock layouts, and theme preset serialization remain compatible.
|
||||
Reference in New Issue
Block a user