Skip to main content

guise/
mark.rs

1//! `Mark` — an inline highlighted span of text.
2//!
3//! ```ignore
4//! Group::new()
5//!     .gap(Size::Xs)
6//!     .child(Text::new("Highlight the"))
7//!     .child(Mark::new("important part"))
8//!     .child(Text::new("of a sentence."))
9//! ```
10
11use gpui::prelude::*;
12use gpui::{div, px, App, IntoElement, SharedString, Window};
13
14use crate::devtools::Probed;
15use crate::theme::{theme, ColorName, Size};
16
17/// A highlighter-pen span.
18///
19/// Inherits the surrounding font size unless [`Mark::size`] is set, so it
20/// drops into a `Group` next to `Text` runs.
21#[derive(IntoElement)]
22pub struct Mark {
23    content: SharedString,
24    color: ColorName,
25    size: Option<Size>,
26}
27
28impl Mark {
29    pub fn new(content: impl Into<SharedString>) -> Self {
30        Mark {
31            content: content.into(),
32            color: ColorName::Yellow,
33            size: None,
34        }
35    }
36
37    /// The highlight tint (default `Yellow`).
38    pub fn color(mut self, color: ColorName) -> Self {
39        self.color = color;
40        self
41    }
42
43    /// Explicit font size; unset inherits from the parent.
44    pub fn size(mut self, size: Size) -> Self {
45        self.size = Some(size);
46        self
47    }
48}
49
50impl RenderOnce for Mark {
51    fn render(self, _window: &mut Window, cx: &mut App) -> impl IntoElement {
52        let t = theme(cx);
53        // A light shade-2 wash in light mode, a translucent shade-5 tint in
54        // dark mode; text stays the theme text color.
55        let bg = if t.scheme.is_dark() {
56            t.color(self.color, 5).alpha(0.35)
57        } else {
58            t.color(self.color, 2).hsla()
59        };
60        let fg = t.text().hsla();
61
62        let mut el = div()
63            .px(px(4.0))
64            .rounded(px(t.radius(Size::Xs)))
65            .bg(bg)
66            .text_color(fg)
67            .child(self.content);
68        if let Some(size) = self.size {
69            el = el.text_size(px(t.font_size(size)));
70        }
71        el.probe("Mark")
72    }
73}