Add icon support to Button.

This commit is contained in:
Jason Lee 2024-06-29 02:37:22 +08:00
parent a5aea36f75
commit 3c4891cb69
4 changed files with 71 additions and 29 deletions

View file

@ -5,12 +5,12 @@ use gpui::{
use ui::{
button::{Button, ButtonSize, ButtonStyle},
h_flex, v_flex, Clickable, Disableable as _,
h_flex, v_flex, Clickable, Disableable as _, Icon, IconName,
};
use super::story_case;
pub struct ButtonStory;
pub struct ButtonStory {}
impl ButtonStory {
fn on_click(ev: &ClickEvent, _: &mut WindowContext) {
@ -26,6 +26,7 @@ impl Render for ButtonStory {
)
.child(
v_flex()
.w_full()
.justify_start()
.gap_6()
.child(
@ -48,6 +49,28 @@ impl Render for ButtonStory {
.on_click(Self::on_click),
),
)
.child(
h_flex()
.gap_6()
.child(
Button::new("button-icon-1", "Confirm")
.icon(IconName::Check)
.style(ButtonStyle::Primary)
.on_click(Self::on_click),
)
.child(
Button::new("button-icon-2", "Abort")
.icon(IconName::Close)
.style(ButtonStyle::Secondary)
.on_click(Self::on_click),
)
.child(
Button::new("button-icon-3", "Maximize")
.icon(Icon::new(IconName::Maximize))
.style(ButtonStyle::Secondary)
.on_click(Self::on_click),
),
)
.child(
h_flex()
.items_center()

View file

@ -1,13 +1,13 @@
use gpui::{
div, prelude::FluentBuilder as _, px, ClickEvent, DefiniteLength, Div, ElementId, Hsla,
InteractiveElement, IntoElement, MouseButton, ParentElement, RenderOnce, SharedString,
div, prelude::FluentBuilder as _, px, AnyElement, ClickEvent, DefiniteLength, Div, ElementId,
Hsla, InteractiveElement, IntoElement, MouseButton, ParentElement, RenderOnce, SharedString,
StatefulInteractiveElement as _, Styled, WindowContext,
};
use crate::{
span,
h_flex, span,
theme::{ActiveTheme, Colorize as _, ThemeMode},
Clickable, Disableable, Selectable,
Clickable, Disableable, Icon, IconName, Selectable,
};
pub enum ButtonRounded {
@ -17,11 +17,13 @@ pub enum ButtonRounded {
Large,
}
#[derive(Clone, Copy)]
pub enum ButtonSize {
Small,
Medium,
}
#[derive(Clone, Copy)]
pub enum ButtonStyle {
Primary,
Secondary,
@ -32,6 +34,7 @@ pub enum ButtonStyle {
pub struct Button {
pub base: Div,
id: ElementId,
icon: Option<Icon>,
label: SharedString,
disabled: bool,
selected: bool,
@ -49,6 +52,7 @@ impl Button {
Self {
base: div(),
id: id.into(),
icon: None,
label: label.into(),
disabled: false,
selected: false,
@ -82,6 +86,11 @@ impl Button {
self
}
pub fn icon(mut self, icon: impl Into<Icon>) -> Self {
self.icon = Some(icon.into());
self
}
pub fn tooltip(mut self, tooltip: impl Into<SharedString>) -> Self {
self.tooltip = Some(tooltip.into());
self
@ -175,9 +184,15 @@ impl RenderOnce for Button {
normal_style.fg
};
span()
.child(self.label)
h_flex()
.items_center()
.justify_center()
.gap_2()
.text_color(text_color)
.when_some(self.icon, |this, icon| {
this.child(icon.text_color(text_color))
})
.child(self.label)
.map(|this| match self.size {
ButtonSize::Small => this.text_sm(),
ButtonSize::Medium => this.text_base(),

View file

@ -1,4 +1,7 @@
use gpui::{svg, IntoElement, RenderOnce, SharedString, Styled, Svg, WindowContext};
use gpui::{
div, rgb, svg, Div, InteractiveElement, IntoElement, ParentElement as _, RenderOnce,
SharedString, StyleRefinement, Styled, Svg, TextStyle, TextStyleRefinement, WindowContext,
};
use crate::theme::ActiveTheme;
@ -30,6 +33,12 @@ impl IconName {
}
}
impl Into<Icon> for IconName {
fn into(self) -> Icon {
Icon::new(self)
}
}
impl RenderOnce for IconName {
fn render(self, _cx: &mut WindowContext) -> impl IntoElement {
Icon::new(self)
@ -42,16 +51,10 @@ pub struct Icon {
path: SharedString,
}
impl Styled for Icon {
fn style(&mut self) -> &mut gpui::StyleRefinement {
self.base.style()
}
}
impl Icon {
pub fn new(name: IconName) -> Self {
Self {
base: svg().flex_none().size_4(),
base: svg().flex_none().size_4().text_color(rgb(0x000000)),
path: name.path(),
}
}
@ -65,8 +68,14 @@ impl Icon {
}
}
impl RenderOnce for Icon {
fn render(self, cx: &mut WindowContext) -> impl IntoElement {
self.base.text_color(cx.theme().foreground).path(self.path)
impl Styled for Icon {
fn style(&mut self) -> &mut StyleRefinement {
self.base.style()
}
}
impl RenderOnce for Icon {
fn render(self, _cx: &mut WindowContext) -> impl IntoElement {
self.base.path(self.path)
}
}

View file

@ -3,12 +3,7 @@ use gpui::{
SharedString, Styled, ViewContext, VisualContext, WindowContext,
};
use crate::{
h_flex,
styled_ext::ElevationIndex,
theme::{ActiveTheme, Colorize},
v_flex,
};
use crate::{h_flex, styled_ext::ElevationIndex, theme::ActiveTheme, v_flex};
pub struct Tooltip {
title: SharedString,
@ -64,13 +59,13 @@ pub fn tooltip_container<V>(
// padding to avoid tooltip appearing right below the mouse cursor
div().pl_2().pt_2p5().child(
v_flex()
.bg(cx.theme().popover.invert_l())
.bg(cx.theme().popover)
.rounded(px(8.))
.border_1()
.border_color(cx.theme().border.invert_l())
.border_color(cx.theme().border)
.shadow(ElevationIndex::ElevatedSurface.shadow())
.text_color(cx.theme().background)
.py_1()
.text_color(cx.theme().popover_foreground)
.py_1p5()
.px_2()
.map(|el| f(el, cx)),
)