natrix 0.2.0

Rust-First frontend framework.
Documentation
//! Implementations of various traits for closures.

use crate::element::Element;
use crate::html_elements::ToAttribute;
use crate::render_callbacks::{ReactiveAttribute, ReactiveNode, SimpleReactive};
use crate::signal::RenderingState;
use crate::state::{ComponentData, RenderCtx, State};

#[diagnostic::do_not_recommend]
impl<F, C, R> Element<C> for F
where
    F: Fn(&mut RenderCtx<C>) -> R + 'static,
    R: Element<C> + 'static,
    C: ComponentData,
{
    fn render_box(
        self: Box<Self>,
        ctx: &mut State<C>,
        render_state: &mut RenderingState,
    ) -> web_sys::Node {
        let (me, node) = ReactiveNode::create_inital(Box::new(self), ctx);
        render_state.hooks.push(me);
        node
    }
}

#[diagnostic::do_not_recommend]
impl<F, C, R> ToAttribute<C> for F
where
    F: Fn(&mut RenderCtx<C>) -> R + 'static,
    R: ToAttribute<C>,
    C: ComponentData,
{
    fn apply_attribute(
        self: Box<Self>,
        name: &'static str,
        node: &web_sys::Element,
        ctx: &mut State<C>,
        rendering_state: &mut RenderingState,
    ) {
        let hook = SimpleReactive::init_new(
            Box::new(move |ctx| ReactiveAttribute {
                name,
                data: self(ctx),
            }),
            node.clone(),
            ctx,
        );
        rendering_state.hooks.push(hook);
    }
}

/// Utility trait for use in stateless components
///
/// When defining a stateless component it is much easier to use `impl Event<C>` than writting out
/// the whole function trait yourself.
///
/// ```
/// fn my_button<C>(click: impl EventHandler<C>) -> impl Element<C> {
///     e::button().on("click", click)
/// }
/// ```
pub trait EventHandler<C, E> {
    /// Return a boxed version of the function in this event
    fn func(self) -> impl Fn(&mut State<C>, E) + 'static;
}
impl<C, E, F: Fn(&mut State<C>, E) + 'static> EventHandler<C, E> for F {
    fn func(self) -> impl Fn(&mut State<C>, E) + 'static {
        self
    }
}