Fixing Multiple Panics (#121)

* init

* wip

* wip
pull/124/head
Kirawi 4 years ago committed by GitHub
parent 5a344a3ae5
commit c17dcb8633
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -45,7 +45,10 @@ pub fn move_vertically(
let new_line = match dir { let new_line = match dir {
Direction::Backward => row.saturating_sub(count), Direction::Backward => row.saturating_sub(count),
Direction::Forward => std::cmp::min(row.saturating_add(count), text.len_lines() - 2), Direction::Forward => std::cmp::min(
row.saturating_add(count),
text.len_lines().saturating_sub(2),
),
}; };
// convert to 0-indexed, subtract another 1 because len_chars() counts \n // convert to 0-indexed, subtract another 1 because len_chars() counts \n

@ -383,7 +383,7 @@ pub fn split_on_matches(
// TODO: retain range direction // TODO: retain range direction
let end = text.byte_to_char(start_byte + mat.start()); let end = text.byte_to_char(start_byte + mat.start());
result.push(Range::new(start, end - 1)); result.push(Range::new(start, end.saturating_sub(1)));
start = text.byte_to_char(start_byte + mat.end()); start = text.byte_to_char(start_byte + mat.end());
} }

@ -90,7 +90,8 @@ impl ChangeSet {
return; return;
} }
self.len_after += fragment.len(); // Avoiding std::str::len() to account for UTF-8 characters.
self.len_after += fragment.chars().count();
let new_last = match self.changes.as_mut_slice() { let new_last = match self.changes.as_mut_slice() {
[.., Insert(prev)] | [.., Insert(prev), Delete(_)] => { [.., Insert(prev)] | [.., Insert(prev), Delete(_)] => {
@ -754,4 +755,21 @@ mod test {
use Operation::*; use Operation::*;
assert_eq!(changes.changes, &[Insert("a".into())]); assert_eq!(changes.changes, &[Insert("a".into())]);
} }
#[test]
fn combine_with_utf8() {
const TEST_CASE: &'static str = "Hello, これはヒレクスエディターです!";
let empty = Rope::from("");
let mut a = ChangeSet::new(&empty);
let mut b = ChangeSet::new(&empty);
b.insert(TEST_CASE.into());
let changes = a.compose(b);
use Operation::*;
assert_eq!(changes.changes, &[Insert(TEST_CASE.into())]);
assert_eq!(changes.len_after, TEST_CASE.chars().count());
}
} }

@ -669,7 +669,7 @@ fn _search(doc: &mut Document, view: &mut View, contents: &str, regex: &Regex, e
return; return;
} }
let head = end - 1; let head = end;
let selection = if extend { let selection = if extend {
selection.clone().push(Range::new(start, head)) selection.clone().push(Range::new(start, head))
@ -749,7 +749,9 @@ pub fn select_line(cx: &mut Context) {
let line = text.char_to_line(pos.head); let line = text.char_to_line(pos.head);
let start = text.line_to_char(line); let start = text.line_to_char(line);
let end = text.line_to_char(line + count).saturating_sub(1); let end = text
.line_to_char(std::cmp::min(doc.text().len_lines(), line + count))
.saturating_sub(1);
doc.set_selection(view.id, Selection::single(start, end)); doc.set_selection(view.id, Selection::single(start, end));
} }

@ -341,7 +341,7 @@ impl EditorView {
let info: Style = theme.get("info"); let info: Style = theme.get("info");
let hint: Style = theme.get("hint"); let hint: Style = theme.get("hint");
for (i, line) in (view.first_line..last_line).enumerate() { for (i, line) in (view.first_line..=last_line).enumerate() {
use helix_core::diagnostic::Severity; use helix_core::diagnostic::Severity;
if let Some(diagnostic) = doc.diagnostics.iter().find(|d| d.line == line) { if let Some(diagnostic) = doc.diagnostics.iter().find(|d| d.line == line) {
surface.set_stringn( surface.set_stringn(

@ -114,7 +114,7 @@ impl Prompt {
let selected_color = theme.get("ui.menu.selected"); let selected_color = theme.get("ui.menu.selected");
// completion // completion
let max_col = area.width / BASE_WIDTH; let max_col = std::cmp::max(1, area.width / BASE_WIDTH);
let height = ((self.completion.len() as u16 + max_col - 1) / max_col); let height = ((self.completion.len() as u16 + max_col - 1) / max_col);
let completion_area = Rect::new( let completion_area = Rect::new(
area.x, area.x,

@ -106,7 +106,7 @@ impl View {
/// Calculates the last visible line on screen /// Calculates the last visible line on screen
#[inline] #[inline]
pub fn last_line(&self, doc: &Document) -> usize { pub fn last_line(&self, doc: &Document) -> usize {
let height = self.area.height.saturating_sub(1); // - 1 for statusline let height = self.area.height.saturating_sub(2); // - 2 for statusline
std::cmp::min( std::cmp::min(
self.first_line + height as usize, self.first_line + height as usize,
doc.text().len_lines() - 1, doc.text().len_lines() - 1,

Loading…
Cancel
Save