From b4b9464bdd7dad4eed935f40fc8335d2da4d4cb9 Mon Sep 17 00:00:00 2001 From: meleki Date: Sat, 3 Oct 2026 21:45:43 +0200 Subject: [PATCH] Drag variables, fields, ports and list items into order (#310) Behaviors gets an entry Reordering. The mark in front of a row is the grip, a drag starts after 4 px, rows move among siblings only, and every move is one undo step. - Structs: fields of a Struct asset are dragged there, typed copies and Pack/Expand follow. - Architecture: sortBlocks and the pure rules in ui/sortable.ts. - Development: e2e sum 1739. Co-Authored-By: Claude Opus 5.5 --- Architecture.md | 4 ++-- Behaviors.md | 12 ++++++++++++ Development.md | 2 +- Structs.md | 3 +++ 4 files changed, 18 insertions(+), 3 deletions(-) diff --git a/Architecture.md b/Architecture.md index feb0f95..96cdc3c 100644 --- a/Architecture.md +++ b/Architecture.md @@ -169,7 +169,7 @@ src/runtime/physics/ engine (loads Rapier once, reports its state, converts be src/ui/ widget toolkit (generic, knows nothing about assets); fonts (the faces the editor ships: Source Sans 3 in 400, 500 and 600, Source Code Pro 400, Latin only, #202/#214/#273), icons + Icon (the menu's tick boxes and current-entry dot as SVG files, and a widget that shows one file - on its own: a symbol the Latin subset lacks is never written as a character, #214); SortableList + sortable (the layer list of every editor that has one: rows dragged into order, eye, duplicate, cross, rename in place; the index arithmetic of a list shown upside down, kept apart so it is measured without a canvas) + on its own: a symbol the Latin subset lacks is never written as a character, #214); SortableList + sortable (the layer list of every editor that has one: rows dragged into order, eye, duplicate, cross, rename in place; the index arithmetic of a list shown upside down, of a drop in the tile strip and of blocks of rows of any height, kept apart so it is measured without a canvas); blockDrag (`sortBlocks`: the inspector's own rows dragged into order by a grip, a block being every row it covers, #310) src/viewport/ WorldViewport (the drawing of a world or a holder, the base of every view; it draws from a `ViewSource` — the project and word of a change — so a released game draws without the editor, #266; a view through a camera keeps only what that camera `Sees` and lays one @@ -326,7 +326,7 @@ src/editor/curve/ CurveEditor (header: Preset, the picked point's type, Pre preview dot and its rail) + curveView (the curve laid onto a picture for those gestures and read back, a point held between its neighbours, a point put down on free space) src/editor/tile/ TileEditor (header + kind), TileCanvas (every tile of the block and a sample map, animated), - PictureStrip (the pictures as animation steps; dropIndex is the reorder maths), + PictureStrip (the pictures as animation steps; its reorder maths is `dropIndex` in ui/sortable), TilePalette (the tiles as a grid of pictures in the tilemap panel, #139) src/editor/statemachine/ StateMachineEditor (header, on the graph canvas) src/editor/particles/ ParticlesEditor (graph canvas left of a preview panel, splitter between them), diff --git a/Behaviors.md b/Behaviors.md index 35e39d6..fdae8e2 100644 --- a/Behaviors.md +++ b/Behaviors.md @@ -181,6 +181,18 @@ the inspector). single field. All of it sits on **one column grid** with the rest of the inspector: mark (28 px), gap and name (90 px) are exactly as wide as a plain row's label (124 px), a nested field's name gives up what its indent takes, and names are cut with `…` rather than pushing their value out of line. +- **Reordering** (#310): variables, the fields of a struct at any depth, the items of a list and the + declared ports of a Start, End, `Pack`/`Expand` or shader function are **dragged by the mark in + front of their row** — the kind mark, for a list item its number. A press that moves less than + 4 px stays a click, so the kind picker of a list item still opens. A block moves with all of its + rows (a struct with its fields, an item with its nested list) and is dimmed while it is carried; + an accent line shows where it lands, and at the top or bottom edge the panel scrolls along. It + moves among its siblings only: a field stays in its struct, an item in its list. Every move is + one undo step. Values and edges hang on names, so only the order changes: of the rows, of the + fields of `Pack`/`Expand`, of the ports on every node running the behavior. A list's order is its + value, so `Item at` 0 reads the new first item. A list cut off with `… N more` is reordered among + the rows drawn, the whole list in its tab. A placed object draws its variables in the asset's + order and cannot change it, and the fields of a typed struct are moved on the Struct asset. - **Owner** = parent: a placed behavior is usually parented to the object it controls (inspector → Parent, or drag it onto that object in the hierarchy; dashed line in the viewport). The `Owner` node returns it; `Self` returns the behavior itself; `Parent` walks up diff --git a/Development.md b/Development.md index 0dcc153..e0ecd57 100644 --- a/Development.md +++ b/Development.md @@ -18,7 +18,7 @@ php tests/php/accounts.test.php # the API's accoun # has and the web server's container has not (SKIP there) php tests/php/snapshots.test.php # the snapshot store (#231), the same way php tests/php/releases.test.php # the release store (#266), the same way -node tools/seed-e2e.mjs && node tools/e2e.mjs # 1735 editor checks, screenshots in /tmp/gm-e2e-*.png +node tools/seed-e2e.mjs && node tools/e2e.mjs # 1739 editor checks, screenshots in /tmp/gm-e2e-*.png GM_STEPS=20 node tools/e2e.mjs # or 1-12, or 6,20 — a subset while working on one step ./e2e.sh start [GM_STEPS] # the same run detached, see below ./e2e.sh status # live progress, or the last run's result diff --git a/Structs.md b/Structs.md index 7183bd1..fd2cf78 100644 --- a/Structs.md +++ b/Structs.md @@ -15,6 +15,9 @@ a **FIELDS** section that works like the VARIABLES section of a behavior or a Va an object, a list or a struct. - The name field renames it, the remove button at the end of the row removes it. - The value next to it is the field's **default**: what a struct of this type starts with. +- Dragging the mark in front of a field moves it to another place (#310). Every place of the type + follows the new order: its variables and struct fields, the ports of `Pack`/`Expand` and the + fields of a split output. - **Open** shows the fields in a tab of their own, as it does for variables. A field may itself be a struct with a type. What it may not be is its own type, directly or through