icon_button.rs

 1use gpui2::elements::div;
 2use gpui2::style::{StyleHelpers, Styleable};
 3use gpui2::{Element, IntoElement, ParentElement, ViewContext};
 4
 5use crate::{icon, theme, IconColor};
 6use crate::{prelude::*, IconAsset};
 7
 8#[derive(Element)]
 9pub struct IconButton {
10    icon: IconAsset,
11    color: IconColor,
12    variant: ButtonVariant,
13    state: InteractionState,
14}
15
16pub fn icon_button() -> IconButton {
17    IconButton {
18        icon: IconAsset::default(),
19        color: IconColor::default(),
20        variant: ButtonVariant::default(),
21        state: InteractionState::default(),
22    }
23}
24
25impl IconButton {
26    pub fn new(icon: IconAsset) -> Self {
27        Self {
28            icon,
29            color: IconColor::default(),
30            variant: ButtonVariant::default(),
31            state: InteractionState::default(),
32        }
33    }
34
35    pub fn icon(mut self, icon: IconAsset) -> Self {
36        self.icon = icon;
37        self
38    }
39
40    pub fn color(mut self, color: IconColor) -> Self {
41        self.color = color;
42        self
43    }
44
45    pub fn variant(mut self, variant: ButtonVariant) -> Self {
46        self.variant = variant;
47        self
48    }
49
50    pub fn state(mut self, state: InteractionState) -> Self {
51        self.state = state;
52        self
53    }
54
55    fn render<V: 'static>(&mut self, _: &mut V, cx: &mut ViewContext<V>) -> impl IntoElement<V> {
56        let theme = theme(cx);
57
58        let icon_color = match (self.state, self.color) {
59            (InteractionState::Disabled, _) => IconColor::Disabled,
60            _ => self.color,
61        };
62
63        let mut div = div();
64        if self.variant == ButtonVariant::Filled {
65            div = div.fill(theme.highest.on.default.background);
66        }
67
68        div.w_7()
69            .h_6()
70            .flex()
71            .items_center()
72            .justify_center()
73            .rounded_md()
74            .hover()
75            .fill(theme.highest.base.hovered.background)
76            .active()
77            .fill(theme.highest.base.pressed.background)
78            .child(icon(self.icon).color(icon_color))
79    }
80}