diff --git a/src/margins.rs b/src/margins.rs index 0321143..5376005 100644 --- a/src/margins.rs +++ b/src/margins.rs @@ -23,22 +23,27 @@ impl Margins { } } + /// Returns left + right. pub fn horizontal(&self) -> u32 { self.left + self.right } + /// Returns top + bottom. pub fn vertical(&self) -> u32 { self.top + self.bottom } + /// Returns (left+right, top+bottom). pub fn combined(&self) -> Vec2 { Vec2::new(self.horizontal(), self.vertical()) } + /// Returns (left, top). pub fn top_left(&self) -> Vec2 { Vec2::new(self.left, self.top) } + /// Returns (right, bottom). pub fn bot_right(&self) -> Vec2 { Vec2::new(self.right, self.bottom) } diff --git a/src/view/dialog.rs b/src/view/dialog.rs index c0cb80a..053e144 100644 --- a/src/view/dialog.rs +++ b/src/view/dialog.rs @@ -15,6 +15,13 @@ enum Focus { Button(usize), } +/// Popup-like view with a main content, and optional buttons under it. +/// +/// # Examples +/// +/// ``` +/// let dialog = Dialog::new(TextView::new("Hello!")).button("Ok", |s,_| s.quit()); +/// ``` pub struct Dialog { content: Box, @@ -27,6 +34,7 @@ pub struct Dialog { } impl Dialog { + /// Creates a new Dialog with the given content. pub fn new(view: V) -> Self { Dialog { content: Box::new(view), @@ -37,6 +45,9 @@ impl Dialog { } } + /// Adds a button to the dialog with the given label and callback. + /// + /// Consumes and returns self for easy chaining. pub fn button<'a, F>(mut self, label: &'a str, cb: F) -> Self where F: Fn(&mut Cursive, &ViewPath) + 'static { diff --git a/src/view/sized_view.rs b/src/view/sized_view.rs index 3b5a333..d7ccdc3 100644 --- a/src/view/sized_view.rs +++ b/src/view/sized_view.rs @@ -4,7 +4,9 @@ use view::ViewWrapper; /// Wrapper around a view that remembers its size. pub struct SizedView { + /// Wrapped view. pub view: T, + /// Cached size from the last layout() call. pub size: Vec2, } diff --git a/src/view/view_path.rs b/src/view/view_path.rs index 85283d7..bdb670a 100644 --- a/src/view/view_path.rs +++ b/src/view/view_path.rs @@ -13,12 +13,15 @@ impl ViewPath { } } + /// Creates a path from the given item. pub fn from(path: T) -> Self { path.to_path() } } +/// Generic trait for elements that can be converted into a ViewPath. pub trait ToPath { + /// Creates a path from the element. fn to_path(self) -> ViewPath; } diff --git a/src/view/view_wrapper.rs b/src/view/view_wrapper.rs index b3cddf2..82ec6f2 100644 --- a/src/view/view_wrapper.rs +++ b/src/view/view_wrapper.rs @@ -3,25 +3,37 @@ use view::{View,SizeRequest}; use printer::Printer; use event::EventResult; +/// Wrapper around a view. Can override some methods, forwards the others. pub trait ViewWrapper { + /// Get an immutable reference to the wrapped view, so that we can forward some calls to it. fn get_view(&self) -> &View; + /// Get a mutable reference to the wrapped view, for the mutable methods. fn get_view_mut(&mut self) -> &mut View; + /// Wraps the draw method. fn wrap_draw(&self, printer: &Printer, focused: bool) { self.get_view().draw(printer, focused); } + /// Wraps the get_min_size method. fn wrap_get_min_size(&self, req: SizeRequest) -> Vec2 { self.get_view().get_min_size(req) } + /// Wraps the on_key_event method. fn wrap_on_key_event(&mut self, ch: i32) -> EventResult { self.get_view_mut().on_key_event(ch) } + /// Wraps the layout method fn wrap_layout(&mut self, size: Vec2) { self.get_view_mut().layout(size); } + + /// Wraps the take_focus method + fn wrap_take_focus(&mut self) -> bool { + self.get_view_mut().take_focus() + } } impl View for T { @@ -40,8 +52,39 @@ impl View for T { fn layout(&mut self, size: Vec2) { self.wrap_layout(size); } + + fn take_focus(&mut self) -> bool { + self.wrap_take_focus() + } } +/// Convenient macro to implement to two methods required for the ViewWrapper trait. +/// +/// # Examples +/// +/// If the wrapped view is in a box, just name it in the macro: +/// +/// ``` +/// struct BoxFooView { +/// content: Box, +/// } +/// +/// impl ViewWrapper for FooView { +/// wrap_impl!(self.content); +/// } +/// ``` +/// +/// If the content is directly a view, reference it: +/// +/// ``` +/// struct FooView { +/// view: T, +/// } +/// +/// impl ViewWrapper for FooView { +/// wrap_impl!(&self.view); +/// } +/// ``` #[macro_export] macro_rules! wrap_impl { (&self.$v:ident) => {