Unnamed repository; edit this file 'description' to name the repository.
Diffstat (limited to 'crates/ide-completion/src/render.rs')
-rw-r--r--crates/ide-completion/src/render.rs97
1 files changed, 51 insertions, 46 deletions
diff --git a/crates/ide-completion/src/render.rs b/crates/ide-completion/src/render.rs
index c6091645ca..9c339a13e7 100644
--- a/crates/ide-completion/src/render.rs
+++ b/crates/ide-completion/src/render.rs
@@ -17,7 +17,7 @@ use ide_db::{
use syntax::{SmolStr, SyntaxKind, TextRange};
use crate::{
- context::{IdentContext, NameRefContext, NameRefKind, PathCompletionCtx, PathKind},
+ context::{PathCompletionCtx, PathKind},
item::{Builder, CompletionRelevanceTypeMatch},
render::{function::render_fn, literal::render_variant_lit, macro_::render_macro},
CompletionContext, CompletionItem, CompletionItemKind, CompletionRelevance,
@@ -74,16 +74,6 @@ impl<'a> RenderContext<'a> {
.map_or(false, |it| it.kind() == SyntaxKind::MACRO_CALL)
}
- pub(crate) fn path_is_call(&self) -> bool {
- matches!(
- self.completion.ident_ctx,
- IdentContext::NameRef(NameRefContext {
- kind: NameRefKind::Path(PathCompletionCtx { has_call_parens: true, .. }),
- ..
- })
- )
- }
-
fn is_deprecated(&self, def: impl HasAttrs) -> bool {
let attrs = def.attrs(self.db());
attrs.by_key("deprecated").exists()
@@ -163,12 +153,13 @@ pub(crate) fn render_tuple_field(
item.build()
}
-pub(crate) fn render_resolution(
+pub(crate) fn render_path_resolution(
ctx: RenderContext<'_>,
+ path_ctx: &PathCompletionCtx,
local_name: hir::Name,
resolution: ScopeDef,
) -> Builder {
- render_resolution_(ctx, local_name, None, resolution)
+ render_resolution_(ctx, path_ctx, local_name, None, resolution)
}
pub(crate) fn render_resolution_simple(
@@ -181,6 +172,7 @@ pub(crate) fn render_resolution_simple(
pub(crate) fn render_resolution_with_import(
ctx: RenderContext<'_>,
+ path_ctx: &PathCompletionCtx,
import_edit: LocatedImport,
) -> Option<Builder> {
let resolution = ScopeDef::from(import_edit.original_item);
@@ -190,7 +182,7 @@ pub(crate) fn render_resolution_with_import(
ScopeDef::ModuleDef(hir::ModuleDef::TypeAlias(t)) => t.name(ctx.completion.db),
_ => item_name(ctx.db(), import_edit.original_item)?,
};
- Some(render_resolution_(ctx, local_name, Some(import_edit), resolution))
+ Some(render_resolution_(ctx, path_ctx, local_name, Some(import_edit), resolution))
}
pub(crate) fn render_type_inference(ty_string: String, ctx: &CompletionContext) -> CompletionItem {
@@ -202,6 +194,7 @@ pub(crate) fn render_type_inference(ty_string: String, ctx: &CompletionContext)
fn render_resolution_(
ctx: RenderContext<'_>,
+ path_ctx: &PathCompletionCtx,
local_name: hir::Name,
import_to_add: Option<LocatedImport>,
resolution: ScopeDef,
@@ -212,21 +205,61 @@ fn render_resolution_(
match resolution {
ScopeDef::ModuleDef(Macro(mac)) => {
let ctx = ctx.import_to_add(import_to_add);
- return render_macro(ctx, local_name, mac);
+ return render_macro(ctx, path_ctx, local_name, mac);
}
ScopeDef::ModuleDef(Function(func)) => {
let ctx = ctx.import_to_add(import_to_add);
- return render_fn(ctx, Some(local_name), func);
+ return render_fn(ctx, path_ctx, Some(local_name), func);
}
ScopeDef::ModuleDef(Variant(var)) => {
let ctx = ctx.clone().import_to_add(import_to_add.clone());
- if let Some(item) = render_variant_lit(ctx, Some(local_name.clone()), var, None) {
+ if let Some(item) =
+ render_variant_lit(ctx, path_ctx, Some(local_name.clone()), var, None)
+ {
return item;
}
}
_ => (),
}
- render_resolution_simple_(ctx, local_name, import_to_add, resolution)
+ render_resolution_simple_type(ctx, path_ctx, local_name, import_to_add, resolution)
+}
+
+fn render_resolution_simple_type(
+ ctx: RenderContext<'_>,
+ path_ctx: &PathCompletionCtx,
+ local_name: hir::Name,
+ import_to_add: Option<LocatedImport>,
+ resolution: ScopeDef,
+) -> Builder {
+ let cap = ctx.snippet_cap();
+ let db = ctx.completion.db;
+ let config = ctx.completion.config;
+ let name = local_name.to_smol_str();
+ let mut item = render_resolution_simple_(ctx, local_name, import_to_add, resolution);
+ // Add `<>` for generic types
+ let type_path_no_ty_args = matches!(
+ path_ctx,
+ PathCompletionCtx { kind: PathKind::Type { .. }, has_type_args: false, .. }
+ ) && config.callable.is_some();
+ if type_path_no_ty_args {
+ if let Some(cap) = cap {
+ let has_non_default_type_params = match resolution {
+ ScopeDef::ModuleDef(hir::ModuleDef::Adt(it)) => it.has_non_default_type_params(db),
+ ScopeDef::ModuleDef(hir::ModuleDef::TypeAlias(it)) => {
+ it.has_non_default_type_params(db)
+ }
+ _ => false,
+ };
+ if has_non_default_type_params {
+ cov_mark::hit!(inserts_angle_brackets_for_generics);
+ item.lookup_by(name.clone())
+ .label(SmolStr::from_iter([&name, "<…>"]))
+ .trigger_call_info()
+ .insert_snippet(cap, format!("{}<$0>", name));
+ }
+ }
+ }
+ item
}
fn render_resolution_simple_(
@@ -289,34 +322,6 @@ fn render_resolution_simple_(
}
};
- // Add `<>` for generic types
- let type_path_no_ty_args = matches!(
- ctx.completion.ident_ctx,
- IdentContext::NameRef(NameRefContext {
- kind: NameRefKind::Path(PathCompletionCtx {
- kind: PathKind::Type { .. },
- has_type_args: false,
- ..
- }),
- ..
- })
- ) && ctx.completion.config.callable.is_some();
- if type_path_no_ty_args {
- if let Some(cap) = ctx.snippet_cap() {
- let has_non_default_type_params = match resolution {
- ScopeDef::ModuleDef(Adt(it)) => it.has_non_default_type_params(db),
- ScopeDef::ModuleDef(TypeAlias(it)) => it.has_non_default_type_params(db),
- _ => false,
- };
- if has_non_default_type_params {
- cov_mark::hit!(inserts_angle_brackets_for_generics);
- item.lookup_by(local_name.clone())
- .label(SmolStr::from_iter([&local_name, "<…>"]))
- .trigger_call_info()
- .insert_snippet(cap, format!("{}<$0>", local_name));
- }
- }
- }
item.set_documentation(scope_def_docs(db, resolution))
.set_deprecated(scope_def_is_deprecated(&ctx, resolution));