Repository: GraphiteEditor/Graphite (language: rust)

Issue:
Layers physically move when being transferred to a new folder which has a different transform
This requires some knowledge of linear algebra and transforms, for example by people who have experience with computer graphics or gamedev.

https://github.com/GraphiteEditor/Graphite/pull/2177 can be useful reference for how transforms are modified for cross-scope movement.


Discussion / hints:
Hey @Keavon Is this still on ? I could take it if it's the case
@lyingpasta go for it! This'll be valuable to solve.
@Keavon can you give some example of what it's intended for this behavior ? Do we need the transform property of the parent layer to be applied to all it's children or compute a new transform based on the original one and the parent's ? 
@lyingpasta For each layer that's dragged out of a certain folder, it should have a transform applied to it that puts it back into its original transformation as if the user had dragged it back there (and resized/scaled/skewed it). If multiple layers are dragged out of a certain folder, that applies individually to each one of them.
It seems like it's actually the case, I created 3 layers one of them with a scaling transform when I drag one layer to it, the transform applies to it also, then I drag it back out and it goes back to its original state. Isn't this what we need ?
It needs to do exactly not that. Any layer rearranged in the layer panel should never change its transform within the canvas.

Fix patch:
diff --git a/editor/src/messages/portfolio/document/document_message_handler.rs b/editor/src/messages/portfolio/document/document_message_handler.rs
index 2ef3f20a37..0dc243eb5f 100644
--- a/editor/src/messages/portfolio/document/document_message_handler.rs
+++ b/editor/src/messages/portfolio/document/document_message_handler.rs
@@ -622,6 +622,16 @@ impl MessageHandler<DocumentMessage, DocumentMessageData<'_>> for DocumentMessag
 						parent,
 						insert_index: calculated_insert_index,
 					});
+
+					let layer_local_transform = self.network_interface.document_metadata().transform_to_viewport(layer_to_move);
+					let undo_transform = self.network_interface.document_metadata().transform_to_viewport(parent).inverse();
+					let transform = undo_transform * layer_local_transform;
+					responses.add(GraphOperationMessage::TransformSet {
+						layer: layer_to_move,
+						transform,
+						transform_in: TransformIn::Local,
+						skip_rerender: false,
+					});
 				}
 
 				responses.add(NodeGraphMessage::RunDocumentGraph);
@@ -1194,6 +1204,16 @@ impl MessageHandler<DocumentMessage, DocumentMessageData<'_>> for DocumentMessag
 						parent,
 						insert_index: folder_index,
 					});
+
+					let layer_local_transform = self.network_interface.document_metadata().transform_to_viewport(child);
+					let undo_transform = self.network_interface.document_metadata().transform_to_viewport(parent).inverse();
+					let transform = undo_transform * layer_local_transform;
+					responses.add(GraphOperationMessage::TransformSet {
+						layer: child,
+						transform,
+						transform_in: TransformIn::Local,
+						skip_rerender: false,
+					});
 				}
 
 				// Delete empty group folder


Test patch: