Version: observed on 4.0.4 with Godot 4.7.2. The do-path code below is unchanged in 4.2.3 (f58314d, also current main); I checked the source, but did not re-run the repro on 4.2.3.
Code: plugin/addons/godot_ai/handlers/node_handler.gd, reparent_node. After snapshotting
descendants := _collect_descendants(node), the do path records
add_do_method(child, "set_owner", scene_root) for every descendant. The undo path (fixed for
#904) restores each descendant's prior owner correctly.
Effect: when the reparented node is, or contains, an instanced scene, the instance's
internal nodes (owned by the instance root, not the edited scene root) become scene-owned. On save
they are written into the parent .tscn as local nodes, and the instance's overrides are lost.
Seen on a real scene: four instanced widgets were flattened, and one lost its rect override.
Repro:
- In a scene, instance a sub-scene
W.tscn that has at least one child node, under node A.
reparent_node A (or the instance itself) to another parent.
- Save, and open the
.tscn: W's internal nodes now appear as local nodes of the parent scene.
Expected: the same as the editor's Scene-dock reparent: only nodes that were owned by the
edited scene root get scene_root again. Nodes owned by an instance root keep that owner, and a
null owner stays null.
Suggested fix: in the do path, record each descendant's snapshotted prior owner (the same
prior_owner the undo loop already uses), instead of scene_root. remove_child clears only
owners that sit outside the pruned subtree (which is scene_root here), so restoring the snapshot
is enough. Regression test: reparent a subtree containing an instance, then assert that an
internal node's owner is still the instance root.
Version: observed on 4.0.4 with Godot 4.7.2. The do-path code below is unchanged in 4.2.3 (
f58314d, also currentmain); I checked the source, but did not re-run the repro on 4.2.3.Code:
plugin/addons/godot_ai/handlers/node_handler.gd,reparent_node. After snapshottingdescendants := _collect_descendants(node), the do path recordsadd_do_method(child, "set_owner", scene_root)for every descendant. The undo path (fixed for#904) restores each descendant's prior owner correctly.
Effect: when the reparented node is, or contains, an instanced scene, the instance's
internal nodes (owned by the instance root, not the edited scene root) become scene-owned. On save
they are written into the parent
.tscnas local nodes, and the instance's overrides are lost.Seen on a real scene: four instanced widgets were flattened, and one lost its rect override.
Repro:
W.tscnthat has at least one child node, under nodeA.reparent_nodeA(or the instance itself) to another parent..tscn:W's internal nodes now appear as local nodes of the parent scene.Expected: the same as the editor's Scene-dock reparent: only nodes that were owned by the
edited scene root get
scene_rootagain. Nodes owned by an instance root keep that owner, and anull owner stays null.
Suggested fix: in the do path, record each descendant's snapshotted prior owner (the same
prior_ownerthe undo loop already uses), instead ofscene_root.remove_childclears onlyowners that sit outside the pruned subtree (which is
scene_roothere), so restoring the snapshotis enough. Regression test: reparent a subtree containing an instance, then assert that an
internal node's owner is still the instance root.