input.rs

 1use crate::prelude::{InputVariant, InteractionState};
 2use crate::theme::theme;
 3use gpui2::style::{StyleHelpers, Styleable};
 4use gpui2::{elements::div, IntoElement};
 5use gpui2::{Element, ParentElement, ViewContext};
 6
 7#[derive(Element)]
 8pub struct Input {
 9    placeholder: &'static str,
10    value: String,
11    state: InteractionState,
12    variant: InputVariant,
13}
14
15pub fn input(placeholder: &'static str) -> Input {
16    Input {
17        placeholder,
18        value: "".to_string(),
19        state: InteractionState::default(),
20        variant: InputVariant::default(),
21    }
22}
23
24impl Input {
25    pub fn value(mut self, value: String) -> Self {
26        self.value = value;
27        self
28    }
29    pub fn state(mut self, state: InteractionState) -> Self {
30        self.state = state;
31        self
32    }
33    pub fn variant(mut self, variant: InputVariant) -> Self {
34        self.variant = variant;
35        self
36    }
37
38    fn render<V: 'static>(&mut self, _: &mut V, cx: &mut ViewContext<V>) -> impl IntoElement<V> {
39        let theme = theme(cx);
40
41        let text_el;
42        let text_color;
43        let background_color_default;
44        let background_color_active;
45
46        let mut border_color_default = theme.middle.base.default.border;
47        let mut border_color_hover = theme.middle.base.hovered.border;
48        let mut border_color_active = theme.middle.base.pressed.border;
49        let border_color_focus = theme.middle.base.pressed.background;
50
51        match self.variant {
52            InputVariant::Ghost => {
53                background_color_default = theme.middle.base.default.background;
54                background_color_active = theme.middle.base.active.background;
55            }
56            InputVariant::Filled => {
57                background_color_default = theme.middle.on.default.background;
58                background_color_active = theme.middle.on.active.background;
59            }
60        };
61
62        if self.state == InteractionState::Focused {
63            border_color_default = theme.players[0].cursor;
64            border_color_hover = theme.players[0].cursor;
65            border_color_active = theme.players[0].cursor;
66        }
67
68        if self.state == InteractionState::Focused || self.state == InteractionState::Active {
69            text_el = self.value.clone();
70            text_color = theme.lowest.base.default.foreground;
71        } else {
72            text_el = self.placeholder.to_string().clone();
73            text_color = theme.lowest.base.disabled.foreground;
74        }
75
76        div()
77            .h_7()
78            .px_2()
79            .border()
80            .border_color(border_color_default)
81            .fill(background_color_default)
82            .hover()
83            .border_color(border_color_hover)
84            .active()
85            .border_color(border_color_active)
86            .fill(background_color_active)
87            .flex()
88            .items_center()
89            .child(
90                div()
91                    .flex()
92                    .items_center()
93                    .text_sm()
94                    .text_color(text_color)
95                    .child(text_el)
96                    .child(div().text_color(theme.players[0].cursor).child("|")),
97            )
98    }
99}