Skip to content

Commit 15bdfae

Browse files
committed
feat: add horizontal scroll for diff viewer and file list panels
1 parent bb83bfe commit 15bdfae

4 files changed

Lines changed: 51 additions & 7 deletions

File tree

‎src/app.rs‎

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,8 @@ pub struct App {
117117
pub selected: usize,
118118
pub hunks: Vec<DiffHunk>,
119119
pub scroll: usize,
120+
pub diff_scroll_x: usize,
121+
pub file_scroll_x: usize,
120122
pub focus: Focus,
121123
pub status: Option<String>,
122124
pub repo_path: String,
@@ -163,6 +165,8 @@ impl App {
163165
selected: 0,
164166
hunks: Vec::new(),
165167
scroll: 0,
168+
diff_scroll_x: 0,
169+
file_scroll_x: 0,
166170
focus: Focus::FileList,
167171
status: None,
168172
repo_path,
@@ -335,6 +339,7 @@ impl App {
335339
self.selected = 0;
336340
self.hunks.clear();
337341
self.scroll = 0;
342+
self.diff_scroll_x = 0;
338343
self.commits.clear();
339344
self.log_selected = 0;
340345
self.log_diff_title.clear();
@@ -508,6 +513,7 @@ impl App {
508513
self.hunks = hunks;
509514
if reset_scroll {
510515
self.scroll = 0;
516+
self.diff_scroll_x = 0;
511517
self.diff_search_cursor = 0;
512518
} else {
513519
self.scroll = previous_scroll;
@@ -531,6 +537,7 @@ impl App {
531537
self.diff_search_matches.clear();
532538
self.diff_search_cursor = 0;
533539
self.scroll = 0;
540+
self.diff_scroll_x = 0;
534541
}
535542

536543
fn restore_selection(&mut self, previous_path: Option<&str>) -> Option<String> {
@@ -643,6 +650,22 @@ impl App {
643650
self.diff_line_count().saturating_sub(1)
644651
}
645652

653+
pub fn diff_scroll_left(&mut self) {
654+
self.diff_scroll_x = self.diff_scroll_x.saturating_sub(4);
655+
}
656+
657+
pub fn diff_scroll_right(&mut self) {
658+
self.diff_scroll_x = self.diff_scroll_x.saturating_add(4);
659+
}
660+
661+
pub fn file_scroll_left(&mut self) {
662+
self.file_scroll_x = self.file_scroll_x.saturating_sub(4);
663+
}
664+
665+
pub fn file_scroll_right(&mut self) {
666+
self.file_scroll_x = self.file_scroll_x.saturating_add(4);
667+
}
668+
646669
fn recompute_diff_matches(&mut self, scroll_to_match: bool) {
647670
self.diff_search_matches.clear();
648671
if self.diff_search_query.is_empty() {
@@ -824,6 +847,7 @@ impl App {
824847
Ok(hunks) => {
825848
self.hunks = hunks;
826849
self.scroll = 0;
850+
self.diff_scroll_x = 0;
827851
self.log_diff_title = title;
828852
if !self.diff_search_query.is_empty() {
829853
self.recompute_diff_matches(true);
@@ -926,6 +950,7 @@ impl App {
926950
Ok(hunks) => {
927951
self.hunks = hunks;
928952
self.scroll = 0;
953+
self.diff_scroll_x = 0;
929954
self.log_diff_title = title;
930955
if !self.diff_search_query.is_empty() {
931956
self.recompute_diff_matches(true);
@@ -1164,6 +1189,8 @@ mod tests {
11641189
selected: 0,
11651190
hunks: Vec::new(),
11661191
scroll: 0,
1192+
diff_scroll_x: 0,
1193+
file_scroll_x: 0,
11671194
focus: Focus::FileList,
11681195
status: None,
11691196
repo_path: ".".to_string(),

‎src/main.rs‎

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -383,13 +383,17 @@ fn handle_unmapped_upper_key(app: &mut App, key: KeyEvent) {
383383
KeyCode::Esc if app.log_drill_down => app.log_drill_out(),
384384
KeyCode::Char('/') if app.mode == ViewMode::Status => app.start_search(),
385385
KeyCode::Esc if !app.search_query.is_empty() => app.cancel_search(),
386+
KeyCode::Left => app.file_scroll_left(),
387+
KeyCode::Right => app.file_scroll_right(),
386388
_ => {}
387389
},
388390
Focus::DiffViewer => match key.code {
389391
KeyCode::Char('/') => app.start_diff_search(),
390392
KeyCode::Char('n') => app.next_diff_match(),
391393
KeyCode::Char('N') => app.prev_diff_match(),
392394
KeyCode::Esc if !app.diff_search_query.is_empty() => app.cancel_diff_search(),
395+
KeyCode::Left => app.diff_scroll_left(),
396+
KeyCode::Right => app.diff_scroll_right(),
393397
_ => {}
394398
},
395399
Focus::Terminal => {}

‎src/ui/diff_viewer.rs‎

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -215,12 +215,14 @@ pub fn render(
215215
.take(visible_height)
216216
.collect();
217217

218-
let para = Paragraph::new(visible_lines).block(
219-
Block::default()
220-
.borders(Borders::ALL)
221-
.title(title)
222-
.border_style(border_style),
223-
);
218+
let para = Paragraph::new(visible_lines)
219+
.block(
220+
Block::default()
221+
.borders(Borders::ALL)
222+
.title(title)
223+
.border_style(border_style),
224+
)
225+
.scroll((0, app.diff_scroll_x as u16));
224226

225227
frame.render_widget(para, diff_area);
226228

‎src/ui/file_list.rs‎

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,9 +32,20 @@ pub fn render(frame: &mut Frame, app: &App, area: Rect, accent: Color) {
3232
let f = &app.files[idx];
3333
let symbol = f.status.symbol();
3434
let color = super::status_color(f.status);
35+
let path: &str = if app.file_scroll_x == 0 {
36+
&f.path
37+
} else {
38+
let byte_off = f
39+
.path
40+
.char_indices()
41+
.nth(app.file_scroll_x)
42+
.map(|(b, _)| b)
43+
.unwrap_or(f.path.len());
44+
&f.path[byte_off..]
45+
};
3546
let line = Line::from(vec![
3647
Span::styled(format!("{symbol} "), Style::default().fg(color)),
37-
Span::raw(&f.path),
48+
Span::raw(path.to_owned()),
3849
]);
3950
ListItem::new(line)
4051
})

0 commit comments

Comments
 (0)