@@ -2411,7 +2411,7 @@ fn item_struct(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
24112411 } ) . peekable ( ) ;
24122412 if let doctree:: Plain = s. struct_type {
24132413 if fields. peek ( ) . is_some ( ) {
2414- write ! ( w, "<h2 class='fields'>Fields</h2>" ) ?;
2414+ write ! ( w, "<h2 id='fields' class='fields'>Fields</h2>" ) ?;
24152415 for ( field, ty) in fields {
24162416 let id = derive_id ( format ! ( "{}.{}" ,
24172417 ItemType :: StructField ,
@@ -2459,7 +2459,7 @@ fn item_union(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
24592459 }
24602460 } ) . peekable ( ) ;
24612461 if fields. peek ( ) . is_some ( ) {
2462- write ! ( w, "<h2 class='fields'>Fields</h2>" ) ?;
2462+ write ! ( w, "<h2 id='fields' class='fields'>Fields</h2>" ) ?;
24632463 for ( field, ty) in fields {
24642464 write ! ( w, "<span id='{shortty}.{name}' class=\" {shortty}\" ><code>{name}: {ty}</code>
24652465 </span>" ,
@@ -2535,7 +2535,7 @@ fn item_enum(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
25352535
25362536 document ( w, cx, it) ?;
25372537 if !e. variants . is_empty ( ) {
2538- write ! ( w, "<h2 class='variants'>Variants</h2>\n " ) ?;
2538+ write ! ( w, "<h2 id='variants' class='variants'>Variants</h2>\n " ) ?;
25392539 for variant in & e. variants {
25402540 let id = derive_id ( format ! ( "{}.{}" ,
25412541 ItemType :: Variant ,
@@ -3077,6 +3077,37 @@ impl<'a> fmt::Display for Sidebar<'a> {
30773077 let it = self . item ;
30783078 let parentlen = cx. current . len ( ) - if it. is_mod ( ) { 1 } else { 0 } ;
30793079
3080+ if it. is_struct ( ) || it. is_trait ( ) || it. is_primitive ( ) || it. is_union ( )
3081+ || it. is_enum ( ) || it. is_mod ( )
3082+ {
3083+ write ! ( fmt, "<p class='location'>" ) ?;
3084+ match it. inner {
3085+ clean:: StructItem ( ..) => write ! ( fmt, "Struct " ) ?,
3086+ clean:: TraitItem ( ..) => write ! ( fmt, "Trait " ) ?,
3087+ clean:: PrimitiveItem ( ..) => write ! ( fmt, "Primitive Type " ) ?,
3088+ clean:: UnionItem ( ..) => write ! ( fmt, "Union " ) ?,
3089+ clean:: EnumItem ( ..) => write ! ( fmt, "Enum " ) ?,
3090+ clean:: ModuleItem ( ..) => if it. is_crate ( ) {
3091+ write ! ( fmt, "Crate " ) ?;
3092+ } else {
3093+ write ! ( fmt, "Module " ) ?;
3094+ } ,
3095+ _ => ( ) ,
3096+ }
3097+ write ! ( fmt, "{}" , it. name. as_ref( ) . unwrap( ) ) ?;
3098+ write ! ( fmt, "</p>" ) ?;
3099+
3100+ match it. inner {
3101+ clean:: StructItem ( ref s) => sidebar_struct ( fmt, it, s) ?,
3102+ clean:: TraitItem ( ref t) => sidebar_trait ( fmt, it, t) ?,
3103+ clean:: PrimitiveItem ( ref p) => sidebar_primitive ( fmt, it, p) ?,
3104+ clean:: UnionItem ( ref u) => sidebar_union ( fmt, it, u) ?,
3105+ clean:: EnumItem ( ref e) => sidebar_enum ( fmt, it, e) ?,
3106+ clean:: ModuleItem ( ref m) => sidebar_module ( fmt, it, & m. items ) ?,
3107+ _ => ( ) ,
3108+ }
3109+ }
3110+
30803111 // The sidebar is designed to display sibling functions, modules and
30813112 // other miscellaneous information. since there are lots of sibling
30823113 // items (and that causes quadratic growth in large modules),
@@ -3119,6 +3150,193 @@ impl<'a> fmt::Display for Sidebar<'a> {
31193150 }
31203151}
31213152
3153+ fn sidebar_assoc_items ( it : & clean:: Item ) -> String {
3154+ let mut out = String :: new ( ) ;
3155+ let c = cache ( ) ;
3156+ if let Some ( v) = c. impls . get ( & it. def_id ) {
3157+ if v. iter ( ) . any ( |i| i. inner_impl ( ) . trait_ . is_none ( ) ) {
3158+ out. push_str ( "<li><a href=\" #methods\" >Methods</a></li>" ) ;
3159+ }
3160+
3161+ if v. iter ( ) . any ( |i| i. inner_impl ( ) . trait_ . is_some ( ) ) {
3162+ if let Some ( impl_) = v. iter ( )
3163+ . filter ( |i| i. inner_impl ( ) . trait_ . is_some ( ) )
3164+ . find ( |i| i. inner_impl ( ) . trait_ . def_id ( ) == c. deref_trait_did ) {
3165+ if let Some ( target) = impl_. inner_impl ( ) . items . iter ( ) . filter_map ( |item| {
3166+ match item. inner {
3167+ clean:: TypedefItem ( ref t, true ) => Some ( & t. type_ ) ,
3168+ _ => None ,
3169+ }
3170+ } ) . next ( ) {
3171+ let inner_impl = target. def_id ( ) . or ( target. primitive_type ( ) . and_then ( |prim| {
3172+ c. primitive_locations . get ( & prim) . cloned ( )
3173+ } ) ) . and_then ( |did| c. impls . get ( & did) ) ;
3174+ if inner_impl. is_some ( ) {
3175+ out. push_str ( "<li><a href=\" #deref-methods\" >" ) ;
3176+ out. push_str ( & format ! ( "Methods from {:#}<Target={:#}>" ,
3177+ impl_. inner_impl( ) . trait_. as_ref( ) . unwrap( ) ,
3178+ target) ) ;
3179+ out. push_str ( "</a></li>" ) ;
3180+ }
3181+ }
3182+ }
3183+ out. push_str ( "<li><a href=\" #implementations\" >Trait Implementations</a></li>" ) ;
3184+ }
3185+ }
3186+
3187+ out
3188+ }
3189+
3190+ fn sidebar_struct ( fmt : & mut fmt:: Formatter , it : & clean:: Item ,
3191+ s : & clean:: Struct ) -> fmt:: Result {
3192+ let mut sidebar = String :: new ( ) ;
3193+
3194+ if s. fields . iter ( )
3195+ . any ( |f| if let clean:: StructFieldItem ( ..) = f. inner { true } else { false } ) {
3196+ if let doctree:: Plain = s. struct_type {
3197+ sidebar. push_str ( "<li><a href=\" #fields\" >Fields</a></li>" ) ;
3198+ }
3199+ }
3200+
3201+ sidebar. push_str ( & sidebar_assoc_items ( it) ) ;
3202+
3203+ if !sidebar. is_empty ( ) {
3204+ write ! ( fmt, "<div class=\" block items\" ><ul>{}</ul></div>" , sidebar) ?;
3205+ }
3206+ Ok ( ( ) )
3207+ }
3208+
3209+ fn sidebar_trait ( fmt : & mut fmt:: Formatter , it : & clean:: Item ,
3210+ t : & clean:: Trait ) -> fmt:: Result {
3211+ let mut sidebar = String :: new ( ) ;
3212+
3213+ let has_types = t. items . iter ( ) . any ( |m| m. is_associated_type ( ) ) ;
3214+ let has_consts = t. items . iter ( ) . any ( |m| m. is_associated_const ( ) ) ;
3215+ let has_required = t. items . iter ( ) . any ( |m| m. is_ty_method ( ) ) ;
3216+ let has_provided = t. items . iter ( ) . any ( |m| m. is_method ( ) ) ;
3217+
3218+ if has_types {
3219+ sidebar. push_str ( "<li><a href=\" #associated-types\" >Associated Types</a></li>" ) ;
3220+ }
3221+ if has_consts {
3222+ sidebar. push_str ( "<li><a href=\" #associated-const\" >Associated Constants</a></li>" ) ;
3223+ }
3224+ if has_required {
3225+ sidebar. push_str ( "<li><a href=\" #required-methods\" >Required Methods</a></li>" ) ;
3226+ }
3227+ if has_provided {
3228+ sidebar. push_str ( "<li><a href=\" #provided-methods\" >Provided Methods</a></li>" ) ;
3229+ }
3230+
3231+ sidebar. push_str ( & sidebar_assoc_items ( it) ) ;
3232+
3233+ sidebar. push_str ( "<li><a href=\" #implementors\" >Implementors</a></li>" ) ;
3234+
3235+ write ! ( fmt, "<div class=\" block items\" ><ul>{}</ul></div>" , sidebar)
3236+ }
3237+
3238+ fn sidebar_primitive ( fmt : & mut fmt:: Formatter , it : & clean:: Item ,
3239+ _p : & clean:: PrimitiveType ) -> fmt:: Result {
3240+ let sidebar = sidebar_assoc_items ( it) ;
3241+
3242+ if !sidebar. is_empty ( ) {
3243+ write ! ( fmt, "<div class=\" block items\" ><ul>{}</ul></div>" , sidebar) ?;
3244+ }
3245+ Ok ( ( ) )
3246+ }
3247+
3248+ fn sidebar_union ( fmt : & mut fmt:: Formatter , it : & clean:: Item ,
3249+ u : & clean:: Union ) -> fmt:: Result {
3250+ let mut sidebar = String :: new ( ) ;
3251+
3252+ if u. fields . iter ( )
3253+ . any ( |f| if let clean:: StructFieldItem ( ..) = f. inner { true } else { false } ) {
3254+ sidebar. push_str ( "<li><a href=\" #fields\" >Fields</a></li>" ) ;
3255+ }
3256+
3257+ sidebar. push_str ( & sidebar_assoc_items ( it) ) ;
3258+
3259+ if !sidebar. is_empty ( ) {
3260+ write ! ( fmt, "<div class=\" block items\" ><ul>{}</ul></div>" , sidebar) ?;
3261+ }
3262+ Ok ( ( ) )
3263+ }
3264+
3265+ fn sidebar_enum ( fmt : & mut fmt:: Formatter , it : & clean:: Item ,
3266+ e : & clean:: Enum ) -> fmt:: Result {
3267+ let mut sidebar = String :: new ( ) ;
3268+
3269+ if !e. variants . is_empty ( ) {
3270+ sidebar. push_str ( "<li><a href=\" #variants\" >Variants</a></li>" ) ;
3271+ }
3272+
3273+ sidebar. push_str ( & sidebar_assoc_items ( it) ) ;
3274+
3275+ if !sidebar. is_empty ( ) {
3276+ write ! ( fmt, "<div class=\" block items\" ><ul>{}</ul></div>" , sidebar) ?;
3277+ }
3278+ Ok ( ( ) )
3279+ }
3280+
3281+ fn sidebar_module ( fmt : & mut fmt:: Formatter , _it : & clean:: Item ,
3282+ items : & [ clean:: Item ] ) -> fmt:: Result {
3283+ let mut sidebar = String :: new ( ) ;
3284+
3285+ if items. iter ( ) . any ( |it| it. type_ ( ) == ItemType :: ExternCrate ||
3286+ it. type_ ( ) == ItemType :: Import ) {
3287+ sidebar. push_str ( & format ! ( "<li><a href=\" #{id}\" >{name}</a></li>" ,
3288+ id = "reexports" ,
3289+ name = "Reexports" ) ) ;
3290+ }
3291+
3292+ // ordering taken from item_module, reorder, where it prioritized elements in a certain order
3293+ // to print its headings
3294+ for & myty in & [ ItemType :: Primitive , ItemType :: Module , ItemType :: Macro , ItemType :: Struct ,
3295+ ItemType :: Enum , ItemType :: Constant , ItemType :: Static , ItemType :: Trait ,
3296+ ItemType :: Function , ItemType :: Typedef , ItemType :: Union , ItemType :: Impl ,
3297+ ItemType :: TyMethod , ItemType :: Method , ItemType :: StructField , ItemType :: Variant ,
3298+ ItemType :: AssociatedType , ItemType :: AssociatedConst ] {
3299+ if items. iter ( ) . any ( |it| {
3300+ if let clean:: DefaultImplItem ( ..) = it. inner {
3301+ false
3302+ } else {
3303+ !maybe_ignore_item ( it) && !it. is_stripped ( ) && it. type_ ( ) == myty
3304+ }
3305+ } ) {
3306+ let ( short, name) = match myty {
3307+ ItemType :: ExternCrate |
3308+ ItemType :: Import => ( "reexports" , "Reexports" ) ,
3309+ ItemType :: Module => ( "modules" , "Modules" ) ,
3310+ ItemType :: Struct => ( "structs" , "Structs" ) ,
3311+ ItemType :: Union => ( "unions" , "Unions" ) ,
3312+ ItemType :: Enum => ( "enums" , "Enums" ) ,
3313+ ItemType :: Function => ( "functions" , "Functions" ) ,
3314+ ItemType :: Typedef => ( "types" , "Type Definitions" ) ,
3315+ ItemType :: Static => ( "statics" , "Statics" ) ,
3316+ ItemType :: Constant => ( "constants" , "Constants" ) ,
3317+ ItemType :: Trait => ( "traits" , "Traits" ) ,
3318+ ItemType :: Impl => ( "impls" , "Implementations" ) ,
3319+ ItemType :: TyMethod => ( "tymethods" , "Type Methods" ) ,
3320+ ItemType :: Method => ( "methods" , "Methods" ) ,
3321+ ItemType :: StructField => ( "fields" , "Struct Fields" ) ,
3322+ ItemType :: Variant => ( "variants" , "Variants" ) ,
3323+ ItemType :: Macro => ( "macros" , "Macros" ) ,
3324+ ItemType :: Primitive => ( "primitives" , "Primitive Types" ) ,
3325+ ItemType :: AssociatedType => ( "associated-types" , "Associated Types" ) ,
3326+ ItemType :: AssociatedConst => ( "associated-consts" , "Associated Constants" ) ,
3327+ } ;
3328+ sidebar. push_str ( & format ! ( "<li><a href=\" #{id}\" >{name}</a></li>" ,
3329+ id = short,
3330+ name = name) ) ;
3331+ }
3332+ }
3333+
3334+ if !sidebar. is_empty ( ) {
3335+ write ! ( fmt, "<div class=\" block items\" ><ul>{}</ul></div>" , sidebar) ?;
3336+ }
3337+ Ok ( ( ) )
3338+ }
3339+
31223340impl < ' a > fmt:: Display for Source < ' a > {
31233341 fn fmt ( & self , fmt : & mut fmt:: Formatter ) -> fmt:: Result {
31243342 let Source ( s) = * self ;
0 commit comments