fix: add a separate setting for enum variants

This commit is contained in:
roife 2024-04-19 21:31:54 +08:00
parent 6bb85985d7
commit e0e28ec856
8 changed files with 183 additions and 52 deletions

View file

@ -188,7 +188,7 @@ impl HirDisplay for Struct {
StructKind::Record => {
let has_where_clause = write_where_clause(def_id, f)?;
if let Some(limit) = f.entity_limit {
display_fields_or_variants(&self.fields(f.db), has_where_clause, limit, f)?;
display_fields(&self.fields(f.db), has_where_clause, limit, f)?;
}
}
StructKind::Unit => _ = write_where_clause(def_id, f)?,
@ -208,7 +208,7 @@ impl HirDisplay for Enum {
let has_where_clause = write_where_clause(def_id, f)?;
if let Some(limit) = f.entity_limit {
display_fields_or_variants(&self.variants(f.db), has_where_clause, limit, f)?;
display_variants(&self.variants(f.db), has_where_clause, limit, f)?;
}
Ok(())
@ -225,35 +225,83 @@ impl HirDisplay for Union {
let has_where_clause = write_where_clause(def_id, f)?;
if let Some(limit) = f.entity_limit {
display_fields_or_variants(&self.fields(f.db), has_where_clause, limit, f)?;
display_fields(&self.fields(f.db), has_where_clause, limit, f)?;
}
Ok(())
}
}
fn display_fields_or_variants<T: HirDisplay>(
fields_or_variants: &[T],
fn display_fields(
fields: &[Field],
has_where_clause: bool,
limit: usize,
f: &mut HirFormatter<'_>,
) -> Result<(), HirDisplayError> {
let count = fields_or_variants.len().min(limit);
let count = fields.len().min(limit);
f.write_char(if !has_where_clause { ' ' } else { '\n' })?;
if count == 0 {
if fields_or_variants.is_empty() {
if fields.is_empty() {
f.write_str("{}")?;
} else {
f.write_str("{ /* … */ }")?;
}
} else {
f.write_str("{\n")?;
for field in &fields_or_variants[..count] {
for field in &fields[..count] {
f.write_str(" ")?;
field.hir_fmt(f)?;
f.write_str(",\n")?;
}
if fields_or_variants.len() > count {
if fields.len() > count {
f.write_str(" /* … */\n")?;
}
f.write_str("}")?;
}
Ok(())
}
fn display_variants(
variants: &[Variant],
has_where_clause: bool,
limit: usize,
f: &mut HirFormatter<'_>,
) -> Result<(), HirDisplayError> {
let count = variants.len().min(limit);
f.write_char(if !has_where_clause { ' ' } else { '\n' })?;
if count == 0 {
if variants.is_empty() {
f.write_str("{}")?;
} else {
f.write_str("{ /* … */ }")?;
}
} else {
f.write_str("{\n")?;
for variant in &variants[..count] {
f.write_str(" ")?;
write!(f, "{}", variant.name(f.db).display(f.db.upcast()))?;
match variant.kind(f.db) {
StructKind::Tuple => {
if variant.fields(f.db).is_empty() {
f.write_str("()")?;
} else {
f.write_str("( /* … */ )")?;
}
}
StructKind::Record => {
if variant.fields(f.db).is_empty() {
f.write_str(" {}")?;
} else {
f.write_str(" { /* … */ }")?;
}
}
StructKind::Unit => {}
}
f.write_str(",\n")?;
}
if variants.len() > count {
f.write_str(" /* … */\n")?;
}
f.write_str("}")?;

View file

@ -33,7 +33,8 @@ pub struct HoverConfig {
pub keywords: bool,
pub format: HoverDocFormat,
pub max_trait_assoc_items_count: Option<usize>,
pub max_adt_fields_or_variants_count: Option<usize>,
pub max_struct_or_union_fields_count: Option<usize>,
pub max_enum_variants_count: Option<usize>,
}
#[derive(Copy, Clone, Debug, PartialEq, Eq)]

View file

@ -410,14 +410,17 @@ pub(super) fn definition(
Definition::Trait(trait_) => {
trait_.display_limited(db, config.max_trait_assoc_items_count).to_string()
}
Definition::Adt(adt) => {
adt.display_limited(db, config.max_adt_fields_or_variants_count).to_string()
Definition::Adt(adt @ (Adt::Struct(_) | Adt::Union(_))) => {
adt.display_limited(db, config.max_struct_or_union_fields_count).to_string()
}
Definition::Adt(adt @ Adt::Enum(_)) => {
adt.display_limited(db, config.max_enum_variants_count).to_string()
}
Definition::SelfType(impl_def) => {
let self_ty = &impl_def.self_ty(db);
match self_ty.as_adt() {
Some(adt) => {
adt.display_limited(db, config.max_adt_fields_or_variants_count).to_string()
adt.display_limited(db, config.max_struct_or_union_fields_count).to_string()
}
None => self_ty.display(db).to_string(),
}

View file

@ -18,7 +18,8 @@ const HOVER_BASE_CONFIG: HoverConfig = HoverConfig {
format: HoverDocFormat::Markdown,
keywords: true,
max_trait_assoc_items_count: None,
max_adt_fields_or_variants_count: Some(5),
max_struct_or_union_fields_count: Some(5),
max_enum_variants_count: Some(5),
};
fn check_hover_no_result(ra_fixture: &str) {
@ -51,8 +52,8 @@ fn check(ra_fixture: &str, expect: Expect) {
}
#[track_caller]
fn check_hover_adt_fields_or_variants_limit(
count: Option<usize>,
fn check_hover_struct_or_union_fields_limit(
fields_count: impl Into<Option<usize>>,
ra_fixture: &str,
expect: Expect,
) {
@ -61,7 +62,33 @@ fn check_hover_adt_fields_or_variants_limit(
.hover(
&HoverConfig {
links_in_hover: true,
max_adt_fields_or_variants_count: count,
max_struct_or_union_fields_count: fields_count.into(),
..HOVER_BASE_CONFIG
},
FileRange { file_id: position.file_id, range: TextRange::empty(position.offset) },
)
.unwrap()
.unwrap();
let content = analysis.db.file_text(position.file_id);
let hovered_element = &content[hover.range];
let actual = format!("*{hovered_element}*\n{}\n", hover.info.markup);
expect.assert_eq(&actual)
}
#[track_caller]
fn check_hover_enum_variants_limit(
variants_count: impl Into<Option<usize>>,
ra_fixture: &str,
expect: Expect,
) {
let (analysis, position) = fixture::position(ra_fixture);
let hover = analysis
.hover(
&HoverConfig {
links_in_hover: true,
max_enum_variants_count: variants_count.into(),
..HOVER_BASE_CONFIG
},
FileRange { file_id: position.file_id, range: TextRange::empty(position.offset) },
@ -912,8 +939,8 @@ struct Foo$0 where u32: Copy { field: u32 }
#[test]
fn hover_record_struct_limit() {
check_hover_adt_fields_or_variants_limit(
Some(3),
check_hover_struct_or_union_fields_limit(
3,
r#"
struct Foo$0 { a: u32, b: i32, c: i32 }
"#,
@ -934,8 +961,8 @@ fn hover_record_struct_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(3),
check_hover_struct_or_union_fields_limit(
3,
r#"
struct Foo$0 { a: u32 }
"#,
@ -954,8 +981,8 @@ fn hover_record_struct_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(3),
check_hover_struct_or_union_fields_limit(
3,
r#"
struct Foo$0 { a: u32, b: i32, c: i32, d: u32 }
"#,
@ -977,7 +1004,7 @@ fn hover_record_struct_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
check_hover_struct_or_union_fields_limit(
None,
r#"
struct Foo$0 { a: u32, b: i32, c: i32 }
@ -995,8 +1022,8 @@ fn hover_record_struct_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(0),
check_hover_struct_or_union_fields_limit(
0,
r#"
struct Foo$0 { a: u32, b: i32, c: i32 }
"#,
@ -1017,8 +1044,8 @@ fn hover_record_struct_limit() {
#[test]
fn hover_enum_limit() {
check_hover_adt_fields_or_variants_limit(
Some(5),
check_hover_enum_variants_limit(
5,
r#"enum Foo$0 { A, B }"#,
expect![[r#"
*Foo*
@ -1036,8 +1063,8 @@ fn hover_enum_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(1),
check_hover_enum_variants_limit(
1,
r#"enum Foo$0 { A, B }"#,
expect![[r#"
*Foo*
@ -1055,8 +1082,8 @@ fn hover_enum_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(0),
check_hover_enum_variants_limit(
0,
r#"enum Foo$0 { A, B }"#,
expect![[r#"
*Foo*
@ -1071,7 +1098,7 @@ fn hover_enum_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
check_hover_enum_variants_limit(
None,
r#"enum Foo$0 { A, B }"#,
expect![[r#"
@ -1087,12 +1114,46 @@ fn hover_enum_limit() {
```
"#]],
);
check_hover_enum_variants_limit(
7,
r#"enum Enum$0 {
Variant {},
Variant2 { field: i32 },
Variant3 { field: i32, field2: i32 },
Variant4(),
Variant5(i32),
Variant6(i32, i32),
Variant7,
Variant8,
}"#,
expect![[r#"
*Enum*
```rust
test
```
```rust
// size = 12 (0xC), align = 4, niches = 4294967288
enum Enum {
Variant {},
Variant2 { /**/ },
Variant3 { /**/ },
Variant4(),
Variant5( /**/ ),
Variant6( /**/ ),
Variant7,
/**/
}
```
"#]],
);
}
#[test]
fn hover_union_limit() {
check_hover_adt_fields_or_variants_limit(
Some(5),
check_hover_struct_or_union_fields_limit(
5,
r#"union Foo$0 { a: u32, b: i32 }"#,
expect![[r#"
*Foo*
@ -1110,8 +1171,8 @@ fn hover_union_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(1),
check_hover_struct_or_union_fields_limit(
1,
r#"union Foo$0 { a: u32, b: i32 }"#,
expect![[r#"
*Foo*
@ -1129,8 +1190,8 @@ fn hover_union_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
Some(0),
check_hover_struct_or_union_fields_limit(
0,
r#"union Foo$0 { a: u32, b: i32 }"#,
expect![[r#"
*Foo*
@ -1145,7 +1206,7 @@ fn hover_union_limit() {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
check_hover_struct_or_union_fields_limit(
None,
r#"union Foo$0 { a: u32, b: i32 }"#,
expect![[r#"
@ -1630,12 +1691,12 @@ impl Thing {
```
"#]],
);
check_hover_adt_fields_or_variants_limit(
check_hover_struct_or_union_fields_limit(
None,
r#"
struct Thing { x: u32 }
impl Thing {
fn new() -> Self { Self$0 { x: 0 } }
fn new() -> Self$0 { Self { x: 0 } }
}
"#,
expect![[r#"
@ -2599,8 +2660,8 @@ fn test_hover_layout_of_enum() {
```rust
// size = 16 (0x10), align = 8, niches = 254
enum Foo {
Variant1(u8, u16),
Variant2(i32, u8, i64),
Variant1( /**/ ),
Variant2( /**/ ),
}
```
"#]],

View file

@ -167,7 +167,8 @@ impl StaticIndex<'_> {
keywords: true,
format: crate::HoverDocFormat::Markdown,
max_trait_assoc_items_count: None,
max_adt_fields_or_variants_count: Some(5),
max_struct_or_union_fields_count: Some(5),
max_enum_variants_count: Some(5),
};
let tokens = tokens.filter(|token| {
matches!(

View file

@ -312,8 +312,10 @@ config_data! {
/// How to render the size information in a memory layout hover.
hover_memoryLayout_size: Option<MemoryLayoutHoverRenderKindDef> = Some(MemoryLayoutHoverRenderKindDef::Both),
/// How many fields or variants of an ADT (struct, enum or union) to display when hovering on. Show none if empty.
hover_show_adtFieldsOrVariants: Option<usize> = Some(5),
/// How many variants of an enum to display when hovering on. Show none if empty.
hover_show_enumVariants: Option<usize> = Some(5),
/// How many fields of a struct or union to display when hovering on. Show none if empty.
hover_show_structOrUnionFields: Option<usize> = Some(5),
/// How many associated items of a trait to display when hovering a trait.
hover_show_traitAssocItems: Option<usize> = None,
@ -1112,7 +1114,8 @@ impl Config {
},
keywords: self.hover_documentation_keywords_enable().to_owned(),
max_trait_assoc_items_count: self.hover_show_traitAssocItems().to_owned(),
max_adt_fields_or_variants_count: self.hover_show_adtFieldsOrVariants().to_owned(),
max_struct_or_union_fields_count: self.hover_show_structOrUnionFields().to_owned(),
max_enum_variants_count: self.hover_show_enumVariants().to_owned(),
}
}

View file

@ -533,10 +533,15 @@ How to render the offset information in a memory layout hover.
--
How to render the size information in a memory layout hover.
--
[[rust-analyzer.hover.show.adtFieldsOrVariants]]rust-analyzer.hover.show.adtFieldsOrVariants (default: `5`)::
[[rust-analyzer.hover.show.enumVariants]]rust-analyzer.hover.show.enumVariants (default: `5`)::
+
--
How many fields or variants of an ADT (struct, enum or union) to display when hovering on. Show none if empty.
How many variants of an enum to display when hovering on. Show none if empty.
--
[[rust-analyzer.hover.show.structOrUnionFields]]rust-analyzer.hover.show.structOrUnionFields (default: `5`)::
+
--
How many fields of a struct or union to display when hovering on. Show none if empty.
--
[[rust-analyzer.hover.show.traitAssocItems]]rust-analyzer.hover.show.traitAssocItems (default: `null`)::
+

View file

@ -1152,8 +1152,17 @@
}
]
},
"rust-analyzer.hover.show.adtFieldsOrVariants": {
"markdownDescription": "How many fields or variants of an ADT (struct, enum or union) to display when hovering on. Show none if empty.",
"rust-analyzer.hover.show.enumVariants": {
"markdownDescription": "How many variants of an enum to display when hovering on. Show none if empty.",
"default": 5,
"type": [
"null",
"integer"
],
"minimum": 0
},
"rust-analyzer.hover.show.structOrUnionFields": {
"markdownDescription": "How many fields of a struct or union to display when hovering on. Show none if empty.",
"default": 5,
"type": [
"null",