//!
//!

πŸŒ—πŸš€ πŸ“¦ Dioxus

//!

//! A concurrent, functional, virtual DOM for Rust //!

//!
//! Dioxus: a concurrent, functional, reactive virtual dom for any renderer in Rust. //! //! This crate aims to maintain a hook-based, renderer-agnostic framework for cross-platform UI development. //! //! ## Overview and Goals //! Dioxus' ultimate goal is to save you from writing new code when bringing your application to new platforms. We forsee //! a future where WebApps, Mobile Apps, Desktop Apps, and even AR apps can be written in the same language, ecosystem, //! and leverage the same platform-agnostic libraries. //! //! In this aim we chose to use a variety of techniques: //! - We use a VirtualDOM to abstract the true renderer from application logic. //! - We use functions as components to limit the API churn for greater stability. //! - We use hooks as state to allow reusable logic across the whole ecosystem. //! - We support an extensible and compile-time safe DSL for building interfaces. //! //! Our guiding stars (in order of priority): //! - Ergonomics //! - Reusability //! - Speed and memory efficiency //! - Safety //! //! ## Components //! The base unit of Dioxus is the `component`. Components can be easily created from just a function - no traits or //! proc macros required: //! //! ``` //! use dioxus::prelude::*; //! //! fn Example(ctx: Context<()>) -> VNode { //! html! {
"Hello, world!"
} //! } //! ``` //! Components need to take a "Context" parameter which is generic over some properties. This defines how the component can be used //! and what properties can be used to specify it in the VNode output. Components without properties may be generic over //! `()`, and components with properties must declare their properties as a struct: //! //! ``` //! #[derive(Props)] //! struct Props { name: String } //! //! fn Example(ctx: Context) -> VNode { //! html! {
"Hello {ctx.props.name}!"
} //! } //! ``` //! //! Props that are valid for the `'static` lifetime automatically get memoized by Diouxs. This means the component won't //! re-render if its Props didn't change. However, Props that borrow data from their parent cannot be safely memoized, and //! will always re-render if their parent changes. To borrow data from a parent, your component needs to add explicit lifetimes, //! otherwise Rust will get confused about whether data is borrowed from either Props or Context. Since Dioxus manages //! these lifetimes internally, Context and your Props must share the same lifetime: //! //! ``` //! #[derive(Props)] //! struct Props<'a> { name: &'a str } //! //! fn Example<'a>(ctx: Context<'a, Props<'a>>) -> VNode { //! html! {
"Hello {ctx.props.name}!"
} //! } //! ``` //! //! //! //! The lifetimes might look a little messy, but are crucially important for Dioxus's efficiency and overall ergonimics. //! Components can also be crafted as static closures, enabling type inference without all the type signature noise. However, //! closure-style components cannot work with borrowed data, due to limitations in Rust's lifetime system. //! //! ``` //! #[derive(Props)] //! struct Props { name: String } //! //! static Example: FC = |ctx| { //! html! {
"Hello {ctx.props.name}!"
} //! } //! ``` //! //! To use custom properties for components, you'll need to derive the `Props` trait for your properties. This trait //! exposes a compile-time correct builder pattern (similar to typed-builder) that can be used in the `rsx!` and `html!` //! macros to build components. Component props may have default fields notated by the `Default` attribute: //! //! ``` //! #[derive(Props)] //! struct Props { //! name: String //! //! #[props(default = false)] //! checked: bool, //! //! #[props(default, setter(strip_option, into))] //! title: Option //! } //! ``` //! //! These flags roughly follow that of typed-builder, though tweaked to support the `Props` usecase. //! //! ## Hooks and State //! Dioxus uses hooks for state management. Hooks are a form of state persisted between calls of the function component. //! //! ``` //! static Example: FC<()> = |ctx| { //! let (val, set_val) = use_state(&ctx, || 0); //! ctx.render(rsx!( //! button { onclick: move |_| set_val(val + 1) } //! )) //! } //! ```` //! //! Instead of using a single struct to represent a component and its state, hooks use the "use_hook" building block //! which allows the persistence of data between function component renders. This primitive is exposed directly through //! the `Context` item: //! ``` //! fn my_hook<'a>(ctx: &impl Scoped<'a>) -> &'a String { //! ctx.use_hook( //! // Initializer stores a value //! || String::new("stored_data"), //! //! // Runner returns the hook value every time the component is rendered //! |hook| &*hook, //! //! // Cleanup runs after the component is unmounted //! |hook| log::debug!("cleaning up hook with value {:#?}", hook) //! ) //! } //! ``` //! Under the hood, hooks store their data in a series of "memory cells". The first render defines the layout of these //! memory cells, and on each subsequent render, each `use_hook` call accesses its corresponding memory cell. If a hook //! accesses the wrong memory cell, `use_hook` will panic, and your app will crash. You can always use `try_use_hook` but //! these types of errors can be easily mitigated by following the rules of hooks: //! //! - Don’t call Hooks inside loops, conditions, or nested functions //! - Don't call hooks in changing order between renders //! //! Hooks provide a very powerful way to reuse stateful logic between components, simplify large complex components, //! and adopt more clear context subscription patterns to make components easier to read. The mechanics of hooks in Dioxus //! shares a great amount of similarity with React's hooks and there are many guides to hooks in React online. //! //! ## Supported Renderers //! Instead of being tightly coupled to a platform, browser, or toolkit, Dioxus implements a VirtualDOM object which //! can be consumed to draw the UI. The Dioxus VDOM is reactive and easily consumable by 3rd-party renderers via //! the `Patch` object. See [Implementing a Renderer](docs/8-custom-renderer.md) and the `StringRenderer` classes for information //! on how to implement your own custom renderer. We provide 1st-class support for these renderers: //! //! - dioxus-desktop (via WebView) //! - dioxus-web (via WebSys) //! - dioxus-ssr (via StringRenderer) //! - dioxus-liveview (SSR + StringRenderer) //! //! In the main `Dioxus` crate, these are all accessible through configuration flags. //! //! ## Rendering to the Web //! //! Most dioxus apps will be initialized in roughly the same way. The `launch` method in `web` will immediately start a //! VirtualDOM and await it using `wasm_bindgen_futures`. //! //! VirtualDOM from //! a component root and immediately awaits it //! //! //! ``` //! use dioxus::prelude::*; //! fn main() { //! wasm_logger::init(wasm_logger::Config::new(log::Level::Debug)); //! console_error_panic_hook::set_once(); //! //! diouxs::web::launch(Example); //! } //! //! static Example: FC<()> = |ctx| { //! ctx.render(rsx! { //! div { "Hello World!" } //! }) //! }; //! ``` pub mod prelude { //! A glob import that includes helper types like FC, rsx!, html!, and required traits pub use dioxus_core::prelude::*; pub use dioxus_core_macro::fc; } pub mod builder { // pub use dioxus_core::builder::*; } pub mod events { // pub use dioxus_core::events::*; } // Just a heads-up, the core functionality of dioxus rests in Dioxus-Core. This crate just wraps a bunch of utilities // together and exports their namespaces to something predicatble. #[cfg(feature = "core")] pub mod core { //! Core functionality that includes the VirtualDOM, diffing, and Context APIs // Re-export core completely pub use dioxus_core::*; } // Input elements work differently on different platforms. // This module helps abstract over Selects, TextInputs, TextAreas, Radios, etc for a cross-platform input experience pub mod inputs { //! Cross-platform abstractions over user inputs } #[cfg(feature = "web")] pub mod web { //! A web-sys based renderer for building fast and interactive web applications } #[cfg(feature = "ssr")] pub mod ssr { //! A dedicated renderer for writing a Dioxus VirtualDOM to a string } #[cfg(feature = "ssr")] pub mod hooks { //! Useful hooks like use_state, use_ref } #[cfg(feature = "ssr")] pub mod router { //! A cross-platform router implementation } #[cfg(feature = "ssr")] pub mod testing { //! Tools to make it easier to write tests for Dioxus components } #[cfg(feature = "atoms")] pub mod atoms {} // #[cfg(feature = "desktop")] pub mod webview { //! A webview based renderer for building desktop applications with Dioxus use dioxus_core::prelude::FC; pub fn launch

(f: FC

) {} }