Simplify
This commit is contained in:
parent
06b0cbf607
commit
3956a5b757
@ -1,4 +1,6 @@
|
||||
//! Completes keywords.
|
||||
//! Completes keywords, except:
|
||||
//! - `self`, `super` and `crate`, as these are considered part of path completions.
|
||||
//! - `await`, as this is a postfix completion we handle this in the postfix completions.
|
||||
|
||||
use syntax::{SyntaxKind, T};
|
||||
|
||||
@ -25,18 +27,6 @@ pub(crate) fn complete_expr_keyword(acc: &mut Completions, ctx: &CompletionConte
|
||||
return;
|
||||
}
|
||||
|
||||
// Suggest .await syntax for types that implement Future trait
|
||||
if let Some(receiver) = ctx.dot_receiver() {
|
||||
if let Some(ty) = ctx.sema.type_of_expr(receiver) {
|
||||
if ty.impls_future(ctx.db) {
|
||||
let mut item =
|
||||
CompletionItem::new(CompletionKind::Keyword, ctx.source_range(), "await");
|
||||
item.kind(CompletionItemKind::Keyword).detail("expr.await");
|
||||
item.add_to(acc);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
let mut add_keyword = |kw, snippet| add_keyword(ctx, acc, kw, snippet);
|
||||
|
||||
let expects_assoc_item = ctx.expects_assoc_item();
|
||||
|
@ -42,6 +42,13 @@ pub(crate) fn complete_postfix(acc: &mut Completions, ctx: &CompletionContext) {
|
||||
None => return,
|
||||
};
|
||||
|
||||
// Suggest .await syntax for types that implement Future trait
|
||||
if receiver_ty.impls_future(ctx.db) {
|
||||
let mut item = CompletionItem::new(CompletionKind::Keyword, ctx.source_range(), "await");
|
||||
item.kind(CompletionItemKind::Keyword).detail("expr.await");
|
||||
item.add_to(acc);
|
||||
}
|
||||
|
||||
let cap = match ctx.config.snippet_cap {
|
||||
Some(it) => it,
|
||||
None => return,
|
||||
|
@ -6,10 +6,12 @@
|
||||
use rustc_hash::FxHashSet;
|
||||
use syntax::{ast, AstNode};
|
||||
|
||||
use crate::{context::PathCompletionContext, CompletionContext, Completions};
|
||||
use crate::{
|
||||
context::PathCompletionContext, patterns::ImmediateLocation, CompletionContext, Completions,
|
||||
};
|
||||
|
||||
pub(crate) fn complete_qualified_path(acc: &mut Completions, ctx: &CompletionContext) {
|
||||
if ctx.is_path_disallowed() {
|
||||
if ctx.is_path_disallowed() || ctx.has_impl_or_trait_prev_sibling() {
|
||||
return;
|
||||
}
|
||||
let (path, use_tree_parent) = match &ctx.path_context {
|
||||
@ -26,10 +28,11 @@ pub(crate) fn complete_qualified_path(acc: &mut Completions, ctx: &CompletionCon
|
||||
|
||||
let context_module = ctx.scope.module();
|
||||
|
||||
if ctx.expects_item() || ctx.expects_assoc_item() {
|
||||
if let Some(ImmediateLocation::ItemList | ImmediateLocation::Trait | ImmediateLocation::Impl) =
|
||||
ctx.completion_location
|
||||
{
|
||||
if let hir::PathResolution::Def(hir::ModuleDef::Module(module)) = resolution {
|
||||
let module_scope = module.scope(ctx.db, context_module);
|
||||
for (name, def) in module_scope {
|
||||
for (name, def) in module.scope(ctx.db, context_module) {
|
||||
if let hir::ScopeDef::MacroDef(macro_def) = def {
|
||||
if macro_def.is_fn_like() {
|
||||
acc.add_macro(ctx, Some(name.clone()), macro_def);
|
||||
|
@ -12,7 +12,7 @@ pub(crate) fn complete_unqualified_path(acc: &mut Completions, ctx: &CompletionC
|
||||
|
||||
if ctx.in_use_tree() {
|
||||
// only show modules in a fresh UseTree
|
||||
cov_mark::hit!(only_completes_modules_in_import);
|
||||
cov_mark::hit!(unqualified_path_only_modules_in_import);
|
||||
ctx.scope.process_all_names(&mut |name, res| {
|
||||
if let ScopeDef::ModuleDef(hir::ModuleDef::Module(_)) = res {
|
||||
acc.add_resolution(ctx, name, &res);
|
||||
@ -24,37 +24,39 @@ pub(crate) fn complete_unqualified_path(acc: &mut Completions, ctx: &CompletionC
|
||||
return;
|
||||
}
|
||||
std::array::IntoIter::new(["self", "super", "crate"]).for_each(|kw| acc.add_keyword(ctx, kw));
|
||||
if let Some(ImmediateLocation::Visibility(_)) = ctx.completion_location {
|
||||
return;
|
||||
}
|
||||
|
||||
if ctx.expects_item() || ctx.expects_assoc_item() {
|
||||
// only show macros in {Assoc}ItemList
|
||||
ctx.scope.process_all_names(&mut |name, res| {
|
||||
if let hir::ScopeDef::MacroDef(mac) = res {
|
||||
if mac.is_fn_like() {
|
||||
acc.add_macro(ctx, Some(name.clone()), mac);
|
||||
match &ctx.completion_location {
|
||||
Some(ImmediateLocation::Visibility(_)) => return,
|
||||
Some(ImmediateLocation::ItemList | ImmediateLocation::Trait | ImmediateLocation::Impl) => {
|
||||
// only show macros in {Assoc}ItemList
|
||||
ctx.scope.process_all_names(&mut |name, res| {
|
||||
if let hir::ScopeDef::MacroDef(mac) = res {
|
||||
if mac.is_fn_like() {
|
||||
acc.add_macro(ctx, Some(name.clone()), mac);
|
||||
}
|
||||
}
|
||||
}
|
||||
if let hir::ScopeDef::ModuleDef(hir::ModuleDef::Module(_)) = res {
|
||||
acc.add_resolution(ctx, name, &res);
|
||||
}
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
if matches!(&ctx.completion_location, Some(ImmediateLocation::TypeBound)) {
|
||||
ctx.scope.process_all_names(&mut |name, res| {
|
||||
let add_resolution = match res {
|
||||
ScopeDef::MacroDef(mac) => mac.is_fn_like(),
|
||||
ScopeDef::ModuleDef(hir::ModuleDef::Trait(_) | hir::ModuleDef::Module(_)) => true,
|
||||
_ => false,
|
||||
};
|
||||
if add_resolution {
|
||||
acc.add_resolution(ctx, name, &res);
|
||||
}
|
||||
});
|
||||
return;
|
||||
if let hir::ScopeDef::ModuleDef(hir::ModuleDef::Module(_)) = res {
|
||||
acc.add_resolution(ctx, name, &res);
|
||||
}
|
||||
});
|
||||
return;
|
||||
}
|
||||
Some(ImmediateLocation::TypeBound) => {
|
||||
ctx.scope.process_all_names(&mut |name, res| {
|
||||
let add_resolution = match res {
|
||||
ScopeDef::MacroDef(mac) => mac.is_fn_like(),
|
||||
ScopeDef::ModuleDef(hir::ModuleDef::Trait(_) | hir::ModuleDef::Module(_)) => {
|
||||
true
|
||||
}
|
||||
_ => false,
|
||||
};
|
||||
if add_resolution {
|
||||
acc.add_resolution(ctx, name, &res);
|
||||
}
|
||||
});
|
||||
return;
|
||||
}
|
||||
_ => (),
|
||||
}
|
||||
|
||||
if !ctx.expects_type() {
|
||||
|
@ -1,4 +1,8 @@
|
||||
//! Patterns telling us certain facts about current syntax element, they are used in completion context
|
||||
//!
|
||||
//! Most logic in this module first expands the token below the cursor to a maximum node that acts similar to the token itself.
|
||||
//! This means we for example expand a NameRef token to its outermost Path node, as semantically these act in the same location
|
||||
//! and the completions usually query for path specific things on the Path context instead. This simplifies some location handling.
|
||||
|
||||
use hir::Semantics;
|
||||
use ide_db::RootDatabase;
|
||||
|
@ -201,7 +201,7 @@ pub(crate) fn check_pattern_is_not_applicable(code: &str, check: fn(SyntaxElemen
|
||||
|
||||
pub(crate) fn get_all_items(config: CompletionConfig, code: &str) -> Vec<CompletionItem> {
|
||||
let (db, position) = position(code);
|
||||
crate::completions(&db, &config, position).unwrap().into()
|
||||
crate::completions(&db, &config, position).map_or_else(Vec::default, Into::into)
|
||||
}
|
||||
|
||||
fn check_no_completion(ra_fixture: &str) {
|
||||
|
@ -68,7 +68,7 @@ fn after_trait_name_in_trait_def() {
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn after_trait_or_target_name_in_impl() {
|
||||
fn after_target_name_in_impl() {
|
||||
check(
|
||||
r"impl Trait $0",
|
||||
expect![[r#"
|
||||
@ -76,6 +76,8 @@ fn after_trait_or_target_name_in_impl() {
|
||||
kw for
|
||||
"#]],
|
||||
);
|
||||
// FIXME: This should emit `kw where`
|
||||
check(r"impl Trait for Type $0", expect![[r#""#]]);
|
||||
}
|
||||
|
||||
#[test]
|
||||
|
@ -10,7 +10,7 @@ fn check(ra_fixture: &str, expect: Expect) {
|
||||
|
||||
#[test]
|
||||
fn use_tree_start() {
|
||||
cov_mark::check!(only_completes_modules_in_import);
|
||||
cov_mark::check!(unqualified_path_only_modules_in_import);
|
||||
check(
|
||||
r#"
|
||||
//- /lib.rs crate:main deps:other_crate
|
||||
|
@ -23,3 +23,35 @@ fn empty_pub() {
|
||||
"#]],
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn after_in_kw() {
|
||||
check(
|
||||
r#"
|
||||
pub(in $0)
|
||||
"#,
|
||||
expect![[r#"
|
||||
kw self
|
||||
kw super
|
||||
kw crate
|
||||
"#]],
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn qualified() {
|
||||
// FIXME: only show parent modules
|
||||
check(
|
||||
r#"
|
||||
mod foo {
|
||||
pub(in crate::$0)
|
||||
}
|
||||
|
||||
mod bar {}
|
||||
"#,
|
||||
expect![[r#"
|
||||
md bar
|
||||
md foo
|
||||
"#]],
|
||||
);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user