1use std::{io::stdout, path::Path};
2
3use crate::*;
4use crossterm::{clipboard::CopyToClipboard, cursor, execute, style, terminal};
5use git2::Oid;
6
7pub struct Cli {
8 renderer: BlameRenderer,
9}
10
11impl Cli {
12 pub fn new(path: &Path) -> anyhow::Result<Self> {
13 Ok(Self {
14 renderer: BlameRenderer::new(path)?,
15 })
16 }
17
18 pub fn run(&mut self) -> anyhow::Result<()> {
19 let _ = TerminalRawModeScope::new(true)?;
20
21 let renderer = &mut self.renderer;
22 let size = terminal::size()?;
23 renderer.set_view_size((size.0, size.1 - 1));
24 renderer.read()?;
25 let mut history: Vec<Oid> = vec![];
26 let mut out = stdout();
27 let mut prompt: CommandPrompt = CommandPrompt::None;
28 loop {
29 renderer.render(&mut out)?;
30
31 let command = Command::read(renderer.rendered_rows(), &prompt)?;
32 prompt = CommandPrompt::None;
33 match command {
34 Command::PrevDiff => renderer.move_to_prev_diff(),
35 Command::NextDiff => renderer.move_to_next_diff(),
36 Command::PrevPage => renderer.move_to_prev_page(),
37 Command::NextPage => renderer.move_to_next_page(),
38 Command::FirstLine => renderer.move_to_first_line(),
39 Command::LastLine => renderer.move_to_last_line(),
40 Command::LineNumber(number) => renderer.set_current_line_number(number),
41 Command::Older => {
42 execute!(
43 out,
44 terminal::Clear(terminal::ClearType::All),
45 cursor::MoveTo(0, 0),
46 style::Print("Working...")
47 )?;
48 let old_commit_id = renderer.commit_id();
49 if let Err(error) = renderer.set_commit_id_to_older_than_current_line() {
50 prompt = CommandPrompt::Err { error };
51 renderer.invalidate_render();
53 continue;
54 }
55 history.push(old_commit_id);
56 }
57 Command::Newer => {
58 if let Some(commit_id) = history.pop() {
59 renderer.set_commit_id(commit_id)?;
60 }
61 }
62 Command::Copy => execute!(
63 out,
64 CopyToClipboard::to_clipboard_from(
65 renderer.current_line_commit_id().to_string()
66 )
67 )?,
68 Command::Resize(columns, rows) => renderer.set_view_size((columns, rows - 1)),
69 Command::Quit => break,
70 }
71 }
72 Ok(())
73 }
74}