Auto merge of #88490 - GuillaumeGomez:associated-types-implementors-display, r=camelid,Manishearth
Display associated types of implementors Fixes #86631. Contrary to before, it doesn't display methods. I also had to "resurrect" the `auto-hide-trait-implementations` setting. :3 Only question at this point: should I move the `render_impl` boolean arguments into one struct? We're starting to have quite a lot of them... cc `@cynecx` r? `@camelid`
This commit is contained in:
commit
767edcf616
7 changed files with 112 additions and 50 deletions
|
@ -710,11 +710,15 @@ fn render_impls(
|
||||||
containing_item,
|
containing_item,
|
||||||
assoc_link,
|
assoc_link,
|
||||||
RenderMode::Normal,
|
RenderMode::Normal,
|
||||||
true,
|
|
||||||
None,
|
None,
|
||||||
false,
|
|
||||||
true,
|
|
||||||
&[],
|
&[],
|
||||||
|
ImplRenderingParameters {
|
||||||
|
show_def_docs: true,
|
||||||
|
is_on_foreign_type: false,
|
||||||
|
show_default_items: true,
|
||||||
|
show_non_assoc_items: true,
|
||||||
|
toggle_open_by_default: true,
|
||||||
|
},
|
||||||
);
|
);
|
||||||
buffer.into_inner()
|
buffer.into_inner()
|
||||||
})
|
})
|
||||||
|
@ -1049,11 +1053,15 @@ fn render_assoc_items(
|
||||||
containing_item,
|
containing_item,
|
||||||
AssocItemLink::Anchor(None),
|
AssocItemLink::Anchor(None),
|
||||||
render_mode,
|
render_mode,
|
||||||
true,
|
|
||||||
None,
|
None,
|
||||||
false,
|
|
||||||
true,
|
|
||||||
&[],
|
&[],
|
||||||
|
ImplRenderingParameters {
|
||||||
|
show_def_docs: true,
|
||||||
|
is_on_foreign_type: false,
|
||||||
|
show_default_items: true,
|
||||||
|
show_non_assoc_items: true,
|
||||||
|
toggle_open_by_default: true,
|
||||||
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1243,6 +1251,16 @@ fn notable_traits_decl(decl: &clean::FnDecl, cx: &Context<'_>) -> String {
|
||||||
out.into_inner()
|
out.into_inner()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, Debug)]
|
||||||
|
struct ImplRenderingParameters {
|
||||||
|
show_def_docs: bool,
|
||||||
|
is_on_foreign_type: bool,
|
||||||
|
show_default_items: bool,
|
||||||
|
/// Whether or not to show methods.
|
||||||
|
show_non_assoc_items: bool,
|
||||||
|
toggle_open_by_default: bool,
|
||||||
|
}
|
||||||
|
|
||||||
fn render_impl(
|
fn render_impl(
|
||||||
w: &mut Buffer,
|
w: &mut Buffer,
|
||||||
cx: &Context<'_>,
|
cx: &Context<'_>,
|
||||||
|
@ -1250,13 +1268,9 @@ fn render_impl(
|
||||||
parent: &clean::Item,
|
parent: &clean::Item,
|
||||||
link: AssocItemLink<'_>,
|
link: AssocItemLink<'_>,
|
||||||
render_mode: RenderMode,
|
render_mode: RenderMode,
|
||||||
show_def_docs: bool,
|
|
||||||
use_absolute: Option<bool>,
|
use_absolute: Option<bool>,
|
||||||
is_on_foreign_type: bool,
|
|
||||||
show_default_items: bool,
|
|
||||||
// This argument is used to reference same type with different paths to avoid duplication
|
|
||||||
// in documentation pages for trait with automatic implementations like "Send" and "Sync".
|
|
||||||
aliases: &[String],
|
aliases: &[String],
|
||||||
|
rendering_params: ImplRenderingParameters,
|
||||||
) {
|
) {
|
||||||
let cache = cx.cache();
|
let cache = cx.cache();
|
||||||
let traits = &cache.traits;
|
let traits = &cache.traits;
|
||||||
|
@ -1279,12 +1293,13 @@ fn render_impl(
|
||||||
render_mode: RenderMode,
|
render_mode: RenderMode,
|
||||||
is_default_item: bool,
|
is_default_item: bool,
|
||||||
trait_: Option<&clean::Trait>,
|
trait_: Option<&clean::Trait>,
|
||||||
show_def_docs: bool,
|
rendering_params: ImplRenderingParameters,
|
||||||
) {
|
) {
|
||||||
let item_type = item.type_();
|
let item_type = item.type_();
|
||||||
let name = item.name.as_ref().unwrap();
|
let name = item.name.as_ref().unwrap();
|
||||||
|
|
||||||
let render_method_item = match render_mode {
|
let render_method_item = rendering_params.show_non_assoc_items
|
||||||
|
&& match render_mode {
|
||||||
RenderMode::Normal => true,
|
RenderMode::Normal => true,
|
||||||
RenderMode::ForDeref { mut_: deref_mut_ } => {
|
RenderMode::ForDeref { mut_: deref_mut_ } => {
|
||||||
should_render_item(&item, deref_mut_, cx.cache())
|
should_render_item(&item, deref_mut_, cx.cache())
|
||||||
|
@ -1312,18 +1327,32 @@ fn render_impl(
|
||||||
} else {
|
} else {
|
||||||
// In case the item isn't documented,
|
// In case the item isn't documented,
|
||||||
// provide short documentation from the trait.
|
// provide short documentation from the trait.
|
||||||
document_short(&mut doc_buffer, it, cx, link, parent, show_def_docs);
|
document_short(
|
||||||
|
&mut doc_buffer,
|
||||||
|
it,
|
||||||
|
cx,
|
||||||
|
link,
|
||||||
|
parent,
|
||||||
|
rendering_params.show_def_docs,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
document_item_info(&mut info_buffer, cx, item, Some(parent));
|
document_item_info(&mut info_buffer, cx, item, Some(parent));
|
||||||
if show_def_docs {
|
if rendering_params.show_def_docs {
|
||||||
document_full(&mut doc_buffer, item, cx);
|
document_full(&mut doc_buffer, item, cx);
|
||||||
short_documented = false;
|
short_documented = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
document_short(&mut doc_buffer, item, cx, link, parent, show_def_docs);
|
document_short(
|
||||||
|
&mut doc_buffer,
|
||||||
|
item,
|
||||||
|
cx,
|
||||||
|
link,
|
||||||
|
parent,
|
||||||
|
rendering_params.show_def_docs,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let w = if short_documented && trait_.is_some() { interesting } else { boring };
|
let w = if short_documented && trait_.is_some() { interesting } else { boring };
|
||||||
|
@ -1455,7 +1484,7 @@ fn render_impl(
|
||||||
render_mode,
|
render_mode,
|
||||||
false,
|
false,
|
||||||
trait_.map(|t| &t.trait_),
|
trait_.map(|t| &t.trait_),
|
||||||
show_def_docs,
|
rendering_params,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1468,7 +1497,7 @@ fn render_impl(
|
||||||
parent: &clean::Item,
|
parent: &clean::Item,
|
||||||
containing_item: &clean::Item,
|
containing_item: &clean::Item,
|
||||||
render_mode: RenderMode,
|
render_mode: RenderMode,
|
||||||
show_def_docs: bool,
|
rendering_params: ImplRenderingParameters,
|
||||||
) {
|
) {
|
||||||
for trait_item in &t.items {
|
for trait_item in &t.items {
|
||||||
let n = trait_item.name;
|
let n = trait_item.name;
|
||||||
|
@ -1490,7 +1519,7 @@ fn render_impl(
|
||||||
render_mode,
|
render_mode,
|
||||||
true,
|
true,
|
||||||
Some(t),
|
Some(t),
|
||||||
show_def_docs,
|
rendering_params,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1499,7 +1528,7 @@ fn render_impl(
|
||||||
// default items which weren't overridden in the implementation block.
|
// default items which weren't overridden in the implementation block.
|
||||||
// We don't emit documentation for default items if they appear in the
|
// We don't emit documentation for default items if they appear in the
|
||||||
// Implementations on Foreign Types or Implementors sections.
|
// Implementations on Foreign Types or Implementors sections.
|
||||||
if show_default_items {
|
if rendering_params.show_default_items {
|
||||||
if let Some(t) = trait_ {
|
if let Some(t) = trait_ {
|
||||||
render_default_items(
|
render_default_items(
|
||||||
&mut default_impl_items,
|
&mut default_impl_items,
|
||||||
|
@ -1510,7 +1539,7 @@ fn render_impl(
|
||||||
&i.impl_item,
|
&i.impl_item,
|
||||||
parent,
|
parent,
|
||||||
render_mode,
|
render_mode,
|
||||||
show_def_docs,
|
rendering_params,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1518,7 +1547,11 @@ fn render_impl(
|
||||||
let toggled = !(impl_items.is_empty() && default_impl_items.is_empty());
|
let toggled = !(impl_items.is_empty() && default_impl_items.is_empty());
|
||||||
if toggled {
|
if toggled {
|
||||||
close_tags.insert_str(0, "</details>");
|
close_tags.insert_str(0, "</details>");
|
||||||
write!(w, "<details class=\"rustdoc-toggle implementors-toggle\" open>");
|
write!(
|
||||||
|
w,
|
||||||
|
"<details class=\"rustdoc-toggle implementors-toggle\"{}>",
|
||||||
|
if rendering_params.toggle_open_by_default { " open" } else { "" }
|
||||||
|
);
|
||||||
write!(w, "<summary>")
|
write!(w, "<summary>")
|
||||||
}
|
}
|
||||||
render_impl_summary(
|
render_impl_summary(
|
||||||
|
@ -1527,9 +1560,9 @@ fn render_impl(
|
||||||
i,
|
i,
|
||||||
parent,
|
parent,
|
||||||
parent,
|
parent,
|
||||||
show_def_docs,
|
rendering_params.show_def_docs,
|
||||||
use_absolute,
|
use_absolute,
|
||||||
is_on_foreign_type,
|
rendering_params.is_on_foreign_type,
|
||||||
aliases,
|
aliases,
|
||||||
);
|
);
|
||||||
if toggled {
|
if toggled {
|
||||||
|
|
|
@ -16,8 +16,8 @@ use rustc_span::symbol::{kw, sym, Symbol};
|
||||||
use super::{
|
use super::{
|
||||||
collect_paths_for_type, document, ensure_trailing_slash, item_ty_to_strs, notable_traits_decl,
|
collect_paths_for_type, document, ensure_trailing_slash, item_ty_to_strs, notable_traits_decl,
|
||||||
render_assoc_item, render_assoc_items, render_attributes_in_code, render_attributes_in_pre,
|
render_assoc_item, render_assoc_items, render_attributes_in_code, render_attributes_in_pre,
|
||||||
render_impl, render_impl_summary, render_stability_since_raw, write_srclink, AssocItemLink,
|
render_impl, render_stability_since_raw, write_srclink, AssocItemLink, Context,
|
||||||
Context,
|
ImplRenderingParameters,
|
||||||
};
|
};
|
||||||
use crate::clean::{self, GetDefId};
|
use crate::clean::{self, GetDefId};
|
||||||
use crate::formats::item_type::ItemType;
|
use crate::formats::item_type::ItemType;
|
||||||
|
@ -736,11 +736,15 @@ fn item_trait(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Tra
|
||||||
it,
|
it,
|
||||||
assoc_link,
|
assoc_link,
|
||||||
RenderMode::Normal,
|
RenderMode::Normal,
|
||||||
false,
|
|
||||||
None,
|
None,
|
||||||
true,
|
|
||||||
false,
|
|
||||||
&[],
|
&[],
|
||||||
|
ImplRenderingParameters {
|
||||||
|
show_def_docs: false,
|
||||||
|
is_on_foreign_type: true,
|
||||||
|
show_default_items: false,
|
||||||
|
show_non_assoc_items: true,
|
||||||
|
toggle_open_by_default: false,
|
||||||
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1395,16 +1399,22 @@ fn render_implementor(
|
||||||
} => implementor_dups[&path.last()].1,
|
} => implementor_dups[&path.last()].1,
|
||||||
_ => false,
|
_ => false,
|
||||||
};
|
};
|
||||||
render_impl_summary(
|
render_impl(
|
||||||
w,
|
w,
|
||||||
cx,
|
cx,
|
||||||
implementor,
|
implementor,
|
||||||
trait_,
|
trait_,
|
||||||
trait_,
|
AssocItemLink::Anchor(None),
|
||||||
false,
|
RenderMode::Normal,
|
||||||
Some(use_absolute),
|
Some(use_absolute),
|
||||||
false,
|
|
||||||
aliases,
|
aliases,
|
||||||
|
ImplRenderingParameters {
|
||||||
|
show_def_docs: false,
|
||||||
|
is_on_foreign_type: false,
|
||||||
|
show_default_items: false,
|
||||||
|
show_non_assoc_items: false,
|
||||||
|
toggle_open_by_default: false,
|
||||||
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -3,14 +3,14 @@
|
||||||
goto: file://|DOC_PATH|/implementors/trait.Whatever.html
|
goto: file://|DOC_PATH|/implementors/trait.Whatever.html
|
||||||
assert: "#implementors-list"
|
assert: "#implementors-list"
|
||||||
// There are supposed to be two implementors listed.
|
// There are supposed to be two implementors listed.
|
||||||
assert-count: ("#implementors-list > .impl", 2)
|
assert-count: ("#implementors-list .impl", 2)
|
||||||
// Now we check that both implementors have an anchor, an ID and a similar DOM.
|
// Now we check that both implementors have an anchor, an ID and a similar DOM.
|
||||||
assert: ("#implementors-list > .impl:nth-child(1) > a.anchor")
|
assert: ("#implementors-list .impl:nth-child(1) > a.anchor")
|
||||||
assert-attribute: ("#implementors-list > .impl:nth-child(1)", {"id": "impl-Whatever"})
|
assert-attribute: ("#implementors-list .impl:nth-child(1)", {"id": "impl-Whatever"})
|
||||||
assert-attribute: ("#implementors-list > .impl:nth-child(1) > a.anchor", {"href": "#impl-Whatever"})
|
assert-attribute: ("#implementors-list .impl:nth-child(1) > a.anchor", {"href": "#impl-Whatever"})
|
||||||
assert: "#implementors-list > .impl:nth-child(1) > .code-header.in-band"
|
assert: "#implementors-list .impl:nth-child(1) > .code-header.in-band"
|
||||||
|
|
||||||
assert: ("#implementors-list > .impl:nth-child(2) > a.anchor")
|
assert: ("#implementors-list .impl:nth-child(2) > a.anchor")
|
||||||
assert-attribute: ("#implementors-list > .impl:nth-child(2)", {"id": "impl-Whatever-1"})
|
assert-attribute: ("#implementors-list .impl:nth-child(2)", {"id": "impl-Whatever-1"})
|
||||||
assert-attribute: ("#implementors-list > .impl:nth-child(2) > a.anchor", {"href": "#impl-Whatever-1"})
|
assert-attribute: ("#implementors-list .impl:nth-child(2) > a.anchor", {"href": "#impl-Whatever-1"})
|
||||||
assert: "#implementors-list > .impl:nth-child(2) > .code-header.in-band"
|
assert: "#implementors-list .impl:nth-child(2) > .code-header.in-band"
|
||||||
|
|
|
@ -1,7 +1,11 @@
|
||||||
pub trait Whatever {
|
pub trait Whatever {
|
||||||
|
type Foo;
|
||||||
|
|
||||||
fn method() {}
|
fn method() {}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct Struct;
|
pub struct Struct;
|
||||||
|
|
||||||
impl Whatever for Struct {}
|
impl Whatever for Struct {
|
||||||
|
type Foo = u8;
|
||||||
|
}
|
||||||
|
|
|
@ -38,7 +38,9 @@ impl Trait for Foo {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
impl implementors::Whatever for Foo {}
|
impl implementors::Whatever for Foo {
|
||||||
|
type Foo = u32;
|
||||||
|
}
|
||||||
|
|
||||||
pub mod sub_mod {
|
pub mod sub_mod {
|
||||||
/// ```txt
|
/// ```txt
|
||||||
|
|
4
src/test/rustdoc-gui/toggle-implementors.goml
Normal file
4
src/test/rustdoc-gui/toggle-implementors.goml
Normal file
|
@ -0,0 +1,4 @@
|
||||||
|
// This test ensures that the implementors toggle are not open by default.
|
||||||
|
goto: file://|DOC_PATH|/implementors/trait.Whatever.html
|
||||||
|
|
||||||
|
assert-attribute-false: ("#implementors-list > details", {"open": ""}, ALL)
|
|
@ -1,6 +1,6 @@
|
||||||
pub trait MyTrait {
|
pub trait MyTrait {
|
||||||
type Assoc;
|
type Assoc;
|
||||||
const VALUE: u32;
|
const VALUE: u32 = 12;
|
||||||
fn trait_function(&self);
|
fn trait_function(&self);
|
||||||
fn defaulted(&self) {}
|
fn defaulted(&self) {}
|
||||||
fn defaulted_override(&self) {}
|
fn defaulted_override(&self) {}
|
||||||
|
@ -38,9 +38,11 @@ impl MyTrait for Vec<u8> {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl MyTrait for MyStruct {
|
impl MyTrait for MyStruct {
|
||||||
|
// @has trait_impl_items_links_and_anchors/trait.MyTrait.html '//div[@id="associatedtype.Assoc-3"]//a[@class="anchor"]/@href' #associatedtype.Assoc-3
|
||||||
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedtype.Assoc"]//a[@class="type"]/@href' trait.MyTrait.html#associatedtype.Assoc
|
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedtype.Assoc"]//a[@class="type"]/@href' trait.MyTrait.html#associatedtype.Assoc
|
||||||
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedtype.Assoc"]//a[@class="anchor"]/@href' #associatedtype.Assoc
|
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedtype.Assoc"]//a[@class="anchor"]/@href' #associatedtype.Assoc
|
||||||
type Assoc = bool;
|
type Assoc = bool;
|
||||||
|
// @has trait_impl_items_links_and_anchors/trait.MyTrait.html '//div[@id="associatedconstant.VALUE-3"]//a[@class="anchor"]/@href' #associatedconstant.VALUE-3
|
||||||
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedconstant.VALUE"]//a[@class="constant"]/@href' trait.MyTrait.html#associatedconstant.VALUE
|
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedconstant.VALUE"]//a[@class="constant"]/@href' trait.MyTrait.html#associatedconstant.VALUE
|
||||||
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedconstant.VALUE"]//a[@class="anchor"]/@href' #associatedconstant.VALUE
|
// @has trait_impl_items_links_and_anchors/struct.MyStruct.html '//div[@id="associatedconstant.VALUE"]//a[@class="anchor"]/@href' #associatedconstant.VALUE
|
||||||
const VALUE: u32 = 20;
|
const VALUE: u32 = 20;
|
||||||
|
@ -55,3 +57,10 @@ impl MyTrait for MyStruct {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct MyStruct;
|
pub struct MyStruct;
|
||||||
|
|
||||||
|
// We check that associated items with default values aren't generated in the implementors list.
|
||||||
|
impl MyTrait for (u8, u8) {
|
||||||
|
// @!has trait_impl_items_links_and_anchors/trait.MyTrait.html '//div[@id="associatedconstant.VALUE-4"]'
|
||||||
|
type Assoc = bool;
|
||||||
|
fn trait_function(&self) {}
|
||||||
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue