-
Notifications
You must be signed in to change notification settings - Fork 1.6k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #18483 from tareknaser/syntax_factory_introduce_na…
…med_generic Migrate `introduce_named_generic` Assist to Use `SyntaxFactory`
- Loading branch information
Showing
4 changed files
with
123 additions
and
27 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
//! Structural editing for ast using `SyntaxEditor` | ||
use crate::{ | ||
ast::make, ast::AstNode, ast::Fn, ast::GenericParam, ast::HasGenericParams, ast::HasName, | ||
syntax_editor::Position, syntax_editor::SyntaxEditor, SyntaxKind, | ||
}; | ||
|
||
impl SyntaxEditor { | ||
/// Adds a new generic param to the function using `SyntaxEditor` | ||
pub fn add_generic_param(&mut self, function: &Fn, new_param: GenericParam) { | ||
match function.generic_param_list() { | ||
Some(generic_param_list) => match generic_param_list.generic_params().last() { | ||
Some(last_param) => { | ||
// There exists a generic param list and it's not empty | ||
let position = generic_param_list.r_angle_token().map_or_else( | ||
|| Position::last_child_of(function.syntax()), | ||
Position::before, | ||
); | ||
|
||
if last_param | ||
.syntax() | ||
.next_sibling_or_token() | ||
.map_or(false, |it| it.kind() == SyntaxKind::COMMA) | ||
{ | ||
self.insert( | ||
Position::after(last_param.syntax()), | ||
new_param.syntax().clone(), | ||
); | ||
self.insert( | ||
Position::after(last_param.syntax()), | ||
make::token(SyntaxKind::WHITESPACE), | ||
); | ||
self.insert( | ||
Position::after(last_param.syntax()), | ||
make::token(SyntaxKind::COMMA), | ||
); | ||
} else { | ||
let elements = vec![ | ||
make::token(SyntaxKind::COMMA).into(), | ||
make::token(SyntaxKind::WHITESPACE).into(), | ||
new_param.syntax().clone().into(), | ||
]; | ||
self.insert_all(position, elements); | ||
} | ||
} | ||
None => { | ||
// There exists a generic param list but it's empty | ||
let position = Position::after(generic_param_list.l_angle_token().unwrap()); | ||
self.insert(position, new_param.syntax()); | ||
} | ||
}, | ||
None => { | ||
// There was no generic param list | ||
let position = if let Some(name) = function.name() { | ||
Position::after(name.syntax) | ||
} else if let Some(fn_token) = function.fn_token() { | ||
Position::after(fn_token) | ||
} else if let Some(param_list) = function.param_list() { | ||
Position::before(param_list.syntax) | ||
} else { | ||
Position::last_child_of(function.syntax()) | ||
}; | ||
let elements = vec![ | ||
make::token(SyntaxKind::L_ANGLE).into(), | ||
new_param.syntax().clone().into(), | ||
make::token(SyntaxKind::R_ANGLE).into(), | ||
]; | ||
self.insert_all(position, elements); | ||
} | ||
} | ||
} | ||
} |