diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/lib.rs | 4 | ||||
| -rw-r--r-- | src/runtime.rs | 106 | ||||
| -rw-r--r-- | src/user_interface.rs | 116 | 
3 files changed, 118 insertions, 108 deletions
| @@ -15,8 +15,8 @@ mod node;  mod point;  mod rectangle;  mod renderer; -mod runtime;  mod style; +mod user_interface;  mod vector;  #[doc(no_inline)] @@ -31,7 +31,7 @@ pub use node::Node;  pub use point::Point;  pub use rectangle::Rectangle;  pub use renderer::Renderer; -pub use runtime::{Interface, Runtime};  pub use style::{Align, Justify, Style}; +pub use user_interface::{Cache, UserInterface};  pub use vector::Vector;  pub use widget::*; diff --git a/src/runtime.rs b/src/runtime.rs deleted file mode 100644 index 926e29ea..00000000 --- a/src/runtime.rs +++ /dev/null @@ -1,106 +0,0 @@ -use crate::{input::mouse, Column, Element, Event, Layout, MouseCursor, Point}; - -use std::hash::Hasher; -use stretch::result; - -pub struct Runtime { -    cache: Cache, -    events: Vec<Event>, -    cursor_position: Point, -} - -impl Runtime { -    pub fn new() -> Runtime { -        // We use this as a placeholder to initialize the cache. -        // This way, we can avoid the overhead of using an `Option` -        // in `compute`. -        let root: Element<'_, (), ()> = Column::new().into(); - -        let hasher = &mut crate::Hasher::default(); -        root.hash(hasher); - -        Runtime { -            cache: Cache { -                hash: hasher.finish(), -                layout: root.compute_layout(&()), -            }, -            events: Vec::new(), -            cursor_position: Point::new(0.0, 0.0), -        } -    } - -    pub fn on_event(&mut self, event: Event) { -        match event { -            Event::Mouse(mouse::Event::CursorMoved { x, y }) => { -                self.cursor_position = Point::new(x, y); -            } -            _ => {} -        } - -        self.events.push(event); -    } - -    pub fn compute<'a, Message, Renderer>( -        &'a mut self, -        root: Element<'a, Message, Renderer>, -        renderer: &Renderer, -    ) -> Interface<'a, Message, Renderer> { -        let hasher = &mut crate::Hasher::default(); -        root.hash(hasher); - -        let hash = hasher.finish(); - -        if hash != self.cache.hash { -            self.cache = Cache { -                hash, -                layout: root.compute_layout(renderer), -            }; -        } - -        Interface { -            root, -            layout: &self.cache.layout, -            events: &mut self.events, -            cursor_position: self.cursor_position, -        } -    } -} - -struct Cache { -    hash: u64, -    layout: result::Layout, -} - -pub struct Interface<'a, Message, Renderer> { -    root: Element<'a, Message, Renderer>, -    layout: &'a result::Layout, -    events: &'a mut Vec<Event>, -    cursor_position: Point, -} - -impl<'a, Message, Renderer> Interface<'a, Message, Renderer> { -    pub fn update(&mut self) -> Vec<Message> { -        let mut messages = Vec::new(); - -        for event in self.events.drain(..) { -            self.root.widget.on_event( -                event, -                Layout::new(&self.layout), -                self.cursor_position, -                &mut messages, -            ); -        } - -        messages -    } - -    pub fn draw(&self, renderer: &mut Renderer) -> MouseCursor { -        let cursor = self.root.widget.draw( -            renderer, -            Layout::new(self.layout), -            self.cursor_position, -        ); - -        cursor -    } -} diff --git a/src/user_interface.rs b/src/user_interface.rs new file mode 100644 index 00000000..5d02bf9a --- /dev/null +++ b/src/user_interface.rs @@ -0,0 +1,116 @@ +use crate::{input::mouse, Column, Element, Event, Layout, MouseCursor, Point}; + +use std::hash::Hasher; +use stretch::result; + +pub struct UserInterface<'a, Message, Renderer> { +    hash: u64, +    root: Element<'a, Message, Renderer>, +    layout: result::Layout, +    cursor_position: Point, +} + +impl<'a, Message, Renderer> UserInterface<'a, Message, Renderer> { +    pub fn build( +        root: Element<'a, Message, Renderer>, +        renderer: &Renderer, +        cache: Cache, +    ) -> Self { +        let hasher = &mut crate::Hasher::default(); +        root.hash(hasher); + +        let hash = hasher.finish(); + +        let layout = if hash == cache.hash { +            cache.layout +        } else { +            root.compute_layout(renderer) +        }; + +        UserInterface { +            hash, +            root, +            layout, +            cursor_position: cache.cursor_position, +        } +    } + +    pub fn update( +        &mut self, +        events: std::vec::Drain<'_, Event>, +    ) -> Vec<Message> { +        let mut messages = Vec::new(); + +        for event in events { +            match event { +                Event::Mouse(mouse::Event::CursorMoved { x, y }) => { +                    self.cursor_position = Point::new(x, y); +                } +                _ => {} +            } + +            self.root.widget.on_event( +                event, +                Layout::new(&self.layout), +                self.cursor_position, +                &mut messages, +            ); +        } + +        messages +    } + +    pub fn draw(&self, renderer: &mut Renderer) -> MouseCursor { +        let cursor = self.root.widget.draw( +            renderer, +            Layout::new(&self.layout), +            self.cursor_position, +        ); + +        cursor +    } + +    pub fn into_cache(self) -> Cache { +        Cache { +            hash: self.hash, +            layout: self.layout, +            cursor_position: self.cursor_position, +        } +    } +} + +#[derive(Debug, Clone)] +pub struct Cache { +    hash: u64, +    layout: result::Layout, +    cursor_position: Point, +} + +impl Cache { +    pub fn new() -> Cache { +        let root: Element<'_, (), ()> = Column::new().into(); + +        let hasher = &mut crate::Hasher::default(); +        root.hash(hasher); + +        Cache { +            hash: hasher.finish(), +            layout: root.compute_layout(&()), +            cursor_position: Point::new(0.0, 0.0), +        } +    } +} + +impl Default for Cache { +    fn default() -> Cache { +        Cache::new() +    } +} + +impl PartialEq for Cache { +    fn eq(&self, other: &Cache) -> bool { +        self.hash == other.hash && self.cursor_position == other.cursor_position +    } +} + +impl Eq for Cache {} | 
