From adb51dba7ede90643b723799b7018697f28a3dfe Mon Sep 17 00:00:00 2001 From: Jonathan Johnson Date: Sun, 7 Jan 2024 15:57:23 -0800 Subject: [PATCH] More user guide work --- guide/guide-examples/examples/hello-world.rs | 2 +- .../examples/thread-progress.rs | 34 +++++++ guide/src/SUMMARY.md | 2 + guide/src/about/philosophies.md | 4 +- guide/src/about/reactive.md | 93 ++++++++++++++++++ guide/src/about/widgets.md | 38 +++++++ guide/src/examples/thread_progress.png | Bin 0 -> 24738 bytes guide/src/widgets/utility/space.md | 5 +- src/value.rs | 2 +- src/widget.rs | 4 +- src/window.rs | 8 +- 11 files changed, 182 insertions(+), 10 deletions(-) create mode 100644 guide/guide-examples/examples/thread-progress.rs create mode 100644 guide/src/about/reactive.md create mode 100644 guide/src/about/widgets.md create mode 100644 guide/src/examples/thread_progress.png diff --git a/guide/guide-examples/examples/hello-world.rs b/guide/guide-examples/examples/hello-world.rs index fd91cc0..e9744d5 100644 --- a/guide/guide-examples/examples/hello-world.rs +++ b/guide/guide-examples/examples/hello-world.rs @@ -8,7 +8,7 @@ fn main() -> cushy::Result { #[test] fn book() { - fn hello_world() -> impl MakeWidget { + fn hello_world() -> impl cushy::widget::MakeWidget { "Hello, World!" } diff --git a/guide/guide-examples/examples/thread-progress.rs b/guide/guide-examples/examples/thread-progress.rs new file mode 100644 index 0000000..ad27315 --- /dev/null +++ b/guide/guide-examples/examples/thread-progress.rs @@ -0,0 +1,34 @@ +use std::time::Duration; + +use cushy::value::{Destination, Dynamic, Source}; +use cushy::widget::MakeWidget; +use cushy::widgets::progress::Progressable; +use guide_examples::book_example; + +fn thread_progress() -> impl MakeWidget { + // ANCHOR: example + let progress = Dynamic::new(0_u8); + std::thread::spawn({ + let progress = progress.clone(); + move || { + while progress.get() < 10 { + std::thread::sleep(Duration::from_millis(100)); + progress.set(progress.get() + 1); + } + } + }); + + progress.progress_bar_to(10) + // ANCHOR_END: example +} + +fn main() { + book_example!(thread_progress).animated(|recorder| { + recorder.wait_for(Duration::from_secs(2)).unwrap(); + }); +} + +#[test] +fn runs() { + main(); +} diff --git a/guide/src/SUMMARY.md b/guide/src/SUMMARY.md index c26ca99..630ba06 100644 --- a/guide/src/SUMMARY.md +++ b/guide/src/SUMMARY.md @@ -6,6 +6,8 @@ - [About Cushy](./about.md) - [Cushy's Philosophies](./about/philosophies.md) + - [Everything is a `Widget`](./about/widgets.md) + - [Reactive Data Model](./about/reactive.md) - [Widgets]() - [Layout Widgets](./widgets/layout.md) - [Align](./widgets/layout/align.md) diff --git a/guide/src/about/philosophies.md b/guide/src/about/philosophies.md index b517b8b..2627e15 100644 --- a/guide/src/about/philosophies.md +++ b/guide/src/about/philosophies.md @@ -5,8 +5,8 @@ displayed. Here's the philosophies that drive Cushy's design: - Cushy retains information between redraws so that many events can be handled without redrawing the user interface. -- Everything is a widget. The "root" of a user interface/window is a widget, and - widgets can contain other widgets. +- [Everything is a widget](./widgets.md). The "root" of a user interface/window + is a widget, and widgets can contain other widgets. - Composition is powerful and easy to reason about. The built-in widget library is aimed at providing a suite of single-purpose widgets that can be composed to create more complex user interfaces. diff --git a/guide/src/about/reactive.md b/guide/src/about/reactive.md new file mode 100644 index 0000000..5c8ca39 --- /dev/null +++ b/guide/src/about/reactive.md @@ -0,0 +1,93 @@ +# Reactive Data Model + +Cushy is designed around a reactive data model. In many UI frameworks, setting +the text of a [`Label`][label] is done by telling the label what it's new text +is. The Cushy way is to create a `Dynamic` containing the value you want to +display, and give a copy to the label and keep a copy for your application to +update as needed. + +When a widget uses a `Dynamic`, it informs Cushy that it needs to be either +redrawn or invalidated when its contents change. In turn, when Cushy detects a +change, it invalidates what is necessary. + +This means that updating a progress bar from a different thread is as simple as +passing a clone of a `Dynamic` that has been provided to a progress bar: + +```rust,no_run,no_playground +{{#include ../../guide-examples/examples/thread-progress.rs:example}} +``` + +The above snippet produces this user interface: + +![Threaded Progress Bar Update](../examples/thread_progress.png) + +This example just shows one simple way that Cushy's reactive model simplifies +development. To learn more, let's dive into the data types and traits that power +everything. + +## How widgets interact with data + +In Cushy, it's conventional for widgets to accept data using one of these +traits: + +| Trait | Target Type | Purpose | +|-------|-------------|---------| +| [`IntoValue`][intovalue] | [`Value`][value] | For possibly constant or dynamic values. Can be either a `T` or a `Dynamic`. | +| [`IntoDynamic`][intodynamic] | [`Dynamic`][dynamic] | For values that are read from and written to. | +| [`IntoReadOnly`][intoreadonly] | [`ReadOnly`][readonly] | For values that are read-only. Can be either a `T` or a `DynamicReader`. | +| [`IntoDynamicReader`][intodynamicreader] | [`DynamicReader`][dynamicreader] | For values that are read-only, but are unexpected to be constant. In general, `IntoValue` should be preferred if a single value makes sense to accept. | + +Let's look at an example of how these traits are utilizes. +[`Label::new()`][label-new] accepts the value it is to display as a +`ReadOnly` where `T: Display + ...`. + +This showcases Cushy's philosophy of embracing the Rust type system. Rather than +forcing `Label` to receive a `String`, it accepts any type that implements +`Display`, This allows it to accept a wide variety of types. + +Beyond basic values, it can also be given a special type that the `Label` can +react to when updated: a `Dynamic` or a `DynamicReader`. + +## What is a `Dynamic`? + +A [`Dynamic`][dynamic] is a reference-counted, threadsafe, async-friendly +location in memory that can invoke a series of callbacks when its contents +change. Let's revisit the example from the [intro](../intro.md): + +```rust,no_run,no_playground +{{#include ../../guide-examples/examples/intro.rs:example}} +``` + +![Hello Ferris Example](../examples/intro.png) + +Both the [`Input`][input] and the [`Label`][label] widgets have been given +instances of `Dynamic`s, but they are two different dynamics. The text +input field was given the dynamic we want to be edited. We react to the changes +through the `name.map_each(...)` callback. + +## What is a `DynamicReader`? + +A [`DynamicReader`][dynamicreader] provides read-only access to a +`Dynamic`, and also can: + +- [block][block] the current thread until the underlying `Dynamic` is changed. +- [wait][wait] for a change in an async task. +- Detect when the underlying `Dynamic` has had all of its instances dropped. + +`DynamicReader`s can be created using [`Dynamic::into_reader`][into-reader]/[`Dynamic::create_reader`][create-reader]. + +[value]: <{{ docs }}/value/enum.Value.html> +[readonly]: <{{ docs }}/value/enum.ReadOnly.html> +[dynamic]: <{{ docs }}/value/struct.Dynamic.html> +[into-reader]: <{{ docs }}/value/struct.Dynamic.html#method.into_reader> +[create-reader]: <{{ docs }}/value/struct.Dynamic.html#method.create_reader> +[dynamicreader]: <{{ docs }}/value/struct.DynamicReader.html> +[block]: <{{ docs }}/value/struct.DynamicReader.html#method.block_until_updated> +[wait]: <{{ docs }}/value/struct.DynamicReader.html#method.wait_until_updated> +[intovalue]: <{{ docs }}/value/trait.IntoValue.html> +[intodynamic]: <{{ docs }}/value/trait.IntoDynamic.html> +[intoreadonly]: <{{ docs }}/value/trait.IntoReadOnly.html> +[intodynamicreader]: <{{ docs }}/value/trait.IntoDynamicReader.html> +[label-new]: <{{ docs }}/widgets/label/struct.Label.html#method.new> +[label]: <{{ docs }}/widgets/label/struct.Label.html> +[input]: <{{ docs }}/widgets/input/struct.Input.html> diff --git a/guide/src/about/widgets.md b/guide/src/about/widgets.md new file mode 100644 index 0000000..d179b70 --- /dev/null +++ b/guide/src/about/widgets.md @@ -0,0 +1,38 @@ +# Everything is a `Widget` + +A widget is a rectangular area of a screen that implements the +[`Widget`][widget] trait. Widgets are the fundamental building block of Cushy. + +The `Widget` trait can look daunting, as it defines every possible function a +`Widget` might need in a graphical user interface. Thankfully, the details of +how this trait works can be ignored until you're ready to create custom widgets. + +Developing a user interface in Cushy is a two-step process: gather the +information for the interface and present the information in one or more +widgets. + +Cushy makes the process of creating widgets easy through the +[`MakeWidget`][makewidget] trait. Every `Widget` implementor automatically +implements `MakeWidget`, but it can also be implemented by any type to make it +easy to utilize within Cushy. For example, `String` implements `MakeWidget` by +returning a [`Label`][label]. This approach can also be used to convert complex +structures into multi-widget components without needing to create any new +`Widget` implementations. + +`MakeWidget` is also responsible for why `"Hello, World".run()` works. The +[`Run`][run] trait is automatically implemented for all `MakeWidget` +implementations. The implementation simply creates a [`Window`][window] from the +widget and runs it: + +```rust,no_run,no_playground +{{#include ../../../src/widget.rs:run}} +``` + +So now that we know our goal is to create one or more widgets to represent our +data, how do we transform our data and application state into widgets? + +[widget]: <{{ docs }}/widget/trait.Widget.html> +[makewidget]: <{{ docs }}/widget/trait.MakeWidget.html> +[label]: <{{docs}}/widgets/label/struct.Label.html> +[run]: <{{ docs }}/trait.Run.html> +[window]: <{{ docs }}/window/struct.Window.html> diff --git a/guide/src/examples/thread_progress.png b/guide/src/examples/thread_progress.png new file mode 100644 index 0000000000000000000000000000000000000000..fcb4c34c011a6ca87a1b5ba5460cb9763a06deab GIT binary patch literal 24738 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 Y1DbP=3=Eaw3IG5A07*qoM6N<$f>OdR$p8QV literal 0 HcmV?d00001 diff --git a/guide/src/widgets/utility/space.md b/guide/src/widgets/utility/space.md index 01d908a..47f45ef 100644 --- a/guide/src/widgets/utility/space.md +++ b/guide/src/widgets/utility/space.md @@ -1,5 +1,8 @@ # Space Widget -The [`Space`][space] +The [`Space`][space] widget is used to fill space. It is not interactive, and +will always occupy the smallest size it can. + +It can render a color or be clear. [space]: <{{ docs }}/widgets/struct.Space.html> diff --git a/src/value.rs b/src/value.rs index acece66..edd22dd 100644 --- a/src/value.rs +++ b/src/value.rs @@ -2030,7 +2030,7 @@ impl PartialEq> for Dynamic { } } -/// A reader that tracks the last generation accessed through this reader. +/// A reader of a [`Dynamic`] that tracks the last generation accessed. pub struct DynamicReader { source: Arc>, read_generation: Mutex, diff --git a/src/widget.rs b/src/widget.rs index d30de58..42e152c 100644 --- a/src/widget.rs +++ b/src/widget.rs @@ -455,14 +455,16 @@ pub trait Widget: Send + Debug + 'static { } } +// ANCHOR: run impl Run for T where T: MakeWidget, { fn run(self) -> crate::Result { - Window::::new(self.make_widget()).run() + Window::for_widget(self).run() } } +// ANCHOR_END: run impl Open for T where diff --git a/src/window.rs b/src/window.rs index 00a1d12..c93d2f2 100644 --- a/src/window.rs +++ b/src/window.rs @@ -56,8 +56,8 @@ use crate::value::{ Destination, Dynamic, DynamicReader, Generation, IntoDynamic, IntoValue, Source, Value, }; use crate::widget::{ - EventHandling, MakeWidget, MountedWidget, OnceCallback, RootBehavior, Widget, WidgetId, - WidgetInstance, HANDLED, IGNORED, + EventHandling, MakeWidget, MountedWidget, OnceCallback, RootBehavior, WidgetId, WidgetInstance, + HANDLED, IGNORED, }; use crate::window::sealed::WindowCommand; use crate::{initialize_tracing, ConstraintLimit}; @@ -496,9 +496,9 @@ impl Window { /// Returns a new instance using `widget` as its contents. pub fn for_widget(widget: W) -> Self where - W: Widget, + W: MakeWidget, { - Self::new(WidgetInstance::new(widget)) + Self::new(widget.make_widget()) } /// Sets `focused` to be the dynamic updated when this window's focus status