aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_editor/src/assists.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_editor/src/assists.rs')
-rw-r--r--crates/ra_editor/src/assists.rs23
1 files changed, 23 insertions, 0 deletions
diff --git a/crates/ra_editor/src/assists.rs b/crates/ra_editor/src/assists.rs
index a320caabf..f839f6a7a 100644
--- a/crates/ra_editor/src/assists.rs
+++ b/crates/ra_editor/src/assists.rs
@@ -9,12 +9,15 @@ mod add_impl;
9mod introduce_variable; 9mod introduce_variable;
10mod change_visibility; 10mod change_visibility;
11mod split_import; 11mod split_import;
12mod replace_if_let_with_match;
12 13
13use ra_text_edit::{TextEdit, TextEditBuilder}; 14use ra_text_edit::{TextEdit, TextEditBuilder};
14use ra_syntax::{ 15use ra_syntax::{
15 Direction, SyntaxNode, TextUnit, TextRange, SourceFile, AstNode, 16 Direction, SyntaxNode, TextUnit, TextRange, SourceFile, AstNode,
16 algo::{find_leaf_at_offset, find_covering_node, LeafAtOffset}, 17 algo::{find_leaf_at_offset, find_covering_node, LeafAtOffset},
18 ast::{self, AstToken},
17}; 19};
20use itertools::Itertools;
18 21
19use crate::find_node_at_offset; 22use crate::find_node_at_offset;
20 23
@@ -25,6 +28,7 @@ pub use self::{
25 introduce_variable::introduce_variable, 28 introduce_variable::introduce_variable,
26 change_visibility::change_visibility, 29 change_visibility::change_visibility,
27 split_import::split_import, 30 split_import::split_import,
31 replace_if_let_with_match::replace_if_let_with_match,
28}; 32};
29 33
30/// Return all the assists applicable at the given position. 34/// Return all the assists applicable at the given position.
@@ -37,6 +41,7 @@ pub fn assists(file: &SourceFile, range: TextRange) -> Vec<LocalEdit> {
37 introduce_variable, 41 introduce_variable,
38 change_visibility, 42 change_visibility,
39 split_import, 43 split_import,
44 replace_if_let_with_match,
40 ] 45 ]
41 .iter() 46 .iter()
42 .filter_map(|&assist| ctx.clone().apply(assist)) 47 .filter_map(|&assist| ctx.clone().apply(assist))
@@ -160,6 +165,13 @@ impl AssistBuilder {
160 fn replace(&mut self, range: TextRange, replace_with: impl Into<String>) { 165 fn replace(&mut self, range: TextRange, replace_with: impl Into<String>) {
161 self.edit.replace(range, replace_with.into()) 166 self.edit.replace(range, replace_with.into())
162 } 167 }
168 fn replace_node_and_indent(&mut self, node: &SyntaxNode, replace_with: impl Into<String>) {
169 let mut replace_with = replace_with.into();
170 if let Some(indent) = calc_indent(node) {
171 replace_with = reindent(&replace_with, indent)
172 }
173 self.replace(node.range(), replace_with)
174 }
163 #[allow(unused)] 175 #[allow(unused)]
164 fn delete(&mut self, range: TextRange) { 176 fn delete(&mut self, range: TextRange) {
165 self.edit.delete(range) 177 self.edit.delete(range)
@@ -172,6 +184,17 @@ impl AssistBuilder {
172 } 184 }
173} 185}
174 186
187fn calc_indent(node: &SyntaxNode) -> Option<&str> {
188 let prev = node.prev_sibling()?;
189 let ws_text = ast::Whitespace::cast(prev)?.text();
190 ws_text.rfind('\n').map(|pos| &ws_text[pos + 1..])
191}
192
193fn reindent(text: &str, indent: &str) -> String {
194 let indent = format!("\n{}", indent);
195 text.lines().intersperse(&indent).collect()
196}
197
175#[cfg(test)] 198#[cfg(test)]
176fn check_assist(assist: fn(AssistCtx) -> Option<Assist>, before: &str, after: &str) { 199fn check_assist(assist: fn(AssistCtx) -> Option<Assist>, before: &str, after: &str) {
177 crate::test_utils::check_action(before, after, |file, off| { 200 crate::test_utils::check_action(before, after, |file, off| {