use gpui::{Div, SharedString, Svg, div, prelude::*, px};
use icons::Icon;
use theme::{TextStyle, Theme, ThemeExt, Typeset, ink};
pub trait Content: ThemeExt {
fn badge(&self, label: impl Into<SharedString>) -> Div {
let theme = self.theme();
div()
.flex_none()
.px(px(8.0))
.py(px(2.0))
.rounded_full()
.border_1()
.border_color(theme.border)
.text_style(TextStyle::Caption)
.text_color(theme.text_muted)
.child(label.into())
}
fn badge_active(&self, label: impl Into<SharedString>) -> Div {
let theme = self.theme();
let emerald = theme.success;
let emerald_text = theme.success_muted; div()
.flex_none()
.px(px(8.0))
.py(px(2.0))
.rounded_full()
.bg(emerald.opacity(0.12))
.text_style(TextStyle::Caption)
.text_color(emerald_text.opacity(0.9))
.child(label.into())
}
fn avatar(&self, initials: impl Into<SharedString>) -> Div {
let theme = self.theme();
div()
.flex_none()
.size(px(28.0))
.rounded_full()
.bg(ink(0.12))
.flex()
.items_center()
.justify_center()
.text_style(TextStyle::Subheadline)
.font_weight(gpui::FontWeight::MEDIUM)
.text_color(theme.text_muted)
.child(initials.into())
}
fn tag(&self, label: impl Into<SharedString>) -> Div {
let theme = self.theme();
div()
.self_start()
.flex()
.flex_row()
.items_center()
.gap(px(5.0))
.pl(px(8.0))
.pr(px(5.0))
.py(px(3.0))
.rounded(px(Theme::control_radius()))
.bg(ink(0.07))
.border_1()
.border_color(theme.border)
.text_style(TextStyle::Callout)
.text_color(theme.text)
.child(label.into())
.child(
crate::icons::icon(crate::icons::glyph::X)
.size(px(10.0))
.text_color(theme.text_faint),
)
}
fn breadcrumb(&self) -> Div {
div()
.self_start()
.flex()
.flex_row()
.items_center()
.gap(px(4.0))
.min_w_0()
}
fn breadcrumb_item(&self, label: impl Into<SharedString>, current: bool) -> Div {
let theme = self.theme();
let mut crumb = div()
.min_w_0()
.truncate()
.text_style(TextStyle::Callout)
.child(label.into());
crumb = if current {
crumb.text_color(theme.text)
} else {
crumb.text_color(theme.text_muted).cursor_pointer()
};
crumb
}
fn breadcrumb_separator(&self) -> Svg {
let theme = self.theme();
crate::icons::icon(crate::icons::glyph::ChevronRight)
.size(px(12.0))
.text_color(theme.text_faint)
}
fn empty_state(
&self,
icon: impl Into<Icon>,
title: impl Into<SharedString>,
hint: impl Into<SharedString>,
) -> Div {
let theme = self.theme();
div()
.w_full()
.flex()
.flex_col()
.items_center()
.justify_center()
.gap(px(6.0))
.py(px(40.0))
.child(
crate::icons::icon(icon)
.size(px(24.0))
.text_color(theme.text_faint),
)
.child(
div()
.text_style(TextStyle::Headline)
.text_color(theme.text)
.child(title.into()),
)
.child(
div()
.text_style(TextStyle::Callout)
.text_color(theme.text_muted)
.child(hint.into()),
)
}
}
impl Content for Theme {}