dropdown_button: Keep rounded when is a ghost variant. (#992)

<img width="159" alt="image"
src="https://github.com/user-attachments/assets/fcb08439-34fc-42f6-bbf4-ca0efbca8e89"
/>
This commit is contained in:
Jason Lee 2025-06-19 22:45:16 +08:00 committed by GitHub
parent 389c25c287
commit b5922f9d92
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 33 additions and 23 deletions

View file

@ -10,10 +10,11 @@ use gpui::{
RenderOnce, SharedString, StatefulInteractiveElement as _, Styled, Window, RenderOnce, SharedString, StatefulInteractiveElement as _, Styled, Window,
}; };
#[derive(Clone, Copy)] #[derive(Default, Clone, Copy)]
pub enum ButtonRounded { pub enum ButtonRounded {
None, None,
Small, Small,
#[default]
Medium, Medium,
Large, Large,
Size(Pixels), Size(Pixels),
@ -155,14 +156,22 @@ impl Default for ButtonVariant {
} }
impl ButtonVariant { impl ButtonVariant {
fn is_link(&self) -> bool { #[inline]
pub fn is_link(&self) -> bool {
matches!(self, Self::Link) matches!(self, Self::Link)
} }
fn is_text(&self) -> bool { #[inline]
pub fn is_text(&self) -> bool {
matches!(self, Self::Text) matches!(self, Self::Text)
} }
#[inline]
pub fn is_ghost(&self) -> bool {
matches!(self, Self::Ghost)
}
#[inline]
fn no_padding(&self) -> bool { fn no_padding(&self) -> bool {
self.is_link() || self.is_text() self.is_link() || self.is_text()
} }

View file

@ -1,25 +1,24 @@
use gpui::{ use gpui::{
prelude::FluentBuilder, App, Context, Corner, Corners, Div, Edges, ElementId, div, prelude::FluentBuilder, App, Context, Corner, Corners, Edges, ElementId,
InteractiveElement as _, IntoElement, ParentElement, RenderOnce, Styled, Window, InteractiveElement as _, IntoElement, ParentElement, RenderOnce, StyleRefinement, Styled,
Window,
}; };
use crate::{ use crate::{
h_flex,
popup_menu::{PopupMenu, PopupMenuExt}, popup_menu::{PopupMenu, PopupMenuExt},
IconName, Selectable, Sizable, Size, IconName, Selectable, Sizable, Size, StyledExt as _,
}; };
use super::{Button, ButtonRounded, ButtonVariant, ButtonVariants}; use super::{Button, ButtonRounded, ButtonVariant, ButtonVariants};
#[derive(IntoElement)] #[derive(IntoElement)]
pub struct DropdownButton { pub struct DropdownButton {
base: Div, style: StyleRefinement,
id: ElementId, id: ElementId,
button: Option<Button>, button: Option<Button>,
popup_menu: popup_menu:
Option<Box<dyn Fn(PopupMenu, &mut Window, &mut Context<PopupMenu>) -> PopupMenu + 'static>>, Option<Box<dyn Fn(PopupMenu, &mut Window, &mut Context<PopupMenu>) -> PopupMenu + 'static>>,
selected: bool, selected: bool,
// The button props // The button props
compact: Option<bool>, compact: Option<bool>,
outline: Option<bool>, outline: Option<bool>,
@ -31,7 +30,7 @@ pub struct DropdownButton {
impl DropdownButton { impl DropdownButton {
pub fn new(id: impl Into<ElementId>) -> Self { pub fn new(id: impl Into<ElementId>) -> Self {
Self { Self {
base: h_flex(), style: StyleRefinement::default(),
id: id.into(), id: id.into(),
button: None, button: None,
popup_menu: None, popup_menu: None,
@ -40,7 +39,7 @@ impl DropdownButton {
outline: None, outline: None,
variant: None, variant: None,
size: None, size: None,
rounded: ButtonRounded::Medium, rounded: ButtonRounded::default(),
} }
} }
@ -71,16 +70,11 @@ impl DropdownButton {
self.outline = Some(true); self.outline = Some(true);
self self
} }
pub fn selected(mut self, selected: bool) -> Self {
self.selected = selected;
self
}
} }
impl Styled for DropdownButton { impl Styled for DropdownButton {
fn style(&mut self) -> &mut gpui::StyleRefinement { fn style(&mut self) -> &mut gpui::StyleRefinement {
self.base.style() &mut self.style
} }
} }
@ -115,17 +109,24 @@ impl Selectable for DropdownButton {
impl RenderOnce for DropdownButton { impl RenderOnce for DropdownButton {
fn render(self, _: &mut Window, _: &mut App) -> impl IntoElement { fn render(self, _: &mut Window, _: &mut App) -> impl IntoElement {
self.base let is_ghost = self
.variant
.map(|variant| variant.is_ghost())
.unwrap_or(false);
div()
.id(self.id) .id(self.id)
.refine_style(&self.style)
.h_flex()
.when_some(self.button, |this, button| { .when_some(self.button, |this, button| {
this.child( this.child(
button button
.rounded(self.rounded) .rounded(self.rounded)
.border_corners(Corners { .border_corners(Corners {
top_left: true, top_left: true,
top_right: false, top_right: is_ghost,
bottom_left: true, bottom_left: true,
bottom_right: false, bottom_right: is_ghost,
}) })
.border_edges(Edges { .border_edges(Edges {
left: true, left: true,
@ -145,15 +146,15 @@ impl RenderOnce for DropdownButton {
.icon(IconName::ChevronDown) .icon(IconName::ChevronDown)
.rounded(self.rounded) .rounded(self.rounded)
.border_edges(Edges { .border_edges(Edges {
left: false, left: is_ghost,
top: true, top: true,
right: true, right: true,
bottom: true, bottom: true,
}) })
.border_corners(Corners { .border_corners(Corners {
top_left: false, top_left: is_ghost,
top_right: true, top_right: true,
bottom_left: false, bottom_left: is_ghost,
bottom_right: true, bottom_right: true,
}) })
.selected(self.selected) .selected(self.selected)