Detailed changes
@@ -1,4 +1,4 @@
-use crate::{Direction, SearchOption, SelectMatch};
+use crate::{active_match_index, match_index_for_direction, Direction, SearchOption, SelectMatch};
use collections::HashMap;
use editor::{display_map::ToDisplayPoint, Anchor, Autoscroll, Bias, Editor};
use gpui::{
@@ -8,10 +8,7 @@ use gpui::{
use language::AnchorRangeExt;
use postage::watch;
use project::search::SearchQuery;
-use std::{
- cmp::{self, Ordering},
- ops::Range,
-};
+use std::ops::Range;
use workspace::{ItemViewHandle, Pane, Settings, Toolbar, Workspace};
action!(Deploy, bool);
@@ -334,43 +331,23 @@ impl SearchBar {
cx.notify();
}
- fn select_match(&mut self, SelectMatch(direction): &SelectMatch, cx: &mut ViewContext<Self>) {
- if let Some(mut index) = self.active_match_index {
+ fn select_match(&mut self, &SelectMatch(direction): &SelectMatch, cx: &mut ViewContext<Self>) {
+ if let Some(index) = self.active_match_index {
if let Some(editor) = self.active_editor.as_ref() {
editor.update(cx, |editor, cx| {
- let newest_selection = editor.newest_anchor_selection().clone();
if let Some(ranges) = self.editors_with_matches.get(&cx.weak_handle()) {
- let position = newest_selection.head();
- let buffer = editor.buffer().read(cx).read(cx);
- if ranges[index].start.cmp(&position, &buffer).unwrap().is_gt() {
- if *direction == Direction::Prev {
- if index == 0 {
- index = ranges.len() - 1;
- } else {
- index -= 1;
- }
- }
- } else if ranges[index].end.cmp(&position, &buffer).unwrap().is_lt() {
- if *direction == Direction::Next {
- index = 0;
- }
- } else if *direction == Direction::Prev {
- if index == 0 {
- index = ranges.len() - 1;
- } else {
- index -= 1;
- }
- } else if *direction == Direction::Next {
- if index == ranges.len() - 1 {
- index = 0
- } else {
- index += 1;
- }
- }
-
- let range_to_select = ranges[index].clone();
- drop(buffer);
- editor.select_ranges([range_to_select], Some(Autoscroll::Fit), cx);
+ let new_index = match_index_for_direction(
+ ranges,
+ &editor.newest_anchor_selection().head(),
+ index,
+ direction,
+ &editor.buffer().read(cx).read(cx),
+ );
+ editor.select_ranges(
+ [ranges[new_index].clone()],
+ Some(Autoscroll::Fit),
+ cx,
+ );
}
});
}
@@ -518,30 +495,18 @@ impl SearchBar {
}
fn update_match_index(&mut self, cx: &mut ViewContext<Self>) {
- self.active_match_index = self.active_match_index(cx);
- cx.notify();
- }
-
- fn active_match_index(&mut self, cx: &mut ViewContext<Self>) -> Option<usize> {
- let editor = self.active_editor.as_ref()?;
- let ranges = self.editors_with_matches.get(&editor.downgrade())?;
- let editor = editor.read(cx);
- let position = editor.newest_anchor_selection().head();
- if ranges.is_empty() {
- None
- } else {
- let buffer = editor.buffer().read(cx).read(cx);
- match ranges.binary_search_by(|probe| {
- if probe.end.cmp(&position, &*buffer).unwrap().is_lt() {
- Ordering::Less
- } else if probe.start.cmp(&position, &*buffer).unwrap().is_gt() {
- Ordering::Greater
- } else {
- Ordering::Equal
- }
- }) {
- Ok(i) | Err(i) => Some(cmp::min(i, ranges.len() - 1)),
- }
+ let new_index = self.active_editor.as_ref().and_then(|editor| {
+ let ranges = self.editors_with_matches.get(&editor.downgrade())?;
+ let editor = editor.read(cx);
+ active_match_index(
+ &ranges,
+ &editor.newest_anchor_selection().head(),
+ &editor.buffer().read(cx).read(cx),
+ )
+ });
+ if new_index != self.active_match_index {
+ self.active_match_index = new_index;
+ cx.notify();
}
}
}
@@ -1,4 +1,7 @@
-use crate::{Direction, SearchOption, SelectMatch, ToggleSearchOption};
+use crate::{
+ active_match_index, match_index_for_direction, Direction, SearchOption, SelectMatch,
+ ToggleSearchOption,
+};
use collections::HashMap;
use editor::{Anchor, Autoscroll, Editor, MultiBuffer, SelectAll};
use gpui::{
@@ -10,7 +13,6 @@ use postage::watch;
use project::{search::SearchQuery, Project};
use std::{
any::{Any, TypeId},
- cmp::{self, Ordering},
ops::Range,
path::PathBuf,
};
@@ -496,42 +498,17 @@ impl ProjectSearchView {
}
fn select_match(&mut self, &SelectMatch(direction): &SelectMatch, cx: &mut ViewContext<Self>) {
- if let Some(mut index) = self.active_match_index {
- let range_to_select = {
- let model = self.model.read(cx);
- let results_editor = self.results_editor.read(cx);
- let buffer = results_editor.buffer().read(cx).read(cx);
- let cursor = results_editor.newest_anchor_selection().head();
- let ranges = &model.match_ranges;
-
- if ranges[index].start.cmp(&cursor, &buffer).unwrap().is_gt() {
- if direction == Direction::Prev {
- if index == 0 {
- index = ranges.len() - 1;
- } else {
- index -= 1;
- }
- }
- } else if ranges[index].end.cmp(&cursor, &buffer).unwrap().is_lt() {
- if direction == Direction::Next {
- index = 0;
- }
- } else if direction == Direction::Prev {
- if index == 0 {
- index = ranges.len() - 1;
- } else {
- index -= 1;
- }
- } else if direction == Direction::Next {
- if index == ranges.len() - 1 {
- index = 0
- } else {
- index += 1;
- }
- };
- ranges[index].clone()
- };
-
+ if let Some(index) = self.active_match_index {
+ let model = self.model.read(cx);
+ let results_editor = self.results_editor.read(cx);
+ let new_index = match_index_for_direction(
+ &model.match_ranges,
+ &results_editor.newest_anchor_selection().head(),
+ index,
+ direction,
+ &results_editor.buffer().read(cx).read(cx),
+ );
+ let range_to_select = model.match_ranges[new_index].clone();
self.results_editor.update(cx, |editor, cx| {
editor.select_ranges([range_to_select], Some(Autoscroll::Fit), cx);
});
@@ -595,30 +572,15 @@ impl ProjectSearchView {
}
fn update_match_index(&mut self, cx: &mut ViewContext<Self>) {
- let match_ranges = self.model.read(cx).match_ranges.clone();
- if match_ranges.is_empty() {
- self.active_match_index = None;
- } else {
- let results_editor = &self.results_editor.read(cx);
- let cursor = results_editor.newest_anchor_selection().head();
- let new_index = {
- let buffer = results_editor.buffer().read(cx).read(cx);
- match match_ranges.binary_search_by(|probe| {
- if probe.end.cmp(&cursor, &*buffer).unwrap().is_lt() {
- Ordering::Less
- } else if probe.start.cmp(&cursor, &*buffer).unwrap().is_gt() {
- Ordering::Greater
- } else {
- Ordering::Equal
- }
- }) {
- Ok(i) | Err(i) => Some(cmp::min(i, match_ranges.len() - 1)),
- }
- };
- if self.active_match_index != new_index {
- self.active_match_index = new_index;
- cx.notify();
- }
+ let results_editor = self.results_editor.read(cx);
+ let new_index = active_match_index(
+ &self.model.read(cx).match_ranges,
+ &results_editor.newest_anchor_selection().head(),
+ &results_editor.buffer().read(cx).read(cx),
+ );
+ if self.active_match_index != new_index {
+ self.active_match_index = new_index;
+ cx.notify();
}
}
@@ -1,3 +1,9 @@
+use std::{
+ cmp::{self, Ordering},
+ ops::Range,
+};
+
+use editor::{Anchor, MultiBufferSnapshot};
use gpui::{action, MutableAppContext};
mod buffer_search;
@@ -23,3 +29,60 @@ pub enum Direction {
Prev,
Next,
}
+
+pub(crate) fn active_match_index(
+ ranges: &[Range<Anchor>],
+ cursor: &Anchor,
+ buffer: &MultiBufferSnapshot,
+) -> Option<usize> {
+ if ranges.is_empty() {
+ None
+ } else {
+ match ranges.binary_search_by(|probe| {
+ if probe.end.cmp(&cursor, &*buffer).unwrap().is_lt() {
+ Ordering::Less
+ } else if probe.start.cmp(&cursor, &*buffer).unwrap().is_gt() {
+ Ordering::Greater
+ } else {
+ Ordering::Equal
+ }
+ }) {
+ Ok(i) | Err(i) => Some(cmp::min(i, ranges.len() - 1)),
+ }
+ }
+}
+
+pub(crate) fn match_index_for_direction(
+ ranges: &[Range<Anchor>],
+ cursor: &Anchor,
+ mut index: usize,
+ direction: Direction,
+ buffer: &MultiBufferSnapshot,
+) -> usize {
+ if ranges[index].start.cmp(&cursor, &buffer).unwrap().is_gt() {
+ if direction == Direction::Prev {
+ if index == 0 {
+ index = ranges.len() - 1;
+ } else {
+ index -= 1;
+ }
+ }
+ } else if ranges[index].end.cmp(&cursor, &buffer).unwrap().is_lt() {
+ if direction == Direction::Next {
+ index = 0;
+ }
+ } else if direction == Direction::Prev {
+ if index == 0 {
+ index = ranges.len() - 1;
+ } else {
+ index -= 1;
+ }
+ } else if direction == Direction::Next {
+ if index == ranges.len() - 1 {
+ index = 0
+ } else {
+ index += 1;
+ }
+ };
+ index
+}