diff --git a/packages/core/src/global_context.rs b/packages/core/src/global_context.rs index 6966b682b..3ff52092d 100644 --- a/packages/core/src/global_context.rs +++ b/packages/core/src/global_context.rs @@ -108,20 +108,47 @@ pub fn remove_future(id: Task) { /// Store a value between renders. The foundational hook for all other hooks. /// -/// Accepts an `initializer` closure, which is run on the first use of the hook (typically the initial render). The return value of this closure is stored for the lifetime of the component, and a mutable reference to it is provided on every render as the return value of `use_hook`. +/// Accepts an `initializer` closure, which is run on the first use of the hook (typically the initial render). +/// `use_hook` will return a clone of the value on every render. /// -/// When the component is unmounted (removed from the UI), the value is dropped. This means you can return a custom type and provide cleanup code by implementing the [`Drop`] trait +/// In order to clean up resources you would need to implement the [`Drop`] trait for an inner value stored in a RC or similar (Signals for instance), +/// as these only drop their inner value once all references have been dropped, which only happens when the component is dropped. /// /// # Example /// -/// ``` -/// use dioxus_core::use_hook; +/// ```rust +/// use dioxus::prelude::*; /// /// // prints a greeting on the initial render /// pub fn use_hello_world() { /// use_hook(|| println!("Hello, world!")); /// } /// ``` +/// +/// # Custom Hook Example +/// +/// ```rust +/// use dioxus::prelude::*; +/// +/// pub struct InnerCustomState(usize); +/// +/// impl Drop for InnerCustomState { +/// fn drop(&mut self){ +/// println!("Component has been dropped."); +/// } +/// } +/// +/// #[derive(Clone, Copy)] +/// pub struct CustomState { +/// inner: Signal +/// } +/// +/// pub fn use_custom_state() -> CustomState { +/// use_hook(|| CustomState { +/// inner: Signal::new(InnerCustomState) +/// }) +/// } +/// ``` pub fn use_hook(initializer: impl FnOnce() -> State) -> State { Runtime::with_current_scope(|cx| cx.use_hook(initializer)).expect("to be in a dioxus runtime") } diff --git a/packages/core/src/scope_context.rs b/packages/core/src/scope_context.rs index 431e9b714..1c605626d 100644 --- a/packages/core/src/scope_context.rs +++ b/packages/core/src/scope_context.rs @@ -273,19 +273,47 @@ impl Scope { /// Store a value between renders. The foundational hook for all other hooks. /// - /// Accepts an `initializer` closure, which is run on the first use of the hook (typically the initial render). The return value of this closure is stored for the lifetime of the component, and a mutable reference to it is provided on every render as the return value of `use_hook`. + /// Accepts an `initializer` closure, which is run on the first use of the hook (typically the initial render). + /// `use_hook` will return a clone of the value on every render. /// - /// When the component is unmounted (removed from the UI), the value is dropped. This means you can return a custom type and provide cleanup code by implementing the [`Drop`] trait + /// In order to clean up resources you would need to implement the [`Drop`] trait for an inner value stored in a RC or similar (Signals for instance), + /// as these only drop their inner value once all references have been dropped, which only happens when the component is dropped. /// /// # Example /// - /// ``` - /// # use dioxus::prelude::*; + /// ```rust + /// use dioxus::prelude::*; + /// /// // prints a greeting on the initial render /// pub fn use_hello_world() { /// use_hook(|| println!("Hello, world!")); /// } /// ``` + /// + /// # Custom Hook Example + /// + /// ```rust + /// use dioxus::prelude::*; + /// + /// pub struct InnerCustomState(usize); + /// + /// impl Drop for InnerCustomState { + /// fn drop(&mut self){ + /// println!("Component has been dropped."); + /// } + /// } + /// + /// #[derive(Clone, Copy)] + /// pub struct CustomState { + /// inner: Signal + /// } + /// + /// pub fn use_custom_state() -> CustomState { + /// use_hook(|| CustomState { + /// inner: Signal::new(InnerCustomState) + /// }) + /// } + /// ``` pub fn use_hook(&self, initializer: impl FnOnce() -> State) -> State { let cur_hook = self.hook_index.get(); let mut hooks = self.hooks.try_borrow_mut().expect("The hook list is already borrowed: This error is likely caused by trying to use a hook inside a hook which violates the rules of hooks.");