use super::super::framework::{NodeImpl, eval_input};
use crate::gui_builder::nodes::{Node, NodeCategory, NodeGraph, NodeLibrary, NodeParams, Pin, PinType};
use crate::gui_builder::node_registry::{NodeSpec, ParamKind};
use crate::gui_builder::interpreter::ExecutionStack;
use crate::gui_builder::runtime::RuntimeContext;

pub struct BranchNode;

impl NodeImpl for BranchNode {
    fn execute(&self, graph: &NodeGraph, ctx: &mut RuntimeContext, node: &Node) -> Result<Option<usize>, String> {
        let condition = eval_input(graph, ctx, node.id, "condition")?.as_bool();

        let pin_name = if condition { "true" } else { "false" };
        // Handle case-insensitivity or standard naming if needed, but existing code checks for "true"/"True"
        // Let's stick to standard "true"/"false" first, then fallback?
        // Existing interpreter: let true_pin = node.pins.iter().find(|p| !p.is_input && (p.name == "true" || p.name == "True") ...

        let pin = node.pins.iter()
            .find(|p| !p.is_input && p.pin_type == PinType::Exec && (p.name.eq_ignore_ascii_case(pin_name)))
            .map(|p| p.id);

        Ok(pin)
    }
}

impl super::super::framework::NodeDescription for BranchNode {
    fn description(&self) -> &str {
        "If-Else logic. Takes a boolean condition and executes one of two paths."
    }
}

fn default_params() -> NodeParams {
    NodeParams::None
}

fn pins(next_pin_id: &mut usize) -> Vec<Pin> {
    let mut pins = Vec::new();
    pins.push(Pin::new(*next_pin_id, PinType::Exec, true, ""));
    *next_pin_id += 1;
    pins.push(Pin::new(*next_pin_id, PinType::Exec, false, "true"));
    *next_pin_id += 1;
    pins.push(Pin::new(*next_pin_id, PinType::Exec, false, "false"));
    *next_pin_id += 1;
    pins.push(Pin::new(*next_pin_id, PinType::Bool, true, "condition"));
    *next_pin_id += 1;
    pins
}

fn execute(graph: &NodeGraph, ctx: &mut RuntimeContext, node: &Node, _stack: &mut ExecutionStack) -> Result<Option<usize>, String> {
    BranchNode.execute(graph, ctx, node)
}

crate::register_node!(NodeSpec {
    id: "Branch",
    display_name: "Branch",
    documentation: "If-Else logic. Takes a boolean condition and executes one of two paths.",
    category: NodeCategory::ControlFlow,
    library: NodeLibrary::Core,
    param_kind: ParamKind::None,
    default_params,
    pins,
    execute: Some(execute),
    evaluate: None,
});
