editor: Fix function completion expansion in string contexts and call expressions (#30351)

Closes #27582

Now, when accepting function completion, it doesn't expand with
parentheses and arguments in the following cases:
1. If it's in a string (like `type Foo = MyClass["sayHello"]` instead of
`type Foo = MyClass["sayHello(name)"]`)
2. If it's in a call expression (like `useRef<HTMLDivElement>(null)`
over `useRef(initialValue)<HTMLDivElement>(null)`)

This is a follow-up to https://github.com/zed-industries/zed/pull/30312,
more like cleaner version of it.

Release Notes:

- Fixed an issue where accepting a method as an object string in
JavaScript would incorrectly expand. E.g. `MyClass["sayHello(name)"]`
instead of `MyClass["sayHello"]`.
This commit is contained in:
Smit Barmase 2025-05-09 02:22:52 -07:00 committed by GitHub
parent 851ab13f94
commit b88ba44b32
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 39 additions and 21 deletions

View file

@ -5051,27 +5051,19 @@ impl Editor {
let snippet;
let new_text;
if completion.is_snippet() {
// lsp returns function definition with placeholders in "new_text"
// when configured from language server, even when renaming a function
//
// in such cases, we use the label instead
// https://github.com/zed-industries/zed/issues/29982
let snippet_source = completion
.label()
.filter(|label| {
completion.kind() == Some(CompletionItemKind::FUNCTION)
&& label != &completion.new_text
})
.and_then(|label| {
let cursor_offset = newest_anchor.head().to_offset(&snapshot);
let next_char_is_not_whitespace = snapshot
.chars_at(cursor_offset)
.next()
.map_or(true, |ch| !ch.is_whitespace());
next_char_is_not_whitespace.then_some(label)
})
.unwrap_or(completion.new_text.clone());
let mut snippet_source = completion.new_text.clone();
if let Some(scope) = snapshot.language_scope_at(newest_anchor.head()) {
if scope.prefers_label_for_snippet_in_completion() {
if let Some(label) = completion.label() {
if matches!(
completion.kind(),
Some(CompletionItemKind::FUNCTION) | Some(CompletionItemKind::METHOD)
) {
snippet_source = label;
}
}
}
}
snippet = Some(Snippet::parse(&snippet_source).log_err()?);
new_text = snippet.as_ref().unwrap().text.clone();
} else {