1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
use crate::{use_theme, Ripple};
use dioxus::prelude::*;

/// Filled button component.
///
/// Buttons let people take action and make choices with one tap.
///
/// [material.io](https://m3.material.io/components/buttons)
///
/// ## Panics
/// This component requires access to a [`Theme`](crate::Theme).
///
/// ## Examples
/// ```rust
/// use dioxus::prelude::*;
/// use dioxus_material::{Button, Theme};
///
/// fn app(cx: Scope) -> Element {
///    render!(Theme {
///         Button { onpress: |_| log::info!("clicked!"), "Click me!" } }
///    )
/// }
/// ```
#[component]
pub fn Button<'a>(
    cx: Scope<'a>,

    /// Handler for button press events.
    onpress: EventHandler<'a, Event<MouseData>>,

    /// Label child element.
    children: Element<'a>,

    /// Background color of the container (optional).
    background_color: Option<&'a str>,

    /// Border radius of the container (optional).
    border_radius: Option<&'a str>,

    /// Height of the container (optional).
    height: Option<&'a str>,
) -> Element<'a> {
    let theme = use_theme(cx);
    let background_color = background_color.unwrap_or(&theme.primary_color);
    let border_radius = border_radius.unwrap_or(&theme.border_radius_medium);
    let height = height.unwrap_or("50px");

    render!(
        div {
            display: "inline-block",
            position: "relative",
            height: "{height}",
            line_height: "{height}",
            color: "#fff",
            background: "{background_color}",
            border_radius: "{border_radius}",
            overflow: "hidden",
            cursor: "pointer",
            Ripple { onclick: move |event| onpress.call(event),
                div {
                    position: "relative",
                    z_index: 9,
                    padding: "0 25px",
                    font_family: "sans-serif",
                    user_select: "none",
                    webkit_user_select: "none",
                    children
                }
            }
        }
    )
}

#[component]
pub fn TextButton<'a>(
    cx: Scope<'a>,

    /// Handler for button press events.
    onpress: EventHandler<'a, Event<MouseData>>,

    /// Label child element.
    children: Element<'a>,

    /// Border radiusof the container (optional).
    border_radius: Option<&'a str>,

    /// Text color (optional).
    color: Option<&'a str>,

    /// Height of the container (optional).
    height: Option<&'a str>,
) -> Element<'a> {
    let theme = use_theme(cx);
    let color = color.unwrap_or(&theme.primary_color);
    let border_radius = border_radius.unwrap_or(&theme.border_radius_medium);
    let height = height.unwrap_or("40px");

    render!(
        div {
            display: "inline-block",
            position: "relative",
            height: "{height}",
            line_height: "{height}",
            border_radius: "{border_radius}",
            color: "{color}",
            font_weight: "bold",
            overflow: "hidden",
            cursor: "pointer",
            Ripple { onclick: move |event| onpress.call(event),
                div {
                    position: "relative",
                    z_index: 9,
                    padding: "0 25px",
                    font_family: "sans-serif",
                    user_select: "none",
                    webkit_user_select: "none",
                    children
                }
            }
        }
    )
}