199 lines · 6.3 KB · Rust
RawDownload
use crate::{Icon, IconName, IconSize, IconWithIndicator, Indicator, prelude::*};use gpui::Hsla; /// An icon that appears within a button.////// Can be used as either an icon alongside a label, like in [`Button`](crate::Button),/// or as a standalone icon, like in [`IconButton`](crate::IconButton).#[derive(IntoElement, RegisterComponent)]pub(super) struct ButtonIcon {    icon: IconName,    size: IconSize,    color: Color,    disabled: bool,    selected: bool,    selected_icon: Option<IconName>,    selected_icon_color: Option<Color>,    selected_style: Option<ButtonStyle>,    indicator: Option<Indicator>,    indicator_border_color: Option<Hsla>,} impl ButtonIcon {    pub fn new(icon: IconName) -> Self {        Self {            icon,            size: IconSize::default(),            color: Color::default(),            disabled: false,            selected: false,            selected_icon: None,            selected_icon_color: None,            selected_style: None,            indicator: None,            indicator_border_color: None,        }    }     pub fn size(mut self, size: impl Into<Option<IconSize>>) -> Self {        if let Some(size) = size.into() {            self.size = size;        }        self    }     pub fn color(mut self, color: impl Into<Option<Color>>) -> Self {        if let Some(color) = color.into() {            self.color = color;        }        self    }     pub fn selected_icon(mut self, icon: impl Into<Option<IconName>>) -> Self {        self.selected_icon = icon.into();        self    }     pub fn selected_icon_color(mut self, color: impl Into<Option<Color>>) -> Self {        self.selected_icon_color = color.into();        self    }     pub fn indicator(mut self, indicator: Indicator) -> Self {        self.indicator = Some(indicator);        self    }     pub fn indicator_border_color(mut self, color: Option<Hsla>) -> Self {        self.indicator_border_color = color;        self    }} impl Disableable for ButtonIcon {    fn disabled(mut self, disabled: bool) -> Self {        self.disabled = disabled;        self    }} impl Toggleable for ButtonIcon {    fn toggle_state(mut self, selected: bool) -> Self {        self.selected = selected;        self    }} impl SelectableButton for ButtonIcon {    fn selected_style(mut self, style: ButtonStyle) -> Self {        self.selected_style = Some(style);        self    }} impl RenderOnce for ButtonIcon {    fn render(self, _window: &mut Window, _cx: &mut App) -> impl IntoElement {        let icon = self            .selected_icon            .filter(|_| self.selected)            .unwrap_or(self.icon);         let icon_color = if self.disabled {            Color::Disabled        } else if self.selected_style.is_some() && self.selected {            self.selected_style.unwrap().into()        } else if self.selected {            self.selected_icon_color.unwrap_or(Color::Selected)        } else {            self.color        };         let icon = Icon::new(icon).size(self.size).color(icon_color);         match self.indicator {            Some(indicator) => IconWithIndicator::new(icon, Some(indicator))                .indicator_border_color(self.indicator_border_color)                .into_any_element(),            None => icon.into_any_element(),        }    }} impl Component for ButtonIcon {    fn scope() -> ComponentScope {        ComponentScope::Input    }     fn name() -> &'static str {        "ButtonIcon"    }     fn description() -> Option<&'static str> {        Some("An icon component specifically designed for use within buttons.")    }     fn preview(_window: &mut Window, _cx: &mut App) -> Option<AnyElement> {        Some(            v_flex()                .gap_6()                .children(vec![                    example_group_with_title(                        "Basic Usage",                        vec![                            single_example(                                "Default",                                ButtonIcon::new(IconName::Star).into_any_element(),                            ),                            single_example(                                "Custom Size",                                ButtonIcon::new(IconName::Star)                                    .size(IconSize::Medium)                                    .into_any_element(),                            ),                            single_example(                                "Custom Color",                                ButtonIcon::new(IconName::Star)                                    .color(Color::Accent)                                    .into_any_element(),                            ),                        ],                    ),                    example_group_with_title(                        "States",                        vec![                            single_example(                                "Selected",                                ButtonIcon::new(IconName::Star)                                    .toggle_state(true)                                    .into_any_element(),                            ),                            single_example(                                "Disabled",                                ButtonIcon::new(IconName::Star)                                    .disabled(true)                                    .into_any_element(),                            ),                        ],                    ),                    example_group_with_title(                        "With Indicator",                        vec![                            single_example(                                "Default Indicator",                                ButtonIcon::new(IconName::Star)                                    .indicator(Indicator::dot())                                    .into_any_element(),                            ),                            single_example(                                "Custom Indicator",                                ButtonIcon::new(IconName::Star)                                    .indicator(Indicator::dot().color(Color::Error))                                    .into_any_element(),                            ),                        ],                    ),                ])                .into_any_element(),        )    }}