diff options
Diffstat (limited to 'examples/clock/src')
| -rw-r--r-- | examples/clock/src/lib.rs | 187 | ||||
| -rw-r--r-- | examples/clock/src/main.rs | 188 | 
2 files changed, 189 insertions, 186 deletions
| diff --git a/examples/clock/src/lib.rs b/examples/clock/src/lib.rs new file mode 100644 index 00000000..229ba8fe --- /dev/null +++ b/examples/clock/src/lib.rs @@ -0,0 +1,187 @@ +use iced::{ +    canvas, executor, Application, Canvas, Color, Command, Container, Element, +    Length, Point, Subscription, Vector, +}; + +#[derive(Debug)] +pub struct Clock { +    now: LocalTime, +    clock: canvas::layer::Cache<LocalTime>, +} + +#[derive(Debug, Clone, Copy)] +pub enum Message { +    Tick(chrono::DateTime<chrono::Local>), +} + +impl Application for Clock { +    type Executor = executor::Default; +    type Message = Message; + +    fn new() -> (Self, Command<Message>) { +        ( +            Clock { +                now: chrono::Local::now().into(), +                clock: canvas::layer::Cache::new(), +            }, +            Command::none(), +        ) +    } + +    fn title(&self) -> String { +        String::from("Clock - Iced") +    } + +    fn update(&mut self, message: Message) -> Command<Message> { +        match message { +            Message::Tick(local_time) => { +                let now = local_time.into(); + +                if now != self.now { +                    self.now = now; +                    self.clock.clear(); +                } +            } +        } + +        Command::none() +    } + +    fn subscription(&self) -> Subscription<Message> { +        time::every(std::time::Duration::from_millis(500)).map(Message::Tick) +    } + +    fn view(&mut self) -> Element<Message> { +        let canvas = Canvas::new() +            .width(Length::Units(400)) +            .height(Length::Units(400)) +            .push(self.clock.with(&self.now)); + +        Container::new(canvas) +            .width(Length::Fill) +            .height(Length::Fill) +            .center_x() +            .center_y() +            .into() +    } +} + +#[derive(Debug, PartialEq, Eq)] +struct LocalTime { +    hour: u32, +    minute: u32, +    second: u32, +} + +impl From<chrono::DateTime<chrono::Local>> for LocalTime { +    fn from(date_time: chrono::DateTime<chrono::Local>) -> LocalTime { +        use chrono::Timelike; + +        LocalTime { +            hour: date_time.hour(), +            minute: date_time.minute(), +            second: date_time.second(), +        } +    } +} + +impl canvas::Drawable for LocalTime { +    fn draw(&self, frame: &mut canvas::Frame) { +        let center = frame.center(); +        let radius = frame.width().min(frame.height()) / 2.0; +        let offset = Vector::new(center.x, center.y); + +        let clock = canvas::Path::new(|path| path.circle(center, radius)); + +        frame.fill( +            &clock, +            canvas::Fill::Color(Color::from_rgb8(0x12, 0x93, 0xD8)), +        ); + +        fn draw_hand( +            n: u32, +            total: u32, +            length: f32, +            offset: Vector, +            path: &mut canvas::path::Builder, +        ) { +            let turns = n as f32 / total as f32; +            let t = 2.0 * std::f32::consts::PI * (turns - 0.25); + +            let x = length * t.cos(); +            let y = length * t.sin(); + +            path.line_to(Point::new(x, y) + offset); +        } + +        let hour_and_minute_hands = canvas::Path::new(|path| { +            path.move_to(center); +            draw_hand(self.hour, 12, 0.5 * radius, offset, path); + +            path.move_to(center); +            draw_hand(self.minute, 60, 0.8 * radius, offset, path) +        }); + +        frame.stroke( +            &hour_and_minute_hands, +            canvas::Stroke { +                width: 6.0, +                color: Color::WHITE, +                line_cap: canvas::LineCap::Round, +                ..canvas::Stroke::default() +            }, +        ); + +        let second_hand = canvas::Path::new(|path| { +            path.move_to(center); +            draw_hand(self.second, 60, 0.8 * radius, offset, path) +        }); + +        frame.stroke( +            &second_hand, +            canvas::Stroke { +                width: 3.0, +                color: Color::WHITE, +                line_cap: canvas::LineCap::Round, +                ..canvas::Stroke::default() +            }, +        ); +    } +} + +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/clock/src/main.rs b/examples/clock/src/main.rs index d8266f06..454ff4f0 100644 --- a/examples/clock/src/main.rs +++ b/examples/clock/src/main.rs @@ -1,7 +1,5 @@ -use iced::{ -    canvas, executor, Application, Canvas, Color, Command, Container, Element, -    Length, Point, Settings, Subscription, Vector, -}; +use clock::Clock; +use iced::{Application, Settings};  pub fn main() {      Clock::run(Settings { @@ -9,185 +7,3 @@ pub fn main() {          ..Settings::default()      })  } - -struct Clock { -    now: LocalTime, -    clock: canvas::layer::Cache<LocalTime>, -} - -#[derive(Debug, Clone, Copy)] -enum Message { -    Tick(chrono::DateTime<chrono::Local>), -} - -impl Application for Clock { -    type Executor = executor::Default; -    type Message = Message; - -    fn new() -> (Self, Command<Message>) { -        ( -            Clock { -                now: chrono::Local::now().into(), -                clock: canvas::layer::Cache::new(), -            }, -            Command::none(), -        ) -    } - -    fn title(&self) -> String { -        String::from("Clock - Iced") -    } - -    fn update(&mut self, message: Message) -> Command<Message> { -        match message { -            Message::Tick(local_time) => { -                let now = local_time.into(); - -                if now != self.now { -                    self.now = now; -                    self.clock.clear(); -                } -            } -        } - -        Command::none() -    } - -    fn subscription(&self) -> Subscription<Message> { -        time::every(std::time::Duration::from_millis(500)).map(Message::Tick) -    } - -    fn view(&mut self) -> Element<Message> { -        let canvas = Canvas::new() -            .width(Length::Units(400)) -            .height(Length::Units(400)) -            .push(self.clock.with(&self.now)); - -        Container::new(canvas) -            .width(Length::Fill) -            .height(Length::Fill) -            .center_x() -            .center_y() -            .into() -    } -} - -#[derive(Debug, PartialEq, Eq)] -struct LocalTime { -    hour: u32, -    minute: u32, -    second: u32, -} - -impl From<chrono::DateTime<chrono::Local>> for LocalTime { -    fn from(date_time: chrono::DateTime<chrono::Local>) -> LocalTime { -        use chrono::Timelike; - -        LocalTime { -            hour: date_time.hour(), -            minute: date_time.minute(), -            second: date_time.second(), -        } -    } -} - -impl canvas::Drawable for LocalTime { -    fn draw(&self, frame: &mut canvas::Frame) { -        let center = frame.center(); -        let radius = frame.width().min(frame.height()) / 2.0; -        let offset = Vector::new(center.x, center.y); - -        let clock = canvas::Path::new(|path| path.circle(center, radius)); - -        frame.fill( -            &clock, -            canvas::Fill::Color(Color::from_rgb8(0x12, 0x93, 0xD8)), -        ); - -        fn draw_hand( -            n: u32, -            total: u32, -            length: f32, -            offset: Vector, -            path: &mut canvas::path::Builder, -        ) { -            let turns = n as f32 / total as f32; -            let t = 2.0 * std::f32::consts::PI * (turns - 0.25); - -            let x = length * t.cos(); -            let y = length * t.sin(); - -            path.line_to(Point::new(x, y) + offset); -        } - -        let hour_and_minute_hands = canvas::Path::new(|path| { -            path.move_to(center); -            draw_hand(self.hour, 12, 0.5 * radius, offset, path); - -            path.move_to(center); -            draw_hand(self.minute, 60, 0.8 * radius, offset, path) -        }); - -        frame.stroke( -            &hour_and_minute_hands, -            canvas::Stroke { -                width: 6.0, -                color: Color::WHITE, -                line_cap: canvas::LineCap::Round, -                ..canvas::Stroke::default() -            }, -        ); - -        let second_hand = canvas::Path::new(|path| { -            path.move_to(center); -            draw_hand(self.second, 60, 0.8 * radius, offset, path) -        }); - -        frame.stroke( -            &second_hand, -            canvas::Stroke { -                width: 3.0, -                color: Color::WHITE, -                line_cap: canvas::LineCap::Round, -                ..canvas::Stroke::default() -            }, -        ); -    } -} - -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() -        } -    } -} | 
