1
1
mirror of https://github.com/wez/wezterm.git synced 2024-12-25 06:12:16 +03:00

fix an issue with the selection when in scrollback

This commit is contained in:
Wez Furlong 2018-02-19 16:26:10 -08:00
parent dd238d5b50
commit 25e2dc2a96
3 changed files with 64 additions and 13 deletions

View File

@ -90,7 +90,7 @@ pub struct TerminalState {
/// purely for display purposes. /// purely for display purposes.
/// The offset is measured from the top of the physical viewable /// The offset is measured from the top of the physical viewable
/// screen with larger numbers going backwards. /// screen with larger numbers going backwards.
viewport_offset: VisibleRowIndex, pub(crate) viewport_offset: VisibleRowIndex,
/// Remembers the starting coordinate of the selection prior to /// Remembers the starting coordinate of the selection prior to
/// dragging. /// dragging.
@ -281,13 +281,15 @@ impl TerminalState {
self.selection_range = None; self.selection_range = None;
self.selection_start = Some(SelectionCoordinate { self.selection_start = Some(SelectionCoordinate {
x: event.x, x: event.x,
y: event.y as ScrollbackOrVisibleRowIndex, y: event.y as ScrollbackOrVisibleRowIndex -
self.viewport_offset as ScrollbackOrVisibleRowIndex,
}); });
host.set_clipboard(None)?; host.set_clipboard(None)?;
} }
// Double click to select a word on the current line // Double click to select a word on the current line
Some(&LastMouseClick { streak: 2, .. }) => { Some(&LastMouseClick { streak: 2, .. }) => {
let y = event.y as ScrollbackOrVisibleRowIndex; let y = event.y as ScrollbackOrVisibleRowIndex -
self.viewport_offset as ScrollbackOrVisibleRowIndex;
let idx = self.screen().scrollback_or_visible_row(y); let idx = self.screen().scrollback_or_visible_row(y);
let line = self.screen().lines[idx].as_str(); let line = self.screen().lines[idx].as_str();
use unicode_segmentation::UnicodeSegmentation; use unicode_segmentation::UnicodeSegmentation;
@ -324,18 +326,14 @@ impl TerminalState {
} }
// triple click to select the current line // triple click to select the current line
Some(&LastMouseClick { streak: 3, .. }) => { Some(&LastMouseClick { streak: 3, .. }) => {
self.selection_start = Some(SelectionCoordinate { let y = event.y as ScrollbackOrVisibleRowIndex -
x: event.x, self.viewport_offset as ScrollbackOrVisibleRowIndex;
y: event.y as ScrollbackOrVisibleRowIndex, self.selection_start = Some(SelectionCoordinate { x: event.x, y });
});
self.selection_range = Some(SelectionRange { self.selection_range = Some(SelectionRange {
start: SelectionCoordinate { start: SelectionCoordinate { x: 0, y },
x: 0,
y: event.y as ScrollbackOrVisibleRowIndex,
},
end: SelectionCoordinate { end: SelectionCoordinate {
x: usize::max_value(), x: usize::max_value(),
y: event.y as ScrollbackOrVisibleRowIndex, y,
}, },
}); });
self.dirty_selection_lines(); self.dirty_selection_lines();
@ -395,7 +393,8 @@ impl TerminalState {
self.dirty_selection_lines(); self.dirty_selection_lines();
let end = SelectionCoordinate { let end = SelectionCoordinate {
x: event.x, x: event.x,
y: event.y as ScrollbackOrVisibleRowIndex, y: event.y as ScrollbackOrVisibleRowIndex -
self.viewport_offset as ScrollbackOrVisibleRowIndex,
}; };
let sel = match self.selection_range.take() { let sel = match self.selection_range.take() {
None => { None => {

View File

@ -204,6 +204,34 @@ impl TestTerm {
reason reason
); );
} }
fn viewport_lines(&self) -> Vec<Line> {
let screen = self.screen();
let line_count = screen.lines.len();
let viewport = self.viewport_offset;
let phs_rows = screen.physical_rows;
screen
.all_lines()
.iter()
.skip((line_count as i64 - phs_rows as i64 - viewport) as usize)
.take(phs_rows)
.cloned()
.collect()
}
fn print_viewport_lines(&self) {
println!("viewport contents are:");
for line in self.viewport_lines() {
println!("[{}]", line.as_str());
}
}
fn assert_viewport_contents(&self, expect_lines: &[&str]) {
self.print_viewport_lines();
let expect: Vec<Line> = expect_lines.iter().map(|s| (*s).into()).collect();
assert_lines_equal(&self.viewport_lines(), &expect, Compare::TEXT);
}
} }
impl Deref for TestTerm { impl Deref for TestTerm {

View File

@ -62,3 +62,27 @@ fn triple_click_selection() {
assert_eq!(term.get_clipboard().unwrap(), "hello worl"); assert_eq!(term.get_clipboard().unwrap(), "hello worl");
} }
/// Make sure that we adjust for the viewport offset when scrolling
#[test]
fn selection_in_scrollback() {
let mut term = TestTerm::new(2, 1, 4);
term.print("1234");
assert_all_contents(&term, &["1", "2", "3", "4"]);
// Scroll back one line
term.scroll_viewport(-1);
term.assert_viewport_contents(&["2", "3"]);
term.click_n(0, 0, MouseButton::Left, 2);
assert_eq!(term.get_clipboard().unwrap(), "2");
// Clear the click streak
term.click_n(0, 1, MouseButton::Right, 1);
term.click_n(0, 1, MouseButton::Left, 3);
assert_eq!(term.get_clipboard().unwrap(), "3");
term.drag_select(0, 0, 0, 1);
assert_eq!(term.get_clipboard().unwrap(), "2\n3");
}