Auto merge of #115948 - notriddle:notriddle/logo-lockup, r=fmease
rustdoc: show crate name beside smaller logo *Blocked on https://github.com/rust-lang/cargo/pull/12800* ## Summary In this PR, the crate name and version are always shown in the sidebar, even in subpages, and the lateral navigation is always shown in the sidebar, even in modules. Clicking the crate name does the same thing clicking the logo always did: take you to the crate root (the crate's home page, at least within Rustdoc). The Rust logo is also no longer shown by default for non-Rust docs. ### Screenshots <details><summary>Before</summary> | | Macro | Module | |--|-------|--------| | In crate |  | | In module[^1] |  |  [^1]: This PR also includes a bug fix for derive macros not showing up in the lateral navigation part of the sidebar </details> #### Whole sidebar screenshots | | Macro | Module | |--|-------|--------| | In crate |  |  | In module |  |  #### Different logo configurations | | Short crate name | Long crate name | |---------|------------------|-----------------| | Root | ![short-root] | ![long-root] | Subpage | ![short-subpage] | ![long-subpage] [short-root]:9e2b4fa8
-f581-4106-b562-1e0372c13f79 [short-subpage]:8331cdb8
-fa13-4671-a1e2-dcc1cdca7451 [long-root]:7d377fec
-0f1d-4343-9f82-0e35a8f58056 [long-subpage]:3b3094a4
-63c9-477c-8c15-b6075837df30 ##### Without a logo  ### Preview pages https://notriddle.com/rustdoc-html-demo-5/sidebar-layout-rocket/rocket/index.html https://notriddle.com/rustdoc-html-demo-5/sidebar-layout-rocket/rocket_sync_db_pools/index.html https://notriddle.com/rustdoc-html-demo-5/sidebar-layout-rust-compiler/index.html https://notriddle.com/rustdoc-html-demo-5/sidebar-layout-rust/std/index.html https://notriddle.com/rustdoc-html-demo-5/sidebar-layout-rocket/tokio/index.html ## Motivation This improves visual information density (the construct with the logo and crate name is *shorter* than the logo on its own, because it's not square) and navigation clarity (we can now see what clicking the Rust logo does, specifically). Compare this with the layout at [Phoenix's Hexdocs] (which is what this proposal is closely based on), the old proposal on [Internals Discourse] (which always says "Rust standard library" in the sidebar, but doesn't do the side-by-side layout). [Phoenix's Hexdocs]: https://hexdocs.pm/phoenix/1.7.7/overview.html [Internals Discourse]: https://internals.rust-lang.org/t/poc-of-a-new-design-for-the-generated-rustdoc/11018 ## Guide-level explanation This PR cleans up some of the sidebar navigation. It makes the logo in the desktop sidebar a bit smaller, and puts the crate name and version next to it (either beside it, or below it, depending on if there's space), making it clearer what clicking on it does: click the crate name to open the crate's home page. It also removes the Rust logo from non-official-Rust crates, again to make the navigation and supply chain clearer (since the crate name has been added, the logo is no longer necessary for navigation). It adds a bit more clarifying information for lateral navigation. On items that don't add their own sidebar items, it just shows its siblings directly below the crate name and logo, but for other items, it shows "In crate alloc" instead of just "In alloc". It also shows the lateral navigation tools on module pages, making modules consistent with every other item. ## Drawbacks While this actually takes up less screen real estate than the old layout on desktop, it takes up more HTML. It's also a bit more visually complex. ## Rationale and alternatives I could do what the Internals POC did and keep the vertically stacked layout all the time, instead of doing a horizontal stack where possible. It would take up more screen real estate, though. ## Prior art This design is lifted almost verbatim from Hexdocs. It seems to work for them. [`opentelemetry_process_propagator`], for example, has a long application name. [`opentelemetry_process_propagator`]: https://hexdocs.pm/opentelemetry_process_propagator/OpentelemetryProcessPropagator.html ## Unresolved questions Maybe we should encourage crate authors to include their own logo more often? It certainly helps give people a better sense of "place." This seems to be blocked on coming up with an API to do it without requiring them to host the file somewhere. ## Future possibilities Beyond this, plenty of other changes could be made to improve the layout, like * Fix things so that clicking an item in the sidebar doesn't cause it to scroll back to the top. * The [Internals demo](https://utherii.github.io/new.html) does this right: clicking an item in the sidebar changes the content area, but the sidebar itself does not change. This is nice, because clicking is cheap and I can skim the opening few paragraphs while browsing. * The layout of the docs sidebar causes trouble to implement this, because it's different on different pages, but at least fix this on the file browser. * Come up with a less cluttered way to do disclosure. There's a lot of `[-]` on the page. * We don't lack ideas to fix this one. We have *too many*. * Do a better job of separating local navigation (vec::Vec links to vec::IntoIter) and the table of contents (vec::Vec links to vec::Vec::new). * A possibility: add a Back arrow next to the "In [module]" header?  * Give readers more control of how much rustdoc shows them, and giving doc authors more control of how much it generates. Basically, https://github.com/rust-lang/rust/pull/115660 is great, let's do it too. But those are mostly orthogonal, not future possibilities unlocked by this change.
This commit is contained in:
commit
6d05c430d2
64 changed files with 433 additions and 99 deletions
|
@ -11,6 +11,8 @@
|
||||||
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
||||||
test(no_crate_inject, attr(deny(warnings)))
|
test(no_crate_inject, attr(deny(warnings)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(core_intrinsics)]
|
#![feature(core_intrinsics)]
|
||||||
#![feature(dropck_eyepatch)]
|
#![feature(dropck_eyepatch)]
|
||||||
#![feature(new_uninit)]
|
#![feature(new_uninit)]
|
||||||
|
|
|
@ -8,6 +8,9 @@
|
||||||
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
||||||
test(attr(deny(warnings)))
|
test(attr(deny(warnings)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(associated_type_bounds)]
|
#![feature(associated_type_bounds)]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(const_trait_impl)]
|
#![feature(const_trait_impl)]
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(associated_type_bounds)]
|
#![feature(associated_type_bounds)]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(if_let_guard)]
|
#![feature(if_let_guard)]
|
||||||
|
|
|
@ -5,6 +5,9 @@
|
||||||
//! This API is completely unstable and subject to change.
|
//! This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(lazy_cell)]
|
#![feature(lazy_cell)]
|
||||||
#![feature(decl_macro)]
|
#![feature(decl_macro)]
|
||||||
#![feature(panic_update_hook)]
|
#![feature(panic_update_hook)]
|
||||||
|
|
|
@ -3,6 +3,8 @@
|
||||||
//! This module contains the code for creating and emitting diagnostics.
|
//! This module contains the code for creating and emitting diagnostics.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(array_windows)]
|
#![feature(array_windows)]
|
||||||
#![feature(extract_if)]
|
#![feature(extract_if)]
|
||||||
#![feature(if_let_guard)]
|
#![feature(if_let_guard)]
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(proc_macro_diagnostic)]
|
#![feature(proc_macro_diagnostic)]
|
||||||
#![feature(proc_macro_span)]
|
#![feature(proc_macro_span)]
|
||||||
#![deny(rustc::untranslatable_diagnostic)]
|
#![deny(rustc::untranslatable_diagnostic)]
|
||||||
|
|
|
@ -273,6 +273,9 @@
|
||||||
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
||||||
test(attr(allow(unused_variables), deny(warnings)))
|
test(attr(allow(unused_variables), deny(warnings)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![deny(rustc::untranslatable_diagnostic)]
|
#![deny(rustc::untranslatable_diagnostic)]
|
||||||
#![deny(rustc::diagnostic_outside_of_impl)]
|
#![deny(rustc::diagnostic_outside_of_impl)]
|
||||||
|
|
||||||
|
|
|
@ -57,6 +57,9 @@ This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![allow(rustc::potential_query_instability)]
|
#![allow(rustc::potential_query_instability)]
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(control_flow_enum)]
|
#![feature(control_flow_enum)]
|
||||||
#![feature(if_let_guard)]
|
#![feature(if_let_guard)]
|
||||||
|
|
|
@ -2,6 +2,9 @@
|
||||||
|
|
||||||
#![deny(missing_docs)]
|
#![deny(missing_docs)]
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(never_type)]
|
#![feature(never_type)]
|
||||||
#![recursion_limit = "256"]
|
#![recursion_limit = "256"]
|
||||||
#![deny(rustc::untranslatable_diagnostic)]
|
#![deny(rustc::untranslatable_diagnostic)]
|
||||||
|
|
|
@ -13,6 +13,9 @@
|
||||||
//! This API is completely unstable and subject to change.
|
//! This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(associated_type_bounds)]
|
#![feature(associated_type_bounds)]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(control_flow_enum)]
|
#![feature(control_flow_enum)]
|
||||||
|
|
|
@ -27,6 +27,8 @@
|
||||||
|
|
||||||
#![allow(rustc::potential_query_instability)]
|
#![allow(rustc::potential_query_instability)]
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(array_windows)]
|
#![feature(array_windows)]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(control_flow_enum)]
|
#![feature(control_flow_enum)]
|
||||||
|
|
|
@ -1,6 +1,9 @@
|
||||||
#![deny(rustc::untranslatable_diagnostic)]
|
#![deny(rustc::untranslatable_diagnostic)]
|
||||||
#![deny(rustc::diagnostic_outside_of_impl)]
|
#![deny(rustc::diagnostic_outside_of_impl)]
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
|
|
||||||
// NOTE: This crate only exists to allow linking on mingw targets.
|
// NOTE: This crate only exists to allow linking on mingw targets.
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(decl_macro)]
|
#![feature(decl_macro)]
|
||||||
#![feature(extract_if)]
|
#![feature(extract_if)]
|
||||||
#![feature(generators)]
|
#![feature(generators)]
|
||||||
|
|
|
@ -23,6 +23,8 @@
|
||||||
//! This API is completely unstable and subject to change.
|
//! This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(allocator_api)]
|
#![feature(allocator_api)]
|
||||||
#![feature(array_windows)]
|
#![feature(array_windows)]
|
||||||
#![feature(assert_matches)]
|
#![feature(assert_matches)]
|
||||||
|
|
|
@ -9,6 +9,9 @@
|
||||||
html_playground_url = "https://play.rust-lang.org/",
|
html_playground_url = "https://play.rust-lang.org/",
|
||||||
test(attr(deny(warnings)))
|
test(attr(deny(warnings)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![deny(rustc::untranslatable_diagnostic)]
|
#![deny(rustc::untranslatable_diagnostic)]
|
||||||
#![deny(rustc::diagnostic_outside_of_impl)]
|
#![deny(rustc::diagnostic_outside_of_impl)]
|
||||||
// We want to be able to build this crate with a stable compiler, so no
|
// We want to be able to build this crate with a stable compiler, so no
|
||||||
|
|
|
@ -1108,6 +1108,7 @@ impl CheckAttrVisitor<'_> {
|
||||||
| sym::html_root_url
|
| sym::html_root_url
|
||||||
| sym::html_no_source
|
| sym::html_no_source
|
||||||
| sym::test
|
| sym::test
|
||||||
|
| sym::rust_logo
|
||||||
if !self.check_attr_crate_level(attr, meta, hir_id) =>
|
if !self.check_attr_crate_level(attr, meta, hir_id) =>
|
||||||
{
|
{
|
||||||
is_valid = false;
|
is_valid = false;
|
||||||
|
@ -1166,6 +1167,18 @@ impl CheckAttrVisitor<'_> {
|
||||||
| sym::plugins
|
| sym::plugins
|
||||||
| sym::fake_variadic => {}
|
| sym::fake_variadic => {}
|
||||||
|
|
||||||
|
sym::rust_logo => {
|
||||||
|
if !self.tcx.features().rustdoc_internals {
|
||||||
|
feature_err(
|
||||||
|
&self.tcx.sess.parse_sess,
|
||||||
|
sym::rustdoc_internals,
|
||||||
|
meta.span(),
|
||||||
|
"the `#[doc(rust_logo)]` attribute is used for Rust branding",
|
||||||
|
)
|
||||||
|
.emit();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
sym::test => {
|
sym::test => {
|
||||||
if !self.check_test_attr(meta, hir_id) {
|
if !self.check_test_attr(meta, hir_id) {
|
||||||
is_valid = false;
|
is_valid = false;
|
||||||
|
|
|
@ -6,6 +6,9 @@
|
||||||
|
|
||||||
#![allow(rustc::potential_query_instability)]
|
#![allow(rustc::potential_query_instability)]
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(iter_intersperse)]
|
#![feature(iter_intersperse)]
|
||||||
#![feature(let_chains)]
|
#![feature(let_chains)]
|
||||||
#![feature(map_try_insert)]
|
#![feature(map_try_insert)]
|
||||||
|
|
|
@ -7,6 +7,9 @@
|
||||||
//! of the Unstable Book for some examples.
|
//! of the Unstable Book for some examples.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![recursion_limit = "256"]
|
#![recursion_limit = "256"]
|
||||||
#![deny(rustc::untranslatable_diagnostic)]
|
#![deny(rustc::untranslatable_diagnostic)]
|
||||||
#![deny(rustc::diagnostic_outside_of_impl)]
|
#![deny(rustc::diagnostic_outside_of_impl)]
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(associated_type_defaults)]
|
#![feature(associated_type_defaults)]
|
||||||
#![feature(rustc_private)]
|
#![feature(rustc_private)]
|
||||||
#![feature(try_blocks)]
|
#![feature(try_blocks)]
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
//! Support for serializing the dep-graph and reloading it.
|
//! Support for serializing the dep-graph and reloading it.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
// this shouldn't be necessary, but the check for `&mut _` is too naive and denies returning a function pointer that takes a mut ref
|
// this shouldn't be necessary, but the check for `&mut _` is too naive and denies returning a function pointer that takes a mut ref
|
||||||
#![feature(const_mut_refs)]
|
#![feature(const_mut_refs)]
|
||||||
#![feature(const_refs_to_cell)]
|
#![feature(const_refs_to_cell)]
|
||||||
|
|
|
@ -7,6 +7,8 @@
|
||||||
//! Type-relative name resolution (methods, fields, associated items) happens in `rustc_hir_analysis`.
|
//! Type-relative name resolution (methods, fields, associated items) happens in `rustc_hir_analysis`.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(assert_matches)]
|
#![feature(assert_matches)]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(extract_if)]
|
#![feature(extract_if)]
|
||||||
|
|
|
@ -5,6 +5,9 @@
|
||||||
html_playground_url = "https://play.rust-lang.org/",
|
html_playground_url = "https://play.rust-lang.org/",
|
||||||
test(attr(allow(unused_variables), deny(warnings)))
|
test(attr(allow(unused_variables), deny(warnings)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(allocator_api)]
|
#![feature(allocator_api)]
|
||||||
#![feature(associated_type_bounds)]
|
#![feature(associated_type_bounds)]
|
||||||
#![feature(const_option)]
|
#![feature(const_option)]
|
||||||
|
|
|
@ -10,6 +10,9 @@
|
||||||
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/",
|
||||||
test(attr(allow(unused_variables), deny(warnings)))
|
test(attr(allow(unused_variables), deny(warnings)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
|
|
||||||
pub mod rustc_internal;
|
pub mod rustc_internal;
|
||||||
|
|
||||||
|
|
|
@ -14,6 +14,8 @@
|
||||||
//! This API is completely unstable and subject to change.
|
//! This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(array_windows)]
|
#![feature(array_windows)]
|
||||||
#![feature(if_let_guard)]
|
#![feature(if_let_guard)]
|
||||||
#![feature(negative_impls)]
|
#![feature(negative_impls)]
|
||||||
|
|
|
@ -1327,6 +1327,7 @@ symbols! {
|
||||||
rust_cold_cc,
|
rust_cold_cc,
|
||||||
rust_eh_catch_typeinfo,
|
rust_eh_catch_typeinfo,
|
||||||
rust_eh_personality,
|
rust_eh_personality,
|
||||||
|
rust_logo,
|
||||||
rustc,
|
rustc,
|
||||||
rustc_abi,
|
rustc_abi,
|
||||||
rustc_allocator,
|
rustc_allocator,
|
||||||
|
|
|
@ -88,6 +88,9 @@
|
||||||
//! DefPaths which are much more robust in the face of changes to the code base.
|
//! DefPaths which are much more robust in the face of changes to the code base.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(never_type)]
|
#![feature(never_type)]
|
||||||
#![recursion_limit = "256"]
|
#![recursion_limit = "256"]
|
||||||
#![allow(rustc::potential_query_instability)]
|
#![allow(rustc::potential_query_instability)]
|
||||||
|
|
|
@ -8,6 +8,8 @@
|
||||||
//! LLVM.
|
//! LLVM.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(assert_matches)]
|
#![feature(assert_matches)]
|
||||||
#![feature(associated_type_bounds)]
|
#![feature(associated_type_bounds)]
|
||||||
#![feature(exhaustive_patterns)]
|
#![feature(exhaustive_patterns)]
|
||||||
|
|
|
@ -11,6 +11,9 @@
|
||||||
//! This API is completely unstable and subject to change.
|
//! This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(associated_type_bounds)]
|
#![feature(associated_type_bounds)]
|
||||||
#![feature(box_patterns)]
|
#![feature(box_patterns)]
|
||||||
#![feature(control_flow_enum)]
|
#![feature(control_flow_enum)]
|
||||||
|
|
|
@ -5,6 +5,9 @@
|
||||||
//! This API is completely unstable and subject to change.
|
//! This API is completely unstable and subject to change.
|
||||||
|
|
||||||
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
|
#![cfg_attr(not(bootstrap), allow(internal_features))]
|
||||||
#![feature(assert_matches)]
|
#![feature(assert_matches)]
|
||||||
#![feature(iterator_try_collect)]
|
#![feature(iterator_try_collect)]
|
||||||
#![feature(let_chains)]
|
#![feature(let_chains)]
|
||||||
|
|
|
@ -78,6 +78,8 @@
|
||||||
not(no_sync),
|
not(no_sync),
|
||||||
target_has_atomic = "ptr"
|
target_has_atomic = "ptr"
|
||||||
))]
|
))]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![no_std]
|
#![no_std]
|
||||||
#![needs_allocator]
|
#![needs_allocator]
|
||||||
// Lints:
|
// Lints:
|
||||||
|
|
|
@ -68,6 +68,7 @@
|
||||||
test(no_crate_inject, attr(deny(warnings))),
|
test(no_crate_inject, attr(deny(warnings))),
|
||||||
test(attr(allow(dead_code, deprecated, unused_variables, unused_mut)))
|
test(attr(allow(dead_code, deprecated, unused_variables, unused_mut)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
#![doc(cfg_hide(
|
#![doc(cfg_hide(
|
||||||
not(test),
|
not(test),
|
||||||
any(not(feature = "miri-test-libstd"), test, doctest),
|
any(not(feature = "miri-test-libstd"), test, doctest),
|
||||||
|
|
|
@ -17,6 +17,8 @@
|
||||||
test(no_crate_inject, attr(deny(warnings))),
|
test(no_crate_inject, attr(deny(warnings))),
|
||||||
test(attr(allow(dead_code, deprecated, unused_variables, unused_mut)))
|
test(attr(allow(dead_code, deprecated, unused_variables, unused_mut)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
// This library is copied into rust-analyzer to allow loading rustc compiled proc macros.
|
// This library is copied into rust-analyzer to allow loading rustc compiled proc macros.
|
||||||
// Please avoid unstable features where possible to minimize the amount of changes necessary
|
// Please avoid unstable features where possible to minimize the amount of changes necessary
|
||||||
// to make it compile with rust-analyzer on stable.
|
// to make it compile with rust-analyzer on stable.
|
||||||
|
|
|
@ -227,6 +227,7 @@
|
||||||
test(no_crate_inject, attr(deny(warnings))),
|
test(no_crate_inject, attr(deny(warnings))),
|
||||||
test(attr(allow(dead_code, deprecated, unused_variables, unused_mut)))
|
test(attr(allow(dead_code, deprecated, unused_variables, unused_mut)))
|
||||||
)]
|
)]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
#![doc(cfg_hide(
|
#![doc(cfg_hide(
|
||||||
not(test),
|
not(test),
|
||||||
not(any(test, bootstrap)),
|
not(any(test, bootstrap)),
|
||||||
|
|
|
@ -16,6 +16,8 @@
|
||||||
|
|
||||||
#![unstable(feature = "test", issue = "50297")]
|
#![unstable(feature = "test", issue = "50297")]
|
||||||
#![doc(test(attr(deny(warnings))))]
|
#![doc(test(attr(deny(warnings))))]
|
||||||
|
#![cfg_attr(not(bootstrap), doc(rust_logo))]
|
||||||
|
#![cfg_attr(not(bootstrap), feature(rustdoc_internals))]
|
||||||
#![feature(internal_output_capture)]
|
#![feature(internal_output_capture)]
|
||||||
#![feature(staged_api)]
|
#![feature(staged_api)]
|
||||||
#![feature(process_exitcode_internals)]
|
#![feature(process_exitcode_internals)]
|
||||||
|
|
|
@ -207,6 +207,21 @@ To do so, the `#[doc(keyword = "...")]` attribute is used. Example:
|
||||||
mod empty_mod {}
|
mod empty_mod {}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Use the Rust logo as the crate logo
|
||||||
|
|
||||||
|
This is for official Rust project use only.
|
||||||
|
|
||||||
|
Internal Rustdoc pages like settings.html and scrape-examples-help.html show the Rust logo.
|
||||||
|
This logo is tracked as a static resource. The attribute `#![doc(rust_logo)]` makes this same
|
||||||
|
built-in resource act as the main logo.
|
||||||
|
|
||||||
|
```rust
|
||||||
|
#![feature(rustdoc_internals)]
|
||||||
|
#![allow(internal_features)]
|
||||||
|
#![doc(rust_logo)]
|
||||||
|
//! This crate has the Rust(tm) branding on it.
|
||||||
|
```
|
||||||
|
|
||||||
## Effects of other nightly features
|
## Effects of other nightly features
|
||||||
|
|
||||||
These nightly-only features are not primarily related to Rustdoc,
|
These nightly-only features are not primarily related to Rustdoc,
|
||||||
|
|
|
@ -17,6 +17,7 @@ pub(crate) struct Layout {
|
||||||
pub(crate) external_html: ExternalHtml,
|
pub(crate) external_html: ExternalHtml,
|
||||||
pub(crate) default_settings: FxHashMap<String, String>,
|
pub(crate) default_settings: FxHashMap<String, String>,
|
||||||
pub(crate) krate: String,
|
pub(crate) krate: String,
|
||||||
|
pub(crate) krate_version: String,
|
||||||
/// The given user css file which allow to customize the generated
|
/// The given user css file which allow to customize the generated
|
||||||
/// documentation theme.
|
/// documentation theme.
|
||||||
pub(crate) css_file_extension: Option<PathBuf>,
|
pub(crate) css_file_extension: Option<PathBuf>,
|
||||||
|
@ -31,6 +32,7 @@ pub(crate) struct Page<'a> {
|
||||||
pub(crate) static_root_path: Option<&'a str>,
|
pub(crate) static_root_path: Option<&'a str>,
|
||||||
pub(crate) description: &'a str,
|
pub(crate) description: &'a str,
|
||||||
pub(crate) resource_suffix: &'a str,
|
pub(crate) resource_suffix: &'a str,
|
||||||
|
pub(crate) rust_logo: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> Page<'a> {
|
impl<'a> Page<'a> {
|
||||||
|
@ -54,9 +56,19 @@ struct PageLayout<'a> {
|
||||||
themes: Vec<String>,
|
themes: Vec<String>,
|
||||||
sidebar: String,
|
sidebar: String,
|
||||||
content: String,
|
content: String,
|
||||||
krate_with_trailing_slash: String,
|
|
||||||
rust_channel: &'static str,
|
rust_channel: &'static str,
|
||||||
pub(crate) rustdoc_version: &'a str,
|
pub(crate) rustdoc_version: &'a str,
|
||||||
|
// same as layout.krate, except on top-level pages like
|
||||||
|
// Settings, Help, All Crates, and About Scraped Examples,
|
||||||
|
// where these things instead give Rustdoc name and version.
|
||||||
|
//
|
||||||
|
// These are separate from the variables used for the search
|
||||||
|
// engine, because "Rustdoc" isn't necessarily a crate in
|
||||||
|
// the current workspace.
|
||||||
|
display_krate: &'a str,
|
||||||
|
display_krate_with_trailing_slash: String,
|
||||||
|
display_krate_version_number: &'a str,
|
||||||
|
display_krate_version_extra: &'a str,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn render<T: Print, S: Print>(
|
pub(crate) fn render<T: Print, S: Print>(
|
||||||
|
@ -66,12 +78,26 @@ pub(crate) fn render<T: Print, S: Print>(
|
||||||
t: T,
|
t: T,
|
||||||
style_files: &[StylePath],
|
style_files: &[StylePath],
|
||||||
) -> String {
|
) -> String {
|
||||||
|
let rustdoc_version = rustc_interface::util::version_str!().unwrap_or("unknown version");
|
||||||
|
|
||||||
|
let (display_krate, display_krate_version, display_krate_with_trailing_slash) =
|
||||||
|
if page.root_path == "./" {
|
||||||
|
// top level pages use Rust branding
|
||||||
|
("Rustdoc", rustdoc_version, String::new())
|
||||||
|
} else {
|
||||||
|
let display_krate_with_trailing_slash =
|
||||||
|
ensure_trailing_slash(&layout.krate).to_string();
|
||||||
|
(&layout.krate[..], &layout.krate_version[..], display_krate_with_trailing_slash)
|
||||||
|
};
|
||||||
let static_root_path = page.get_static_root_path();
|
let static_root_path = page.get_static_root_path();
|
||||||
let krate_with_trailing_slash = ensure_trailing_slash(&layout.krate).to_string();
|
|
||||||
|
// bootstrap passes in parts of the version separated by tabs, but other stuff might use spaces
|
||||||
|
let (display_krate_version_number, display_krate_version_extra) =
|
||||||
|
display_krate_version.split_once([' ', '\t']).unwrap_or((display_krate_version, ""));
|
||||||
|
|
||||||
let mut themes: Vec<String> = style_files.iter().map(|s| s.basename().unwrap()).collect();
|
let mut themes: Vec<String> = style_files.iter().map(|s| s.basename().unwrap()).collect();
|
||||||
themes.sort();
|
themes.sort();
|
||||||
|
|
||||||
let rustdoc_version = rustc_interface::util::version_str!().unwrap_or("unknown version");
|
|
||||||
let content = Buffer::html().to_display(t); // Note: This must happen before making the sidebar.
|
let content = Buffer::html().to_display(t); // Note: This must happen before making the sidebar.
|
||||||
let sidebar = Buffer::html().to_display(sidebar);
|
let sidebar = Buffer::html().to_display(sidebar);
|
||||||
PageLayout {
|
PageLayout {
|
||||||
|
@ -82,7 +108,10 @@ pub(crate) fn render<T: Print, S: Print>(
|
||||||
themes,
|
themes,
|
||||||
sidebar,
|
sidebar,
|
||||||
content,
|
content,
|
||||||
krate_with_trailing_slash,
|
display_krate,
|
||||||
|
display_krate_with_trailing_slash,
|
||||||
|
display_krate_version_number,
|
||||||
|
display_krate_version_extra,
|
||||||
rust_channel: *crate::clean::utils::DOC_CHANNEL,
|
rust_channel: *crate::clean::utils::DOC_CHANNEL,
|
||||||
rustdoc_version,
|
rustdoc_version,
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,6 +24,7 @@ use super::{
|
||||||
sidebar::{sidebar_module_like, Sidebar},
|
sidebar::{sidebar_module_like, Sidebar},
|
||||||
AllTypes, LinkFromSrc, StylePath,
|
AllTypes, LinkFromSrc, StylePath,
|
||||||
};
|
};
|
||||||
|
use crate::clean::utils::has_doc_flag;
|
||||||
use crate::clean::{self, types::ExternalLocation, ExternalCrate, TypeAliasItem};
|
use crate::clean::{self, types::ExternalLocation, ExternalCrate, TypeAliasItem};
|
||||||
use crate::config::{ModuleSorting, RenderOptions};
|
use crate::config::{ModuleSorting, RenderOptions};
|
||||||
use crate::docfs::{DocFS, PathError};
|
use crate::docfs::{DocFS, PathError};
|
||||||
|
@ -277,6 +278,7 @@ impl<'tcx> Context<'tcx> {
|
||||||
title: &title,
|
title: &title,
|
||||||
description: &desc,
|
description: &desc,
|
||||||
resource_suffix: &clone_shared.resource_suffix,
|
resource_suffix: &clone_shared.resource_suffix,
|
||||||
|
rust_logo: has_doc_flag(self.tcx(), LOCAL_CRATE.as_def_id(), sym::rust_logo),
|
||||||
};
|
};
|
||||||
let mut page_buffer = Buffer::html();
|
let mut page_buffer = Buffer::html();
|
||||||
print_item(self, it, &mut page_buffer, &page);
|
print_item(self, it, &mut page_buffer, &page);
|
||||||
|
@ -528,12 +530,14 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
||||||
if let Some(url) = playground_url {
|
if let Some(url) = playground_url {
|
||||||
playground = Some(markdown::Playground { crate_name: Some(krate.name(tcx)), url });
|
playground = Some(markdown::Playground { crate_name: Some(krate.name(tcx)), url });
|
||||||
}
|
}
|
||||||
|
let krate_version = cache.crate_version.as_deref().unwrap_or_default();
|
||||||
let mut layout = layout::Layout {
|
let mut layout = layout::Layout {
|
||||||
logo: String::new(),
|
logo: String::new(),
|
||||||
favicon: String::new(),
|
favicon: String::new(),
|
||||||
external_html,
|
external_html,
|
||||||
default_settings,
|
default_settings,
|
||||||
krate: krate.name(tcx).to_string(),
|
krate: krate.name(tcx).to_string(),
|
||||||
|
krate_version: krate_version.to_string(),
|
||||||
css_file_extension: extension_css,
|
css_file_extension: extension_css,
|
||||||
scrape_examples_extension: !call_locations.is_empty(),
|
scrape_examples_extension: !call_locations.is_empty(),
|
||||||
};
|
};
|
||||||
|
@ -658,21 +662,22 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
||||||
let shared = Rc::clone(&self.shared);
|
let shared = Rc::clone(&self.shared);
|
||||||
let mut page = layout::Page {
|
let mut page = layout::Page {
|
||||||
title: "List of all items in this crate",
|
title: "List of all items in this crate",
|
||||||
css_class: "mod",
|
css_class: "mod sys",
|
||||||
root_path: "../",
|
root_path: "../",
|
||||||
static_root_path: shared.static_root_path.as_deref(),
|
static_root_path: shared.static_root_path.as_deref(),
|
||||||
description: "List of all items in this crate",
|
description: "List of all items in this crate",
|
||||||
resource_suffix: &shared.resource_suffix,
|
resource_suffix: &shared.resource_suffix,
|
||||||
|
rust_logo: has_doc_flag(self.tcx(), LOCAL_CRATE.as_def_id(), sym::rust_logo),
|
||||||
};
|
};
|
||||||
let all = shared.all.replace(AllTypes::new());
|
let all = shared.all.replace(AllTypes::new());
|
||||||
let mut sidebar = Buffer::html();
|
let mut sidebar = Buffer::html();
|
||||||
|
|
||||||
let blocks = sidebar_module_like(all.item_sections());
|
let blocks = sidebar_module_like(all.item_sections());
|
||||||
let bar = Sidebar {
|
let bar = Sidebar {
|
||||||
title_prefix: "Crate ",
|
title_prefix: "",
|
||||||
title: crate_name.as_str(),
|
title: "",
|
||||||
is_crate: false,
|
is_crate: false,
|
||||||
version: "",
|
is_mod: false,
|
||||||
blocks: vec![blocks],
|
blocks: vec![blocks],
|
||||||
path: String::new(),
|
path: String::new(),
|
||||||
};
|
};
|
||||||
|
@ -689,9 +694,10 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
||||||
shared.fs.write(final_file, v)?;
|
shared.fs.write(final_file, v)?;
|
||||||
|
|
||||||
// Generating settings page.
|
// Generating settings page.
|
||||||
page.title = "Rustdoc settings";
|
page.title = "Settings";
|
||||||
page.description = "Settings of Rustdoc";
|
page.description = "Settings of Rustdoc";
|
||||||
page.root_path = "./";
|
page.root_path = "./";
|
||||||
|
page.rust_logo = true;
|
||||||
|
|
||||||
let sidebar = "<h2 class=\"location\">Settings</h2><div class=\"sidebar-elems\"></div>";
|
let sidebar = "<h2 class=\"location\">Settings</h2><div class=\"sidebar-elems\"></div>";
|
||||||
let v = layout::render(
|
let v = layout::render(
|
||||||
|
@ -739,9 +745,10 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
||||||
shared.fs.write(settings_file, v)?;
|
shared.fs.write(settings_file, v)?;
|
||||||
|
|
||||||
// Generating help page.
|
// Generating help page.
|
||||||
page.title = "Rustdoc help";
|
page.title = "Help";
|
||||||
page.description = "Documentation for Rustdoc";
|
page.description = "Documentation for Rustdoc";
|
||||||
page.root_path = "./";
|
page.root_path = "./";
|
||||||
|
page.rust_logo = true;
|
||||||
|
|
||||||
let sidebar = "<h2 class=\"location\">Help</h2><div class=\"sidebar-elems\"></div>";
|
let sidebar = "<h2 class=\"location\">Help</h2><div class=\"sidebar-elems\"></div>";
|
||||||
let v = layout::render(
|
let v = layout::render(
|
||||||
|
|
|
@ -2094,6 +2094,7 @@ impl ItemSection {
|
||||||
const ALL: &'static [Self] = {
|
const ALL: &'static [Self] = {
|
||||||
use ItemSection::*;
|
use ItemSection::*;
|
||||||
// NOTE: The order here affects the order in the UI.
|
// NOTE: The order here affects the order in the UI.
|
||||||
|
// Keep this synchronized with addSidebarItems in main.js
|
||||||
&[
|
&[
|
||||||
Reexports,
|
Reexports,
|
||||||
PrimitiveTypes,
|
PrimitiveTypes,
|
||||||
|
|
|
@ -19,7 +19,7 @@ pub(super) struct Sidebar<'a> {
|
||||||
pub(super) title_prefix: &'static str,
|
pub(super) title_prefix: &'static str,
|
||||||
pub(super) title: &'a str,
|
pub(super) title: &'a str,
|
||||||
pub(super) is_crate: bool,
|
pub(super) is_crate: bool,
|
||||||
pub(super) version: &'a str,
|
pub(super) is_mod: bool,
|
||||||
pub(super) blocks: Vec<LinkBlock<'a>>,
|
pub(super) blocks: Vec<LinkBlock<'a>>,
|
||||||
pub(super) path: String,
|
pub(super) path: String,
|
||||||
}
|
}
|
||||||
|
@ -99,12 +99,12 @@ pub(super) fn print_sidebar(cx: &Context<'_>, it: &clean::Item, buffer: &mut Buf
|
||||||
|| it.is_primitive()
|
|| it.is_primitive()
|
||||||
|| it.is_union()
|
|| it.is_union()
|
||||||
|| it.is_enum()
|
|| it.is_enum()
|
||||||
|| it.is_mod()
|
// crate title is displayed as part of logo lockup
|
||||||
|
|| (it.is_mod() && !it.is_crate())
|
||||||
|| it.is_type_alias()
|
|| it.is_type_alias()
|
||||||
{
|
{
|
||||||
(
|
(
|
||||||
match *it.kind {
|
match *it.kind {
|
||||||
clean::ModuleItem(..) if it.is_crate() => "Crate ",
|
|
||||||
clean::ModuleItem(..) => "Module ",
|
clean::ModuleItem(..) => "Module ",
|
||||||
_ => "",
|
_ => "",
|
||||||
},
|
},
|
||||||
|
@ -113,14 +113,22 @@ pub(super) fn print_sidebar(cx: &Context<'_>, it: &clean::Item, buffer: &mut Buf
|
||||||
} else {
|
} else {
|
||||||
("", "")
|
("", "")
|
||||||
};
|
};
|
||||||
let version =
|
// need to show parent path header if:
|
||||||
if it.is_crate() { cx.cache().crate_version.as_deref().unwrap_or_default() } else { "" };
|
// - it's a child module, instead of the crate root
|
||||||
let path: String = if !it.is_mod() {
|
// - there's a sidebar section for the item itself
|
||||||
cx.current.iter().map(|s| s.as_str()).intersperse("::").collect()
|
//
|
||||||
|
// otherwise, the parent path header is redundant with the big crate
|
||||||
|
// branding area at the top of the sidebar
|
||||||
|
let sidebar_path =
|
||||||
|
if it.is_mod() { &cx.current[..cx.current.len() - 1] } else { &cx.current[..] };
|
||||||
|
let path: String = if sidebar_path.len() > 1 || !title.is_empty() {
|
||||||
|
let path = sidebar_path.iter().map(|s| s.as_str()).intersperse("::").collect();
|
||||||
|
if sidebar_path.len() == 1 { format!("crate {path}") } else { path }
|
||||||
} else {
|
} else {
|
||||||
"".into()
|
"".into()
|
||||||
};
|
};
|
||||||
let sidebar = Sidebar { title_prefix, title, is_crate: it.is_crate(), version, blocks, path };
|
let sidebar =
|
||||||
|
Sidebar { title_prefix, title, is_mod: it.is_mod(), is_crate: it.is_crate(), blocks, path };
|
||||||
sidebar.render_into(buffer).unwrap();
|
sidebar.render_into(buffer).unwrap();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -336,11 +336,12 @@ if (typeof exports !== 'undefined') {exports.searchIndex = searchIndex};
|
||||||
let dst = cx.dst.join("index.html");
|
let dst = cx.dst.join("index.html");
|
||||||
let page = layout::Page {
|
let page = layout::Page {
|
||||||
title: "Index of crates",
|
title: "Index of crates",
|
||||||
css_class: "mod",
|
css_class: "mod sys",
|
||||||
root_path: "./",
|
root_path: "./",
|
||||||
static_root_path: shared.static_root_path.as_deref(),
|
static_root_path: shared.static_root_path.as_deref(),
|
||||||
description: "List of crates",
|
description: "List of crates",
|
||||||
resource_suffix: &shared.resource_suffix,
|
resource_suffix: &shared.resource_suffix,
|
||||||
|
rust_logo: true,
|
||||||
};
|
};
|
||||||
|
|
||||||
let content = format!(
|
let content = format!(
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
use crate::clean;
|
use crate::clean;
|
||||||
|
use crate::clean::utils::has_doc_flag;
|
||||||
use crate::docfs::PathError;
|
use crate::docfs::PathError;
|
||||||
use crate::error::Error;
|
use crate::error::Error;
|
||||||
use crate::html::format;
|
use crate::html::format;
|
||||||
|
@ -13,6 +14,7 @@ use rustc_hir::def_id::LOCAL_CRATE;
|
||||||
use rustc_middle::ty::TyCtxt;
|
use rustc_middle::ty::TyCtxt;
|
||||||
use rustc_session::Session;
|
use rustc_session::Session;
|
||||||
use rustc_span::source_map::FileName;
|
use rustc_span::source_map::FileName;
|
||||||
|
use rustc_span::sym;
|
||||||
|
|
||||||
use std::cell::RefCell;
|
use std::cell::RefCell;
|
||||||
use std::ffi::OsStr;
|
use std::ffi::OsStr;
|
||||||
|
@ -231,6 +233,7 @@ impl SourceCollector<'_, '_> {
|
||||||
static_root_path: shared.static_root_path.as_deref(),
|
static_root_path: shared.static_root_path.as_deref(),
|
||||||
description: &desc,
|
description: &desc,
|
||||||
resource_suffix: &shared.resource_suffix,
|
resource_suffix: &shared.resource_suffix,
|
||||||
|
rust_logo: has_doc_flag(self.cx.tcx(), LOCAL_CRATE.as_def_id(), sym::rust_logo),
|
||||||
};
|
};
|
||||||
let v = layout::render(
|
let v = layout::render(
|
||||||
&shared.layout,
|
&shared.layout,
|
||||||
|
|
|
@ -461,19 +461,9 @@ img {
|
||||||
display: none !important;
|
display: none !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
.sidebar .logo-container {
|
|
||||||
margin-top: 10px;
|
|
||||||
margin-bottom: 10px;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.version {
|
|
||||||
overflow-wrap: break-word;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo-container > img {
|
.logo-container > img {
|
||||||
height: 100px;
|
height: 48px;
|
||||||
width: 100px;
|
width: 48px;
|
||||||
}
|
}
|
||||||
|
|
||||||
ul.block, .block li {
|
ul.block, .block li {
|
||||||
|
@ -502,6 +492,7 @@ ul.block, .block li {
|
||||||
}
|
}
|
||||||
|
|
||||||
.sidebar-elems,
|
.sidebar-elems,
|
||||||
|
.sidebar > .version,
|
||||||
.sidebar > h2 {
|
.sidebar > h2 {
|
||||||
padding-left: 24px;
|
padding-left: 24px;
|
||||||
}
|
}
|
||||||
|
@ -510,6 +501,8 @@ ul.block, .block li {
|
||||||
color: var(--sidebar-link-color);
|
color: var(--sidebar-link-color);
|
||||||
}
|
}
|
||||||
.sidebar .current,
|
.sidebar .current,
|
||||||
|
.sidebar .current a,
|
||||||
|
.sidebar-crate a.logo-container:hover + h2 a,
|
||||||
.sidebar a:hover:not(.logo-container) {
|
.sidebar a:hover:not(.logo-container) {
|
||||||
background-color: var(--sidebar-current-link-background-color);
|
background-color: var(--sidebar-current-link-background-color);
|
||||||
}
|
}
|
||||||
|
@ -524,6 +517,75 @@ ul.block, .block li {
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.sidebar-crate {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
/* there's a 10px padding at the top of <main>, and a 4px margin at the
|
||||||
|
top of the search form. To line them up, add them. */
|
||||||
|
margin: 14px 32px 1rem;
|
||||||
|
row-gap: 10px;
|
||||||
|
column-gap: 32px;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar-crate h2 {
|
||||||
|
flex-grow: 1;
|
||||||
|
/* This setup with the margins and row-gap is designed to make flex-wrap
|
||||||
|
work the way we want. If they're in the side-by-side lockup, there
|
||||||
|
should be a 16px margin to the left of the logo (visually the same as
|
||||||
|
the 24px one on everything else, which are not giant circles) and 8px
|
||||||
|
between it and the crate's name and version. When they're line wrapped,
|
||||||
|
the logo needs to have the same margin on both sides of itself (to
|
||||||
|
center properly) and the crate name and version need 24px on their
|
||||||
|
left margin. */
|
||||||
|
margin: 0 -8px;
|
||||||
|
/* To align this with the search bar, it should not be centered, even when
|
||||||
|
the logo is. */
|
||||||
|
align-self: start;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar-crate .logo-container {
|
||||||
|
/* The logo is expected to have 8px "slop" along its edges, so we can optically
|
||||||
|
center it. */
|
||||||
|
margin: 0 -16px 0 -16px;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar-crate h2 a {
|
||||||
|
display: block;
|
||||||
|
margin: 0 calc(-24px + 0.25rem) 0 -0.5rem;
|
||||||
|
/* Align the sidebar crate link with the search bar, which have different
|
||||||
|
font sizes.
|
||||||
|
|
||||||
|
| | font-size | line-height | total line-height | padding-y | total |
|
||||||
|
|:-------|----------:|------------:|------------------:|----------:|-------------:|
|
||||||
|
| crate | 1.375rem | 1.25 | 1.72rem | x | 2x+1.72rem |
|
||||||
|
| search | 1rem | 1.15 | 1.15rem | 8px | 1.15rem+16px |
|
||||||
|
|
||||||
|
2x + 1.72rem = 1.15rem + 16px
|
||||||
|
2x = 1.15rem + 16px - 1.72rem
|
||||||
|
2x = 16px - 0.57rem
|
||||||
|
x = ( 16px - 0.57rem ) / 2
|
||||||
|
*/
|
||||||
|
padding: calc( ( 16px - 0.57rem ) / 2 ) 0.25rem;
|
||||||
|
padding-left: 0.5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar-crate h2 .version {
|
||||||
|
display: block;
|
||||||
|
font-weight: normal;
|
||||||
|
font-size: 1rem;
|
||||||
|
overflow-wrap: break-word;
|
||||||
|
/* opposite of the link padding, cut in half again */
|
||||||
|
margin-top: calc( ( -16px + 0.57rem ) / 2 );
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar-crate + .version {
|
||||||
|
margin-top: -1rem;
|
||||||
|
margin-bottom: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
.mobile-topbar {
|
.mobile-topbar {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
|
|
@ -51,9 +51,14 @@ function setMobileTopbar() {
|
||||||
// but with the current code it's hard to get the right information in the right place.
|
// but with the current code it's hard to get the right information in the right place.
|
||||||
const mobileTopbar = document.querySelector(".mobile-topbar");
|
const mobileTopbar = document.querySelector(".mobile-topbar");
|
||||||
const locationTitle = document.querySelector(".sidebar h2.location");
|
const locationTitle = document.querySelector(".sidebar h2.location");
|
||||||
if (mobileTopbar && locationTitle) {
|
if (mobileTopbar) {
|
||||||
const mobileTitle = document.createElement("h2");
|
const mobileTitle = document.createElement("h2");
|
||||||
mobileTitle.innerHTML = locationTitle.innerHTML;
|
mobileTitle.className = "location";
|
||||||
|
if (hasClass(document.body, "crate")) {
|
||||||
|
mobileTitle.innerText = `Crate ${window.currentCrate}`;
|
||||||
|
} else if (locationTitle) {
|
||||||
|
mobileTitle.innerHTML = locationTitle.innerHTML;
|
||||||
|
}
|
||||||
mobileTopbar.appendChild(mobileTitle);
|
mobileTopbar.appendChild(mobileTitle);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -480,22 +485,27 @@ function preLoadCss(cssUrl) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const modpath = hasClass(document.body, "mod") ? "../" : "";
|
||||||
|
|
||||||
const h3 = document.createElement("h3");
|
const h3 = document.createElement("h3");
|
||||||
h3.innerHTML = `<a href="index.html#${id}">${longty}</a>`;
|
h3.innerHTML = `<a href="${modpath}index.html#${id}">${longty}</a>`;
|
||||||
const ul = document.createElement("ul");
|
const ul = document.createElement("ul");
|
||||||
ul.className = "block " + shortty;
|
ul.className = "block " + shortty;
|
||||||
|
|
||||||
for (const name of filtered) {
|
for (const name of filtered) {
|
||||||
let path;
|
let path;
|
||||||
if (shortty === "mod") {
|
if (shortty === "mod") {
|
||||||
path = name + "/index.html";
|
path = `${modpath}${name}/index.html`;
|
||||||
} else {
|
} else {
|
||||||
path = shortty + "." + name + ".html";
|
path = `${modpath}${shortty}.${name}.html`;
|
||||||
|
}
|
||||||
|
let current_page = document.location.href.toString();
|
||||||
|
if (current_page.endsWith("/")) {
|
||||||
|
current_page += "index.html";
|
||||||
}
|
}
|
||||||
const current_page = document.location.href.split("/").pop();
|
|
||||||
const link = document.createElement("a");
|
const link = document.createElement("a");
|
||||||
link.href = path;
|
link.href = path;
|
||||||
if (path === current_page) {
|
if (link.href === current_page) {
|
||||||
link.className = "current";
|
link.className = "current";
|
||||||
}
|
}
|
||||||
link.textContent = name;
|
link.textContent = name;
|
||||||
|
@ -508,19 +518,33 @@ function preLoadCss(cssUrl) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sidebar) {
|
if (sidebar) {
|
||||||
|
// keep this synchronized with ItemSection::ALL in html/render/mod.rs
|
||||||
|
// Re-exports aren't shown here, because they don't have child pages
|
||||||
|
//block("reexport", "reexports", "Re-exports");
|
||||||
block("primitive", "primitives", "Primitive Types");
|
block("primitive", "primitives", "Primitive Types");
|
||||||
block("mod", "modules", "Modules");
|
block("mod", "modules", "Modules");
|
||||||
block("macro", "macros", "Macros");
|
block("macro", "macros", "Macros");
|
||||||
block("struct", "structs", "Structs");
|
block("struct", "structs", "Structs");
|
||||||
block("enum", "enums", "Enums");
|
block("enum", "enums", "Enums");
|
||||||
block("union", "unions", "Unions");
|
|
||||||
block("constant", "constants", "Constants");
|
block("constant", "constants", "Constants");
|
||||||
block("static", "static", "Statics");
|
block("static", "static", "Statics");
|
||||||
block("trait", "traits", "Traits");
|
block("trait", "traits", "Traits");
|
||||||
block("fn", "functions", "Functions");
|
block("fn", "functions", "Functions");
|
||||||
block("type", "types", "Type Aliases");
|
block("type", "types", "Type Aliases");
|
||||||
|
block("union", "unions", "Unions");
|
||||||
|
// No point, because these items don't appear in modules
|
||||||
|
//block("impl", "impls", "Implementations");
|
||||||
|
//block("tymethod", "tymethods", "Type Methods");
|
||||||
|
//block("method", "methods", "Methods");
|
||||||
|
//block("structfield", "fields", "Fields");
|
||||||
|
//block("variant", "variants", "Variants");
|
||||||
|
//block("associatedtype", "associated-types", "Associated Types");
|
||||||
|
//block("associatedconstant", "associated-consts", "Associated Constants");
|
||||||
block("foreigntype", "foreign-types", "Foreign Types");
|
block("foreigntype", "foreign-types", "Foreign Types");
|
||||||
block("keyword", "keywords", "Keywords");
|
block("keyword", "keywords", "Keywords");
|
||||||
|
block("opaque", "opaque-types", "Opaque Types");
|
||||||
|
block("attr", "attributes", "Attribute Macros");
|
||||||
|
block("derive", "derives", "Derive Macros");
|
||||||
block("traitalias", "trait-aliases", "Trait Aliases");
|
block("traitalias", "trait-aliases", "Trait Aliases");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,6 +42,8 @@
|
||||||
<script defer src="{{page.root_path|safe}}src-files{{page.resource_suffix}}.js"></script> {# #}
|
<script defer src="{{page.root_path|safe}}src-files{{page.resource_suffix}}.js"></script> {# #}
|
||||||
{% else if !page.css_class.contains("mod") %}
|
{% else if !page.css_class.contains("mod") %}
|
||||||
<script defer src="sidebar-items{{page.resource_suffix}}.js"></script> {# #}
|
<script defer src="sidebar-items{{page.resource_suffix}}.js"></script> {# #}
|
||||||
|
{% else if !page.css_class.contains("sys") %}
|
||||||
|
<script defer src="../sidebar-items{{page.resource_suffix}}.js"></script> {# #}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
<script defer src="{{static_root_path|safe}}{{files.main_js}}"></script> {# #}
|
<script defer src="{{static_root_path|safe}}{{files.main_js}}"></script> {# #}
|
||||||
{% if layout.scrape_examples_extension %}
|
{% if layout.scrape_examples_extension %}
|
||||||
|
@ -77,36 +79,51 @@
|
||||||
{% if page.css_class != "src" %}
|
{% if page.css_class != "src" %}
|
||||||
<nav class="mobile-topbar"> {# #}
|
<nav class="mobile-topbar"> {# #}
|
||||||
<button class="sidebar-menu-toggle">☰</button> {# #}
|
<button class="sidebar-menu-toggle">☰</button> {# #}
|
||||||
<a class="logo-container" href="{{page.root_path|safe}}{{krate_with_trailing_slash|safe}}index.html"> {# #}
|
{% if !layout.logo.is_empty() || page.rust_logo %}
|
||||||
{% if !layout.logo.is_empty() %}
|
<a class="logo-container" href="{{page.root_path|safe}}{{display_krate_with_trailing_slash|safe}}index.html"> {# #}
|
||||||
<img src="{{layout.logo}}" alt="logo"> {# #}
|
{% if page.rust_logo %}
|
||||||
{% else %}
|
<img class="rust-logo" src="{{static_root_path|safe}}{{files.rust_logo_svg}}" alt=""> {# #}
|
||||||
<img class="rust-logo" src="{{static_root_path|safe}}{{files.rust_logo_svg}}" alt="logo"> {# #}
|
{% else if !layout.logo.is_empty() %}
|
||||||
|
<img src="{{layout.logo}}" alt=""> {# #}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</a> {# #}
|
</a> {# #}
|
||||||
|
{% endif %}
|
||||||
</nav>
|
</nav>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
<nav class="sidebar"> {# #}
|
<nav class="sidebar"> {# #}
|
||||||
{% if page.css_class != "src" %}
|
{% if page.css_class != "src" %}
|
||||||
<a class="logo-container" href="{{page.root_path|safe}}{{krate_with_trailing_slash|safe}}index.html"> {# #}
|
<div class="sidebar-crate">
|
||||||
{% if !layout.logo.is_empty() %}
|
{% if !layout.logo.is_empty() || page.rust_logo %}
|
||||||
<img src="{{layout.logo}}" alt="logo"> {# #}
|
<a class="logo-container" href="{{page.root_path|safe}}{{display_krate_with_trailing_slash|safe}}index.html"> {# #}
|
||||||
{% else %}
|
{% if page.rust_logo %}
|
||||||
<img class="rust-logo" src="{{static_root_path|safe}}{{files.rust_logo_svg}}" alt="logo"> {# #}
|
<img class="rust-logo" src="{{static_root_path|safe}}{{files.rust_logo_svg}}" alt="logo"> {# #}
|
||||||
|
{% else if !layout.logo.is_empty() %}
|
||||||
|
<img src="{{layout.logo}}" alt="logo"> {# #}
|
||||||
|
{% endif %}
|
||||||
|
</a> {# #}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</a> {# #}
|
<h2> {# #}
|
||||||
|
<a href="{{page.root_path|safe}}{{display_krate_with_trailing_slash|safe}}index.html">{{display_krate}}</a> {# #}
|
||||||
|
{% if !display_krate_version_number.is_empty() %}
|
||||||
|
<span class="version">{{+ display_krate_version_number}}</span>
|
||||||
|
{% endif %}
|
||||||
|
</h2> {# #}
|
||||||
|
</div> {# #}
|
||||||
|
{% if !display_krate_version_extra.is_empty() %}
|
||||||
|
<div class="version">{{+ display_krate_version_extra}}</div> {# #}
|
||||||
|
{% endif %}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
{{ sidebar|safe }}
|
{{ sidebar|safe }}
|
||||||
</nav> {# #}
|
</nav> {# #}
|
||||||
<main> {# #}
|
<main> {# #}
|
||||||
{% if page.css_class != "src" %}<div class="width-limiter">{% endif %}
|
{% if page.css_class != "src" %}<div class="width-limiter">{% endif %}
|
||||||
<nav class="sub"> {# #}
|
<nav class="sub"> {# #}
|
||||||
{% if page.css_class == "src" %}
|
{% if page.css_class == "src" && (!layout.logo.is_empty() || page.rust_logo) %}
|
||||||
<a class="sub-logo-container" href="{{page.root_path|safe}}{{krate_with_trailing_slash|safe}}index.html"> {# #}
|
<a class="sub-logo-container" href="{{page.root_path|safe}}{{display_krate_with_trailing_slash|safe}}index.html"> {# #}
|
||||||
{% if !layout.logo.is_empty() %}
|
{% if page.rust_logo %}
|
||||||
<img src="{{layout.logo}}" alt="logo"> {# #}
|
<img class="rust-logo" src="{{static_root_path|safe}}{{files.rust_logo_svg}}" alt="{{display_krate}}"> {# #}
|
||||||
{% else %}
|
{% else if !layout.logo.is_empty() %}
|
||||||
<img class="rust-logo" src="{{static_root_path|safe}}{{files.rust_logo_svg}}" alt="logo"> {# #}
|
<img src="{{layout.logo}}" alt="{{display_krate}}"> {# #}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</a> {# #}
|
</a> {# #}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
|
|
@ -6,9 +6,6 @@
|
||||||
<div class="sidebar-elems">
|
<div class="sidebar-elems">
|
||||||
{% if is_crate %}
|
{% if is_crate %}
|
||||||
<ul class="block">
|
<ul class="block">
|
||||||
{% if !version.is_empty() %}
|
|
||||||
<li class="version">Version {{+ version}}</li>
|
|
||||||
{% endif %}
|
|
||||||
<li><a id="all-types" href="all.html">All Items</a></li> {# #}
|
<li><a id="all-types" href="all.html">All Items</a></li> {# #}
|
||||||
</ul>
|
</ul>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
@ -32,6 +29,6 @@
|
||||||
</section>
|
</section>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
{% if !path.is_empty() %}
|
{% if !path.is_empty() %}
|
||||||
<h2><a href="index.html">In {{+ path}}</a></h2>
|
<h2><a href="{% if is_mod %}../{% endif %}index.html">In {{+ path}}</a></h2>
|
||||||
{% endif %}
|
{% endif %}
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -322,7 +322,15 @@ impl TestProps {
|
||||||
);
|
);
|
||||||
|
|
||||||
if let Some(flags) = config.parse_name_value_directive(ln, COMPILE_FLAGS) {
|
if let Some(flags) = config.parse_name_value_directive(ln, COMPILE_FLAGS) {
|
||||||
self.compile_flags.extend(flags.split_whitespace().map(|s| s.to_owned()));
|
self.compile_flags.extend(
|
||||||
|
flags
|
||||||
|
.split("'")
|
||||||
|
.enumerate()
|
||||||
|
.flat_map(|(i, f)| {
|
||||||
|
if i % 2 == 1 { vec![f] } else { f.split_whitespace().collect() }
|
||||||
|
})
|
||||||
|
.map(|s| s.to_owned()),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
if config.parse_name_value_directive(ln, INCORRECT_COMPILER_FLAGS).is_some() {
|
if config.parse_name_value_directive(ln, INCORRECT_COMPILER_FLAGS).is_some() {
|
||||||
panic!("`compiler-flags` directive should be spelled `compile-flags`");
|
panic!("`compiler-flags` directive should be spelled `compile-flags`");
|
||||||
|
|
|
@ -56,7 +56,7 @@ define-function: (
|
||||||
|
|
||||||
assert-css: ("#top-doc-prose-title", {"color": |title_color|})
|
assert-css: ("#top-doc-prose-title", {"color": |title_color|})
|
||||||
|
|
||||||
assert-css: (".sidebar a", {"color": |sidebar_link_color|})
|
assert-css: (".sidebar .block a", {"color": |sidebar_link_color|})
|
||||||
assert-css: (".main-heading h1 a", {"color": |title_color|})
|
assert-css: (".main-heading h1 a", {"color": |title_color|})
|
||||||
|
|
||||||
// We move the cursor over the "Implementations" title so the anchor is displayed.
|
// We move the cursor over the "Implementations" title so the anchor is displayed.
|
||||||
|
|
|
@ -4,8 +4,8 @@ go-to: "file://" + |DOC_PATH| + "/huge_logo/index.html"
|
||||||
|
|
||||||
set-window-size: (1280, 1024)
|
set-window-size: (1280, 1024)
|
||||||
// offsetWidth = width of sidebar
|
// offsetWidth = width of sidebar
|
||||||
assert-property: (".sidebar .logo-container", {"offsetWidth": "200", "offsetHeight": 100})
|
assert-property: (".sidebar-crate .logo-container", {"offsetWidth": "48", "offsetHeight": 48})
|
||||||
assert-property: (".sidebar .logo-container img", {"offsetWidth": "100", "offsetHeight": 100})
|
assert-property: (".sidebar-crate .logo-container img", {"offsetWidth": "48", "offsetHeight": 48})
|
||||||
|
|
||||||
set-window-size: (400, 600)
|
set-window-size: (400, 600)
|
||||||
// offset = size + margin
|
// offset = size + margin
|
||||||
|
|
|
@ -1,18 +1,18 @@
|
||||||
// This test ensures that the correct style is applied to the rust logo in the sidebar.
|
// This test ensures that the correct style is applied to the rust logo in the sidebar.
|
||||||
go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
|
go-to: "file://" + |DOC_PATH| + "/staged_api/index.html"
|
||||||
|
|
||||||
define-function: (
|
define-function: (
|
||||||
"check-logo",
|
"check-logo",
|
||||||
(theme, filter),
|
(theme, filter),
|
||||||
block {
|
block {
|
||||||
// Going to the doc page.
|
// Going to the doc page.
|
||||||
go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
|
go-to: "file://" + |DOC_PATH| + "/staged_api/index.html"
|
||||||
// Changing theme.
|
// Changing theme.
|
||||||
set-local-storage: {"rustdoc-theme": |theme|, "rustdoc-use-system-theme": "false"}
|
set-local-storage: {"rustdoc-theme": |theme|, "rustdoc-use-system-theme": "false"}
|
||||||
reload:
|
reload:
|
||||||
assert-css: (".rust-logo", {"filter": |filter|})
|
assert-css: (".rust-logo", {"filter": |filter|})
|
||||||
// Going to the source code page.
|
// Going to the source code page.
|
||||||
go-to: "file://" + |DOC_PATH| + "/src/test_docs/lib.rs.html"
|
go-to: "file://" + |DOC_PATH| + "/src/staged_api/lib.rs.html"
|
||||||
// Changing theme (since it's local files, the local storage works by folder).
|
// Changing theme (since it's local files, the local storage works by folder).
|
||||||
set-local-storage: {"rustdoc-theme": |theme|, "rustdoc-use-system-theme": "false"}
|
set-local-storage: {"rustdoc-theme": |theme|, "rustdoc-use-system-theme": "false"}
|
||||||
reload:
|
reload:
|
||||||
|
@ -26,6 +26,15 @@ define-function: (
|
||||||
assert-false: ".rust-logo"
|
assert-false: ".rust-logo"
|
||||||
// Check there is no filter.
|
// Check there is no filter.
|
||||||
assert-css: (".sidebar .logo-container img", {"filter": "none"})
|
assert-css: (".sidebar .logo-container img", {"filter": "none"})
|
||||||
|
// Now we check that this page has no logo at all
|
||||||
|
go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
|
||||||
|
assert-false: ".rust-logo"
|
||||||
|
assert-false: ".logo-container"
|
||||||
|
assert-false: ".sub-logo-container"
|
||||||
|
go-to: "file://" + |DOC_PATH| + "/src/test_docs/lib.rs.html"
|
||||||
|
assert-false: ".rust-logo"
|
||||||
|
assert-false: ".logo-container"
|
||||||
|
assert-false: ".sub-logo-container"
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
|
@ -26,7 +26,7 @@ assert-css: (".sidebar", {"left": "0px"})
|
||||||
// Make sure the "struct Foo" header is hidden, since the mobile topbar already does it.
|
// Make sure the "struct Foo" header is hidden, since the mobile topbar already does it.
|
||||||
assert-css: ("//nav[contains(@class, 'sidebar')]//h2/a[text()='Foo']/parent::h2", {"display": "none"})
|
assert-css: ("//nav[contains(@class, 'sidebar')]//h2/a[text()='Foo']/parent::h2", {"display": "none"})
|
||||||
// Make sure the global navigation is still here.
|
// Make sure the global navigation is still here.
|
||||||
assert-css: ("//nav[contains(@class, 'sidebar')]//h2/a[text()='In test_docs']/parent::h2", {"display": "block"})
|
assert-css: ("//nav[contains(@class, 'sidebar')]//h2/a[text()='In crate test_docs']/parent::h2", {"display": "block"})
|
||||||
|
|
||||||
// Click elsewhere.
|
// Click elsewhere.
|
||||||
click: "body"
|
click: "body"
|
||||||
|
@ -50,7 +50,7 @@ assert-position: ("#method\.must_use", {"y": 46})
|
||||||
// Check that the bottom-most item on the sidebar menu can be scrolled fully into view.
|
// Check that the bottom-most item on the sidebar menu can be scrolled fully into view.
|
||||||
click: ".sidebar-menu-toggle"
|
click: ".sidebar-menu-toggle"
|
||||||
scroll-to: ".block.keyword li:nth-child(1)"
|
scroll-to: ".block.keyword li:nth-child(1)"
|
||||||
compare-elements-position-near: (".block.keyword li:nth-child(1)", ".mobile-topbar", {"y": 543.19})
|
compare-elements-position-near: (".block.keyword li:nth-child(1)", ".mobile-topbar", {"y": 544})
|
||||||
|
|
||||||
// Now checking the background color of the sidebar.
|
// Now checking the background color of the sidebar.
|
||||||
show-text: true
|
show-text: true
|
||||||
|
|
|
@ -174,14 +174,14 @@ click: "#src-sidebar-toggle"
|
||||||
wait-for-css: (".sidebar", {"left": "-1000px"})
|
wait-for-css: (".sidebar", {"left": "-1000px"})
|
||||||
// We scroll to line 117 to change the scroll position.
|
// We scroll to line 117 to change the scroll position.
|
||||||
scroll-to: '//*[@id="117"]'
|
scroll-to: '//*[@id="117"]'
|
||||||
assert-window-property: {"pageYOffset": "2542"}
|
assert-window-property: {"pageYOffset": "2516"}
|
||||||
// Expanding the sidebar...
|
// Expanding the sidebar...
|
||||||
click: "#src-sidebar-toggle"
|
click: "#src-sidebar-toggle"
|
||||||
wait-for-css: (".sidebar", {"left": "0px"})
|
wait-for-css: (".sidebar", {"left": "0px"})
|
||||||
click: "#src-sidebar-toggle"
|
click: "#src-sidebar-toggle"
|
||||||
wait-for-css: (".sidebar", {"left": "-1000px"})
|
wait-for-css: (".sidebar", {"left": "-1000px"})
|
||||||
// The "scrollTop" property should be the same.
|
// The "scrollTop" property should be the same.
|
||||||
assert-window-property: {"pageYOffset": "2542"}
|
assert-window-property: {"pageYOffset": "2516"}
|
||||||
|
|
||||||
// We now check that opening the sidebar and clicking a link will close it.
|
// We now check that opening the sidebar and clicking a link will close it.
|
||||||
// The behavior here on mobile is different than the behavior on desktop,
|
// The behavior here on mobile is different than the behavior on desktop,
|
||||||
|
|
|
@ -50,9 +50,9 @@ set-local-storage: {"rustdoc-theme": "light"}
|
||||||
// We reload the page so the local storage settings are being used.
|
// We reload the page so the local storage settings are being used.
|
||||||
reload:
|
reload:
|
||||||
|
|
||||||
assert-text: (".sidebar > .location", "Crate test_docs")
|
assert-text: (".sidebar > .sidebar-crate > h2 > a", "test_docs")
|
||||||
// In modules, we only have one "location" element.
|
// Crate root has no "location" element
|
||||||
assert-count: (".sidebar .location", 1)
|
assert-count: (".sidebar .location", 0)
|
||||||
assert-count: (".sidebar h2", 1)
|
assert-count: (".sidebar h2", 1)
|
||||||
assert-text: ("#all-types", "All Items")
|
assert-text: ("#all-types", "All Items")
|
||||||
assert-css: ("#all-types", {"color": "#356da4"})
|
assert-css: ("#all-types", {"color": "#356da4"})
|
||||||
|
@ -74,8 +74,9 @@ assert-text: ("#structs + .item-table .item-name > a", "Foo")
|
||||||
click: "#structs + .item-table .item-name > a"
|
click: "#structs + .item-table .item-name > a"
|
||||||
|
|
||||||
// PAGE: struct.Foo.html
|
// PAGE: struct.Foo.html
|
||||||
|
assert-count: (".sidebar .sidebar-crate", 1)
|
||||||
assert-count: (".sidebar .location", 1)
|
assert-count: (".sidebar .location", 1)
|
||||||
assert-count: (".sidebar h2", 2)
|
assert-count: (".sidebar h2", 3)
|
||||||
// We check that there is no crate listed outside of the top level.
|
// We check that there is no crate listed outside of the top level.
|
||||||
assert-false: ".sidebar-elems > .crate"
|
assert-false: ".sidebar-elems > .crate"
|
||||||
|
|
||||||
|
@ -94,7 +95,8 @@ click: ".sidebar-elems ul.crate > li:first-child > a"
|
||||||
// PAGE: lib2/index.html
|
// PAGE: lib2/index.html
|
||||||
go-to: "file://" + |DOC_PATH| + "/lib2/index.html"
|
go-to: "file://" + |DOC_PATH| + "/lib2/index.html"
|
||||||
assert-property: (".sidebar", {"clientWidth": "200"})
|
assert-property: (".sidebar", {"clientWidth": "200"})
|
||||||
assert-text: (".sidebar > .location", "Crate lib2")
|
assert-text: (".sidebar > .sidebar-crate > h2 > a", "lib2")
|
||||||
|
assert-count: (".sidebar .location", 0)
|
||||||
// We check that we have the crates list and that the "current" on is now "lib2".
|
// We check that we have the crates list and that the "current" on is now "lib2".
|
||||||
assert-text: (".sidebar-elems ul.crate > li > a.current", "lib2")
|
assert-text: (".sidebar-elems ul.crate > li > a.current", "lib2")
|
||||||
// We now go to the "foobar" function page.
|
// We now go to the "foobar" function page.
|
||||||
|
@ -108,22 +110,39 @@ click: "#functions + .item-table .item-name > a"
|
||||||
|
|
||||||
// PAGE: fn.foobar.html
|
// PAGE: fn.foobar.html
|
||||||
// In items containing no items (like functions or constants) and in modules, we have no
|
// In items containing no items (like functions or constants) and in modules, we have no
|
||||||
// "location" elements. Only the parent module h2.
|
// "location" elements. Only the crate and optional parent module.
|
||||||
|
// This page, being directly below the crate, only has its heading.
|
||||||
|
assert-text: (".sidebar > .sidebar-crate > h2 > a", "lib2")
|
||||||
assert-count: (".sidebar .location", 0)
|
assert-count: (".sidebar .location", 0)
|
||||||
assert-count: (".sidebar h2", 1)
|
assert-count: (".sidebar h2", 1)
|
||||||
assert-text: (".sidebar .sidebar-elems h2", "In lib2")
|
|
||||||
// We check that we don't have the crate list.
|
// We check that we don't have the crate list.
|
||||||
assert-false: ".sidebar-elems > .crate"
|
assert-false: ".sidebar-elems > .crate"
|
||||||
|
|
||||||
go-to: "./module/index.html"
|
go-to: "./module/index.html"
|
||||||
assert-property: (".sidebar", {"clientWidth": "200"})
|
assert-property: (".sidebar", {"clientWidth": "200"})
|
||||||
|
assert-text: (".sidebar > .sidebar-crate > h2 > a", "lib2")
|
||||||
assert-text: (".sidebar > .location", "Module module")
|
assert-text: (".sidebar > .location", "Module module")
|
||||||
|
assert-count: (".sidebar .location", 1)
|
||||||
|
// Module page requires three headings:
|
||||||
|
// - Presistent crate branding (name and version)
|
||||||
|
// - Module name, followed by TOC for module headings
|
||||||
|
// - "In crate [name]" parent pointer, followed by sibling navigation
|
||||||
|
assert-count: (".sidebar h2", 3)
|
||||||
|
assert-text: (".sidebar > .sidebar-elems > h2", "In crate lib2")
|
||||||
|
assert-property: (".sidebar > .sidebar-elems > h2 > a", {
|
||||||
|
"href": "/lib2/index.html",
|
||||||
|
}, ENDS_WITH)
|
||||||
// We check that we don't have the crate list.
|
// We check that we don't have the crate list.
|
||||||
assert-false: ".sidebar-elems > .crate"
|
assert-false: ".sidebar-elems > .crate"
|
||||||
|
|
||||||
go-to: "./sub_module/sub_sub_module/index.html"
|
go-to: "./sub_module/sub_sub_module/index.html"
|
||||||
assert-property: (".sidebar", {"clientWidth": "200"})
|
assert-property: (".sidebar", {"clientWidth": "200"})
|
||||||
|
assert-text: (".sidebar > .sidebar-crate > h2 > a", "lib2")
|
||||||
assert-text: (".sidebar > .location", "Module sub_sub_module")
|
assert-text: (".sidebar > .location", "Module sub_sub_module")
|
||||||
|
assert-text: (".sidebar > .sidebar-elems > h2", "In lib2::module::sub_module")
|
||||||
|
assert-property: (".sidebar > .sidebar-elems > h2 > a", {
|
||||||
|
"href": "/module/sub_module/index.html",
|
||||||
|
}, ENDS_WITH)
|
||||||
// We check that we don't have the crate list.
|
// We check that we don't have the crate list.
|
||||||
assert-false: ".sidebar-elems .crate"
|
assert-false: ".sidebar-elems .crate"
|
||||||
assert-text: (".sidebar-elems > section ul > li:nth-child(1)", "Functions")
|
assert-text: (".sidebar-elems > section ul > li:nth-child(1)", "Functions")
|
||||||
|
@ -152,14 +171,14 @@ assert-property: (".sidebar", {"clientWidth": "200"})
|
||||||
|
|
||||||
// Checks that all.html and index.html have their sidebar link in the same place.
|
// Checks that all.html and index.html have their sidebar link in the same place.
|
||||||
go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
|
go-to: "file://" + |DOC_PATH| + "/test_docs/index.html"
|
||||||
store-property: (".sidebar .location a", {
|
store-property: (".sidebar .sidebar-crate h2 a", {
|
||||||
"clientWidth": index_sidebar_width,
|
"clientWidth": index_sidebar_width,
|
||||||
"clientHeight": index_sidebar_height,
|
"clientHeight": index_sidebar_height,
|
||||||
"offsetTop": index_sidebar_y,
|
"offsetTop": index_sidebar_y,
|
||||||
"offsetLeft": index_sidebar_x,
|
"offsetLeft": index_sidebar_x,
|
||||||
})
|
})
|
||||||
go-to: "file://" + |DOC_PATH| + "/test_docs/all.html"
|
go-to: "file://" + |DOC_PATH| + "/test_docs/all.html"
|
||||||
assert-property: (".sidebar .location a", {
|
assert-property: (".sidebar .sidebar-crate h2 a", {
|
||||||
"clientWidth": |index_sidebar_width|,
|
"clientWidth": |index_sidebar_width|,
|
||||||
"clientHeight": |index_sidebar_height|,
|
"clientHeight": |index_sidebar_height|,
|
||||||
"offsetTop": |index_sidebar_y|,
|
"offsetTop": |index_sidebar_y|,
|
||||||
|
|
|
@ -8,13 +8,13 @@ set-window-size: (600, 800)
|
||||||
assert-property: ("html", {"scrollTop": "0"})
|
assert-property: ("html", {"scrollTop": "0"})
|
||||||
|
|
||||||
click: '//a[text() = "barbar" and @href="#5-7"]'
|
click: '//a[text() = "barbar" and @href="#5-7"]'
|
||||||
assert-property: ("html", {"scrollTop": "149"})
|
assert-property: ("html", {"scrollTop": "123"})
|
||||||
click: '//a[text() = "bar" and @href="#28-36"]'
|
click: '//a[text() = "bar" and @href="#28-36"]'
|
||||||
assert-property: ("html", {"scrollTop": "180"})
|
assert-property: ("html", {"scrollTop": "154"})
|
||||||
click: '//a[text() = "sub_fn" and @href="#2-4"]'
|
click: '//a[text() = "sub_fn" and @href="#2-4"]'
|
||||||
assert-property: ("html", {"scrollTop": "77"})
|
assert-property: ("html", {"scrollTop": "51"})
|
||||||
|
|
||||||
// We now check that clicking on lines doesn't change the scroll
|
// We now check that clicking on lines doesn't change the scroll
|
||||||
// Extra information: the "sub_fn" function header is on line 1.
|
// Extra information: the "sub_fn" function header is on line 1.
|
||||||
click: '//*[@id="6"]'
|
click: '//*[@id="6"]'
|
||||||
assert-property: ("html", {"scrollTop": "77"})
|
assert-property: ("html", {"scrollTop": "51"})
|
||||||
|
|
|
@ -89,9 +89,9 @@ assert-css: (".src-line-numbers", {"text-align": "right"})
|
||||||
// do anything (and certainly not add a `#NaN` to the URL!).
|
// do anything (and certainly not add a `#NaN` to the URL!).
|
||||||
go-to: "file://" + |DOC_PATH| + "/src/test_docs/lib.rs.html"
|
go-to: "file://" + |DOC_PATH| + "/src/test_docs/lib.rs.html"
|
||||||
// We use this assert-position to know where we will click.
|
// We use this assert-position to know where we will click.
|
||||||
assert-position: ("//*[@id='1']", {"x": 88, "y": 112})
|
assert-position: ("//*[@id='1']", {"x": 88, "y": 86})
|
||||||
// We click on the left of the "1" anchor but still in the "src-line-number" `<pre>`.
|
// We click on the left of the "1" anchor but still in the "src-line-number" `<pre>`.
|
||||||
click: (87, 103)
|
click: (87, 77)
|
||||||
assert-document-property: ({"URL": "/lib.rs.html"}, ENDS_WITH)
|
assert-document-property: ({"URL": "/lib.rs.html"}, ENDS_WITH)
|
||||||
|
|
||||||
// Checking the source code sidebar.
|
// Checking the source code sidebar.
|
||||||
|
@ -163,16 +163,16 @@ assert-css: ("nav.sub", {"flex-direction": "row"})
|
||||||
// To check this, we maintain the invariant:
|
// To check this, we maintain the invariant:
|
||||||
//
|
//
|
||||||
// offsetTop[nav.sub form] = offsetTop[#main-content] - offsetHeight[nav.sub form] - offsetTop[nav.sub form]
|
// offsetTop[nav.sub form] = offsetTop[#main-content] - offsetHeight[nav.sub form] - offsetTop[nav.sub form]
|
||||||
assert-property: ("nav.sub form", {"offsetTop": 28, "offsetHeight": 34})
|
assert-property: ("nav.sub form", {"offsetTop": 15, "offsetHeight": 34})
|
||||||
assert-property: ("#main-content", {"offsetTop": 90})
|
assert-property: ("#main-content", {"offsetTop": 64})
|
||||||
// 28 = 90 - 34 - 28
|
// 15 = 64 - 34 - 15
|
||||||
|
|
||||||
// Now do the same check on moderately-sized, tablet mobile.
|
// Now do the same check on moderately-sized, tablet mobile.
|
||||||
set-window-size: (700, 700)
|
set-window-size: (700, 700)
|
||||||
assert-css: ("nav.sub", {"flex-direction": "row"})
|
assert-css: ("nav.sub", {"flex-direction": "row"})
|
||||||
assert-property: ("nav.sub form", {"offsetTop": 21, "offsetHeight": 34})
|
assert-property: ("nav.sub form", {"offsetTop": 8, "offsetHeight": 34})
|
||||||
assert-property: ("#main-content", {"offsetTop": 76})
|
assert-property: ("#main-content", {"offsetTop": 50})
|
||||||
// 21 = 76 - 34 - 21
|
// 8 = 50 - 34 - 8
|
||||||
|
|
||||||
// Check the sidebar directory entries have a marker and spacing (tablet).
|
// Check the sidebar directory entries have a marker and spacing (tablet).
|
||||||
store-property: ("#src-sidebar > .title", {
|
store-property: ("#src-sidebar > .title", {
|
||||||
|
@ -198,7 +198,12 @@ call-function: ("check-sidebar-dir-entry", {
|
||||||
"y": |source_sidebar_title_y| + |source_sidebar_title_height| + 6,
|
"y": |source_sidebar_title_y| + |source_sidebar_title_height| + 6,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// The logo is not present on this page.
|
||||||
|
assert-false: ".sub-logo-container > img"
|
||||||
|
|
||||||
|
// Check the staged-api page instead, which does.
|
||||||
// Now we check that the logo has a bottom margin so it's not stuck to the search input.
|
// Now we check that the logo has a bottom margin so it's not stuck to the search input.
|
||||||
|
go-to: "file://" + |DOC_PATH| + "/src/staged_api/lib.rs.html"
|
||||||
assert-css: (".sub-logo-container > img", {"margin-bottom": "8px"})
|
assert-css: (".sub-logo-container > img", {"margin-bottom": "8px"})
|
||||||
store-property: (".sub-logo-container", {"clientHeight": logo_height})
|
store-property: (".sub-logo-container", {"clientHeight": logo_height})
|
||||||
assert-position: (".search-form", {"y": |logo_height| + 8})
|
assert-position: (".search-form", {"y": |logo_height| + 8})
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
#![feature(staged_api)]
|
#![feature(staged_api)]
|
||||||
|
#![feature(rustdoc_internals)]
|
||||||
#![allow(internal_features)]
|
#![allow(internal_features)]
|
||||||
#![stable(feature = "some_feature", since = "1.3.5")]
|
#![stable(feature = "some_feature", since = "1.3.5")]
|
||||||
|
#![doc(rust_logo)]
|
||||||
|
|
||||||
#[stable(feature = "some_feature", since = "1.3.5")]
|
#[stable(feature = "some_feature", since = "1.3.5")]
|
||||||
pub struct Foo {}
|
pub struct Foo {}
|
||||||
|
|
|
@ -2,4 +2,4 @@
|
||||||
|
|
||||||
#![crate_name = "foo"]
|
#![crate_name = "foo"]
|
||||||
|
|
||||||
// @has 'foo/index.html' '//li[@class="version"]' 'Version <script>alert("hi")</script>'
|
// @has 'foo/index.html' '//*[@class="version"]' '<script>alert("hi")</script>'
|
||||||
|
|
7
tests/rustdoc/crate-version-extra.rs
Normal file
7
tests/rustdoc/crate-version-extra.rs
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
// compile-flags: '--crate-version=1.3.37-nightly (203c57dbe 2023-09-17)'
|
||||||
|
|
||||||
|
#![crate_name="foo"]
|
||||||
|
|
||||||
|
// main version next to logo, extra version data below it
|
||||||
|
// @has 'foo/index.html' '//h2/span[@class="version"]' '1.3.37-nightly'
|
||||||
|
// @has 'foo/index.html' '//nav[@class="sidebar"]/div[@class="version"]' '(203c57dbe 2023-09-17)'
|
|
@ -1,3 +1,3 @@
|
||||||
// compile-flags: --crate-version=1.3.37
|
// compile-flags: --crate-version=1.3.37
|
||||||
|
|
||||||
// @has 'crate_version/index.html' '//*[@class="version"]' 'Version 1.3.37'
|
// @has 'crate_version/index.html' '//*[@class="version"]' '1.3.37'
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
// Note: this test is paired with logo-class.rs.
|
// Note: this test is paired with logo-class.rs and logo-class-rust.rs.
|
||||||
// @has logo_class_default/struct.SomeStruct.html '//*[@class="logo-container"]/img[@class="rust-logo"]' ''
|
// @!has logo_class_default/struct.SomeStruct.html '//*[@class="logo-container"]/img' ''
|
||||||
// @has src/logo_class_default/logo-class-default.rs.html '//*[@class="sub-logo-container"]/img[@class="rust-logo"]' ''
|
// @!has src/logo_class_default/logo-class-default.rs.html '//*[@class="sub-logo-container"]/img' ''
|
||||||
pub struct SomeStruct;
|
pub struct SomeStruct;
|
||||||
|
|
7
tests/rustdoc/logo-class-rust.rs
Normal file
7
tests/rustdoc/logo-class-rust.rs
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
#![feature(rustdoc_internals)]
|
||||||
|
#![allow(internal_features)]
|
||||||
|
#![doc(rust_logo)]
|
||||||
|
// Note: this test is paired with logo-class.rs and logo-class-default.rs.
|
||||||
|
// @has logo_class_rust/struct.SomeStruct.html '//*[@class="logo-container"]/img[@class="rust-logo"]' ''
|
||||||
|
// @has src/logo_class_rust/logo-class-rust.rs.html '//*[@class="sub-logo-container"]/img[@class="rust-logo"]' ''
|
||||||
|
pub struct SomeStruct;
|
|
@ -1,6 +1,6 @@
|
||||||
#![doc(html_logo_url =
|
#![doc(html_logo_url =
|
||||||
"https://raw.githubusercontent.com/sagebind/isahc/master/media/isahc.svg.png")]
|
"https://raw.githubusercontent.com/sagebind/isahc/master/media/isahc.svg.png")]
|
||||||
// Note: this test is paired with logo-class-default.rs.
|
// Note: this test is paired with logo-class-default.rs and logo-class-rust.rs.
|
||||||
|
|
||||||
// @has logo_class/struct.SomeStruct.html '//*[@class="logo-container"]/img[@src="https://raw.githubusercontent.com/sagebind/isahc/master/media/isahc.svg.png"]' ''
|
// @has logo_class/struct.SomeStruct.html '//*[@class="logo-container"]/img[@src="https://raw.githubusercontent.com/sagebind/isahc/master/media/isahc.svg.png"]' ''
|
||||||
// @!has logo_class/struct.SomeStruct.html '//*[@class="logo-container"]/img[@class="rust-logo"]' ''
|
// @!has logo_class/struct.SomeStruct.html '//*[@class="logo-container"]/img[@class="rust-logo"]' ''
|
||||||
|
|
|
@ -2,7 +2,8 @@
|
||||||
#![feature(rustc_attrs)]
|
#![feature(rustc_attrs)]
|
||||||
|
|
||||||
// @matches 'foo/index.html' '//h1' 'Crate foo'
|
// @matches 'foo/index.html' '//h1' 'Crate foo'
|
||||||
// @matches 'foo/index.html' '//h2[@class="location"]' 'Crate foo'
|
// @matches 'foo/index.html' '//div[@class="sidebar-crate"]/h2/a' 'foo'
|
||||||
|
// @count 'foo/index.html' '//h2[@class="location"]' 0
|
||||||
|
|
||||||
// @matches 'foo/foo_mod/index.html' '//h1' 'Module foo::foo_mod'
|
// @matches 'foo/foo_mod/index.html' '//h1' 'Module foo::foo_mod'
|
||||||
// @matches 'foo/foo_mod/index.html' '//h2[@class="location"]' 'Module foo_mod'
|
// @matches 'foo/foo_mod/index.html' '//h2[@class="location"]' 'Module foo_mod'
|
||||||
|
|
5
tests/ui/feature-gates/doc-rust-logo.rs
Normal file
5
tests/ui/feature-gates/doc-rust-logo.rs
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
#![doc(rust_logo)]
|
||||||
|
//~^ ERROR the `#[doc(rust_logo)]` attribute is used for Rust branding
|
||||||
|
//! This is not an official rust crate
|
||||||
|
|
||||||
|
fn main() {}
|
12
tests/ui/feature-gates/doc-rust-logo.stderr
Normal file
12
tests/ui/feature-gates/doc-rust-logo.stderr
Normal file
|
@ -0,0 +1,12 @@
|
||||||
|
error[E0658]: the `#[doc(rust_logo)]` attribute is used for Rust branding
|
||||||
|
--> $DIR/doc-rust-logo.rs:1:8
|
||||||
|
|
|
||||||
|
LL | #![doc(rust_logo)]
|
||||||
|
| ^^^^^^^^^
|
||||||
|
|
|
||||||
|
= note: see issue #90418 <https://github.com/rust-lang/rust/issues/90418> for more information
|
||||||
|
= help: add `#![feature(rustdoc_internals)]` to the crate attributes to enable
|
||||||
|
|
||||||
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0658`.
|
Loading…
Add table
Add a link
Reference in a new issue