mirror of
https://github.com/rust-lang/rust-analyzer
synced 2025-01-28 04:45:05 +00:00
Fix type "items" order.
This commit is contained in:
parent
c50157f330
commit
283ec13fc0
2 changed files with 36 additions and 24 deletions
|
@ -27,7 +27,7 @@ use hir_ty::{
|
||||||
display::{HirDisplayError, HirFormatter},
|
display::{HirDisplayError, HirFormatter},
|
||||||
expr::ExprValidator,
|
expr::ExprValidator,
|
||||||
method_resolution, ApplicationTy, Canonical, GenericPredicate, InEnvironment, OpaqueTyId,
|
method_resolution, ApplicationTy, Canonical, GenericPredicate, InEnvironment, OpaqueTyId,
|
||||||
Substs, TraitEnvironment, Ty, TyDefId, TypeCtor, TypeWalk,
|
Substs, TraitEnvironment, Ty, TyDefId, TypeCtor,
|
||||||
};
|
};
|
||||||
use ra_db::{CrateId, CrateName, Edition, FileId};
|
use ra_db::{CrateId, CrateName, Edition, FileId};
|
||||||
use ra_prof::profile;
|
use ra_prof::profile;
|
||||||
|
@ -1381,7 +1381,7 @@ impl Type {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns a flattened list of all the ADTs and Traits mentioned in the type
|
/// Returns a flattened list of all ADTs and Traits mentioned in the type
|
||||||
pub fn flattened_type_items(&self, db: &dyn HirDatabase) -> Vec<AdtOrTrait> {
|
pub fn flattened_type_items(&self, db: &dyn HirDatabase) -> Vec<AdtOrTrait> {
|
||||||
fn push_new_item(item: AdtOrTrait, acc: &mut Vec<AdtOrTrait>) {
|
fn push_new_item(item: AdtOrTrait, acc: &mut Vec<AdtOrTrait>) {
|
||||||
if !acc.contains(&item) {
|
if !acc.contains(&item) {
|
||||||
|
@ -1398,7 +1398,7 @@ impl Type {
|
||||||
match p {
|
match p {
|
||||||
GenericPredicate::Implemented(trait_ref) => {
|
GenericPredicate::Implemented(trait_ref) => {
|
||||||
push_new_item(Trait::from(trait_ref.trait_).into(), acc);
|
push_new_item(Trait::from(trait_ref.trait_).into(), acc);
|
||||||
walk_types(db, &trait_ref.substs, acc);
|
walk_substs(db, &trait_ref.substs, acc);
|
||||||
}
|
}
|
||||||
GenericPredicate::Projection(_) => {}
|
GenericPredicate::Projection(_) => {}
|
||||||
GenericPredicate::Error => (),
|
GenericPredicate::Error => (),
|
||||||
|
@ -1406,8 +1406,11 @@ impl Type {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn walk_types<T: TypeWalk>(db: &dyn HirDatabase, tw: &T, acc: &mut Vec<AdtOrTrait>) {
|
// TypeWalk::walk does not preserve items order!
|
||||||
tw.walk(&mut |ty| walk_type(db, ty, acc));
|
fn walk_substs(db: &dyn HirDatabase, substs: &Substs, acc: &mut Vec<AdtOrTrait>) {
|
||||||
|
for ty in substs.iter() {
|
||||||
|
walk_type(db, ty, acc);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn walk_type(db: &dyn HirDatabase, ty: &Ty, acc: &mut Vec<AdtOrTrait>) {
|
fn walk_type(db: &dyn HirDatabase, ty: &Ty, acc: &mut Vec<AdtOrTrait>) {
|
||||||
|
@ -1415,10 +1418,18 @@ impl Type {
|
||||||
Ty::Apply(ApplicationTy { ctor, parameters, .. }) => {
|
Ty::Apply(ApplicationTy { ctor, parameters, .. }) => {
|
||||||
match ctor {
|
match ctor {
|
||||||
TypeCtor::Adt(adt_id) => push_new_item(Adt::from(*adt_id).into(), acc),
|
TypeCtor::Adt(adt_id) => push_new_item(Adt::from(*adt_id).into(), acc),
|
||||||
|
TypeCtor::AssociatedType(type_alias_id) => {
|
||||||
|
let trait_id = match type_alias_id.lookup(db.upcast()).container {
|
||||||
|
AssocContainerId::TraitId(it) => it,
|
||||||
|
_ => panic!("not an associated type"),
|
||||||
|
};
|
||||||
|
|
||||||
|
push_new_item(Trait::from(trait_id).into(), acc);
|
||||||
|
}
|
||||||
_ => (),
|
_ => (),
|
||||||
}
|
}
|
||||||
// adt params, tuples, etc...
|
// adt params, tuples, etc...
|
||||||
walk_types(db, parameters, acc);
|
walk_substs(db, parameters, acc);
|
||||||
}
|
}
|
||||||
Ty::Dyn(predicates) => {
|
Ty::Dyn(predicates) => {
|
||||||
push_bounds(db, predicates, acc);
|
push_bounds(db, predicates, acc);
|
||||||
|
@ -1451,7 +1462,7 @@ impl Type {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
push_bounds(db, &bounds.value, acc);
|
push_bounds(db, &bounds.value, acc);
|
||||||
walk_types(db, &opaque_ty.parameters, acc);
|
walk_substs(db, &opaque_ty.parameters, acc);
|
||||||
}
|
}
|
||||||
_ => (),
|
_ => (),
|
||||||
}
|
}
|
||||||
|
|
|
@ -234,9 +234,10 @@ fn runnable_action(
|
||||||
fn goto_type_action(db: &RootDatabase, def: Definition) -> Option<HoverAction> {
|
fn goto_type_action(db: &RootDatabase, def: Definition) -> Option<HoverAction> {
|
||||||
match def {
|
match def {
|
||||||
Definition::Local(it) => {
|
Definition::Local(it) => {
|
||||||
let ty = it.ty(db);
|
let targets = it
|
||||||
let v = ty.flattened_type_items(db);
|
.ty(db)
|
||||||
let targets = v.into_iter()
|
.flattened_type_items(db)
|
||||||
|
.into_iter()
|
||||||
.map(|it| HoverGotoTypeData {
|
.map(|it| HoverGotoTypeData {
|
||||||
mod_path: adt_or_trait_mod_path(db, &it),
|
mod_path: adt_or_trait_mod_path(db, &it),
|
||||||
nav: it.to_nav(db),
|
nav: it.to_nav(db),
|
||||||
|
@ -1980,7 +1981,7 @@ fn func(foo: i32) { if true { <|>foo; }; }
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_hover_arg_goto_type_action() {
|
fn test_hover_goto_type_action_links_order() {
|
||||||
let (_, actions) = check_hover_result(
|
let (_, actions) = check_hover_result(
|
||||||
"
|
"
|
||||||
//- /lib.rs
|
//- /lib.rs
|
||||||
|
@ -1988,10 +1989,10 @@ fn func(foo: i32) { if true { <|>foo; }; }
|
||||||
trait DynTrait<T> {}
|
trait DynTrait<T> {}
|
||||||
struct B<T> {}
|
struct B<T> {}
|
||||||
struct S {}
|
struct S {}
|
||||||
|
|
||||||
fn foo(a<|>rg: &impl ImplTrait<B<dyn DynTrait<S>>>) {}
|
fn foo(a<|>rg: &impl ImplTrait<B<dyn DynTrait<B<S>>>>) {}
|
||||||
",
|
",
|
||||||
&["&impl ImplTrait<B<dyn DynTrait<S>>>"],
|
&["&impl ImplTrait<B<dyn DynTrait<B<S>>>>"],
|
||||||
);
|
);
|
||||||
assert_debug_snapshot!(actions,
|
assert_debug_snapshot!(actions,
|
||||||
@r###"
|
@r###"
|
||||||
|
@ -2018,20 +2019,20 @@ fn func(foo: i32) { if true { <|>foo; }; }
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
HoverGotoTypeData {
|
HoverGotoTypeData {
|
||||||
mod_path: "S",
|
mod_path: "B",
|
||||||
nav: NavigationTarget {
|
nav: NavigationTarget {
|
||||||
file_id: FileId(
|
file_id: FileId(
|
||||||
1,
|
1,
|
||||||
),
|
),
|
||||||
full_range: 58..69,
|
full_range: 43..57,
|
||||||
name: "S",
|
name: "B",
|
||||||
kind: STRUCT_DEF,
|
kind: STRUCT_DEF,
|
||||||
focus_range: Some(
|
focus_range: Some(
|
||||||
65..66,
|
50..51,
|
||||||
),
|
),
|
||||||
container_name: None,
|
container_name: None,
|
||||||
description: Some(
|
description: Some(
|
||||||
"struct S",
|
"struct B",
|
||||||
),
|
),
|
||||||
docs: None,
|
docs: None,
|
||||||
},
|
},
|
||||||
|
@ -2056,20 +2057,20 @@ fn func(foo: i32) { if true { <|>foo; }; }
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
HoverGotoTypeData {
|
HoverGotoTypeData {
|
||||||
mod_path: "B",
|
mod_path: "S",
|
||||||
nav: NavigationTarget {
|
nav: NavigationTarget {
|
||||||
file_id: FileId(
|
file_id: FileId(
|
||||||
1,
|
1,
|
||||||
),
|
),
|
||||||
full_range: 43..57,
|
full_range: 58..69,
|
||||||
name: "B",
|
name: "S",
|
||||||
kind: STRUCT_DEF,
|
kind: STRUCT_DEF,
|
||||||
focus_range: Some(
|
focus_range: Some(
|
||||||
50..51,
|
65..66,
|
||||||
),
|
),
|
||||||
container_name: None,
|
container_name: None,
|
||||||
description: Some(
|
description: Some(
|
||||||
"struct B",
|
"struct S",
|
||||||
),
|
),
|
||||||
docs: None,
|
docs: None,
|
||||||
},
|
},
|
||||||
|
|
Loading…
Reference in a new issue