diff options
| author | 2020-04-30 05:37:44 +0200 | |
|---|---|---|
| committer | 2020-04-30 05:37:44 +0200 | |
| commit | e2076612cb98d04a8a48add14d0068c2974d5653 (patch) | |
| tree | 83ee2bcd2a0ef675a1eb0a7bc9313884055aee67 | |
| parent | bb9ccc4f62ceea08dc1ef0c6c4d3d219897e44a1 (diff) | |
| download | iced-e2076612cb98d04a8a48add14d0068c2974d5653.tar.gz iced-e2076612cb98d04a8a48add14d0068c2974d5653.tar.bz2 iced-e2076612cb98d04a8a48add14d0068c2974d5653.zip  | |
Implement `time::every` in `iced_futures`
| -rw-r--r-- | examples/clock/Cargo.toml | 4 | ||||
| -rw-r--r-- | examples/clock/src/main.rs | 46 | ||||
| -rw-r--r-- | examples/game_of_life/Cargo.toml | 4 | ||||
| -rw-r--r-- | examples/game_of_life/src/main.rs | 3 | ||||
| -rw-r--r-- | examples/game_of_life/src/time.rs | 34 | ||||
| -rw-r--r-- | examples/solar_system/Cargo.toml | 4 | ||||
| -rw-r--r-- | examples/solar_system/src/main.rs | 40 | ||||
| -rw-r--r-- | examples/stopwatch/Cargo.toml | 5 | ||||
| -rw-r--r-- | examples/stopwatch/src/main.rs | 44 | ||||
| -rw-r--r-- | futures/Cargo.toml | 3 | ||||
| -rw-r--r-- | futures/src/lib.rs | 4 | ||||
| -rw-r--r-- | futures/src/time.rs | 70 | ||||
| -rw-r--r-- | src/lib.rs | 4 | ||||
| -rw-r--r-- | src/time.rs | 14 | 
14 files changed, 110 insertions, 169 deletions
diff --git a/examples/clock/Cargo.toml b/examples/clock/Cargo.toml index ab771405..c6e32379 100644 --- a/examples/clock/Cargo.toml +++ b/examples/clock/Cargo.toml @@ -6,7 +6,5 @@ edition = "2018"  publish = false  [dependencies] -iced = { path = "../..", features = ["canvas", "async-std", "debug"] } -iced_native = { path = "../../native" } +iced = { path = "../..", features = ["canvas", "tokio", "debug"] }  chrono = "0.4" -async-std = { version = "1.0", features = ["unstable"] } diff --git a/examples/clock/src/main.rs b/examples/clock/src/main.rs index e6b17d8a..9c583c78 100644 --- a/examples/clock/src/main.rs +++ b/examples/clock/src/main.rs @@ -1,7 +1,7 @@  use iced::{      canvas::{self, Cache, Canvas, Cursor, Geometry, LineCap, Path, Stroke}, -    executor, Application, Color, Command, Container, Element, Length, Point, -    Rectangle, Settings, Subscription, Vector, +    executor, time, Application, Color, Command, Container, Element, Length, +    Point, Rectangle, Settings, Subscription, Vector,  };  pub fn main() { @@ -43,7 +43,7 @@ impl Application for Clock {      fn update(&mut self, message: Message) -> Command<Message> {          match message {              Message::Tick(local_time) => { -                let now = local_time.into(); +                let now = local_time;                  if now != self.now {                      self.now = now; @@ -56,7 +56,8 @@ impl Application for Clock {      }      fn subscription(&self) -> Subscription<Message> { -        time::every(std::time::Duration::from_millis(500)).map(Message::Tick) +        time::every(std::time::Duration::from_millis(500)) +            .map(|_| Message::Tick(chrono::Local::now()))      }      fn view(&mut self) -> Element<Message> { @@ -130,40 +131,3 @@ fn hand_rotation(n: u32, total: u32) -> f32 {      2.0 * std::f32::consts::PI * turns  } - -mod time { -    use iced::futures; - -    pub fn every( -        duration: std::time::Duration, -    ) -> iced::Subscription<chrono::DateTime<chrono::Local>> { -        iced::Subscription::from_recipe(Every(duration)) -    } - -    struct Every(std::time::Duration); - -    impl<H, I> iced_native::subscription::Recipe<H, I> for Every -    where -        H: std::hash::Hasher, -    { -        type Output = chrono::DateTime<chrono::Local>; - -        fn hash(&self, state: &mut H) { -            use std::hash::Hash; - -            std::any::TypeId::of::<Self>().hash(state); -            self.0.hash(state); -        } - -        fn stream( -            self: Box<Self>, -            _input: futures::stream::BoxStream<'static, I>, -        ) -> futures::stream::BoxStream<'static, Self::Output> { -            use futures::stream::StreamExt; - -            async_std::stream::interval(self.0) -                .map(|_| chrono::Local::now()) -                .boxed() -        } -    } -} diff --git a/examples/game_of_life/Cargo.toml b/examples/game_of_life/Cargo.toml index 8855b3e8..413493ae 100644 --- a/examples/game_of_life/Cargo.toml +++ b/examples/game_of_life/Cargo.toml @@ -6,7 +6,5 @@ edition = "2018"  publish = false  [dependencies] -iced = { path = "../..", features = ["async-std", "canvas", "debug"] } -iced_native = { path = "../../native" } -async-std = { version = "1.0", features = ["unstable"] } +iced = { path = "../..", features = ["canvas", "tokio"] }  itertools = "0.9" diff --git a/examples/game_of_life/src/main.rs b/examples/game_of_life/src/main.rs index 9fb4c3e7..5a58a8cb 100644 --- a/examples/game_of_life/src/main.rs +++ b/examples/game_of_life/src/main.rs @@ -1,14 +1,13 @@  //! This example showcases an interactive version of the Game of Life, invented  //! by John Conway. It leverages a `Canvas` together with other widgets.  mod style; -mod time;  use grid::Grid;  use iced::{      button::{self, Button},      executor,      slider::{self, Slider}, -    Align, Application, Column, Command, Container, Element, Length, Row, +    time, Align, Application, Column, Command, Container, Element, Length, Row,      Settings, Subscription, Text,  };  use std::time::{Duration, Instant}; diff --git a/examples/game_of_life/src/time.rs b/examples/game_of_life/src/time.rs deleted file mode 100644 index 7b475ecd..00000000 --- a/examples/game_of_life/src/time.rs +++ /dev/null @@ -1,34 +0,0 @@ -use iced::futures; - -pub fn every( -    duration: std::time::Duration, -) -> iced::Subscription<std::time::Instant> { -    iced::Subscription::from_recipe(Every(duration)) -} - -struct Every(std::time::Duration); - -impl<H, I> iced_native::subscription::Recipe<H, I> for Every -where -    H: std::hash::Hasher, -{ -    type Output = std::time::Instant; - -    fn hash(&self, state: &mut H) { -        use std::hash::Hash; - -        std::any::TypeId::of::<Self>().hash(state); -        self.0.hash(state); -    } - -    fn stream( -        self: Box<Self>, -        _input: futures::stream::BoxStream<'static, I>, -    ) -> futures::stream::BoxStream<'static, Self::Output> { -        use futures::stream::StreamExt; - -        async_std::stream::interval(self.0) -            .map(|_| std::time::Instant::now()) -            .boxed() -    } -} diff --git a/examples/solar_system/Cargo.toml b/examples/solar_system/Cargo.toml index 0555aa96..44ced729 100644 --- a/examples/solar_system/Cargo.toml +++ b/examples/solar_system/Cargo.toml @@ -6,7 +6,5 @@ edition = "2018"  publish = false  [dependencies] -iced = { path = "../..", features = ["canvas", "async-std", "debug"] } -iced_native = { path = "../../native" } -async-std = { version = "1.0", features = ["unstable"] } +iced = { path = "../..", features = ["canvas", "tokio", "debug"] }  rand = "0.7" diff --git a/examples/solar_system/src/main.rs b/examples/solar_system/src/main.rs index a25e43df..98bd3b21 100644 --- a/examples/solar_system/src/main.rs +++ b/examples/solar_system/src/main.rs @@ -8,8 +8,8 @@  //! [1]: https://developer.mozilla.org/en-US/docs/Web/API/Canvas_API/Tutorial/Basic_animations#An_animated_solar_system  use iced::{      canvas::{self, Cursor, Path, Stroke}, -    executor, window, Application, Canvas, Color, Command, Element, Length, -    Point, Rectangle, Settings, Size, Subscription, Vector, +    executor, time, window, Application, Canvas, Color, Command, Element, +    Length, Point, Rectangle, Settings, Size, Subscription, Vector,  };  use std::time::Instant; @@ -212,39 +212,3 @@ impl<Message> canvas::Program<Message> for State {          vec![background, system]      }  } - -mod time { -    use iced::futures; -    use std::time::Instant; - -    pub fn every(duration: std::time::Duration) -> iced::Subscription<Instant> { -        iced::Subscription::from_recipe(Every(duration)) -    } - -    struct Every(std::time::Duration); - -    impl<H, I> iced_native::subscription::Recipe<H, I> for Every -    where -        H: std::hash::Hasher, -    { -        type Output = Instant; - -        fn hash(&self, state: &mut H) { -            use std::hash::Hash; - -            std::any::TypeId::of::<Self>().hash(state); -            self.0.hash(state); -        } - -        fn stream( -            self: Box<Self>, -            _input: futures::stream::BoxStream<'static, I>, -        ) -> futures::stream::BoxStream<'static, Self::Output> { -            use futures::stream::StreamExt; - -            async_std::stream::interval(self.0) -                .map(|_| Instant::now()) -                .boxed() -        } -    } -} diff --git a/examples/stopwatch/Cargo.toml b/examples/stopwatch/Cargo.toml index 1dae3b83..075aa111 100644 --- a/examples/stopwatch/Cargo.toml +++ b/examples/stopwatch/Cargo.toml @@ -6,7 +6,4 @@ edition = "2018"  publish = false  [dependencies] -iced = { path = "../.." } -iced_native = { path = "../../native" } -iced_futures = { path = "../../futures", features = ["async-std"] } -async-std = { version = "1.0", features = ["unstable"] } +iced = { path = "../..", features = ["tokio"] } diff --git a/examples/stopwatch/src/main.rs b/examples/stopwatch/src/main.rs index 5a54ed2b..9de6d39e 100644 --- a/examples/stopwatch/src/main.rs +++ b/examples/stopwatch/src/main.rs @@ -1,6 +1,7 @@  use iced::{ -    button, Align, Application, Button, Column, Command, Container, Element, -    HorizontalAlignment, Length, Row, Settings, Subscription, Text, +    button, executor, time, Align, Application, Button, Column, Command, +    Container, Element, HorizontalAlignment, Length, Row, Settings, +    Subscription, Text,  };  use std::time::{Duration, Instant}; @@ -28,7 +29,7 @@ enum Message {  }  impl Application for Stopwatch { -    type Executor = iced_futures::executor::AsyncStd; +    type Executor = executor::Default;      type Message = Message;      type Flags = (); @@ -143,43 +144,6 @@ impl Application for Stopwatch {      }  } -mod time { -    use iced::futures; - -    pub fn every( -        duration: std::time::Duration, -    ) -> iced::Subscription<std::time::Instant> { -        iced::Subscription::from_recipe(Every(duration)) -    } - -    struct Every(std::time::Duration); - -    impl<H, I> iced_native::subscription::Recipe<H, I> for Every -    where -        H: std::hash::Hasher, -    { -        type Output = std::time::Instant; - -        fn hash(&self, state: &mut H) { -            use std::hash::Hash; - -            std::any::TypeId::of::<Self>().hash(state); -            self.0.hash(state); -        } - -        fn stream( -            self: Box<Self>, -            _input: futures::stream::BoxStream<'static, I>, -        ) -> futures::stream::BoxStream<'static, Self::Output> { -            use futures::stream::StreamExt; - -            async_std::stream::interval(self.0) -                .map(|_| std::time::Instant::now()) -                .boxed() -        } -    } -} -  mod style {      use iced::{button, Background, Color, Vector}; diff --git a/futures/Cargo.toml b/futures/Cargo.toml index f0e2a104..275d0391 100644 --- a/futures/Cargo.toml +++ b/futures/Cargo.toml @@ -22,11 +22,12 @@ version = "0.3"  [target.'cfg(not(target_arch = "wasm32"))'.dependencies.tokio]  version = "0.2"  optional = true -features = ["rt-core", "rt-threaded"] +features = ["rt-core", "rt-threaded", "time", "stream"]  [target.'cfg(not(target_arch = "wasm32"))'.dependencies.async-std]  version = "1.0"  optional = true +features = ["unstable"]  [target.'cfg(target_arch = "wasm32")'.dependencies]  wasm-bindgen-futures = "0.4" diff --git a/futures/src/lib.rs b/futures/src/lib.rs index 966a9cdc..d1a149f7 100644 --- a/futures/src/lib.rs +++ b/futures/src/lib.rs @@ -14,6 +14,10 @@ mod runtime;  pub mod executor;  pub mod subscription; +#[cfg(any(feature = "tokio", feature = "async-std"))] +#[cfg_attr(docsrs, doc(cfg(any(feature = "tokio", feature = "async-std"))))] +pub mod time; +  pub use command::Command;  pub use executor::Executor;  pub use runtime::Runtime; diff --git a/futures/src/time.rs b/futures/src/time.rs new file mode 100644 index 00000000..e87b4a83 --- /dev/null +++ b/futures/src/time.rs @@ -0,0 +1,70 @@ +//! Listen and react to time. +use crate::subscription::{self, Subscription}; + +/// Returns a [`Subscription`] that produces messages at a set interval. +/// +/// The first message is produced after a `duration`, and then continues to +/// produce more messages every `duration` after that. +/// +/// [`Subscription`]: ../subscription/struct.Subscription.html +pub fn every<H: std::hash::Hasher, E>( +    duration: std::time::Duration, +) -> Subscription<H, E, std::time::Instant> { +    Subscription::from_recipe(Every(duration)) +} + +struct Every(std::time::Duration); + +#[cfg(feature = "async-std")] +impl<H, E> subscription::Recipe<H, E> for Every +where +    H: std::hash::Hasher, +{ +    type Output = std::time::Instant; + +    fn hash(&self, state: &mut H) { +        use std::hash::Hash; + +        std::any::TypeId::of::<Self>().hash(state); +        self.0.hash(state); +    } + +    fn stream( +        self: Box<Self>, +        _input: futures::stream::BoxStream<'static, E>, +    ) -> futures::stream::BoxStream<'static, Self::Output> { +        use futures::stream::StreamExt; + +        async_std::stream::interval(self.0) +            .map(|_| std::time::Instant::now()) +            .boxed() +    } +} + +#[cfg(all(feature = "tokio", not(feature = "async-std")))] +impl<H, E> subscription::Recipe<H, E> for Every +where +    H: std::hash::Hasher, +{ +    type Output = std::time::Instant; + +    fn hash(&self, state: &mut H) { +        use std::hash::Hash; + +        std::any::TypeId::of::<Self>().hash(state); +        self.0.hash(state); +    } + +    fn stream( +        self: Box<Self>, +        _input: futures::stream::BoxStream<'static, E>, +    ) -> futures::stream::BoxStream<'static, Self::Output> { +        use futures::stream::StreamExt; + +        let start = tokio::time::Instant::now() + self.0; + +        tokio::time::interval_at(start, self.0) +            .map(|_| std::time::Instant::now()) +            .boxed() +    } +} @@ -190,6 +190,10 @@ pub mod settings;  pub mod widget;  pub mod window; +#[cfg(any(feature = "tokio", feature = "async-std"))] +#[cfg_attr(docsrs, doc(cfg(any(feature = "tokio", feature = "async-std"))))] +pub mod time; +  #[doc(no_inline)]  pub use widget::*; diff --git a/src/time.rs b/src/time.rs new file mode 100644 index 00000000..cd442461 --- /dev/null +++ b/src/time.rs @@ -0,0 +1,14 @@ +//! Listen and react to time. +use crate::Subscription; + +/// Returns a [`Subscription`] that produces messages at a set interval. +/// +/// The first message is produced after a `duration`, and then continues to +/// produce more messages every `duration` after that. +/// +/// [`Subscription`]: ../subscription/struct.Subscription.html +pub fn every( +    duration: std::time::Duration, +) -> Subscription<std::time::Instant> { +    iced_futures::time::every(duration) +}  | 
