Skip to content

Commit f3cbd0e

Browse files
Merge pull request #20985 from Natural-selection1/rename
support rename after adding loop label
2 parents 73f565e + ef05935 commit f3cbd0e

File tree

2 files changed

+69
-36
lines changed

2 files changed

+69
-36
lines changed

crates/ide-assists/src/handlers/add_label_to_loop.rs

Lines changed: 66 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,14 @@
1-
use ide_db::syntax_helpers::node_ext::for_each_break_and_continue_expr;
1+
use ide_db::{
2+
source_change::SourceChangeBuilder, syntax_helpers::node_ext::for_each_break_and_continue_expr,
3+
};
24
use syntax::{
3-
T,
4-
ast::{self, AstNode, HasLoopBody},
5+
SyntaxToken, T,
6+
ast::{
7+
self, AstNode, HasLoopBody,
8+
make::{self, tokens},
9+
syntax_factory::SyntaxFactory,
10+
},
11+
syntax_editor::{Position, SyntaxEditor},
512
};
613

714
use crate::{AssistContext, AssistId, Assists};
@@ -21,9 +28,9 @@ use crate::{AssistContext, AssistId, Assists};
2128
// ->
2229
// ```
2330
// fn main() {
24-
// 'l: loop {
25-
// break 'l;
26-
// continue 'l;
31+
// ${1:'l}: loop {
32+
// break ${2:'l};
33+
// continue ${0:'l};
2734
// }
2835
// }
2936
// ```
@@ -39,30 +46,56 @@ pub(crate) fn add_label_to_loop(acc: &mut Assists, ctx: &AssistContext<'_>) -> O
3946
"Add Label",
4047
loop_expr.syntax().text_range(),
4148
|builder| {
42-
builder.insert(loop_kw.text_range().start(), "'l: ");
49+
let make = SyntaxFactory::with_mappings();
50+
let mut editor = builder.make_editor(loop_expr.syntax());
51+
52+
let label = make.lifetime("'l");
53+
let elements = vec![
54+
label.syntax().clone().into(),
55+
make::token(T![:]).into(),
56+
tokens::single_space().into(),
57+
];
58+
editor.insert_all(Position::before(&loop_kw), elements);
59+
60+
if let Some(cap) = ctx.config.snippet_cap {
61+
editor.add_annotation(label.syntax(), builder.make_placeholder_snippet(cap));
62+
}
4363

4464
let loop_body = loop_expr.loop_body().and_then(|it| it.stmt_list());
45-
for_each_break_and_continue_expr(
46-
loop_expr.label(),
47-
loop_body,
48-
&mut |expr| match expr {
49-
ast::Expr::BreakExpr(break_expr) => {
50-
if let Some(break_token) = break_expr.break_token() {
51-
builder.insert(break_token.text_range().end(), " 'l")
52-
}
53-
}
54-
ast::Expr::ContinueExpr(continue_expr) => {
55-
if let Some(continue_token) = continue_expr.continue_token() {
56-
builder.insert(continue_token.text_range().end(), " 'l")
57-
}
58-
}
59-
_ => {}
60-
},
61-
);
65+
for_each_break_and_continue_expr(loop_expr.label(), loop_body, &mut |expr| {
66+
let token = match expr {
67+
ast::Expr::BreakExpr(break_expr) => break_expr.break_token(),
68+
ast::Expr::ContinueExpr(continue_expr) => continue_expr.continue_token(),
69+
_ => return,
70+
};
71+
if let Some(token) = token {
72+
insert_label_after_token(&mut editor, &make, &token, ctx, builder);
73+
}
74+
});
75+
76+
editor.add_mappings(make.finish_with_mappings());
77+
builder.add_file_edits(ctx.vfs_file_id(), editor);
78+
builder.rename();
6279
},
6380
)
6481
}
6582

83+
fn insert_label_after_token(
84+
editor: &mut SyntaxEditor,
85+
make: &SyntaxFactory,
86+
token: &SyntaxToken,
87+
ctx: &AssistContext<'_>,
88+
builder: &mut SourceChangeBuilder,
89+
) {
90+
let label = make.lifetime("'l");
91+
let elements = vec![tokens::single_space().into(), label.syntax().clone().into()];
92+
editor.insert_all(Position::after(token), elements);
93+
94+
if let Some(cap) = ctx.config.snippet_cap {
95+
editor.add_annotation(label.syntax(), builder.make_placeholder_snippet(cap));
96+
}
97+
}
98+
6699
#[cfg(test)]
67100
mod tests {
68101
use crate::tests::{check_assist, check_assist_not_applicable};
@@ -82,9 +115,9 @@ fn main() {
82115
}"#,
83116
r#"
84117
fn main() {
85-
'l: loop {
86-
break 'l;
87-
continue 'l;
118+
${1:'l}: loop {
119+
break ${2:'l};
120+
continue ${0:'l};
88121
}
89122
}"#,
90123
);
@@ -107,9 +140,9 @@ fn main() {
107140
}"#,
108141
r#"
109142
fn main() {
110-
'l: loop {
111-
break 'l;
112-
continue 'l;
143+
${1:'l}: loop {
144+
break ${2:'l};
145+
continue ${0:'l};
113146
loop {
114147
break;
115148
continue;
@@ -139,9 +172,9 @@ fn main() {
139172
loop {
140173
break;
141174
continue;
142-
'l: loop {
143-
break 'l;
144-
continue 'l;
175+
${1:'l}: loop {
176+
break ${2:'l};
177+
continue ${0:'l};
145178
}
146179
}
147180
}"#,

crates/ide-assists/src/tests/generated.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -183,9 +183,9 @@ fn main() {
183183
"#####,
184184
r#####"
185185
fn main() {
186-
'l: loop {
187-
break 'l;
188-
continue 'l;
186+
${1:'l}: loop {
187+
break ${2:'l};
188+
continue ${0:'l};
189189
}
190190
}
191191
"#####,

0 commit comments

Comments
 (0)