use crate::{Background, Bus, Element, Length, Widget}; use dodrio::bumpalo; /// A generic widget that produces a message when clicked. pub struct Button<'a, Message> { content: Element<'a, Message>, on_press: Option, width: Length, min_width: u32, padding: u16, background: Option, border_radius: u16, } impl<'a, Message> Button<'a, Message> { /// Creates a new [`Button`] with some local [`State`] and the given /// content. /// /// [`Button`]: struct.Button.html /// [`State`]: struct.State.html pub fn new(_state: &'a mut State, content: E) -> Self where E: Into>, { Button { content: content.into(), on_press: None, width: Length::Shrink, min_width: 0, padding: 0, background: None, border_radius: 0, } } /// Sets the width of the [`Button`]. /// /// [`Button`]: struct.Button.html pub fn width(mut self, width: Length) -> Self { self.width = width; self } /// Sets the minimum width of the [`Button`]. /// /// [`Button`]: struct.Button.html pub fn min_width(mut self, min_width: u32) -> Self { self.min_width = min_width; self } /// Sets the padding of the [`Button`]. /// /// [`Button`]: struct.Button.html pub fn padding(mut self, padding: u16) -> Self { self.padding = padding; self } /// Sets the [`Background`] of the [`Button`]. /// /// [`Button`]: struct.Button.html /// [`Background`]: ../../struct.Background.html pub fn background(mut self, background: Background) -> Self { self.background = Some(background); self } /// Sets the border radius of the [`Button`]. /// /// [`Button`]: struct.Button.html pub fn border_radius(mut self, border_radius: u16) -> Self { self.border_radius = border_radius; self } /// Sets the message that will be produced when the [`Button`] is pressed. /// /// [`Button`]: struct.Button.html pub fn on_press(mut self, msg: Message) -> Self { self.on_press = Some(msg); self } } /// The local state of a [`Button`]. /// /// [`Button`]: struct.Button.html #[derive(Debug, Clone, Copy, PartialEq, Eq, Default)] pub struct State; impl State { /// Creates a new [`State`]. /// /// [`State`]: struct.State.html pub fn new() -> State { State::default() } } impl<'a, Message> Widget for Button<'a, Message> where Message: 'static + Copy, { fn node<'b>( &self, bump: &'b bumpalo::Bump, bus: &Bus, ) -> dodrio::Node<'b> { use dodrio::builder::*; let mut node = button(bump).children(vec![self.content.node(bump, bus)]); if let Some(on_press) = self.on_press { let event_bus = bus.clone(); node = node.on("click", move |root, vdom, _event| { event_bus.publish(on_press, root); vdom.schedule_render(); }); } // TODO: Complete styling node.finish() } } impl<'a, Message> From> for Element<'a, Message> where Message: 'static + Copy, { fn from(button: Button<'a, Message>) -> Element<'a, Message> { Element::new(button) } }