Unnamed repository; edit this file 'description' to name the repository.
-rw-r--r--crates/ide-completion/src/context.rs3
-rw-r--r--crates/ide-completion/src/context/analysis.rs3
-rw-r--r--crates/ide-completion/src/render.rs27
-rw-r--r--crates/ide-completion/src/render/function.rs16
-rw-r--r--crates/ide-completion/src/render/literal.rs8
5 files changed, 41 insertions, 16 deletions
diff --git a/crates/ide-completion/src/context.rs b/crates/ide-completion/src/context.rs
index 759742d347..a5e854b74d 100644
--- a/crates/ide-completion/src/context.rs
+++ b/crates/ide-completion/src/context.rs
@@ -64,8 +64,11 @@ pub(crate) struct PathCompletionCtx {
pub(super) qualified: Qualified,
/// The parent of the path we are completing.
pub(super) parent: Option<ast::Path>,
+ #[allow(dead_code)]
/// The path of which we are completing the segment
pub(super) path: ast::Path,
+ /// The path of which we are completing the segment in the original file
+ pub(crate) original_path: Option<ast::Path>,
pub(super) kind: PathKind,
/// Whether the path segment has type args or not.
pub(super) has_type_args: bool,
diff --git a/crates/ide-completion/src/context/analysis.rs b/crates/ide-completion/src/context/analysis.rs
index 22ec7cead4..01dd9a234f 100644
--- a/crates/ide-completion/src/context/analysis.rs
+++ b/crates/ide-completion/src/context/analysis.rs
@@ -588,12 +588,15 @@ impl<'a> CompletionContext<'a> {
};
let path = segment.parent_path();
+ let original_path = find_node_in_file_compensated(sema, original_file, &path);
+
let mut path_ctx = PathCompletionCtx {
has_call_parens: false,
has_macro_bang: false,
qualified: Qualified::No,
parent: None,
path: path.clone(),
+ original_path,
kind: PathKind::Item { kind: ItemListKind::SourceFile },
has_type_args: false,
use_tree_parent: false,
diff --git a/crates/ide-completion/src/render.rs b/crates/ide-completion/src/render.rs
index a2cf6d68e5..86302cb067 100644
--- a/crates/ide-completion/src/render.rs
+++ b/crates/ide-completion/src/render.rs
@@ -323,9 +323,7 @@ fn render_resolution_path(
..CompletionRelevance::default()
});
- if let Some(ref_match) = compute_ref_match(completion, &ty) {
- item.ref_match(ref_match, path_ctx.path.syntax().text_range().start());
- }
+ path_ref_match(completion, path_ctx, &ty, &mut item);
};
item
}
@@ -453,6 +451,29 @@ fn compute_ref_match(
None
}
+fn path_ref_match(
+ completion: &CompletionContext<'_>,
+ path_ctx: &PathCompletionCtx,
+ ty: &hir::Type,
+ item: &mut Builder,
+) {
+ if let Some(original_path) = &path_ctx.original_path {
+ // At least one char was typed by the user already, in that case look for the original path
+ if let Some(original_path) = completion.sema.original_ast_node(original_path.clone()) {
+ if let Some(ref_match) = compute_ref_match(completion, ty) {
+ item.ref_match(ref_match, original_path.syntax().text_range().start());
+ }
+ }
+ } else {
+ // completion requested on an empty identifier, there is no path here yet.
+ // FIXME: This might create inconsistent completions where we show a ref match in macro inputs
+ // as long as nothing was typed yet
+ if let Some(ref_match) = compute_ref_match(completion, ty) {
+ item.ref_match(ref_match, completion.position.offset);
+ }
+ }
+}
+
#[cfg(test)]
mod tests {
use std::cmp;
diff --git a/crates/ide-completion/src/render/function.rs b/crates/ide-completion/src/render/function.rs
index 9cf6469129..3761208460 100644
--- a/crates/ide-completion/src/render/function.rs
+++ b/crates/ide-completion/src/render/function.rs
@@ -79,18 +79,18 @@ fn render(
..ctx.completion_relevance()
});
- if let Some(ref_match) = compute_ref_match(completion, &ret_type) {
- match func_kind {
- FuncKind::Function(path_ctx) => {
- item.ref_match(ref_match, path_ctx.path.syntax().text_range().start());
- }
- FuncKind::Method(DotAccess { receiver: Some(receiver), .. }, _) => {
- if let Some(original_expr) = completion.sema.original_ast_node(receiver.clone()) {
+ match func_kind {
+ FuncKind::Function(path_ctx) => {
+ super::path_ref_match(completion, path_ctx, &ret_type, &mut item);
+ }
+ FuncKind::Method(DotAccess { receiver: Some(receiver), .. }, _) => {
+ if let Some(original_expr) = completion.sema.original_ast_node(receiver.clone()) {
+ if let Some(ref_match) = compute_ref_match(completion, &ret_type) {
item.ref_match(ref_match, original_expr.syntax().text_range().start());
}
}
- _ => (),
}
+ _ => (),
}
item.set_documentation(ctx.docs(func))
diff --git a/crates/ide-completion/src/render/literal.rs b/crates/ide-completion/src/render/literal.rs
index af9c88a7e0..0c791ac570 100644
--- a/crates/ide-completion/src/render/literal.rs
+++ b/crates/ide-completion/src/render/literal.rs
@@ -2,13 +2,12 @@
use hir::{db::HirDatabase, Documentation, HasAttrs, StructKind};
use ide_db::SymbolKind;
-use syntax::AstNode;
use crate::{
context::{CompletionContext, PathCompletionCtx, PathKind},
item::{Builder, CompletionItem},
render::{
- compute_ref_match, compute_type_match,
+ compute_type_match,
variant::{
format_literal_label, format_literal_lookup, render_record_lit, render_tuple_lit,
visible_fields, RenderedLiteral,
@@ -125,9 +124,8 @@ fn render(
type_match: compute_type_match(ctx.completion, &ty),
..ctx.completion_relevance()
});
- if let Some(ref_match) = compute_ref_match(completion, &ty) {
- item.ref_match(ref_match, path_ctx.path.syntax().text_range().start());
- }
+
+ super::path_ref_match(completion, path_ctx, &ty, &mut item);
if let Some(import_to_add) = ctx.import_to_add {
item.add_import(import_to_add);