mirror of
https://github.com/GraphiteEditor/Graphite.git
synced 2026-09-25 05:28:12 +08:00
Fix hiding and collapsing layers (#1481)
* Hide and collapse layers * Reorder imports * Fix Ctrl+H shortcut advertized action and hotkey tooltip; improve graph top right of options bar --------- Co-authored-by: Keavon Chambers <keavon@keavon.com>
This commit is contained in:
co-authored by
Keavon Chambers
parent
6d9dd5fc27
commit
5ee79031ab
@@ -185,10 +185,7 @@ pub enum DocumentMessage {
|
||||
},
|
||||
StartTransaction,
|
||||
ToggleLayerExpansion {
|
||||
layer_path: Vec<LayerId>,
|
||||
},
|
||||
ToggleLayerVisibility {
|
||||
layer_path: Vec<LayerId>,
|
||||
layer: NodeId,
|
||||
},
|
||||
Undo,
|
||||
UndoFinished,
|
||||
|
||||
@@ -162,7 +162,7 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
self.navigation_handler.process_message(
|
||||
message,
|
||||
responses,
|
||||
(&self.document_legacy, document_bounds, ipp, self.metadata().selected_visible_layers_bounding_box_viewport()),
|
||||
(&self.document_legacy, document_bounds, ipp, self.document_legacy.selected_visible_layers_bounding_box_viewport()),
|
||||
);
|
||||
}
|
||||
#[remain::unsorted]
|
||||
@@ -223,7 +223,7 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
AlignAxis::X => DVec2::X,
|
||||
AlignAxis::Y => DVec2::Y,
|
||||
};
|
||||
let Some(combined_box) = self.metadata().selected_visible_layers_bounding_box_viewport() else {
|
||||
let Some(combined_box) = self.document_legacy.selected_visible_layers_bounding_box_viewport() else {
|
||||
return;
|
||||
};
|
||||
|
||||
@@ -276,13 +276,13 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
CreateEmptyFolder { parent } => {
|
||||
let id = generate_uuid();
|
||||
|
||||
responses.add(DocumentMessage::DeselectAllLayers);
|
||||
responses.add(GraphOperationMessage::NewCustomLayer {
|
||||
id,
|
||||
nodes: HashMap::new(),
|
||||
parent,
|
||||
insert_index: -1,
|
||||
});
|
||||
responses.add(NodeGraphMessage::SelectedNodesSet { nodes: vec![id] });
|
||||
}
|
||||
DebugPrintDocument => {
|
||||
info!("{:#?}\n{:#?}", self.document_legacy, self.layer_metadata);
|
||||
@@ -356,7 +356,7 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
// Calculate the bounding box of the region to be exported
|
||||
let bounds = match bounds {
|
||||
ExportBounds::AllArtwork => self.all_layer_bounds(&render_data),
|
||||
ExportBounds::Selection => self.metadata().selected_visible_layers_bounding_box_viewport(),
|
||||
ExportBounds::Selection => self.document_legacy.selected_visible_layers_bounding_box_viewport(),
|
||||
ExportBounds::Artboard(id) => self.metadata().bounding_box_document(id),
|
||||
}
|
||||
.unwrap_or_default();
|
||||
@@ -387,7 +387,7 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
FlipAxis::X => DVec2::new(-1., 1.),
|
||||
FlipAxis::Y => DVec2::new(1., -1.),
|
||||
};
|
||||
if let Some([min, max]) = self.metadata().selected_visible_layers_bounding_box_viewport() {
|
||||
if let Some([min, max]) = self.document_legacy.selected_visible_layers_bounding_box_viewport() {
|
||||
let center = (max + min) / 2.;
|
||||
let bbox_trans = DAffine2::from_translation(-center);
|
||||
for layer in self.metadata().selected_layers() {
|
||||
@@ -428,7 +428,7 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
}
|
||||
GroupSelectedLayers => {
|
||||
// TODO: Add code that changes the insert index of the new folder based on the selected layer
|
||||
let parent = self.metadata().deepest_common_ancestor(self.metadata().selected_layers()).unwrap_or(LayerNodeIdentifier::ROOT);
|
||||
let parent = self.metadata().deepest_common_ancestor(self.metadata().selected_layers(), true).unwrap_or(LayerNodeIdentifier::ROOT);
|
||||
|
||||
let folder_id = generate_uuid();
|
||||
|
||||
@@ -816,17 +816,14 @@ impl MessageHandler<DocumentMessage, DocumentInputs<'_>> for DocumentMessageHand
|
||||
responses.add_front(DocumentMessage::DirtyRenderDocument);
|
||||
}
|
||||
StartTransaction => self.backup(responses),
|
||||
ToggleLayerExpansion { layer_path } => {
|
||||
self.layer_metadata_mut(&layer_path).expanded ^= true;
|
||||
responses.add(DocumentStructureChanged);
|
||||
responses.add(LayerChanged { affected_layer_path: layer_path })
|
||||
}
|
||||
ToggleLayerVisibility { layer_path } => {
|
||||
if let Ok(layer) = self.document_legacy.layer(&layer_path) {
|
||||
let visible = layer.visible;
|
||||
responses.add(DocumentOperation::SetLayerVisibility { path: layer_path, visible: !visible });
|
||||
responses.add(BroadcastEvent::DocumentIsDirty);
|
||||
ToggleLayerExpansion { layer } => {
|
||||
let layer = LayerNodeIdentifier::new(layer, self.network());
|
||||
if self.document_legacy.collapsed_folders.contains(&layer) {
|
||||
self.document_legacy.collapsed_folders.retain(|&collapsed_layer| collapsed_layer != layer);
|
||||
} else {
|
||||
self.document_legacy.collapsed_folders.push(layer);
|
||||
}
|
||||
responses.add(NodeGraphMessage::RunDocumentGraph);
|
||||
}
|
||||
Undo => {
|
||||
self.undo_in_progress = true;
|
||||
@@ -1074,13 +1071,6 @@ impl DocumentMessageHandler {
|
||||
self.layer_metadata.get(path).map(|layer| layer.selected).unwrap_or(false)
|
||||
}
|
||||
|
||||
pub fn selected_visible_layers(&self) -> impl Iterator<Item = &[LayerId]> {
|
||||
self.selected_layers().filter(|path| match self.document_legacy.layer(path) {
|
||||
Ok(layer) => layer.visible,
|
||||
Err(_) => false,
|
||||
})
|
||||
}
|
||||
|
||||
pub fn visible_layers(&self) -> impl Iterator<Item = &[LayerId]> {
|
||||
self.all_layers().filter(|path| match self.document_legacy.layer(path) {
|
||||
Ok(layer) => layer.visible,
|
||||
@@ -1100,7 +1090,7 @@ impl DocumentMessageHandler {
|
||||
for layer_node in folder.children(self.metadata()) {
|
||||
data.push(layer_node.to_node());
|
||||
space += 1;
|
||||
if layer_node.has_children(self.metadata()) {
|
||||
if layer_node.has_children(self.metadata()) && !self.document_legacy.collapsed_folders.contains(&layer_node) {
|
||||
path.push(layer_node.to_node());
|
||||
|
||||
// TODO: Skip if folder is not expanded.
|
||||
@@ -1414,7 +1404,7 @@ impl DocumentMessageHandler {
|
||||
|
||||
pub fn new_layer_parent(&self) -> LayerNodeIdentifier {
|
||||
self.metadata()
|
||||
.deepest_common_ancestor(self.metadata().selected_layers())
|
||||
.deepest_common_ancestor(self.metadata().selected_layers(), false)
|
||||
.unwrap_or_else(|| self.metadata().active_artboard())
|
||||
}
|
||||
|
||||
|
||||
+5
-5
@@ -625,7 +625,7 @@ impl MessageHandler<GraphOperationMessage, (&mut Document, &mut NodeGraphMessage
|
||||
if let Some(layer) = modify_inputs.create_layer(id, modify_inputs.network.original_outputs()[0].node_id, 0, 0) {
|
||||
modify_inputs.insert_artboard(artboard, layer);
|
||||
}
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
}
|
||||
GraphOperationMessage::NewBitmapLayer {
|
||||
id,
|
||||
@@ -678,14 +678,14 @@ impl MessageHandler<GraphOperationMessage, (&mut Document, &mut NodeGraphMessage
|
||||
modify_inputs.responses.add(NodeGraphMessage::SendGraph { should_rerender: true });
|
||||
}
|
||||
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
}
|
||||
GraphOperationMessage::NewVectorLayer { id, subpaths, parent, insert_index } => {
|
||||
let mut modify_inputs = ModifyInputsContext::new(document, node_graph, responses);
|
||||
if let Some(layer) = modify_inputs.create_layer_with_insert_index(id, insert_index, parent) {
|
||||
modify_inputs.insert_vector_data(subpaths, layer);
|
||||
}
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
}
|
||||
GraphOperationMessage::NewTextLayer {
|
||||
id,
|
||||
@@ -699,7 +699,7 @@ impl MessageHandler<GraphOperationMessage, (&mut Document, &mut NodeGraphMessage
|
||||
if let Some(layer) = modify_inputs.create_layer_with_insert_index(id, insert_index, parent) {
|
||||
modify_inputs.insert_text(text, font, size, layer);
|
||||
}
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
}
|
||||
GraphOperationMessage::ResizeArtboard { id, location, dimensions } => {
|
||||
if let Some(mut modify_inputs) = ModifyInputsContext::new_layer(&[id], document, node_graph, responses) {
|
||||
@@ -716,7 +716,7 @@ impl MessageHandler<GraphOperationMessage, (&mut Document, &mut NodeGraphMessage
|
||||
for id in artboard_nodes {
|
||||
modify_inputs.delete_layer(id);
|
||||
}
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -95,7 +95,10 @@ pub enum NodeGraphMessage {
|
||||
ShiftNode {
|
||||
node_id: NodeId,
|
||||
},
|
||||
ToggleHidden,
|
||||
ToggleSelectedHidden,
|
||||
ToggleHidden {
|
||||
node_id: NodeId,
|
||||
},
|
||||
SetHidden {
|
||||
node_id: NodeId,
|
||||
hidden: bool,
|
||||
|
||||
@@ -193,11 +193,17 @@ impl NodeGraphMessageHandler {
|
||||
if let Some(network) = document.document_network.nested_network(&self.network) {
|
||||
let mut widgets = Vec::new();
|
||||
|
||||
// TODO: Replace this with an add node button
|
||||
let add_nodes_label = TextLabel::new("Right Click Graph to Add Nodes").italic(true).widget_holder();
|
||||
widgets.push(add_nodes_label);
|
||||
|
||||
// Don't allow disabling input or output nodes
|
||||
let mut selected_nodes = document.metadata.selected_nodes().filter(|&&id| !network.inputs.contains(&id) && !network.original_outputs_contain(id));
|
||||
|
||||
// If there is at least one other selected node then show the hide or show button
|
||||
if selected_nodes.next().is_some() {
|
||||
widgets.push(Separator::new(SeparatorType::Unrelated).widget_holder());
|
||||
|
||||
// Check if any of the selected nodes are disabled
|
||||
let is_hidden = document.metadata.selected_nodes().any(|id| network.disabled.contains(id));
|
||||
|
||||
@@ -205,10 +211,12 @@ impl NodeGraphMessageHandler {
|
||||
let multiple_nodes = selected_nodes.next().is_some();
|
||||
|
||||
// Generate the enable or disable button accordingly
|
||||
let hide_button = TextButton::new(if is_hidden { "Show" } else { "Hide" })
|
||||
.tooltip(if is_hidden { "Show node" } else { "Hide node" }.to_string() + if multiple_nodes { "s" } else { "" })
|
||||
.tooltip_shortcut(action_keys!(NodeGraphMessageDiscriminant::ToggleHidden))
|
||||
.on_update(move |_| NodeGraphMessage::ToggleHidden.into())
|
||||
let (hide_show_label, hide_show_icon) = if is_hidden { ("Make Visible", "EyeHidden") } else { ("Make Hidden", "EyeVisible") };
|
||||
let hide_button = TextButton::new(hide_show_label)
|
||||
.icon(Some(hide_show_icon.to_string()))
|
||||
.tooltip(if is_hidden { "Show selected nodes/layers" } else { "Hide selected nodes/layers" }.to_string() + if multiple_nodes { "s" } else { "" })
|
||||
.tooltip_shortcut(action_keys!(NodeGraphMessageDiscriminant::ToggleSelectedHidden))
|
||||
.on_update(move |_| NodeGraphMessage::ToggleSelectedHidden.into())
|
||||
.widget_holder();
|
||||
widgets.push(hide_button);
|
||||
}
|
||||
@@ -216,13 +224,16 @@ impl NodeGraphMessageHandler {
|
||||
// If only one node is selected then show the preview or stop previewing button
|
||||
let mut selected_nodes = document.metadata.selected_nodes();
|
||||
if let (Some(&node_id), None) = (selected_nodes.next(), selected_nodes.next()) {
|
||||
widgets.push(Separator::new(SeparatorType::Unrelated).widget_holder());
|
||||
|
||||
// Is this node the current output
|
||||
let is_output = network.outputs_contain(node_id);
|
||||
|
||||
// Don't show stop previewing button on the original output node
|
||||
if !(is_output && network.previous_outputs_contain(node_id).unwrap_or(true)) {
|
||||
let output_button = TextButton::new(if is_output { "End Preview" } else { "Preview" })
|
||||
.tooltip(if is_output { "Restore preview to Output node" } else { "Preview node" }.to_string() + " (Shortcut: Alt-click node)")
|
||||
.icon(Some("Rescale".to_string()))
|
||||
.tooltip(if is_output { "Restore preview to the graph output" } else { "Preview selected node/layer" }.to_string() + " (Shortcut: Alt-click node/layer)")
|
||||
.on_update(move |_| NodeGraphMessage::TogglePreview { node_id }.into())
|
||||
.widget_holder();
|
||||
widgets.push(output_button);
|
||||
@@ -458,7 +469,7 @@ impl<'a> MessageHandler<NodeGraphMessage, NodeGraphHandlerData<'a>> for NodeGrap
|
||||
on: BroadcastEvent::SelectionChanged,
|
||||
send: Box::new(NodeGraphMessage::SelectedNodesUpdated.into()),
|
||||
});
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
responses.add(DocumentMessage::DocumentStructureChanged);
|
||||
}
|
||||
NodeGraphMessage::SelectedNodesUpdated => {
|
||||
@@ -803,7 +814,7 @@ impl<'a> MessageHandler<NodeGraphMessage, NodeGraphHandlerData<'a>> for NodeGrap
|
||||
let structure_changed = node_input.as_node().is_some() || input.as_node().is_some();
|
||||
*node_input = input;
|
||||
if structure_changed {
|
||||
document.metadata.load_structure(&document.document_network);
|
||||
document.load_network_structure();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -882,7 +893,7 @@ impl<'a> MessageHandler<NodeGraphMessage, NodeGraphHandlerData<'a>> for NodeGrap
|
||||
}
|
||||
responses.add(NodeGraphMessage::SendGraph { should_rerender: false });
|
||||
}
|
||||
NodeGraphMessage::ToggleHidden => {
|
||||
NodeGraphMessage::ToggleSelectedHidden => {
|
||||
if let Some(network) = document.document_network.nested_network(&self.network) {
|
||||
responses.add(DocumentMessage::StartTransaction);
|
||||
|
||||
@@ -892,6 +903,12 @@ impl<'a> MessageHandler<NodeGraphMessage, NodeGraphHandlerData<'a>> for NodeGrap
|
||||
}
|
||||
}
|
||||
}
|
||||
NodeGraphMessage::ToggleHidden { node_id } => {
|
||||
if let Some(network) = document.document_network.nested_network(&self.network) {
|
||||
let new_hidden = !network.disabled.contains(&node_id);
|
||||
responses.add(NodeGraphMessage::SetHidden { node_id, hidden: new_hidden });
|
||||
}
|
||||
}
|
||||
NodeGraphMessage::SetHidden { node_id, hidden } => {
|
||||
if let Some(network) = document.document_network.nested_network_mut(&self.network) {
|
||||
if !hidden {
|
||||
@@ -956,7 +973,7 @@ impl<'a> MessageHandler<NodeGraphMessage, NodeGraphHandlerData<'a>> for NodeGrap
|
||||
impl NodeGraphMessageHandler {
|
||||
pub fn actions_with_node_graph_open(&self, graph_open: bool) -> ActionList {
|
||||
if self.has_selection && graph_open {
|
||||
actions!(NodeGraphMessageDiscriminant; DeleteSelectedNodes, Cut, Copy, DuplicateSelectedNodes, ToggleHidden)
|
||||
actions!(NodeGraphMessageDiscriminant; DeleteSelectedNodes, Cut, Copy, DuplicateSelectedNodes, ToggleSelectedHidden)
|
||||
} else {
|
||||
actions!(NodeGraphMessageDiscriminant;)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user