Skip to content

Feature: Ctrl+G groups, rectangle selection, group pivot - #45

Merged
StackEnjoyer merged 63 commits into
mainfrom
feature/grouping
Oct 28, 2026
Merged

StackEnjoyer merged 63 commits into
mainfrom
feature/grouping

Conversation

@StackEnjoyer

@StackEnjoyer StackEnjoyer commented Oct 26, 2026 •

Copy link
Copy Markdown
Owner

Features

  • Ctrl+G (Cmd+G): makes a selection of several an ObjectGroup that its systems hold
  • Ctrl+G on some parts of one group: a group inside it, the outer group changed in place
  • Ctrl+Shift+G: ungroups a group made in the window, or dissolves it into its parent group
  • Ctrl+click on a part of the same group adds it while parts of one group are selected
  • Cards: action "group" on a selection of several, "ungroup" on a group made in the window
  • Ctrl+drag from the background: rectangle adds the visible top-level objects whose center lies inside
  • Ctrl+C, Ctrl+V: copy groups of catalog components and several selected objects
  • Pivot of a group or a selection of several: a dot shows it, dragging the dot moves it
  • Card row "pivot": typed x/y/z, "pick" a part (also inside a subgroup), "center" of the box; set_pivot3d!(gui, group, p)
  • export_script, export_changes: write the groups made in the window, delete!/push!/set_pivot3d! for changed script groups

Bugfixes

  • Inspector: the button "<" of a part covered the actions, e.g. "parts >"

Doc changes

  • live_view and "Kinematic controls": grouping keys, grouping within a group, the selection rectangle, the pivot
  • "Adding and removing components": copying groups, export of groups made or changed in the window
  • Example of the empty table opens in the app layout, as its comment says
  • Agent skill: SKILL.md, API.md updated

Internal changes

Closes #40

Hugo Uittenbosch and others added 30 commits October 23, 2026 22:57
…ui, objs)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The card (compact) and the inspector (app) of a _MultiSelection show
"N objects", the subtitle "Selection", a row per object whose button
selects it alone, the actions hide and remove, no pages and no pin.
Hiding hides all objects (shows all if all are hidden); hidden objects
leave a selection of several. A click on an object of a group of the
selection selects it alone. _label(::LiveView, ::_MultiSelection)
resolves the ambiguity with the generic _label.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… reset, history (W1)

Ctrl+click (Cmd on macOS) adds the top-level object to the selection or removes the
member; its press is consumed, such that Camera3D does not reset. A drag on any member,
the gizmo and the keys move the selection as one, without snapping; Esc deselects it,
Backspace resets all its objects as one undo action; the spectator mode restores it.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…e other features

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…rl+click in the docs

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The tree sets `toggled` instead of `clicked` for a click on a label with Ctrl or Cmd held at
the press; `_tree_toggle!` toggles a movable object via `_toggle_select!`, other rows behave
like a plain click. `_set_selected!` takes a vector of keys (`selected_keys`), highlights all
their rows and scrolls to the last added one; `_on_selected!` reveals and highlights all objects
of a selection of several.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…_is_movable, _drag_snaps trait (W1)

The methods for KinematicController and _MultiSelection are self-contained, since the
untyped ones of the W0 core are removed; _drag_snaps is a trait by dispatch.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… the W0 ambiguities

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…roup

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Members first in their poses when the group was made, then ObjectGroup, set_pivot3d!
and the change of the pose of the group since; the system lists the group.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… on the layout

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
)

_group!/_ungroup! with undo, _show_group!/_unshow_group! (members re-rendered
as parts of the group, their state kept), _unshow! split out of _drop!,
_record_units for the bookkeeping of window groups on removal and undo,
linked views follow (_follow_groups!, _link!), test/TestLiveGroup.jl.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…atch, docs and skill of grouping

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…teps leave the scene as before

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…fter a tilt

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Hugo Uittenbosch and others added 9 commits October 26, 2026 00:00
…sed _axis_angle_from_rotmatrix, _set_pose! is the exact one; clip planes keep their local control axes

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
# Conflicts:
#	src/LiveInteraction.jl
#	src/LiveLinks.jl
#	src/LiveTrace.jl
#	test/runtests.jl
# Conflicts:
#	src/BeamletOpticsGUI.jl
#	src/LiveInteraction.jl
#	test/runtests.jl
…ce a frame drew them, the viewports of their scenes grow by a pixel and take their size again a few ticks later

GLMakie kept the projection of the first frame (default size of a new scene, or the width before the label was set), e.g. for the names of a selection of several and the buttons in the head of the card. The settle now counts ticks and waits for a drawn frame instead of a later clock time, and covers the head actions too.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…f their viewports takes the cameras anew, a move in the same frame laid them out back to their size

Measured on the pages of cards with textboxes (60 steps per layout): with the move, 22 (compact) and 16 (app) plots kept an outdated projection, without it none.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…ixel and take their size again, instead of a move of the columns of its boxes

The form joins the settle list of the cards (`gui.cards.settle`, now the layouts per entry); `_settle_catalog_form!` and the field `settle` of the catalog widget are gone. Checked on all entries of the catalog (117 forms, 336 textboxes per layout): no plot with an outdated projection.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@codecov-commenter

codecov-commenter commented Oct 26, 2026 •

Copy link
Copy Markdown

⚠️ Please install the 'codecov app svg image' to ensure uploads and comments are reliably processed by Codecov.

Codecov Report

❌ Patch coverage is 96.63561% with 65 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
src/LiveGroup.jl 95.14% 18 Missing ⚠️
src/LivePivot.jl 94.44% 16 Missing ⚠️
src/LiveLinks.jl 87.50% 13 Missing ⚠️
src/LiveMultiSelect.jl 93.50% 5 Missing ⚠️
src/LiveCopy.jl 95.95% 4 Missing ⚠️
src/LiveCards.jl 92.85% 3 Missing ⚠️
src/LiveCardPages.jl 0.00% 1 Missing ⚠️
src/LiveExport.jl 99.40% 1 Missing ⚠️
src/LiveInteraction.jl 99.50% 1 Missing ⚠️
src/LiveMarkers.jl 0.00% 1 Missing ⚠️
... and 2 more

📢 Thoughts on this report? Let us know!

Hugo Uittenbosch and others added 15 commits October 26, 2026 17:14
…own after the 3D scene, over its depth

In the 2D scene of the axis it was drawn before the 3D scene and its depth hid the objects behind it, which left the fill over the background. `close` of the controls removes the scene again.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…solves it into that one

An ObjectGroup does not change its members, hence the groups that hold it are made again from the bottom up: new ObjectGroups with the members in place of the dissolved group, with the name, label and pivot of the old ones and the axes of the world. One action of the undo history: undo brings back the old groups, redo the same new ones. Tests of two and three levels, of the export after dissolving and after its undo, a step of the precompile session; docs and skill.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… a group inside it, also in a group of the script

The groups above are made anew (`_remake!`, shared with dissolving): new ObjectGroups with the name, label and pivot of the old ones, world axes, groups made in the window; one that replaces a group of the script records it (`replaces`). One undo step; undo brings back a group of the script as such, with its initial pose. Linked views follow the ungrouping and grouping of a group of the script.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…ected

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…els, refused, linked view

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…e old group from its systems before the new one

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…p made in the window and within a group of the script

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…se replacement was ungrouped are kept for the export

The help of Ctrl+click, Ctrl+G and Ctrl+Shift+G names the parts of a group. `gui.components.dissolved` holds the groups of the script whose replacement made in the window was ungrouped, see `_unshow_group!` and `_show_group!`, for `export_changes`.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…delete! of the old group and push! of its former parts

`export_changes` writes, before the added objects and the groups made in the window, a `delete!` of each group of the script in `gui.components.dissolved` from the systems that held it at the start and a `push!` of its former parts that are top-level now. The old group gets the label of its replacement when that is ungrouped, by which the export names it.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… widened the help card, which left the floating card no room beside it

Also `@nospecialize` in the closure of `_sibling_or_top`.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…and Ctrl+V

A group whose components are all from the catalog is copied with its nested
groups, pivots and relative poses; pasted, it is a group made in the window.
Several selected objects follow the mouse together and are dropped as separate
objects. Both are one undo step; a source is copied only on its own.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…nd delete! of ObjectGroup

A new subgroup takes the place of its first part, the members of a dissolved
group take the place of the group; the outer group and the groups above stay
the same objects with their poses, names and labels, also a group of the
script. A group built from the catalog by code refuses it. `export_changes`
writes `delete!` of the parts that left a group of the script, the code of the
new groups and a `push!` of them. Undo and redo are dropped when the parts were
changed meanwhile, e.g. in a linked view. Needs BeamletOptics with mutable
groups (JuliaPhysics/BeamletOptics.jl#182).

Also the test of Ctrl+C of a multi-selection, which was stale since bbb8cfd.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…nger covers the actions, e.g. "parts ›"

Hidden, the column and its gap take no room, such that the actions stay next to the pin.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…ibes

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…ivot" of the card sets it (x/y/z, pick a part, center of the box), dragging the dot moves it, set_pivot3d!(gui, group, p) from a script

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@StackEnjoyer StackEnjoyer changed the title Feature: Ctrl+G groups made in the window, rectangle selection Feature: Ctrl+G groups, rectangle selection, group pivot Oct 28, 2026
… center of the box, as the button sets it since the manual test

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@StackEnjoyer
StackEnjoyer merged commit 0e2b4de into main Oct 28, 2026
3 checks passed
@StackEnjoyer
StackEnjoyer deleted the feature/grouping branch October 28, 2026 17:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Feature: Selected objects are made a group in the window

2 participants