matchmaker/render/
state_effects.rs1use super::State;
2use crate::{
3 MAX_EFFECTS, SSS, Selection,
4 message::Event,
5 ui::{PickerUI, PreviewUI, UI},
6};
7
8use arrayvec::ArrayVec;
9use ratatui::text::{Span, Text};
10
11#[derive(Debug, Clone)]
12pub enum Effect {
13 ClearPreviewSet,
14 Header(Text<'static>),
15 Footer(Text<'static>),
16 ClearFooter,
17 ClearHeader,
18 ClearSelections,
19 RevalidateSelectons,
20 Reload,
23
24 Prompt(Span<'static>),
25 Input((String, u16)),
27 RestoreInputPrefix,
28
29 DisableCursor(bool),
30 SetIndex(u32),
31 TrySync,
32}
33#[derive(Debug, Default)]
34pub struct Effects(ArrayVec<Effect, MAX_EFFECTS>);
35
36#[macro_export]
37macro_rules! efx {
38 ( $( $x:expr ),* $(,)? ) => {
39 {
40 [$($x),*].into_iter().collect::<$crate::render::Effects>()
41 }
42 };
43}
44pub use crate::acs;
45
46impl<S: Selection> State<S> {
47 pub fn apply_effects<T: SSS>(
49 &mut self,
50 effects: Effects,
51 _ui: &mut UI,
52 picker_ui: &mut PickerUI<T, S>,
53 _preview_ui: &mut Option<PreviewUI>,
54 ) {
55 if !effects.is_empty() {
56 log::debug!("{effects:?}");
57 }
58 for effect in effects {
59 match effect {
60 Effect::ClearPreviewSet => {
62 self.preview_set = None;
63 }
64
65 Effect::Header(text) => {
67 picker_ui.header.set(text);
68 }
69 Effect::Footer(text) => {
70 picker_ui.footer.set(text);
71 }
72 Effect::ClearHeader => {
73 picker_ui.header.show = false;
74 }
75 Effect::ClearFooter => {
76 picker_ui.footer.show = false;
77 }
78
79 Effect::Input((input, cursor)) => {
81 picker_ui.input.set(input, cursor);
82 }
83 Effect::Prompt(prompt) => {
84 picker_ui.input.prompt = prompt;
85 }
86 Effect::RestoreInputPrefix => {
87 picker_ui.input.prompt = Span::from(picker_ui.input.config.prompt.clone());
88 }
89
90 Effect::DisableCursor(disabled) => {
92 picker_ui.results.cursor_disabled = disabled;
93 }
94 Effect::SetIndex(index) => {
95 log::info!("{:?}", picker_ui.results);
96 picker_ui.results.cursor_jump(index);
97 }
98
99 Effect::ClearSelections => {
101 picker_ui.selections.clear();
102 }
103 Effect::RevalidateSelectons => {
104 picker_ui.selections.revalidate();
105 }
106
107 Effect::Reload => {
110 picker_ui.worker.restart(false);
112 }
113 Effect::TrySync => {
114 if !picker_ui.results.status.running {
115 self.insert(Event::Synced);
116 }
117 }
118 }
119 }
120 }
121}
122
123impl PartialEq for Effect {
126 fn eq(&self, other: &Self) -> bool {
127 std::mem::discriminant(self) == std::mem::discriminant(other)
128 }
129}
130
131impl Eq for Effect {}
132
133impl Effects {
134 pub fn new() -> Self {
135 Self(ArrayVec::new())
136 }
137
138 pub fn insert(&mut self, effect: Effect) -> bool {
140 if self.0.contains(&effect) {
141 false
142 } else {
143 self.0.push(effect);
144 true
145 }
146 }
147
148 pub fn len(&self) -> usize {
149 self.0.len()
150 }
151
152 pub fn is_empty(&self) -> bool {
153 self.0.is_empty()
154 }
155
156 pub fn append(&mut self, other: Self) {
157 for effect in other {
158 self.insert(effect);
159 }
160 }
161}
162
163impl IntoIterator for Effects {
164 type Item = Effect;
165 type IntoIter = arrayvec::IntoIter<Effect, 12>;
166
167 fn into_iter(self) -> Self::IntoIter {
168 self.0.into_iter()
169 }
170}
171
172impl FromIterator<Effect> for Effects {
173 fn from_iter<I: IntoIterator<Item = Effect>>(iter: I) -> Self {
174 let mut effects = Effects::new();
175 for e in iter {
176 effects.insert(e);
177 }
178 effects
179 }
180}