diff --git a/crates/ra_ide/src/extend_selection.rs b/crates/ra_ide/src/extend_selection.rs index 4b7bfc0b11..c096ca6ae4 100644 --- a/crates/ra_ide/src/extend_selection.rs +++ b/crates/ra_ide/src/extend_selection.rs @@ -34,6 +34,7 @@ fn try_extend_selection(root: &SyntaxNode, range: TextRange) -> Option Option { TYPE_BOUND => T![+], _ => T![,], }; - if let Some(delimiter_node) = nearby_delimiter(delimiter, node, Direction::Prev) { - return Some(TextRange::from_to( - delimiter_node.text_range().start(), - node.text_range().end(), - )); - } + if let Some(delimiter_node) = nearby_delimiter(delimiter, node, Direction::Next) { // Include any following whitespace when delimiter is after list item. let final_node = delimiter_node @@ -190,6 +186,12 @@ fn extend_list_item(node: &SyntaxNode) -> Option { return Some(TextRange::from_to(node.text_range().start(), final_node.text_range().end())); } + if let Some(delimiter_node) = nearby_delimiter(delimiter, node, Direction::Prev) { + return Some(TextRange::from_to( + delimiter_node.text_range().start(), + node.text_range().end(), + )); + } None } @@ -250,14 +252,14 @@ mod tests { fn test_extend_selection_list() { do_check(r#"fn foo(<|>x: i32) {}"#, &["x", "x: i32"]); do_check(r#"fn foo(<|>x: i32, y: i32) {}"#, &["x", "x: i32", "x: i32, "]); - do_check(r#"fn foo(<|>x: i32,y: i32) {}"#, &["x", "x: i32", "x: i32,"]); + do_check(r#"fn foo(<|>x: i32,y: i32) {}"#, &["x", "x: i32", "x: i32,", "(x: i32,y: i32)"]); do_check(r#"fn foo(x: i32, <|>y: i32) {}"#, &["y", "y: i32", ", y: i32"]); - do_check(r#"fn foo(x: i32, <|>y: i32, ) {}"#, &["y", "y: i32", ", y: i32"]); + do_check(r#"fn foo(x: i32, <|>y: i32, ) {}"#, &["y", "y: i32", "y: i32, "]); do_check(r#"fn foo(x: i32,<|>y: i32) {}"#, &["y", "y: i32", ",y: i32"]); do_check(r#"const FOO: [usize; 2] = [ 22<|> , 33];"#, &["22", "22 , "]); do_check(r#"const FOO: [usize; 2] = [ 22 , 33<|>];"#, &["33", ", 33"]); - do_check(r#"const FOO: [usize; 2] = [ 22 , 33<|> ,];"#, &["33", ", 33"]); + do_check(r#"const FOO: [usize; 2] = [ 22 , 33<|> ,];"#, &["33", "33 ,", "[ 22 , 33 ,]"]); do_check(r#"fn main() { (1, 2<|>) }"#, &["2", ", 2", "(1, 2)"]); @@ -276,7 +278,7 @@ const FOO: [usize; 2] = [ 22 , 33<|>, ]"#, - &["33", ", 33"], + &["33", "33,"], ); } @@ -424,7 +426,7 @@ fn foo() do_check(r#"fn foo() where T: <|>Copy +Display"#, &["Copy", "Copy +"]); do_check(r#"fn foo() where T: <|>Copy+Display"#, &["Copy", "Copy+"]); do_check(r#"fn foo() where T: Copy + <|>Display"#, &["Display", "+ Display"]); - do_check(r#"fn foo() where T: Copy + <|>Display + Sync"#, &["Display", "+ Display"]); + do_check(r#"fn foo() where T: Copy + <|>Display + Sync"#, &["Display", "Display + "]); do_check(r#"fn foo() where T: Copy +<|>Display"#, &["Display", "+Display"]); } @@ -435,7 +437,7 @@ fn foo() do_check(r#"fn fooCopy +Display>() {}"#, &["Copy", "Copy +"]); do_check(r#"fn fooCopy+Display>() {}"#, &["Copy", "Copy+"]); do_check(r#"fn fooDisplay>() {}"#, &["Display", "+ Display"]); - do_check(r#"fn fooDisplay + Sync>() {}"#, &["Display", "+ Display"]); + do_check(r#"fn fooDisplay + Sync>() {}"#, &["Display", "Display + "]); do_check(r#"fn fooDisplay>() {}"#, &["Display", "+Display"]); do_check( r#"fn foo + Display, U: Copy>() {}"#, @@ -449,4 +451,56 @@ fn foo() ], ); } + + #[test] + fn test_extend_selection_on_tuple_in_type() { + do_check( + r#"fn main() { let _: (krate, <|>_crate_def_map, module_id) = (); }"#, + &["_crate_def_map", "_crate_def_map, ", "(krate, _crate_def_map, module_id)"], + ); + // white space variations + do_check( + r#"fn main() { let _: (krate,<|>_crate_def_map,module_id) = (); }"#, + &["_crate_def_map", "_crate_def_map,", "(krate,_crate_def_map,module_id)"], + ); + do_check( + r#" +fn main() { let _: ( + krate, + _crate<|>_def_map, + module_id +) = (); }"#, + &[ + "_crate_def_map", + "_crate_def_map,", + "(\n krate,\n _crate_def_map,\n module_id\n)", + ], + ); + } + + #[test] + fn test_extend_selection_on_tuple_in_rvalue() { + do_check( + r#"fn main() { let var = (krate, _crate_def_map<|>, module_id); }"#, + &["_crate_def_map", "_crate_def_map, ", "(krate, _crate_def_map, module_id)"], + ); + // white space variations + do_check( + r#"fn main() { let var = (krate,_crate<|>_def_map,module_id); }"#, + &["_crate_def_map", "_crate_def_map,", "(krate,_crate_def_map,module_id)"], + ); + do_check( + r#" +fn main() { let var = ( + krate, + _crate_def_map<|>, + module_id +); }"#, + &[ + "_crate_def_map", + "_crate_def_map,", + "(\n krate,\n _crate_def_map,\n module_id\n)", + ], + ); + } }