diff --git a/editor/src/messages/portfolio/document/data_panel/data_panel_message_handler.rs b/editor/src/messages/portfolio/document/data_panel/data_panel_message_handler.rs index da4b663576..a7fd8c9de8 100644 --- a/editor/src/messages/portfolio/document/data_panel/data_panel_message_handler.rs +++ b/editor/src/messages/portfolio/document/data_panel/data_panel_message_handler.rs @@ -578,13 +578,13 @@ impl TableItemLayout for Graphic { fn identifier(&self) -> String { match self { Self::None => "None".to_string(), - Self::Graphic(list) => list.identifier(), - Self::Vector(list) => list.identifier(), - Self::RasterCPU(list) => list.identifier(), - Self::RasterGPU(list) => list.identifier(), - Self::Color(list) => list.identifier(), - Self::Gradient(list) => list.identifier(), - Self::Text(list) => list.identifier(), + Self::GraphicList(list) => list.identifier(), + Self::VectorList(list) => list.identifier(), + Self::RasterCPUList(list) => list.identifier(), + Self::RasterGPUList(list) => list.identifier(), + Self::ColorList(list) => list.identifier(), + Self::GradientList(list) => list.identifier(), + Self::TextList(list) => list.identifier(), } } // Don't put a breadcrumb for Graphic @@ -594,13 +594,13 @@ impl TableItemLayout for Graphic { fn value_page(&self, data: &mut LayoutData) -> Vec { match self { Self::None => label("None"), - Self::Graphic(list) => list.layout_with_breadcrumb(data), - Self::Vector(list) => list.layout_with_breadcrumb(data), - Self::RasterCPU(list) => list.layout_with_breadcrumb(data), - Self::RasterGPU(list) => list.layout_with_breadcrumb(data), - Self::Color(list) => list.layout_with_breadcrumb(data), - Self::Gradient(list) => list.layout_with_breadcrumb(data), - Self::Text(list) => list.layout_with_breadcrumb(data), + Self::GraphicList(list) => list.layout_with_breadcrumb(data), + Self::VectorList(list) => list.layout_with_breadcrumb(data), + Self::RasterCPUList(list) => list.layout_with_breadcrumb(data), + Self::RasterGPUList(list) => list.layout_with_breadcrumb(data), + Self::ColorList(list) => list.layout_with_breadcrumb(data), + Self::GradientList(list) => list.layout_with_breadcrumb(data), + Self::TextList(list) => list.layout_with_breadcrumb(data), } } } diff --git a/editor/src/node_graph_executor/runtime.rs b/editor/src/node_graph_executor/runtime.rs index b7cf3591d5..8ce1ccea57 100644 --- a/editor/src/node_graph_executor/runtime.rs +++ b/editor/src/node_graph_executor/runtime.rs @@ -414,7 +414,7 @@ impl NodeRuntime { continue; }; - // Graphic list: thumbnail (text-aware bounds, since the `BoundingBox` trait can't lay out `Graphic::Text` content) + // Graphic list: thumbnail (text-aware bounds, since the `BoundingBox` trait can't lay out `Graphic::TextList` content) if let Some(io) = introspected_data.downcast_ref::>>() { if update_thumbnails { let bounds = graphene_std::renderer::graphic_list_bounding_box(&io.output, DAffine2::IDENTITY); diff --git a/node-graph/libraries/graphic-types/src/appearance.rs b/node-graph/libraries/graphic-types/src/appearance.rs index c479a6b8c3..9a6c088323 100644 --- a/node-graph/libraries/graphic-types/src/appearance.rs +++ b/node-graph/libraries/graphic-types/src/appearance.rs @@ -282,12 +282,12 @@ mod tests { use vector_types::vector::style::{StrokeAlign, StrokeCap, StrokeJoin}; fn solid_paint(color: Color) -> List { - List::new_from_element(Graphic::Color(List::new_from_element(color))) + List::new_from_element(Graphic::ColorList(List::new_from_element(color))) } fn paint_color(appearance: &Appearance, index: usize) -> Option { let paint = appearance.paint_at(index)?; - let Some(Graphic::Color(colors)) = paint.element(0) else { return None }; + let Some(Graphic::ColorList(colors)) = paint.element(0) else { return None }; colors.element(0).copied() } diff --git a/node-graph/libraries/graphic-types/src/artboard.rs b/node-graph/libraries/graphic-types/src/artboard.rs index f59362bc74..a4c114fef6 100644 --- a/node-graph/libraries/graphic-types/src/artboard.rs +++ b/node-graph/libraries/graphic-types/src/artboard.rs @@ -12,7 +12,7 @@ use glam::DAffine2; /// enclosing `List`, not as fields here. This keeps `Artboard` a pure type-system boundary /// that prevents arbitrary `List>>` nesting. #[derive(Clone, Debug, Default, CacheHash, PartialEq, DynAny)] -pub struct Artboard(List); +pub struct Artboard(pub List); impl Artboard { pub fn new(content: List) -> Self { diff --git a/node-graph/libraries/graphic-types/src/graphic.rs b/node-graph/libraries/graphic-types/src/graphic.rs index 22a225d416..a1130af6c7 100644 --- a/node-graph/libraries/graphic-types/src/graphic.rs +++ b/node-graph/libraries/graphic-types/src/graphic.rs @@ -19,31 +19,31 @@ pub enum Graphic { /// The absence of graphical content, like CSS's `none` keyword: painting it produces nothing. #[default] None, - Graphic(List), - Vector(List), - RasterCPU(List>), - RasterGPU(List>), - Color(List), - Gradient(List), - Text(List), + GraphicList(List), + VectorList(List), + RasterCPUList(List>), + RasterGPUList(List>), + ColorList(List), + GradientList(List), + TextList(List), } -// Graphic +// GraphicList impl From> for Graphic { fn from(graphic: List) -> Self { - Graphic::Graphic(graphic) + Graphic::GraphicList(graphic) } } // Vector impl From for Graphic { fn from(vector: Vector) -> Self { - Graphic::Vector(List::new_from_element(vector)) + Graphic::VectorList(List::new_from_element(vector)) } } impl From> for Graphic { fn from(vector: List) -> Self { - Graphic::Vector(vector) + Graphic::VectorList(vector) } } @@ -52,12 +52,12 @@ impl From> for Graphic { // Raster impl From> for Graphic { fn from(raster: Raster) -> Self { - Graphic::RasterCPU(List::new_from_element(raster)) + Graphic::RasterCPUList(List::new_from_element(raster)) } } impl From>> for Graphic { fn from(raster: List>) -> Self { - Graphic::RasterCPU(raster) + Graphic::RasterCPUList(raster) } } // Note: List conversions handled by blanket impl in gcore @@ -65,12 +65,12 @@ impl From>> for Graphic { // Raster impl From> for Graphic { fn from(raster: Raster) -> Self { - Graphic::RasterGPU(List::new_from_element(raster)) + Graphic::RasterGPUList(List::new_from_element(raster)) } } impl From>> for Graphic { fn from(raster: List>) -> Self { - Graphic::RasterGPU(raster) + Graphic::RasterGPUList(raster) } } // Note: List conversions handled by blanket impl in gcore @@ -78,12 +78,12 @@ impl From>> for Graphic { // Color impl From for Graphic { fn from(color: Color) -> Self { - Graphic::Color(List::new_from_element(color)) + Graphic::ColorList(List::new_from_element(color)) } } impl From> for Graphic { fn from(color: List) -> Self { - Graphic::Color(color) + Graphic::ColorList(color) } } // Note: List conversions handled by blanket impl in gcore @@ -92,24 +92,24 @@ impl From> for Graphic { // Gradient impl From for Graphic { fn from(gradient: Gradient) -> Self { - Graphic::Gradient(List::new_from_element(gradient)) + Graphic::GradientList(List::new_from_element(gradient)) } } impl From> for Graphic { fn from(gradient: List) -> Self { - Graphic::Gradient(gradient) + Graphic::GradientList(gradient) } } // String impl From for Graphic { fn from(text: String) -> Self { - Graphic::Text(List::new_from_element(text)) + Graphic::TextList(List::new_from_element(text)) } } impl From> for Graphic { fn from(text: List) -> Self { - Graphic::Text(text) + Graphic::TextList(text) } } @@ -117,7 +117,7 @@ impl From> for Graphic { /// collapses no structure and rebuilding or snapshotting the result would be busywork. pub fn is_lone_anonymous_leaf(content: &List) -> bool { content.len() == 1 - && !matches!(content.element(0), Some(Graphic::Graphic(_))) + && !matches!(content.element(0), Some(Graphic::GraphicList(_))) && content.attribute::(ATTR_TRANSFORM, 0).is_none() && content.attribute::(ATTR_OPACITY, 0).is_none() && content.attribute::(ATTR_OPACITY_FILL, 0).is_none() @@ -126,7 +126,7 @@ pub fn is_lone_anonymous_leaf(content: &List) -> bool { } /// Deeply flattens a `List`, collecting only elements matching a specific variant (extracted by `extract_variant`) -/// and discarding all other non-matching content. Recursion through `Graphic::Graphic` sub-`List`s composes transforms and opacity. +/// and discarding all other non-matching content. Recursion through `Graphic::GraphicList` sub-`List`s composes transforms and opacity. fn flatten_graphic_list(content: List, extract_variant: fn(Graphic) -> Option>) -> List { // Its list is already the flat answer, so hand it back rather than rebuilding it item by item if is_lone_anonymous_leaf(&content) { @@ -154,7 +154,7 @@ fn flatten_graphic_list(content: List, extract_variant: fn(Graphic) match current_graphic_item.into_element() { // Compose the parent's transform/opacity/fill onto each child, but only for attributes the parent carries. // A child lacking one is padded with the composition identity (`1.` for opacity/fill, identity for transform), so composing through it is a no-op. - Graphic::Graphic(mut sub_list) => { + Graphic::GraphicList(mut sub_list) => { // A group's first child has no preceding sibling, so its clipping flag is inert until splicing // hands it the group's own predecessor. Clear it (keeping the column) to stay clip-neutral. if sub_list.attribute::(ATTR_CLIPPING_MASK, 0).is_some() { @@ -244,13 +244,13 @@ pub fn bake_paint_transforms(attributes: &mut ItemAttributeValues, transform: DA fn bake_graphic_transform(graphic: &mut Graphic, transform: DAffine2) { match graphic { Graphic::None => {} - Graphic::Graphic(list) => bake_list_transform(list, transform), - Graphic::Vector(list) => bake_list_transform(list, transform), - Graphic::RasterCPU(list) => bake_list_transform(list, transform), - Graphic::RasterGPU(list) => bake_list_transform(list, transform), - Graphic::Gradient(list) => bake_list_transform(list, transform), - Graphic::Text(list) => bake_list_transform(list, transform), - Graphic::Color(_) => {} + Graphic::GraphicList(list) => bake_list_transform(list, transform), + Graphic::VectorList(list) => bake_list_transform(list, transform), + Graphic::RasterCPUList(list) => bake_list_transform(list, transform), + Graphic::RasterGPUList(list) => bake_list_transform(list, transform), + Graphic::GradientList(list) => bake_list_transform(list, transform), + Graphic::TextList(list) => bake_list_transform(list, transform), + Graphic::ColorList(_) => {} } } @@ -273,31 +273,31 @@ pub trait TryFromGraphic: Clone + Sized { impl TryFromGraphic for Vector { fn try_from_graphic(graphic: Graphic) -> Option> { - if let Graphic::Vector(t) = graphic { Some(t) } else { None } + if let Graphic::VectorList(t) = graphic { Some(t) } else { None } } } impl TryFromGraphic for Raster { fn try_from_graphic(graphic: Graphic) -> Option> { - if let Graphic::RasterCPU(t) = graphic { Some(t) } else { None } + if let Graphic::RasterCPUList(t) = graphic { Some(t) } else { None } } } impl TryFromGraphic for Color { fn try_from_graphic(graphic: Graphic) -> Option> { - if let Graphic::Color(t) = graphic { Some(t) } else { None } + if let Graphic::ColorList(t) = graphic { Some(t) } else { None } } } impl TryFromGraphic for Gradient { fn try_from_graphic(graphic: Graphic) -> Option> { - if let Graphic::Gradient(t) = graphic { Some(t) } else { None } + if let Graphic::GradientList(t) = graphic { Some(t) } else { None } } } impl TryFromGraphic for String { fn try_from_graphic(graphic: Graphic) -> Option> { - if let Graphic::Text(t) = graphic { Some(t) } else { None } + if let Graphic::TextList(t) = graphic { Some(t) } else { None } } } @@ -324,37 +324,37 @@ impl IntoGraphicList for List { fn into_graphic_list(self) -> List { // A synthetic container, not a real group layer, so it carries no `editor:layer_path` that would // overwrite the inner items' own stamps when flattened back out - List::new_from_element(Graphic::Vector(self)) + List::new_from_element(Graphic::VectorList(self)) } } impl IntoGraphicList for List> { fn into_graphic_list(self) -> List { - List::new_from_element(Graphic::RasterCPU(self)) + List::new_from_element(Graphic::RasterCPUList(self)) } } impl IntoGraphicList for List> { fn into_graphic_list(self) -> List { - List::new_from_element(Graphic::RasterGPU(self)) + List::new_from_element(Graphic::RasterGPUList(self)) } } impl IntoGraphicList for List { fn into_graphic_list(self) -> List { - List::new_from_element(Graphic::Color(self)) + List::new_from_element(Graphic::ColorList(self)) } } impl IntoGraphicList for List { fn into_graphic_list(self) -> List { - List::new_from_element(Graphic::Gradient(self)) + List::new_from_element(Graphic::GradientList(self)) } } impl IntoGraphicList for List { fn into_graphic_list(self) -> List { - List::new_from_element(Graphic::Text(self)) + List::new_from_element(Graphic::TextList(self)) } } @@ -374,50 +374,50 @@ impl From> for Graphic { // DVec2 impl From> for Graphic { fn from(position: Item) -> Self { - Graphic::Vector(List::new_from_element(Vector::from_anchor_position(position.into_element()))) + Graphic::VectorList(List::new_from_element(Vector::from_anchor_position(position.into_element()))) } } // Note: List conversions handled by blanket impl in gcore impl Graphic { - pub fn as_graphic(&self) -> Option<&List> { + pub fn as_graphic_list(&self) -> Option<&List> { match self { - Graphic::Graphic(graphic) => Some(graphic), + Graphic::GraphicList(graphic_list) => Some(graphic_list), _ => None, } } - pub fn as_graphic_mut(&mut self) -> Option<&mut List> { + pub fn as_graphic_list_mut(&mut self) -> Option<&mut List> { match self { - Graphic::Graphic(graphic) => Some(graphic), + Graphic::GraphicList(graphic_list) => Some(graphic_list), _ => None, } } - pub fn as_vector(&self) -> Option<&List> { + pub fn as_vector_list(&self) -> Option<&List> { match self { - Graphic::Vector(vector) => Some(vector), + Graphic::VectorList(vector) => Some(vector), _ => None, } } - pub fn as_vector_mut(&mut self) -> Option<&mut List> { + pub fn as_vector_list_mut(&mut self) -> Option<&mut List> { match self { - Graphic::Vector(vector) => Some(vector), + Graphic::VectorList(vector) => Some(vector), _ => None, } } - pub fn as_raster(&self) -> Option<&List>> { + pub fn as_raster_cpu_list(&self) -> Option<&List>> { match self { - Graphic::RasterCPU(raster) => Some(raster), + Graphic::RasterCPUList(raster) => Some(raster), _ => None, } } - pub fn as_raster_mut(&mut self) -> Option<&mut List>> { + pub fn as_raster_cpu_list_mut(&mut self) -> Option<&mut List>> { match self { - Graphic::RasterCPU(raster) => Some(raster), + Graphic::RasterCPUList(raster) => Some(raster), _ => None, } } @@ -429,19 +429,19 @@ impl Graphic { match self { Graphic::None => true, - Graphic::Vector(list) => all_clipped(list), - Graphic::Graphic(list) => all_clipped(list), - Graphic::RasterCPU(list) => all_clipped(list), - Graphic::RasterGPU(list) => all_clipped(list), - Graphic::Color(list) => all_clipped(list), - Graphic::Gradient(list) => all_clipped(list), - Graphic::Text(list) => all_clipped(list), + Graphic::VectorList(list) => all_clipped(list), + Graphic::GraphicList(list) => all_clipped(list), + Graphic::RasterCPUList(list) => all_clipped(list), + Graphic::RasterGPUList(list) => all_clipped(list), + Graphic::ColorList(list) => all_clipped(list), + Graphic::GradientList(list) => all_clipped(list), + Graphic::TextList(list) => all_clipped(list), } } pub fn can_reduce_to_clip_path(&self) -> bool { match self { - Graphic::Vector(vector) => (0..vector.len()).all(|index| { + Graphic::VectorList(vector) => (0..vector.len()).all(|index| { let opacity: f64 = vector.attribute_cloned_or(ATTR_OPACITY, index, 1.); let appearance = vector.attribute::(ATTR_APPEARANCE, index); @@ -468,8 +468,8 @@ impl Graphic { pub fn is_opaque(&self) -> bool { match self { Graphic::None => false, - Graphic::Graphic(list) => !list.is_empty() && list.iter_element_values().all(Graphic::is_opaque), - Graphic::Vector(list) => { + Graphic::GraphicList(list) => !list.is_empty() && list.iter_element_values().all(Graphic::is_opaque), + Graphic::VectorList(list) => { !list.is_empty() && (0..list.len()).all(|i| { let opacity: f64 = list.attribute_cloned_or(ATTR_OPACITY, i, 1.); @@ -493,17 +493,17 @@ impl Graphic { opacity >= 1. - f64::EPSILON && fill_opaque && strokes_opaque_or_invisible }) } - Graphic::Color(list) => list.element(0).is_some_and(|color| color.is_opaque()), - Graphic::Gradient(list) => list.element(0).is_some_and(|stops| stops.iter().all(|stop| stop.color.is_opaque())), - Graphic::RasterCPU(_) | Graphic::RasterGPU(_) | Graphic::Text(_) => false, + Graphic::ColorList(list) => list.element(0).is_some_and(|color| color.is_opaque()), + Graphic::GradientList(list) => list.element(0).is_some_and(|stops| stops.iter().all(|stop| stop.color.is_opaque())), + Graphic::RasterCPUList(_) | Graphic::RasterGPUList(_) | Graphic::TextList(_) => false, } } pub fn is_fully_transparent(&self) -> bool { match self { Graphic::None => true, - Graphic::Graphic(list) => list.iter_element_values().all(Graphic::is_fully_transparent), - Graphic::Vector(list) => (0..list.len()).all(|i| { + Graphic::GraphicList(list) => list.iter_element_values().all(Graphic::is_fully_transparent), + Graphic::VectorList(list) => (0..list.len()).all(|i| { let opacity: f64 = list.attribute_cloned_or(ATTR_OPACITY, i, 1.); if opacity <= f64::EPSILON { return true; @@ -528,29 +528,29 @@ impl Graphic { fills_invisible && strokes_invisible }), - Graphic::Color(list) => list.iter_element_values().all(|color| color.a() == 0.), - Graphic::Gradient(list) => list.iter_element_values().all(|stops| stops.iter().all(|stop| stop.color.a() == 0.)), - Graphic::RasterCPU(_) | Graphic::RasterGPU(_) | Graphic::Text(_) => false, + Graphic::ColorList(list) => list.iter_element_values().all(|color| color.a() == 0.), + Graphic::GradientList(list) => list.iter_element_values().all(|stops| stops.iter().all(|stop| stop.color.a() == 0.)), + Graphic::RasterCPUList(_) | Graphic::RasterGPUList(_) | Graphic::TextList(_) => false, } } /// True if this paint opaquely covers the entire fill region. /// Vector, Raster, and a nested Graphic may leave gaps, so they return false. pub fn covers_opaquely(&self) -> bool { - matches!(self, Graphic::Color(_) | Graphic::Gradient(_)) && self.is_opaque() + matches!(self, Graphic::ColorList(_) | Graphic::GradientList(_)) && self.is_opaque() } /// Returns true if this graphic contains no content. pub fn is_empty(&self) -> bool { match self { Graphic::None => true, - Graphic::Graphic(list) => list.is_empty(), - Graphic::Vector(list) => list.is_empty(), - Graphic::Color(list) => list.is_empty(), - Graphic::Gradient(list) => list.is_empty(), - Graphic::RasterCPU(list) => list.is_empty(), - Graphic::RasterGPU(list) => list.is_empty(), - Graphic::Text(list) => list.is_empty(), + Graphic::GraphicList(list) => list.is_empty(), + Graphic::VectorList(list) => list.is_empty(), + Graphic::ColorList(list) => list.is_empty(), + Graphic::GradientList(list) => list.is_empty(), + Graphic::RasterCPUList(list) => list.is_empty(), + Graphic::RasterGPUList(list) => list.is_empty(), + Graphic::TextList(list) => list.is_empty(), } } } @@ -595,26 +595,26 @@ impl BoundingBox for Graphic { fn bounding_box(&self, transform: DAffine2, include_stroke: bool) -> RenderBoundingBox { match self { Graphic::None => RenderBoundingBox::None, - Graphic::Vector(list) => vector_list_bounding_box(list, transform, include_stroke), - Graphic::RasterCPU(list) => list.bounding_box(transform, include_stroke), - Graphic::RasterGPU(list) => list.bounding_box(transform, include_stroke), - Graphic::Graphic(list) => list.bounding_box(transform, include_stroke), - Graphic::Color(list) => list.bounding_box(transform, include_stroke), - Graphic::Gradient(list) => list.bounding_box(transform, include_stroke), - Graphic::Text(list) => list.bounding_box(transform, include_stroke), + Graphic::VectorList(list) => vector_list_bounding_box(list, transform, include_stroke), + Graphic::RasterCPUList(list) => list.bounding_box(transform, include_stroke), + Graphic::RasterGPUList(list) => list.bounding_box(transform, include_stroke), + Graphic::GraphicList(list) => list.bounding_box(transform, include_stroke), + Graphic::ColorList(list) => list.bounding_box(transform, include_stroke), + Graphic::GradientList(list) => list.bounding_box(transform, include_stroke), + Graphic::TextList(list) => list.bounding_box(transform, include_stroke), } } fn thumbnail_bounding_box(&self, transform: DAffine2, include_stroke: bool) -> RenderBoundingBox { match self { Graphic::None => RenderBoundingBox::None, - Graphic::Vector(vector) => vector_list_bounding_box(vector, transform, include_stroke), - Graphic::RasterCPU(raster) => raster.thumbnail_bounding_box(transform, include_stroke), - Graphic::RasterGPU(raster) => raster.thumbnail_bounding_box(transform, include_stroke), - Graphic::Graphic(graphic) => graphic.thumbnail_bounding_box(transform, include_stroke), - Graphic::Color(color) => color.thumbnail_bounding_box(transform, include_stroke), - Graphic::Gradient(gradient) => gradient.thumbnail_bounding_box(transform, include_stroke), - Graphic::Text(list) => list.thumbnail_bounding_box(transform, include_stroke), + Graphic::VectorList(vector) => vector_list_bounding_box(vector, transform, include_stroke), + Graphic::RasterCPUList(raster) => raster.thumbnail_bounding_box(transform, include_stroke), + Graphic::RasterGPUList(raster) => raster.thumbnail_bounding_box(transform, include_stroke), + Graphic::GraphicList(list) => list.thumbnail_bounding_box(transform, include_stroke), + Graphic::ColorList(color) => color.thumbnail_bounding_box(transform, include_stroke), + Graphic::GradientList(gradient) => gradient.thumbnail_bounding_box(transform, include_stroke), + Graphic::TextList(list) => list.thumbnail_bounding_box(transform, include_stroke), } } } @@ -623,13 +623,13 @@ impl RenderComplexity for Graphic { fn render_complexity(&self) -> usize { match self { Self::None => 0, - Self::Graphic(list) => list.render_complexity(), - Self::Vector(list) => list.render_complexity(), - Self::RasterCPU(list) => list.render_complexity(), - Self::RasterGPU(list) => list.render_complexity(), - Self::Color(list) => list.render_complexity(), - Self::Gradient(list) => list.render_complexity(), - Self::Text(list) => list.render_complexity(), + Self::GraphicList(list) => list.render_complexity(), + Self::VectorList(list) => list.render_complexity(), + Self::RasterCPUList(list) => list.render_complexity(), + Self::RasterGPUList(list) => list.render_complexity(), + Self::ColorList(list) => list.render_complexity(), + Self::GradientList(list) => list.render_complexity(), + Self::TextList(list) => list.render_complexity(), } } } @@ -712,7 +712,7 @@ mod tests { use core_types::uuid::NodeId; fn vector_graphic() -> Graphic { - Graphic::Vector(List::new_from_element(Vector::default())) + Graphic::VectorList(List::new_from_element(Vector::default())) } fn vector_list_stamped_with_layers(layers: [u64; 2]) -> List { @@ -773,7 +773,7 @@ mod tests { let flattened: List = graphics.into_flattened_list(); assert_eq!(flattened.attribute_cloned_or_default::(ATTR_OPACITY, 0), 0.5); - let mut group = List::new_from_element(Graphic::Graphic(List::new_from_element(vector_graphic()))); + let mut group = List::new_from_element(Graphic::GraphicList(GraphicList(List::new_from_element(vector_graphic())))); group.set_attribute(ATTR_OPACITY, 0, 0.5_f64); let flattened: List = group.into_flattened_list(); assert_eq!(flattened.attribute_cloned_or_default::(ATTR_OPACITY, 0), 0.5); @@ -784,7 +784,7 @@ mod tests { fn flatten_cascades_into_padded_empty_appearance_rows() { use core_types::Color; - let solid = |color: Color| List::new_from_element(Graphic::Color(List::new_from_element(color))); + let solid = |color: Color| List::new_from_element(Graphic::ColorList(List::new_from_element(color))); // Declaring an appearance on row 0 forces the column, padding row 1 with the empty appearance let mut inner = List::new(); @@ -792,13 +792,13 @@ mod tests { inner.push(Item::new_from_element(Vector::default())); inner.set_attribute(ATTR_APPEARANCE, 0, Appearance::new_single(Coverage::new_fill(), solid(Color::BLACK))); - let mut outer = List::new_from_element(Graphic::Vector(inner)); + let mut outer = List::new_from_element(Graphic::VectorList(inner)); outer.set_attribute(ATTR_APPEARANCE, 0, Appearance::new_single(Coverage::new_fill(), solid(Color::WHITE))); let flattened: List = outer.into_flattened_list(); let color_of = |index: usize| { let appearance = flattened.attribute::(ATTR_APPEARANCE, index)?; - let Some(Graphic::Color(colors)) = appearance.paint_at(0)?.element(0) else { return None }; + let Some(Graphic::ColorList(colors)) = appearance.paint_at(0)?.element(0) else { return None }; colors.element(0).copied() }; @@ -816,13 +816,13 @@ mod graphic_is_opaque_tests { fn color_graphic(alpha: f64) -> Graphic { let color = Color::from_rgbaf32(1., 0., 0., alpha as f32).unwrap(); - Graphic::Color(List::new_from_element(color)) + Graphic::ColorList(List::new_from_element(color)) } fn gradient_graphic(gradient: Gradient) -> Graphic { let mut gradient_list = List::new_from_element(gradient); gradient_list.set_attribute(ATTR_GRADIENT_SPREAD, 0, GradientSpread::Pad); - Graphic::Gradient(gradient_list) + Graphic::GradientList(gradient_list) } #[test] @@ -839,7 +839,7 @@ mod graphic_is_opaque_tests { #[test] fn vector_is_not_opaque() { - let g = Graphic::Vector(List::default()); + let g = Graphic::VectorList(List::default()); assert!(!g.is_opaque()); } diff --git a/node-graph/libraries/rendering/src/render_ext.rs b/node-graph/libraries/rendering/src/render_ext.rs index 5cbd65ea4d..3ade761151 100644 --- a/node-graph/libraries/rendering/src/render_ext.rs +++ b/node-graph/libraries/rendering/src/render_ext.rs @@ -242,13 +242,13 @@ impl RenderExt for List { let paint_attr = target.paint_attr(); match fill_graphic { - Some(Graphic::Color(color_list)) => color_list.render(svg_defs, item_transform, element_transform, stroke_transform, bounds, render_params, target), - Some(Graphic::Gradient(gradient_list)) => { + Some(Graphic::ColorList(color_list)) => color_list.render(svg_defs, item_transform, element_transform, stroke_transform, bounds, render_params, target), + Some(Graphic::GradientList(gradient_list)) => { let gradient_id = gradient_list.render(svg_defs, item_transform, element_transform, stroke_transform, bounds, render_params, target); format!(r##" {paint_attr}="url(#{gradient_id})""##) } Some(Graphic::None) => format!(r#" {paint_attr}="none""#), - Some(Graphic::Vector(_)) | Some(Graphic::RasterCPU(_)) | Some(Graphic::RasterGPU(_)) | Some(Graphic::Graphic(_)) | Some(Graphic::Text(_)) => { + Some(Graphic::VectorList(_)) | Some(Graphic::RasterCPUList(_)) | Some(Graphic::RasterGPUList(_)) | Some(Graphic::GraphicList(_)) | Some(Graphic::TextList(_)) => { let bounds = if target == PaintTarget::Stroke { // To prevent a wraparound artefact occurring when the tile boundary and the stroke region are perfectly aligned, the local coordinate is expanded slightly. let inverse = |len: f64| if len > 0. { 1. / len } else { 0. }; diff --git a/node-graph/libraries/rendering/src/renderer.rs b/node-graph/libraries/rendering/src/renderer.rs index 898acf4ea9..c0130b56ac 100644 --- a/node-graph/libraries/rendering/src/renderer.rs +++ b/node-graph/libraries/rendering/src/renderer.rs @@ -655,26 +655,26 @@ impl Render for Graphic { fn render_svg(&self, render: &mut SvgRender, render_params: &RenderParams) { match self { Graphic::None => (), - Graphic::Graphic(list) => list.render_svg(render, render_params), - Graphic::Vector(list) => list.render_svg(render, render_params), - Graphic::RasterCPU(list) => list.render_svg(render, render_params), - Graphic::RasterGPU(_) => (), - Graphic::Color(list) => list.render_svg(render, render_params), - Graphic::Gradient(list) => list.render_svg(render, render_params), - Graphic::Text(list) => list.render_svg(render, render_params), + Graphic::GraphicList(list) => list.render_svg(render, render_params), + Graphic::VectorList(list) => list.render_svg(render, render_params), + Graphic::RasterCPUList(list) => list.render_svg(render, render_params), + Graphic::RasterGPUList(_) => (), + Graphic::ColorList(list) => list.render_svg(render, render_params), + Graphic::GradientList(list) => list.render_svg(render, render_params), + Graphic::TextList(list) => list.render_svg(render, render_params), } } fn render_to_vello(&self, scene: &mut Scene, transform: DAffine2, context: &mut RenderContext, render_params: &RenderParams) { match self { Graphic::None => (), - Graphic::Graphic(list) => list.render_to_vello(scene, transform, context, render_params), - Graphic::Vector(list) => list.render_to_vello(scene, transform, context, render_params), - Graphic::RasterCPU(list) => list.render_to_vello(scene, transform, context, render_params), - Graphic::RasterGPU(list) => list.render_to_vello(scene, transform, context, render_params), - Graphic::Color(list) => list.render_to_vello(scene, transform, context, render_params), - Graphic::Gradient(list) => list.render_to_vello(scene, transform, context, render_params), - Graphic::Text(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::GraphicList(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::VectorList(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::RasterCPUList(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::RasterGPUList(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::ColorList(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::GradientList(list) => list.render_to_vello(scene, transform, context, render_params), + Graphic::TextList(list) => list.render_to_vello(scene, transform, context, render_params), } } @@ -682,10 +682,10 @@ impl Render for Graphic { if let Some(element_id) = element_id { match self { Graphic::None => {} - Graphic::Graphic(_) => { + Graphic::GraphicList(_) => { metadata.upstream_footprints.insert(element_id, footprint); } - Graphic::Vector(list) => { + Graphic::VectorList(list) => { metadata.upstream_footprints.insert(element_id, footprint); // TODO: Find a way to handle more than the first item if !list.is_empty() { @@ -697,7 +697,7 @@ impl Render for Graphic { metadata.local_transforms.insert(element_id, transform); } } - Graphic::RasterCPU(list) => { + Graphic::RasterCPUList(list) => { metadata.upstream_footprints.insert(element_id, footprint); // TODO: Find a way to handle more than the first item @@ -705,7 +705,7 @@ impl Render for Graphic { metadata.local_transforms.insert(element_id, list.attribute_cloned_or_default(ATTR_TRANSFORM, 0)); } } - Graphic::RasterGPU(list) => { + Graphic::RasterGPUList(list) => { metadata.upstream_footprints.insert(element_id, footprint); // TODO: Find a way to handle more than the first item @@ -713,7 +713,7 @@ impl Render for Graphic { metadata.local_transforms.insert(element_id, list.attribute_cloned_or_default(ATTR_TRANSFORM, 0)); } } - Graphic::Color(list) => { + Graphic::ColorList(list) => { metadata.upstream_footprints.insert(element_id, footprint); // TODO: Find a way to handle more than the first item @@ -721,7 +721,7 @@ impl Render for Graphic { metadata.local_transforms.insert(element_id, list.attribute_cloned_or_default(ATTR_TRANSFORM, 0)); } } - Graphic::Gradient(list) => { + Graphic::GradientList(list) => { metadata.upstream_footprints.insert(element_id, footprint); // TODO: Find a way to handle more than the first item @@ -729,7 +729,7 @@ impl Render for Graphic { metadata.local_transforms.insert(element_id, list.attribute_cloned_or_default(ATTR_TRANSFORM, 0)); } } - Graphic::Text(list) => { + Graphic::TextList(list) => { metadata.upstream_footprints.insert(element_id, footprint); // TODO: Find a way to handle more than the first item @@ -742,65 +742,65 @@ impl Render for Graphic { match self { Graphic::None => (), - Graphic::Graphic(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), - Graphic::Vector(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), - Graphic::RasterCPU(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), - Graphic::RasterGPU(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), - Graphic::Color(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), - Graphic::Gradient(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), - Graphic::Text(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::GraphicList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::VectorList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::RasterCPUList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::RasterGPUList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::ColorList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::GradientList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), + Graphic::TextList(list) => list.collect_metadata(metadata, footprint, element_id, inherited_appearance), } } fn add_upstream_click_targets(&self, click_targets: &mut Vec, inherited_appearance: Option<&Appearance>) { match self { Graphic::None => (), - Graphic::Graphic(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), - Graphic::Vector(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), - Graphic::RasterCPU(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), - Graphic::RasterGPU(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), - Graphic::Color(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), - Graphic::Gradient(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), - Graphic::Text(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::GraphicList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::VectorList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::RasterCPUList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::RasterGPUList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::ColorList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::GradientList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), + Graphic::TextList(list) => list.add_upstream_click_targets(click_targets, inherited_appearance), } } fn add_upstream_outline_targets(&self, outlines: &mut Vec, inherited_appearance: Option<&Appearance>) { match self { Graphic::None => (), - Graphic::Graphic(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), - Graphic::Vector(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), - Graphic::RasterCPU(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), - Graphic::RasterGPU(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), - Graphic::Color(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), - Graphic::Gradient(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), - Graphic::Text(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::GraphicList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::VectorList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::RasterCPUList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::RasterGPUList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::ColorList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::GradientList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), + Graphic::TextList(list) => list.add_upstream_outline_targets(outlines, inherited_appearance), } } fn contains_artboard(&self) -> bool { match self { Graphic::None => false, - Graphic::Graphic(list) => list.contains_artboard(), - Graphic::Vector(list) => list.contains_artboard(), - Graphic::RasterCPU(list) => list.contains_artboard(), - Graphic::RasterGPU(list) => list.contains_artboard(), - Graphic::Color(list) => list.contains_artboard(), - Graphic::Gradient(list) => list.contains_artboard(), - Graphic::Text(list) => list.contains_artboard(), + Graphic::GraphicList(list) => list.contains_artboard(), + Graphic::VectorList(list) => list.contains_artboard(), + Graphic::RasterCPUList(list) => list.contains_artboard(), + Graphic::RasterGPUList(list) => list.contains_artboard(), + Graphic::ColorList(list) => list.contains_artboard(), + Graphic::GradientList(list) => list.contains_artboard(), + Graphic::TextList(list) => list.contains_artboard(), } } fn new_ids_from_hash(&mut self, reference: Option) { match self { Graphic::None => (), - Graphic::Graphic(list) => list.new_ids_from_hash(reference), - Graphic::Vector(list) => list.new_ids_from_hash(reference), - Graphic::RasterCPU(_) => (), - Graphic::RasterGPU(_) => (), - Graphic::Color(_) => (), - Graphic::Gradient(_) => (), - Graphic::Text(_) => (), + Graphic::GraphicList(list) => list.new_ids_from_hash(reference), + Graphic::VectorList(list) => list.new_ids_from_hash(reference), + Graphic::RasterCPUList(_) => (), + Graphic::RasterGPUList(_) => (), + Graphic::ColorList(_) => (), + Graphic::GradientList(_) => (), + Graphic::TextList(_) => (), } } } @@ -1279,7 +1279,7 @@ fn render_vector_item_svg(list: &List, index: usize, vector: &Vector, re // The mask must draw at full alpha so the SVG ``/`` fully zeroes the path interior. // The wrapping SVG group (above) handles the user-set opacity. let mut mask_item = Item::new_from_element(cloned_vector).with_attribute(ATTR_TRANSFORM, item_transform); - let black_fill = List::new_from_element(Graphic::Color(List::new_from_element(Color::BLACK))); + let black_fill = List::new_from_element(Graphic::ColorList(List::new_from_element(Color::BLACK))); mask_item.set_attribute(ATTR_APPEARANCE, Appearance::new_single(Coverage::new_fill(), black_fill)); let vector_item = List::new_from_item(mask_item); @@ -1361,7 +1361,7 @@ fn render_vector_item_svg(list: &List, index: usize, vector: &Vector, re // Gradient should align with the fill path bbox so that a shared gradient lines up across fill and stroke. // Only clipping-based paints need the stroke-inclusive bbox. let paint_bounds = match list.element(0) { - Some(Graphic::Color(_)) | Some(Graphic::Gradient(_)) => bounds_matrix, + Some(Graphic::ColorList(_)) | Some(Graphic::GradientList(_)) => bounds_matrix, _ => stroke_bounds_matrix, }; list.render(defs, item_transform, element_transform, applied_stroke_transform, paint_bounds, &render_params, PaintTarget::Stroke) @@ -1429,7 +1429,7 @@ impl Render for List { let mut masked_by = None; if next_clips && clip_mask_state.is_none() { - let masker = Graphic::Vector(List::new_from_item(Item::from_parts(vector.clone(), self.clone_item_attributes(index)))); + let masker = Graphic::VectorList(List::new_from_item(Item::from_parts(vector.clone(), self.clone_item_attributes(index)))); let mask_type = if masker.can_reduce_to_clip_path() { MaskType::Clip } else { MaskType::Mask }; let uuid = generate_uuid(); @@ -1586,13 +1586,13 @@ impl Render for List { let Some(paint) = fill_graphic.element(paint_index) else { continue }; match paint { Graphic::None => continue, - Graphic::Color(list) => { + Graphic::ColorList(list) => { let Some(color) = list.element(0) else { continue }; let fill = peniko::Brush::Solid(SRGBA8::from(*color).to_peniko_color()); scene.fill(fill_rule, kurbo::Affine::new(element_transform.to_cols_array()), &fill, None, path); } - Graphic::Gradient(list) => { + Graphic::GradientList(list) => { let Some((brush, gradient_to_device)) = create_peniko_gradient_brush(list, &multiplied_transform) else { continue; }; @@ -1605,7 +1605,7 @@ impl Render for List { let brush_transform = kurbo::Affine::new((inverse_element_transform * gradient_to_device).to_cols_array()); scene.fill(fill_rule, kurbo::Affine::new(element_transform.to_cols_array()), &brush, Some(brush_transform), path); } - Graphic::Vector(_) | Graphic::RasterCPU(_) | Graphic::RasterGPU(_) | Graphic::Graphic(_) | Graphic::Text(_) => { + Graphic::VectorList(_) | Graphic::RasterCPUList(_) | Graphic::RasterGPUList(_) | Graphic::GraphicList(_) | Graphic::TextList(_) => { scene.push_clip_layer(fill_rule, kurbo::Affine::new(element_transform.to_cols_array()), path); paint.render_to_vello(scene, multiplied_transform, context, &paint_render_params); scene.pop_layer(); @@ -1669,13 +1669,13 @@ impl Render for List { match stroke_graphic { Graphic::None => continue, - Graphic::Color(list) => { + Graphic::ColorList(list) => { let Some(color) = list.element(0) else { continue }; let brush = peniko::Brush::Solid(SRGBA8::from(*color).to_peniko_color()); scene.stroke(&stroke, kurbo::Affine::new(element_transform.to_cols_array()), &brush, None, &path); } - Graphic::Gradient(list) => { + Graphic::GradientList(list) => { let Some((brush, gradient_to_device)) = create_peniko_gradient_brush(list, &multiplied_transform) else { continue; }; @@ -1688,7 +1688,7 @@ impl Render for List { scene.stroke(&stroke, kurbo::Affine::new(element_transform.to_cols_array()), &brush, Some(brush_transform), &path); } - Graphic::Vector(_) | Graphic::RasterCPU(_) | Graphic::RasterGPU(_) | Graphic::Graphic(_) | Graphic::Text(_) => { + Graphic::VectorList(_) | Graphic::RasterCPUList(_) | Graphic::RasterGPUList(_) | Graphic::GraphicList(_) | Graphic::TextList(_) => { let stroked = peniko::kurbo::stroke(path.iter(), &stroke, &StrokeOpts::default(), 0.01); scene.push_clip_layer(peniko::Fill::NonZero, kurbo::Affine::new(element_transform.to_cols_array()), &stroked); @@ -1713,7 +1713,7 @@ impl Render for List { // The mask must draw at full alpha so `SrcOut` fully zeroes the path interior. // The outer opacity/blend layer (above) handles the user-set opacity. let mut mask_item = Item::new_from_element(cloned_element).with_attribute(ATTR_TRANSFORM, item_transform); - let black_fill = List::new_from_element(Graphic::Color(List::new_from_element(Color::BLACK))); + let black_fill = List::new_from_element(Graphic::ColorList(List::new_from_element(Color::BLACK))); mask_item.set_attribute(ATTR_APPEARANCE, Appearance::new_single(Coverage::new_fill(), black_fill)); let vector_list = List::new_from_item(mask_item); @@ -2680,7 +2680,7 @@ pub fn text_list_bounding_box(list: &List, outer_transform: DAffine2) -> } } -/// Like `List::thumbnail_bounding_box`, but lays out `Graphic::Text` items, which the `BoundingBox` trait reports as `None`. +/// Like `List::thumbnail_bounding_box`, but lays out `Graphic::TextList` items, which the `BoundingBox` trait reports as `None`. /// Used for layer thumbnails so text layers (whose content is a `List` wrapping the text) frame their content. pub fn graphic_list_bounding_box(list: &List, transform: DAffine2) -> RenderBoundingBox { let mut combined: Option<[DVec2; 2]> = None; @@ -2690,8 +2690,8 @@ pub fn graphic_list_bounding_box(list: &List, transform: DAffine2) -> R let item_transform = transform * list.attribute_cloned_or_default::(ATTR_TRANSFORM, index); let Some(graphic) = list.element(index) else { continue }; let bounds = match graphic { - Graphic::Text(text_list) => text_list_bounding_box(text_list, item_transform), - Graphic::Graphic(sub_list) => graphic_list_bounding_box(sub_list, item_transform), + Graphic::TextList(text_list) => text_list_bounding_box(text_list, item_transform), + Graphic::GraphicList(sub_list) => graphic_list_bounding_box(sub_list, item_transform), other => other.thumbnail_bounding_box(item_transform, true), }; match bounds { diff --git a/node-graph/libraries/vector-types/src/gradient.rs b/node-graph/libraries/vector-types/src/gradient.rs index 8c66ab7335..9ba8099e34 100644 --- a/node-graph/libraries/vector-types/src/gradient.rs +++ b/node-graph/libraries/vector-types/src/gradient.rs @@ -21,7 +21,7 @@ pub enum GradientForm { /// attributes place each stop along the 0 to 1 range. Stops lacking the `position` attribute distribute evenly, /// and stops lacking the `midpoint` attribute interpolate linearly (`0.5`). #[derive(Default, Debug, Clone, PartialEq, graphene_hash::CacheHash, DynAny)] -pub struct Gradient(List); +pub struct Gradient(pub List); /// A gradient's per-stop parallel arrays, generic over color format: `GradientStops` nests inside the /// [`GradientRamp`] exchange struct, while `GradientStops` is the JS-boundary shape used by the color picker UI. diff --git a/node-graph/nodes/graphic/src/graphic.rs b/node-graph/nodes/graphic/src/graphic.rs index 80ef1c65e2..109b7960ab 100644 --- a/node-graph/nodes/graphic/src/graphic.rs +++ b/node-graph/nodes/graphic/src/graphic.rs @@ -983,7 +983,7 @@ pub async fn flatten_graphic(_: impl Ctx, content: List, fully_flatten: match current_element { // If we're allowed to recurse, flatten any graphics we encounter - Graphic::Graphic(mut current_element) if recurse => { + Graphic::GraphicList(mut current_element) if recurse => { // Apply the parent graphic's transform to all child elements for graphic_transform in current_element.iter_attribute_values_mut_or_default::(ATTR_TRANSFORM) { *graphic_transform = current_transform * *graphic_transform; @@ -991,7 +991,7 @@ pub async fn flatten_graphic(_: impl Ctx, content: List, fully_flatten: flatten_list(output_graphic_list, current_element, fully_flatten, recursion_depth + 1); } - // Push any leaf elements we encounter: either `Graphic::Graphic(...)` values beyond the recursion depth, or non-`Graphic::Graphic` variants (e.g. `Graphic::Vector`, `Graphic::Raster*`, `Graphic::Color`, `Graphic::Gradient`, `Graphic::Text`) + // Push any leaf element: a group beyond the recursion depth, or any non-group variant _ => { let attributes = current_graphic_list.clone_item_attributes(index); output_graphic_list.push(Item::from_parts(current_element, attributes)); diff --git a/node-graph/nodes/path-bool/src/lib.rs b/node-graph/nodes/path-bool/src/lib.rs index b3181f1741..1b83303a96 100644 --- a/node-graph/nodes/path-bool/src/lib.rs +++ b/node-graph/nodes/path-bool/src/lib.rs @@ -224,9 +224,9 @@ fn flatten_vector(graphic_list: &List) -> List { }; match graphic.clone() { - Graphic::Vector(vector) => vector.into_iter().map(compose_parent).collect::>(), - Graphic::Text(text) => text_nodes::shape_text_list(&text, false).into_iter().map(compose_parent).collect::>(), - Graphic::Graphic(mut graphic) => { + Graphic::VectorList(vector) => vector.into_iter().map(compose_parent).collect::>(), + Graphic::TextList(text) => text_nodes::shape_text_list(&text, false).into_iter().map(compose_parent).collect::>(), + Graphic::GraphicList(mut graphic) => { if parent_has_transform { for transform in graphic.iter_attribute_values_mut_or_default::(ATTR_TRANSFORM) { *transform = parent_transform * *transform; @@ -261,7 +261,7 @@ fn flatten_vector(graphic_list: &List) -> List { } } // Rasters, colors, and gradients bound no region, so they contribute no operand - Graphic::None | Graphic::RasterCPU(_) | Graphic::RasterGPU(_) | Graphic::Color(_) | Graphic::Gradient(_) => Vec::new(), + Graphic::None | Graphic::RasterCPUList(_) | Graphic::RasterGPUList(_) | Graphic::ColorList(_) | Graphic::GradientList(_) => Vec::new(), } }) .collect() diff --git a/node-graph/nodes/repeat/src/repeat_nodes.rs b/node-graph/nodes/repeat/src/repeat_nodes.rs index a9ebb86c7a..c3b87556de 100644 --- a/node-graph/nodes/repeat/src/repeat_nodes.rs +++ b/node-graph/nodes/repeat/src/repeat_nodes.rs @@ -321,7 +321,7 @@ mod test { Item::new_from_element(count), ) .await; - let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::Vector(repeated))).await); + let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::VectorList(repeated))).await); let vector = vector_list.element(0).unwrap(); assert_eq!(vector.region_manipulator_groups().count(), 3); for (index, (_, manipulator_groups)) in vector.region_manipulator_groups().enumerate() { @@ -340,7 +340,7 @@ mod test { Item::new_from_element(1), ) .await; - let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::Vector(repeated))).await); + let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::VectorList(repeated))).await); let vector = vector_list.element(0).unwrap(); assert_eq!(vector.region_manipulator_groups().count(), 1); @@ -362,7 +362,7 @@ mod test { Item::new_from_element(count), ) .await; - let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::Vector(repeated))).await); + let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::VectorList(repeated))).await); let vector = vector_list.element(0).unwrap(); assert_eq!(vector.region_manipulator_groups().count(), 8); for (index, (_, manipulator_groups)) in vector.region_manipulator_groups().enumerate() { @@ -381,7 +381,7 @@ mod test { Item::new_from_element(8), ) .await; - let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::Vector(repeated))).await); + let vector_list = List::new_from_item(vector_nodes::combine_paths(Footprint::default(), List::new_from_element(Graphic::VectorList(repeated))).await); let vector = vector_list.element(0).unwrap(); assert_eq!(vector.region_manipulator_groups().count(), 8); diff --git a/node-graph/nodes/vector/src/vector_nodes.rs b/node-graph/nodes/vector/src/vector_nodes.rs index 79d4dbb556..343f2ac3e8 100644 --- a/node-graph/nodes/vector/src/vector_nodes.rs +++ b/node-graph/nodes/vector/src/vector_nodes.rs @@ -47,14 +47,14 @@ trait VectorListIterMut { impl VectorListIterMut for List { fn for_each_vector_list_mut(&mut self, mut f: impl FnMut(&mut List)) { for graphic in self.iter_element_values_mut() { - if let Some(vector_list) = graphic.as_vector_mut() { + if let Some(vector_list) = graphic.as_vector_list_mut() { f(vector_list); }; } } fn vector_count(&self) -> usize { - self.iter_element_values().filter_map(|element| element.as_vector()).map(|list| list.len()).sum() + self.iter_element_values().filter_map(|element| element.as_vector_list()).map(|list| list.len()).sum() } } @@ -83,7 +83,7 @@ impl VectorItemMut for Item { impl VectorItemMut for Item { fn for_each_vector_mut(&mut self, mut f: impl FnMut(&mut Vector, DAffine2)) { - let Some(vector_list) = self.element_mut().as_vector_mut() else { return }; + let Some(vector_list) = self.element_mut().as_vector_list_mut() else { return }; let (elements, transforms) = vector_list.element_and_attribute_slices_mut::(ATTR_TRANSFORM); for (vector, transform) in elements.iter_mut().zip(transforms.iter()) { f(vector, *transform); @@ -115,8 +115,8 @@ impl MapVectorItems for Graphic { fn map_nested(graphic: &mut Graphic, f: &mut impl FnMut(Item) -> Item) { match graphic { // Collecting from zero items would drop the attribute columns, so an empty list is left alone - Graphic::Vector(list) if !list.is_empty() => *list = std::mem::take(list).into_iter().map(&mut *f).collect(), - Graphic::Graphic(list) => list.iter_element_values_mut().for_each(|nested| map_nested(nested, f)), + Graphic::VectorList(list) if !list.is_empty() => *list = std::mem::take(list).into_iter().map(&mut *f).collect(), + Graphic::GraphicList(list) => list.iter_element_values_mut().for_each(|nested| map_nested(nested, f)), _ => {} } } @@ -130,8 +130,8 @@ impl MapVectorItems for Graphic { fn vector_elements_mut(content: &mut Item) -> Vec<&mut Vector> { fn collect<'a>(graphic: &'a mut Graphic, elements: &mut Vec<&'a mut Vector>) { match graphic { - Graphic::Vector(list) => elements.extend(list.iter_element_values_mut()), - Graphic::Graphic(list) => list.iter_element_values_mut().for_each(|nested| collect(nested, elements)), + Graphic::VectorList(list) => elements.extend(list.iter_element_values_mut()), + Graphic::GraphicList(list) => list.iter_element_values_mut().for_each(|nested| collect(nested, elements)), _ => {} } } @@ -159,14 +159,14 @@ impl ExpandVectorItems for Graphic { fn expand_nested(graphic: &mut Graphic, f: &mut impl FnMut(Item) -> List) { match graphic { // Collecting from zero items would drop the attribute columns, so an empty list is left alone - Graphic::Vector(list) if !list.is_empty() => { + Graphic::VectorList(list) if !list.is_empty() => { let mut expanded = List::with_capacity(list.len()); for item in std::mem::take(list) { expanded.extend(f(item)); } *list = expanded; } - Graphic::Graphic(list) => list.iter_element_values_mut().for_each(|nested| expand_nested(nested, f)), + Graphic::GraphicList(list) => list.iter_element_values_mut().for_each(|nested| expand_nested(nested, f)), _ => {} } } @@ -297,7 +297,7 @@ where // Stamp the gradient styling inputs onto any gradient paint missing them, whether the paint arrived as a picker value or a wire for graphic in fill.iter_element_values_mut() { - let Graphic::Gradient(gradient) = graphic else { continue }; + let Graphic::GradientList(gradient) = graphic else { continue }; if gradient.iter_attribute_values::(ATTR_GRADIENT_FORM).is_none() { for value in gradient.iter_attribute_values_mut_or_default::(ATTR_GRADIENT_FORM) { @@ -1510,8 +1510,8 @@ impl SolidifyStroke for Graphic { fn solidify_strokes(content: Item) -> List { fn solidify_nested(graphic: &mut Graphic) { match graphic { - Graphic::Vector(list) if !list.is_empty() => *list = solidify_stroke_list_with_snapshot(std::mem::take(list)), - Graphic::Graphic(list) => list.iter_element_values_mut().for_each(solidify_nested), + Graphic::VectorList(list) if !list.is_empty() => *list = solidify_stroke_list_with_snapshot(std::mem::take(list)), + Graphic::GraphicList(list) => list.iter_element_values_mut().for_each(solidify_nested), _ => {} } } @@ -2594,25 +2594,25 @@ async fn morph( } else { gradient_list.push(Item::new_from_element(stops)); } - Graphic::Gradient(gradient_list) + Graphic::GradientList(gradient_list) }; let graphic = match (a.element(0), b.element(0)) { - (Some(Graphic::Color(color_list_a)), Some(Graphic::Color(color_list_b))) => color_list_a + (Some(Graphic::ColorList(color_list_a)), Some(Graphic::ColorList(color_list_b))) => color_list_a .element(0) .zip(color_list_b.element(0)) .map(|(color_a, color_b)| Graphic::from(color_a.lerp(color_b, time as f32))), - (Some(Graphic::Color(color_list_a)), Some(Graphic::Gradient(gradient_list_b))) => color_list_a.element(0).zip(gradient_list_b.element(0)).map(|(color_a, stops_b)| { + (Some(Graphic::ColorList(color_list_a)), Some(Graphic::GradientList(gradient_list_b))) => color_list_a.element(0).zip(gradient_list_b.element(0)).map(|(color_a, stops_b)| { let solid_to_gradient = stops_b.map_colors(|_| *color_a); let stops = solid_to_gradient.lerp(stops_b, time); gradient_with_stops(gradient_list_b.clone(), stops) }), - (Some(Graphic::Gradient(gradient_list_a)), Some(Graphic::Color(color_list_b))) => gradient_list_a.element(0).zip(color_list_b.element(0)).map(|(stops_a, color_b)| { + (Some(Graphic::GradientList(gradient_list_a)), Some(Graphic::ColorList(color_list_b))) => gradient_list_a.element(0).zip(color_list_b.element(0)).map(|(stops_a, color_b)| { let gradient_to_solid = stops_a.map_colors(|_| *color_b); let stops = stops_a.lerp(&gradient_to_solid, time); gradient_with_stops(gradient_list_a.clone(), stops) }), - (Some(Graphic::Gradient(gradient_list_a)), Some(Graphic::Gradient(gradient_list_b))) => gradient_list_a.element(0).zip(gradient_list_b.element(0)).map(|(stops_a, stops_b)| { + (Some(Graphic::GradientList(gradient_list_a)), Some(Graphic::GradientList(gradient_list_b))) => gradient_list_a.element(0).zip(gradient_list_b.element(0)).map(|(stops_a, stops_b)| { let stops = stops_a.lerp(stops_b, time); let metadata_source = if time < 0.5 { gradient_list_a } else { gradient_list_b }; @@ -3759,7 +3759,7 @@ mod test { Item::new_from_element(0), ) .await; - let combined = List::new_from_item(super::combine_paths(Footprint::default(), List::new_from_element(Graphic::Vector(copy_to_points))).await); + let combined = List::new_from_item(super::combine_paths(Footprint::default(), List::new_from_element(Graphic::VectorList(copy_to_points))).await); let combined_copy_to_points = combined.element(0).unwrap(); assert_eq!(combined_copy_to_points.region_manipulator_groups().count(), expected_points.len()); @@ -3912,7 +3912,7 @@ mod test { let fill = appearance.first_paint_of(Cover::Fill).expect("Morph should keep the fill paint at the midpoint"); // Interpolated color between red and blue should have >0 value on both R and B - let Some(Graphic::Color(colors)) = fill.element(0) else { + let Some(Graphic::ColorList(colors)) = fill.element(0) else { panic!("Expected a solid color fill, got {:?}", fill.element(0)); }; let color = *colors.element(0).expect("Color present"); @@ -3929,7 +3929,7 @@ mod test { let paint_color = |appearance: &Appearance, cover| { let paint = appearance.first_paint_of(cover).expect("Morph should keep both paints at the midpoint"); - let Some(Graphic::Color(colors)) = paint.element(0) else { + let Some(Graphic::ColorList(colors)) = paint.element(0) else { panic!("Expected a solid color paint, got {:?}", paint.element(0)); }; *colors.element(0).expect("Color present")