Skip to main content

ui/components/
section_heading.rs

1use gpui::{AnyElement, FontWeight};
2
3use crate::prelude::*;
4
5/// A mid-page section heading: bold title with optional grouped content
6/// (e.g. a tab bar or filter row) below it. `mb_4` per Tailwind's Section
7/// Heading pattern.
8#[derive(IntoElement, RegisterComponent)]
9pub struct SectionHeading {
10    title: SharedString,
11    content: Option<AnyElement>,
12}
13
14impl SectionHeading {
15    pub fn new(title: impl Into<SharedString>) -> Self {
16        Self {
17            title: title.into(),
18            content: None,
19        }
20    }
21
22    pub fn content(mut self, content: impl IntoElement) -> Self {
23        self.content = Some(content.into_any_element());
24        self
25    }
26}
27
28impl RenderOnce for SectionHeading {
29    fn render(self, _window: &mut Window, cx: &mut App) -> impl IntoElement {
30        v_flex()
31            .w_full()
32            .gap_2()
33            .mb_4()
34            .child(
35                div()
36                    .text_size(rems_from_px(24.))
37                    .font_weight(FontWeight::BOLD)
38                    .text_color(semantic::text(cx))
39                    .child(self.title),
40            )
41            .children(self.content)
42    }
43}
44
45impl Component for SectionHeading {
46    fn scope() -> ComponentScope {
47        ComponentScope::Typography
48    }
49
50    fn description() -> Option<&'static str> {
51        Some("A mid-page section heading with an optional grouped content row below.")
52    }
53
54    fn preview(_window: &mut Window, _cx: &mut App) -> Option<AnyElement> {
55        Some(
56            SectionHeading::new("Billing history")
57                .content(
58                    Label::new("Showing invoices from the last 12 months")
59                        .size(LabelSize::Small)
60                        .color(Color::Muted),
61                )
62                .into_any_element(),
63        )
64    }
65}