mirror of
https://github.com/GraphiteEditor/Graphite.git
synced 2025-07-07 15:55:00 +00:00
Migrate pass through and value node to identity implementation
This commit is contained in:
parent
4075003505
commit
8e04531336
11 changed files with 47 additions and 55 deletions
|
@ -84,11 +84,11 @@ fn static_nodes() -> Vec<DocumentNodeDefinition> {
|
|||
let custom = vec![
|
||||
// TODO: Auto-generate this from its proto node macro
|
||||
DocumentNodeDefinition {
|
||||
identifier: "Identity",
|
||||
identifier: "Pass Through",
|
||||
category: "General",
|
||||
node_template: NodeTemplate {
|
||||
document_node: DocumentNode {
|
||||
implementation: DocumentNodeImplementation::proto("graphene_core::ops::IdentityNode"),
|
||||
implementation: DocumentNodeImplementation::proto("graphene_std::any::IdentityNode"),
|
||||
inputs: vec![NodeInput::value(TaggedValue::None, true)],
|
||||
..Default::default()
|
||||
},
|
||||
|
@ -99,14 +99,14 @@ fn static_nodes() -> Vec<DocumentNodeDefinition> {
|
|||
},
|
||||
},
|
||||
description: Cow::Borrowed("Passes-through the input value without changing it. This is useful for rerouting wires for organization purposes."),
|
||||
properties: Some("identity_properties"),
|
||||
properties: Some("pass_through_properties"),
|
||||
},
|
||||
DocumentNodeDefinition {
|
||||
identifier: "Value",
|
||||
category: "General",
|
||||
node_template: NodeTemplate {
|
||||
document_node: DocumentNode {
|
||||
implementation: DocumentNodeImplementation::proto("graphene_core::any::ValueNode"),
|
||||
implementation: DocumentNodeImplementation::proto("graphene_std::any::IdentityNode"),
|
||||
manual_composition: Some(generic!(T)),
|
||||
inputs: vec![NodeInput::value(TaggedValue::None, false)],
|
||||
..Default::default()
|
||||
|
@ -2161,8 +2161,8 @@ fn static_node_properties() -> NodeProperties {
|
|||
map.insert("grid_properties".to_string(), Box::new(node_properties::grid_properties));
|
||||
map.insert("sample_polyline_properties".to_string(), Box::new(node_properties::sample_polyline_properties));
|
||||
map.insert(
|
||||
"identity_properties".to_string(),
|
||||
Box::new(|_node_id, _context| node_properties::string_properties("The identity node passes its data through.")),
|
||||
"pass_through_properties".to_string(),
|
||||
Box::new(|_node_id, _context| node_properties::string_properties("The Pass Through node can be used to organize wires.")),
|
||||
);
|
||||
map.insert(
|
||||
"monitor_properties".to_string(),
|
||||
|
|
|
@ -139,7 +139,7 @@ const REPLACEMENTS: &[(&str, &str)] = &[
|
|||
("graphene_std::raster::NoisePatternNode", "graphene_raster_nodes::std_nodes::NoisePatternNode"),
|
||||
("graphene_std::raster::MandelbrotNode", "graphene_raster_nodes::std_nodes::MandelbrotNode"),
|
||||
// text
|
||||
("graphene_core::text::TextGeneratorNode", "graphene_core::text::TextNode"),
|
||||
("graphene_core::text::TextGeneratorNode", "graphene_std::text::TextNode"),
|
||||
// transform
|
||||
("graphene_core::transform::SetTransformNode", "graphene_core::transform_nodes::ReplaceTransformNode"),
|
||||
("graphene_core::transform::ReplaceTransformNode", "graphene_core::transform_nodes::ReplaceTransformNode"),
|
||||
|
@ -158,7 +158,7 @@ const REPLACEMENTS: &[(&str, &str)] = &[
|
|||
("graphene_core::vector::generator_nodes::StarGenerator", "graphene_core::vector::generator_nodes::StarNode"),
|
||||
("graphene_std::executor::BlendGpuImageNode", "graphene_std::gpu_nodes::BlendGpuImageNode"),
|
||||
("graphene_std::raster::SampleNode", "graphene_std::raster::SampleImageNode"),
|
||||
("graphene_core::transform::CullNode", "graphene_core::ops::IdentityNode"),
|
||||
("graphene_core::transform::CullNode", "graphene_std::any::IdentityNode"),
|
||||
("graphene_std::raster::MaskImageNode", "graphene_std::raster::MaskNode"),
|
||||
("graphene_core::vector::FlattenVectorElementsNode", "graphene_core::vector::FlattenPathNode"),
|
||||
("graphene_std::vector::BooleanOperationNode", "graphene_path_bool::BooleanOperationNode"),
|
||||
|
|
|
@ -1,13 +1,6 @@
|
|||
use crate::Node;
|
||||
use std::marker::PhantomData;
|
||||
|
||||
// TODO: Rename to "Passthrough"
|
||||
/// Passes-through the input value without changing it. This is useful for rerouting wires for organization purposes.
|
||||
#[node_macro::node(skip_impl)]
|
||||
fn identity<'i, T: 'i + Send>(value: T) -> T {
|
||||
value
|
||||
}
|
||||
|
||||
// Type
|
||||
// TODO: Document this
|
||||
#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Default)]
|
||||
|
|
|
@ -13,28 +13,28 @@ impl<'i, const N: u32, I> Node<'i, I> for IntNode<N> {
|
|||
}
|
||||
}
|
||||
|
||||
// #[derive(Default, Debug, Clone, Copy)]
|
||||
// pub struct ValueNode<T>(pub T);
|
||||
#[derive(Default, Debug, Clone, Copy)]
|
||||
pub struct ValueNode<T>(pub T);
|
||||
|
||||
// impl<'i, T: 'i, I> Node<'i, I> for ValueNode<T> {
|
||||
// type Output = &'i T;
|
||||
// #[inline(always)]
|
||||
// fn eval(&'i self, _input: I) -> Self::Output {
|
||||
// &self.0
|
||||
// }
|
||||
// }
|
||||
impl<'i, T: 'i, I> Node<'i, I> for ValueNode<T> {
|
||||
type Output = &'i T;
|
||||
#[inline(always)]
|
||||
fn eval(&'i self, _input: I) -> Self::Output {
|
||||
&self.0
|
||||
}
|
||||
}
|
||||
|
||||
// impl<T> ValueNode<T> {
|
||||
// pub const fn new(value: T) -> ValueNode<T> {
|
||||
// ValueNode(value)
|
||||
// }
|
||||
// }
|
||||
impl<T> ValueNode<T> {
|
||||
pub const fn new(value: T) -> ValueNode<T> {
|
||||
ValueNode(value)
|
||||
}
|
||||
}
|
||||
|
||||
// impl<T> From<T> for ValueNode<T> {
|
||||
// fn from(value: T) -> Self {
|
||||
// ValueNode::new(value)
|
||||
// }
|
||||
// }
|
||||
impl<T> From<T> for ValueNode<T> {
|
||||
fn from(value: T) -> Self {
|
||||
ValueNode::new(value)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Copy)]
|
||||
pub struct AsRefNode<T: AsRef<U>, U>(pub T, PhantomData<U>);
|
||||
|
|
|
@ -460,7 +460,7 @@ pub enum DocumentNodeImplementation {
|
|||
|
||||
impl Default for DocumentNodeImplementation {
|
||||
fn default() -> Self {
|
||||
Self::ProtoNode(ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode"))
|
||||
Self::ProtoNode(ProtoNodeIdentifier::new("graphene_std::any::IdentityNode"))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -920,7 +920,7 @@ impl NodeNetwork {
|
|||
return;
|
||||
};
|
||||
// If the node is hidden, replace it with an identity node
|
||||
let identity_node = DocumentNodeImplementation::ProtoNode("graphene_core::ops::IdentityNode".into());
|
||||
let identity_node = DocumentNodeImplementation::ProtoNode("graphene_std::any::IdentityNode".into());
|
||||
if !node.visible && node.implementation != identity_node {
|
||||
node.implementation = identity_node;
|
||||
|
||||
|
@ -1096,7 +1096,7 @@ impl NodeNetwork {
|
|||
fn remove_id_node(&mut self, id: NodeId) -> Result<(), String> {
|
||||
let node = self.nodes.get(&id).ok_or_else(|| format!("Node with id {id} does not exist"))?.clone();
|
||||
if let DocumentNodeImplementation::ProtoNode(ident) = &node.implementation {
|
||||
if ident.name == "graphene_core::ops::IdentityNode" {
|
||||
if ident.name == "graphene_std::any::IdentityNode" {
|
||||
assert_eq!(node.inputs.len(), 1, "Id node has more than one input");
|
||||
if let NodeInput::Node { node_id, output_index, .. } = node.inputs[0] {
|
||||
let node_input_output_index = output_index;
|
||||
|
@ -1143,13 +1143,13 @@ impl NodeNetwork {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
/// Strips out any [`graphene_core::ops::IdentityNode`]s that are unnecessary.
|
||||
/// Strips out any [`graphene_std::any::IdentityNode`]s that are unnecessary.
|
||||
pub fn remove_redundant_id_nodes(&mut self) {
|
||||
let id_nodes = self
|
||||
.nodes
|
||||
.iter()
|
||||
.filter(|(_, node)| {
|
||||
matches!(&node.implementation, DocumentNodeImplementation::ProtoNode(ident) if ident == &ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode"))
|
||||
matches!(&node.implementation, DocumentNodeImplementation::ProtoNode(ident) if ident == &ProtoNodeIdentifier::new("graphene_std::any::IdentityNode"))
|
||||
&& node.inputs.len() == 1
|
||||
&& matches!(node.inputs[0], NodeInput::Node { .. })
|
||||
})
|
||||
|
@ -1338,7 +1338,7 @@ mod test {
|
|||
fn extract_node() {
|
||||
let id_node = DocumentNode {
|
||||
inputs: vec![],
|
||||
implementation: DocumentNodeImplementation::ProtoNode("graphene_core::ops::IdentityNode".into()),
|
||||
implementation: DocumentNodeImplementation::ProtoNode("graphene_std::any::IdentityNode".into()),
|
||||
..Default::default()
|
||||
};
|
||||
// TODO: Extend test cases to test nested network
|
||||
|
@ -1540,7 +1540,7 @@ mod test {
|
|||
NodeId(1),
|
||||
DocumentNode {
|
||||
inputs: vec![NodeInput::network(concrete!(u32), 0)],
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode")),
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_std::any::IdentityNode")),
|
||||
..Default::default()
|
||||
},
|
||||
),
|
||||
|
@ -1548,7 +1548,7 @@ mod test {
|
|||
NodeId(2),
|
||||
DocumentNode {
|
||||
inputs: vec![NodeInput::network(concrete!(u32), 1)],
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode")),
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_std::any::IdentityNode")),
|
||||
..Default::default()
|
||||
},
|
||||
),
|
||||
|
@ -1575,7 +1575,7 @@ mod test {
|
|||
NodeId(2),
|
||||
DocumentNode {
|
||||
inputs: vec![result_node_input],
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode")),
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_std::any::IdentityNode")),
|
||||
..Default::default()
|
||||
},
|
||||
),
|
||||
|
|
|
@ -143,7 +143,7 @@ pub struct ProtoNode {
|
|||
impl Default for ProtoNode {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
identifier: ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode"),
|
||||
identifier: ProtoNodeIdentifier::new("graphene_std::any::IdentityNode"),
|
||||
construction_args: ConstructionArgs::Value(value::TaggedValue::U32(0).into()),
|
||||
input: ProtoNodeInput::None,
|
||||
original_location: OriginalLocation::default(),
|
||||
|
|
|
@ -47,20 +47,19 @@ pub fn downcast_node<I: StaticType, O: StaticType>(n: SharedNodeContainer) -> Do
|
|||
DowncastBothNode::new(n)
|
||||
}
|
||||
|
||||
// Same idea as the identity node, but with a hidden primary input in order to have an auto generated properties widget for the value
|
||||
pub struct Value {
|
||||
pub struct IdentityNode {
|
||||
value: SharedNodeContainer,
|
||||
}
|
||||
|
||||
impl<'i> Node<'i, Any<'i>> for Value {
|
||||
impl<'i> Node<'i, Any<'i>> for IdentityNode {
|
||||
type Output = DynFuture<'i, Any<'i>>;
|
||||
fn eval(&'i self, input: Any<'i>) -> Self::Output {
|
||||
Box::pin(async move { self.value.eval(input).await })
|
||||
}
|
||||
}
|
||||
|
||||
impl Value {
|
||||
impl IdentityNode {
|
||||
pub const fn new(value: SharedNodeContainer) -> Self {
|
||||
Value { value }
|
||||
IdentityNode { value }
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,7 +20,7 @@ mod tests {
|
|||
NodeId(0),
|
||||
DocumentNode {
|
||||
inputs: vec![NodeInput::network(concrete!(u32), 0)],
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode")),
|
||||
implementation: DocumentNodeImplementation::ProtoNode(ProtoNodeIdentifier::new("graphene_std::any::IdentityNode")),
|
||||
..Default::default()
|
||||
},
|
||||
),
|
||||
|
|
|
@ -14,7 +14,7 @@ use graphene_std::Context;
|
|||
use graphene_std::GraphicElement;
|
||||
#[cfg(feature = "gpu")]
|
||||
use graphene_std::any::DowncastBothNode;
|
||||
use graphene_std::any::{ComposeTypeErased, DynAnyNode, IntoTypeErasedNode, Value};
|
||||
use graphene_std::any::{ComposeTypeErased, DynAnyNode, IdentityNode, IntoTypeErasedNode};
|
||||
use graphene_std::application_io::{ImageTexture, SurfaceFrame};
|
||||
#[cfg(feature = "gpu")]
|
||||
use graphene_std::wasm_application_io::{WasmEditorApi, WasmSurfaceHandle};
|
||||
|
@ -114,10 +114,10 @@ fn node_registry() -> HashMap<ProtoNodeIdentifier, HashMap<NodeIOTypes, NodeCons
|
|||
),
|
||||
),
|
||||
(
|
||||
ProtoNodeIdentifier::new("graphene_core::any::ValueNode"),
|
||||
ProtoNodeIdentifier::new("graphene_std::any::IdentityNode"),
|
||||
|args| {
|
||||
Box::pin(async move {
|
||||
let node = Value::new(args[0].clone());
|
||||
let node = IdentityNode::new(args[0].clone());
|
||||
node.into_type_erased()
|
||||
})
|
||||
},
|
||||
|
|
|
@ -68,7 +68,7 @@ pub fn wrap_network_in_scope(mut network: NodeNetwork, editor_api: Arc<WasmEdito
|
|||
inner_network,
|
||||
render_node,
|
||||
DocumentNode {
|
||||
implementation: DocumentNodeImplementation::proto("graphene_core::ops::IdentityNode"),
|
||||
implementation: DocumentNodeImplementation::proto("graphene_std::any::IdentityNode"),
|
||||
inputs: vec![NodeInput::value(TaggedValue::EditorApi(editor_api), false)],
|
||||
..Default::default()
|
||||
},
|
||||
|
|
|
@ -49,7 +49,7 @@ pub fn generate_node_substitutions() -> HashMap<String, DocumentNode> {
|
|||
let input_count = inputs.len();
|
||||
let network_inputs = (0..input_count).map(|i| NodeInput::node(NodeId(i as u64), 0)).collect();
|
||||
|
||||
let identity_node = ProtoNodeIdentifier::new("graphene_core::ops::IdentityNode");
|
||||
let identity_node = ProtoNodeIdentifier::new("graphene_std::any::IdentityNode");
|
||||
|
||||
let into_node_registry = &interpreted_executor::node_registry::NODE_REGISTRY;
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue