1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
use std::cell::RefCell;

use super::{
    component::{ComponentBuilder, ComponentConstruction, ComponentStoreInstance},
    hole::NoHoleNode,
    hook::{HookBuilder, HookConstruction},
    subtree::Subtree,
    types::{ComponentFunc, ComponentProps, ComponentReturn, HookReturn},
};
use crate::stores::{StoreCons, StoresList};

impl HookBuilder {
    /// This is a shortcut that calls `cc.init().hook(...)`
    ///
    /// It is here so you don't have to write `let cc = cc.init();` at the beginning of every hook function.
    ///
    /// See the docs at [`crate`] on how to call hooks.
    /// See [`HookConstruction`] for the actual `.hook(...)`.
    pub fn hook<Arg, Out, Ret, RestStores>(
        self,
        hook_func: fn(HookBuilder, Arg) -> Ret,
        hook_arg: Arg,
    ) -> (
        HookConstruction<RestStores, StoreCons<Ret::StoresList, RestStores>>,
        Out,
    )
    where
        RestStores: StoresList,
        Ret: HookReturn<Out>,
    {
        self.init().hook(hook_func, hook_arg)
    }
}

impl ComponentBuilder {
    /// This is a shortcut that calls `cc.init().hook(...)`
    ///
    /// It is here so you don't have to write `let cc = cc.init();` at the beginning of every component.
    ///
    /// See the docs at [`crate`] on how to call hooks.
    /// See [`ComponentConstruction`] for the actual `.hook(...)`.
    pub fn hook<Arg, Out, Ret, RestStores>(
        self,
        hook_func: fn(HookBuilder, Arg) -> Ret,
        hook_arg: Arg,
    ) -> (
        ComponentConstruction<
            RestStores,
            StoreCons<Ret::StoresList, RestStores>,
            NoHoleNode,
            NoHoleNode,
        >,
        Out,
    )
    where
        RestStores: StoresList,
        Ret: HookReturn<Out>,
    {
        self.init().hook(hook_func, hook_arg)
    }

    /// This is a shortcut that calls `cc.init().comp(...)`
    ///
    /// It is here so you don't have to write `let cc = cc.init();` at the beginning of every component.
    ///
    /// See the docs at [`crate`] on how to compose components.
    /// See [`ComponentConstruction`] for the actual `.comp(...)`.
    pub fn comp<Props, Ret, RestStores>(
        self,
        component_func: ComponentFunc<Ret, Props>,
        component_props: Props,
    ) -> ComponentConstruction<
        RestStores,
        StoreCons<ComponentStoreInstance<Ret, Props>, RestStores>,
        Ret::HoleNode,
        NoHoleNode,
    >
    where
        RestStores: StoresList,
        Ret: ComponentReturn,
        Props: ComponentProps,
    {
        self.init().comp(component_func, component_props)
    }

    /// This is a shortcut that calls `cc.init().dyn_comp(...)`
    ///
    /// It is here so you don't have to write `let cc = cc.init();` at the beginning of every component.
    ///
    /// See [`ComponentConstruction`] for the actual `.dyn_comp(...)` for more details.
    pub fn dyn_comp<Props, Ret, RestStores>(
        self,
        component_func: ComponentFunc<Ret, Props>,
        component_props: Props,
    ) -> ComponentConstruction<
        RestStores,
        StoreCons<RefCell<Option<Box<dyn Subtree<Props = Props>>>>, RestStores>,
        NoHoleNode,
        NoHoleNode,
    >
    where
        RestStores: StoresList,
        Ret: ComponentReturn,
        Props: ComponentProps,
    {
        self.init().dyn_comp(component_func, component_props)
    }
}