typography.rs

  1use gpui::{
  2    div, rems, IntoElement, ParentElement, Rems, RenderOnce, SharedString, Styled, WindowContext,
  3};
  4use settings::Settings;
  5use theme::{ActiveTheme, ThemeSettings};
  6
  7#[derive(Debug, Default, Clone)]
  8pub enum UiTextSize {
  9    /// The default size for UI text.
 10    ///
 11    /// `0.825rem` or `14px` at the default scale of `1rem` = `16px`.
 12    ///
 13    /// Note: The absolute size of this text will change based on a user's `ui_scale` setting.
 14    #[default]
 15    Default,
 16    /// The small size for UI text.
 17    ///
 18    /// `0.75rem` or `12px` at the default scale of `1rem` = `16px`.
 19    ///
 20    /// Note: The absolute size of this text will change based on a user's `ui_scale` setting.
 21    Small,
 22
 23    /// The extra small size for UI text.
 24    ///
 25    /// `0.625rem` or `10px` at the default scale of `1rem` = `16px`.
 26    ///
 27    /// Note: The absolute size of this text will change based on a user's `ui_scale` setting.
 28    XSmall,
 29}
 30
 31impl UiTextSize {
 32    pub fn rems(self) -> Rems {
 33        match self {
 34            Self::Default => rems(14. / 16.),
 35            Self::Small => rems(12. / 16.),
 36            Self::XSmall => rems(10. / 16.),
 37        }
 38    }
 39}
 40
 41#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Clone, Copy, Default)]
 42pub enum HeadlineSize {
 43    XSmall,
 44    Small,
 45    #[default]
 46    Medium,
 47    Large,
 48    XLarge,
 49}
 50
 51impl HeadlineSize {
 52    pub fn size(self) -> Rems {
 53        match self {
 54            // Based on the Major Second scale
 55            Self::XSmall => rems(0.88),
 56            Self::Small => rems(1.0),
 57            Self::Medium => rems(1.125),
 58            Self::Large => rems(1.27),
 59            Self::XLarge => rems(1.43),
 60        }
 61    }
 62
 63    pub fn line_height(self) -> Rems {
 64        match self {
 65            Self::XSmall => rems(1.6),
 66            Self::Small => rems(1.6),
 67            Self::Medium => rems(1.6),
 68            Self::Large => rems(1.6),
 69            Self::XLarge => rems(1.6),
 70        }
 71    }
 72}
 73
 74#[derive(IntoElement)]
 75pub struct Headline {
 76    size: HeadlineSize,
 77    text: SharedString,
 78}
 79
 80impl RenderOnce for Headline {
 81    fn render(self, cx: &mut WindowContext) -> impl IntoElement {
 82        let ui_font = ThemeSettings::get_global(cx).ui_font.family.clone();
 83
 84        div()
 85            .font(ui_font)
 86            .line_height(self.size.line_height())
 87            .text_size(self.size.size())
 88            .text_color(cx.theme().colors().text)
 89            .child(self.text)
 90    }
 91}
 92
 93impl Headline {
 94    pub fn new(text: impl Into<SharedString>) -> Self {
 95        Self {
 96            size: HeadlineSize::default(),
 97            text: text.into(),
 98        }
 99    }
100
101    pub fn size(mut self, size: HeadlineSize) -> Self {
102        self.size = size;
103        self
104    }
105}