popover: Improve PopoverContent to support styled methods. (#951)

- Add `refine_style` method to `StyledExt`.
- Also improve the Popover example style.

<img width="1053" alt="image"
src="https://github.com/user-attachments/assets/bf435a79-6c34-41ab-802a-29a7600ecd29"
/>
This commit is contained in:
Jason Lee 2025-06-12 15:00:00 +08:00 committed by GitHub
parent d61b0d2510
commit e29b51cc83
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 25 additions and 12 deletions

View file

@ -187,12 +187,14 @@ impl Render for PopoverStory {
.child(Divider::horizontal())
.child(
Button::new("info1")
.label("Yes")
.primary()
.label("Ok")
.w(px(80.))
.small(),
)
.into_any()
})
.p_4()
.max_w(px(600.))
})
}),
@ -212,12 +214,14 @@ impl Render for PopoverStory {
.child(Divider::horizontal())
.child(
Button::new("info1")
.label("Yes")
.primary()
.label("Ok")
.w(px(80.))
.small(),
)
.into_any()
})
.p_4()
})
}),
),
@ -250,8 +254,10 @@ impl Render for PopoverStory {
.child(
h_flex()
.gap_2()
.justify_end()
.child(
Button::new("info1")
.primary()
.label("Ok")
.w(px(80.))
.small()
@ -278,6 +284,7 @@ impl Render for PopoverStory {
)
.into_any()
})
.p_4()
})
}),
),

View file

@ -16,9 +16,9 @@ pub fn init(cx: &mut App) {
}
pub struct PopoverContent {
style: StyleRefinement,
focus_handle: FocusHandle,
content: Rc<dyn Fn(&mut Window, &mut Context<Self>) -> AnyElement>,
max_width: Option<Pixels>,
}
impl PopoverContent {
@ -29,16 +29,11 @@ impl PopoverContent {
let focus_handle = cx.focus_handle();
Self {
style: StyleRefinement::default().p_2(),
focus_handle,
content: Rc::new(content),
max_width: None,
}
}
pub fn max_w(mut self, max_width: Pixels) -> Self {
self.max_width = Some(max_width);
self
}
}
impl EventEmitter<DismissEvent> for PopoverContent {}
@ -48,17 +43,22 @@ impl Focusable for PopoverContent {
}
}
impl Styled for PopoverContent {
fn style(&mut self) -> &mut StyleRefinement {
&mut self.style
}
}
impl Render for PopoverContent {
fn render(&mut self, window: &mut Window, cx: &mut Context<Self>) -> impl IntoElement {
div()
.refine_style(&self.style)
.track_focus(&self.focus_handle)
.key_context(CONTEXT)
.on_action(cx.listener(|_, _: &Cancel, _, cx| {
cx.propagate();
cx.emit(DismissEvent);
}))
.p_2()
.when_some(self.max_width, |this, v| this.max_w(v))
.child(self.content.clone()(window, cx))
}
}

View file

@ -6,7 +6,7 @@ use crate::{
};
use gpui::{
div, px, App, Axis, DefiniteLength, Div, Edges, Element, ElementId, EntityId, FocusHandle,
Pixels, Styled, Window,
Pixels, Refineable, StyleRefinement, Styled, Window,
};
use serde::{Deserialize, Serialize};
@ -34,6 +34,12 @@ macro_rules! font_weight {
/// Extends [`gpui::Styled`] with specific styling methods.
pub trait StyledExt: Styled + Sized {
/// Refine the style of this element, applying the given style refinement.
fn refine_style(mut self, style: &StyleRefinement) -> Self {
self.style().refine(style);
self
}
/// Apply self into a horizontal flex layout.
#[inline]
fn h_flex(self) -> Self {