git_branchless_undo/tui/
cursive.rs1use cursive::backends::crossterm;
4use cursive_buffered_backend::BufferedBackend;
5use cursive_core::theme::{Color, PaletteColor};
6use cursive_core::{Cursive, CursiveRunner};
7
8use lib::core::effects::Effects;
9
10pub fn with_siv<T, F: FnOnce(Effects, CursiveRunner<Cursive>) -> eyre::Result<T>>(
12 effects: &Effects,
13 f: F,
14) -> eyre::Result<T> {
15 let backend = crossterm::Backend::init()?;
17 let backend = BufferedBackend::new(backend);
18
19 let effects = effects.enable_tui_mode();
20 let mut siv = Cursive::new().into_runner(Box::new(backend));
21 siv.update_theme(|theme| {
22 theme.shadow = false;
23 theme.palette.extend(vec![
24 (PaletteColor::Background, Color::TerminalDefault),
25 (PaletteColor::View, Color::TerminalDefault),
26 (PaletteColor::Primary, Color::TerminalDefault),
27 (PaletteColor::TitlePrimary, Color::TerminalDefault),
28 (PaletteColor::TitleSecondary, Color::TerminalDefault),
29 ]);
30 });
31 f(effects, siv)
32}
33
34pub trait SingletonView<V> {
37 fn find(siv: &mut Cursive) -> cursive_core::views::ViewRef<V>;
40}
41
42#[macro_export]
60macro_rules! declare_views {
61 { $( $k:ident => $v:ty ),* $(,)? } => {
62 $(
63 struct $k {
64 view: cursive_core::views::NamedView<$v>,
65 }
66
67 impl $crate::tui::SingletonView<$v> for $k {
68 fn find(siv: &mut Cursive) -> cursive_core::views::ViewRef<$v> {
69 siv.find_name::<$v>(stringify!($k)).unwrap()
70 }
71 }
72
73 impl From<$v> for $k {
74 fn from(view: $v) -> Self {
75 use cursive_core::view::Nameable;
76 let view = view.with_name(stringify!($k));
77 $k { view }
78 }
79 }
80
81 impl cursive_core::view::ViewWrapper for $k {
82 cursive_core::wrap_impl!(self.view: cursive_core::views::NamedView<$v>);
83 }
84 )*
85 };
86}