diff options
| author | 2025-02-12 01:51:20 +0100 | |
|---|---|---|
| committer | 2025-02-12 01:51:20 +0100 | |
| commit | 89a412695af321356a6f05f9111510d35a839983 (patch) | |
| tree | 12b342eb17688cbb07e6c9fd8748c42ef7591501 /core | |
| parent | bf205a88b66a6fa8ea6d9a259bfd0ed0b42a97b7 (diff) | |
| parent | e78c757cad5619c77a588054b42e9b87335d6e86 (diff) | |
| download | iced-89a412695af321356a6f05f9111510d35a839983.tar.gz iced-89a412695af321356a6f05f9111510d35a839983.tar.bz2 iced-89a412695af321356a6f05f9111510d35a839983.zip | |
Merge pull request #2805 from iced-rs/feature/sipper-support
`sipper` support and some QoL
Diffstat (limited to 'core')
| -rw-r--r-- | core/src/element.rs | 5 | ||||
| -rw-r--r-- | core/src/lib.rs | 57 | 
2 files changed, 60 insertions, 2 deletions
| diff --git a/core/src/element.rs b/core/src/element.rs index ede9e16c..b7d51aeb 100644 --- a/core/src/element.rs +++ b/core/src/element.rs @@ -93,6 +93,7 @@ impl<'a, Message, Theme, Renderer> Element<'a, Message, Theme, Renderer> {      ///      /// ```no_run      /// # mod iced { +    /// #     pub use iced_core::Function;      /// #     pub type Element<'a, Message> = iced_core::Element<'a, Message, iced_core::Theme, ()>;      /// #      /// #     pub mod widget { @@ -119,7 +120,7 @@ impl<'a, Message, Theme, Renderer> Element<'a, Message, Theme, Renderer> {      /// use counter::Counter;      ///      /// use iced::widget::row; -    /// use iced::Element; +    /// use iced::{Element, Function};      ///      /// struct ManyCounters {      ///     counters: Vec<Counter>, @@ -142,7 +143,7 @@ impl<'a, Message, Theme, Renderer> Element<'a, Message, Theme, Renderer> {      ///                     // Here we turn our `Element<counter::Message>` into      ///                     // an `Element<Message>` by combining the `index` and the      ///                     // message of the `element`. -    ///                     counter.map(move |message| Message::Counter(index, message)) +    ///                     counter.map(Message::Counter.with(index))      ///                 }),      ///         )      ///         .into() diff --git a/core/src/lib.rs b/core/src/lib.rs index d5c221ac..03cc0632 100644 --- a/core/src/lib.rs +++ b/core/src/lib.rs @@ -93,3 +93,60 @@ pub use smol_str::SmolStr;  pub fn never<T>(never: std::convert::Infallible) -> T {      match never {}  } + +/// A trait extension for binary functions (`Fn(A, B) -> O`). +/// +/// It enables you to use a bunch of nifty functional programming paradigms +/// that work well with iced. +pub trait Function<A, B, O> { +    /// Applies the given first argument to a binary function and returns +    /// a new function that takes the other argument. +    /// +    /// This lets you partially "apply" a function—equivalent to currying, +    /// but it only works with binary functions. If you want to apply an +    /// arbitrary number of arguments, create a little struct for them. +    /// +    /// # When is this useful? +    /// Sometimes you will want to identify the source or target +    /// of some message in your user interface. This can be achieved through +    /// normal means by defining a closure and moving the identifier +    /// inside: +    /// +    /// ```rust +    /// # let element: Option<()> = Some(()); +    /// # enum Message { ButtonPressed(u32, ()) } +    /// let id = 123; +    /// +    /// # let _ = { +    /// element.map(move |result| Message::ButtonPressed(id, result)) +    /// # }; +    /// ``` +    /// +    /// That's quite a mouthful. [`with`](Self::with) lets you write: +    /// +    /// ```rust +    /// # use iced_core::Function; +    /// # let element: Option<()> = Some(()); +    /// # enum Message { ButtonPressed(u32, ()) } +    /// let id = 123; +    /// +    /// # let _ = { +    /// element.map(Message::ButtonPressed.with(id)) +    /// # }; +    /// ``` +    /// +    /// Effectively creating the same closure that partially applies +    /// the `id` to the message—but much more concise! +    fn with(self, prefix: A) -> impl Fn(B) -> O; +} + +impl<F, A, B, O> Function<A, B, O> for F +where +    F: Fn(A, B) -> O, +    Self: Sized, +    A: Copy, +{ +    fn with(self, prefix: A) -> impl Fn(B) -> O { +        move |result| self(prefix, result) +    } +} | 
