Merge #635
635: switch to positional ids for enum variants r=matklad a=matklad Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
This commit is contained in:
commit
c4a351b736
@ -3,11 +3,14 @@
|
|||||||
|
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
|
||||||
use ra_syntax::ast::{self, NameOwner, StructFlavor};
|
use ra_syntax::{
|
||||||
|
TreeArc,
|
||||||
|
ast::{self, NameOwner, StructFlavor}
|
||||||
|
};
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
Name, AsName, Struct, Enum, EnumVariant, Crate,
|
Name, AsName, Struct, Enum, EnumVariant, Crate,
|
||||||
HirDatabase,
|
HirDatabase, HirFileId,
|
||||||
type_ref::TypeRef,
|
type_ref::TypeRef,
|
||||||
ids::LocationCtx,
|
ids::LocationCtx,
|
||||||
};
|
};
|
||||||
@ -55,6 +58,24 @@ impl StructData {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn variants(enum_def: &ast::EnumDef) -> impl Iterator<Item = &ast::EnumVariant> {
|
||||||
|
enum_def
|
||||||
|
.variant_list()
|
||||||
|
.into_iter()
|
||||||
|
.flat_map(|it| it.variants())
|
||||||
|
}
|
||||||
|
|
||||||
|
impl EnumVariant {
|
||||||
|
pub fn source_impl(&self, db: &impl HirDatabase) -> (HirFileId, TreeArc<ast::EnumVariant>) {
|
||||||
|
let (file_id, enum_def) = self.parent.source(db);
|
||||||
|
let var = variants(&*enum_def)
|
||||||
|
.nth(self.idx as usize)
|
||||||
|
.unwrap()
|
||||||
|
.to_owned();
|
||||||
|
(file_id, var)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||||
pub struct EnumData {
|
pub struct EnumData {
|
||||||
pub(crate) name: Option<Name>,
|
pub(crate) name: Option<Name>,
|
||||||
@ -68,22 +89,19 @@ impl EnumData {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn enum_data_query(db: &impl HirDatabase, e: Enum) -> Arc<EnumData> {
|
pub(crate) fn enum_data_query(db: &impl HirDatabase, e: Enum) -> Arc<EnumData> {
|
||||||
let (file_id, enum_def) = e.source(db);
|
let (_file_id, enum_def) = e.source(db);
|
||||||
let module = e.module(db);
|
let variants = variants(&*enum_def)
|
||||||
let ctx = LocationCtx::new(db, module, file_id);
|
.enumerate()
|
||||||
let variants = if let Some(vl) = enum_def.variant_list() {
|
.filter_map(|(idx, variant_def)| {
|
||||||
vl.variants()
|
let name = variant_def.name()?.as_name();
|
||||||
.filter_map(|variant_def| {
|
let var = EnumVariant {
|
||||||
let name = variant_def.name()?.as_name();
|
parent: e,
|
||||||
let var = EnumVariant {
|
idx: idx as u32,
|
||||||
id: ctx.to_def(variant_def),
|
};
|
||||||
};
|
Some((name, var))
|
||||||
Some((name, var))
|
})
|
||||||
})
|
.collect();
|
||||||
.collect()
|
|
||||||
} else {
|
|
||||||
Vec::new()
|
|
||||||
};
|
|
||||||
Arc::new(EnumData::new(&*enum_def, variants))
|
Arc::new(EnumData::new(&*enum_def, variants))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -15,7 +15,7 @@ use crate::{
|
|||||||
generics::GenericParams,
|
generics::GenericParams,
|
||||||
docs::{Documentation, Docs, docs_from_ast},
|
docs::{Documentation, Docs, docs_from_ast},
|
||||||
module_tree::ModuleId,
|
module_tree::ModuleId,
|
||||||
ids::{FunctionId, StructId, EnumId, EnumVariantId, AstItemDef, ConstId, StaticId, TraitId, TypeId},
|
ids::{FunctionId, StructId, EnumId, AstItemDef, ConstId, StaticId, TraitId, TypeId},
|
||||||
};
|
};
|
||||||
|
|
||||||
/// hir::Crate describes a single crate. It's the main interface with which
|
/// hir::Crate describes a single crate. It's the main interface with which
|
||||||
@ -269,18 +269,19 @@ impl Docs for Enum {
|
|||||||
|
|
||||||
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
|
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
|
||||||
pub struct EnumVariant {
|
pub struct EnumVariant {
|
||||||
pub(crate) id: EnumVariantId,
|
pub(crate) parent: Enum,
|
||||||
|
pub(crate) idx: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl EnumVariant {
|
impl EnumVariant {
|
||||||
pub fn source(&self, db: &impl HirDatabase) -> (HirFileId, TreeArc<ast::EnumVariant>) {
|
pub fn source(&self, db: &impl HirDatabase) -> (HirFileId, TreeArc<ast::EnumVariant>) {
|
||||||
self.id.source(db)
|
self.source_impl(db)
|
||||||
}
|
}
|
||||||
pub fn module(&self, db: &impl HirDatabase) -> Module {
|
pub fn module(&self, db: &impl HirDatabase) -> Module {
|
||||||
self.id.module(db)
|
self.parent.module(db)
|
||||||
}
|
}
|
||||||
pub fn parent_enum(&self, db: &impl HirDatabase) -> Enum {
|
pub fn parent_enum(&self, _db: &impl HirDatabase) -> Enum {
|
||||||
db.enum_variant_data(*self).parent_enum.clone()
|
self.parent
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn name(&self, db: &impl HirDatabase) -> Option<Name> {
|
pub fn name(&self, db: &impl HirDatabase) -> Option<Name> {
|
||||||
|
@ -18,7 +18,6 @@ pub struct HirInterner {
|
|||||||
fns: LocationIntener<ItemLoc<ast::FnDef>, FunctionId>,
|
fns: LocationIntener<ItemLoc<ast::FnDef>, FunctionId>,
|
||||||
structs: LocationIntener<ItemLoc<ast::StructDef>, StructId>,
|
structs: LocationIntener<ItemLoc<ast::StructDef>, StructId>,
|
||||||
enums: LocationIntener<ItemLoc<ast::EnumDef>, EnumId>,
|
enums: LocationIntener<ItemLoc<ast::EnumDef>, EnumId>,
|
||||||
enum_variants: LocationIntener<ItemLoc<ast::EnumVariant>, EnumVariantId>,
|
|
||||||
consts: LocationIntener<ItemLoc<ast::ConstDef>, ConstId>,
|
consts: LocationIntener<ItemLoc<ast::ConstDef>, ConstId>,
|
||||||
statics: LocationIntener<ItemLoc<ast::StaticDef>, StaticId>,
|
statics: LocationIntener<ItemLoc<ast::StaticDef>, StaticId>,
|
||||||
traits: LocationIntener<ItemLoc<ast::TraitDef>, TraitId>,
|
traits: LocationIntener<ItemLoc<ast::TraitDef>, TraitId>,
|
||||||
@ -31,7 +30,6 @@ impl HirInterner {
|
|||||||
+ self.fns.len()
|
+ self.fns.len()
|
||||||
+ self.structs.len()
|
+ self.structs.len()
|
||||||
+ self.enums.len()
|
+ self.enums.len()
|
||||||
+ self.enum_variants.len()
|
|
||||||
+ self.consts.len()
|
+ self.consts.len()
|
||||||
+ self.statics.len()
|
+ self.statics.len()
|
||||||
+ self.traits.len()
|
+ self.traits.len()
|
||||||
@ -261,15 +259,6 @@ impl AstItemDef<ast::EnumDef> for EnumId {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
|
|
||||||
pub struct EnumVariantId(RawId);
|
|
||||||
impl_arena_id!(EnumVariantId);
|
|
||||||
impl AstItemDef<ast::EnumVariant> for EnumVariantId {
|
|
||||||
fn interner(interner: &HirInterner) -> &LocationIntener<ItemLoc<ast::EnumVariant>, Self> {
|
|
||||||
&interner.enum_variants
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
|
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
|
||||||
pub struct ConstId(RawId);
|
pub struct ConstId(RawId);
|
||||||
impl_arena_id!(ConstId);
|
impl_arena_id!(ConstId);
|
||||||
@ -342,9 +331,7 @@ impl SourceFileItems {
|
|||||||
// change parent's id. This means that, say, adding a new function to a
|
// change parent's id. This means that, say, adding a new function to a
|
||||||
// trait does not chage ids of top-level items, which helps caching.
|
// trait does not chage ids of top-level items, which helps caching.
|
||||||
bfs(source_file.syntax(), |it| {
|
bfs(source_file.syntax(), |it| {
|
||||||
if let Some(enum_variant) = ast::EnumVariant::cast(it) {
|
if let Some(module_item) = ast::ModuleItem::cast(it) {
|
||||||
self.alloc(enum_variant.syntax().to_owned());
|
|
||||||
} else if let Some(module_item) = ast::ModuleItem::cast(it) {
|
|
||||||
self.alloc(module_item.syntax().to_owned());
|
self.alloc(module_item.syntax().to_owned());
|
||||||
} else if let Some(macro_call) = ast::MacroCall::cast(it) {
|
} else if let Some(macro_call) = ast::MacroCall::cast(it) {
|
||||||
self.alloc(macro_call.syntax().to_owned());
|
self.alloc(macro_call.syntax().to_owned());
|
||||||
|
Loading…
x
Reference in New Issue
Block a user