@@ -37,7 +37,7 @@ pub use self::ExternalLocation::*;
3737use std:: ascii:: AsciiExt ;
3838use std:: cell:: RefCell ;
3939use std:: cmp:: Ordering ;
40- use std:: collections:: BTreeMap ;
40+ use std:: collections:: { BTreeMap , HashSet } ;
4141use std:: default:: Default ;
4242use std:: error;
4343use std:: fmt:: { self , Display , Formatter , Write as FmtWrite } ;
@@ -3206,12 +3206,37 @@ fn render_deref_methods(w: &mut fmt::Formatter, cx: &Context, impl_: &Impl,
32063206 }
32073207}
32083208
3209+ fn should_render_item ( item : & clean:: Item , deref_mut_ : bool ) -> bool {
3210+ let self_type_opt = match item. inner {
3211+ clean:: MethodItem ( ref method) => method. decl . self_type ( ) ,
3212+ clean:: TyMethodItem ( ref method) => method. decl . self_type ( ) ,
3213+ _ => None
3214+ } ;
3215+
3216+ if let Some ( self_ty) = self_type_opt {
3217+ let ( by_mut_ref, by_box) = match self_ty {
3218+ SelfTy :: SelfBorrowed ( _, mutability) |
3219+ SelfTy :: SelfExplicit ( clean:: BorrowedRef { mutability, .. } ) => {
3220+ ( mutability == Mutability :: Mutable , false )
3221+ } ,
3222+ SelfTy :: SelfExplicit ( clean:: ResolvedPath { did, .. } ) => {
3223+ ( false , Some ( did) == cache ( ) . owned_box_did )
3224+ } ,
3225+ _ => ( false , false ) ,
3226+ } ;
3227+
3228+ ( deref_mut_ || !by_mut_ref) && !by_box
3229+ } else {
3230+ false
3231+ }
3232+ }
3233+
32093234fn render_impl ( w : & mut fmt:: Formatter , cx : & Context , i : & Impl , link : AssocItemLink ,
32103235 render_mode : RenderMode , outer_version : Option < & str > ,
32113236 show_def_docs : bool ) -> fmt:: Result {
32123237 if render_mode == RenderMode :: Normal {
32133238 let id = derive_id ( match i. inner_impl ( ) . trait_ {
3214- Some ( ref t) => format ! ( "impl-{}" , Escape ( & format!( "{:#}" , t) ) ) ,
3239+ Some ( ref t) => format ! ( "impl-{}" , small_url_encode ( & format!( "{:#}" , t) ) ) ,
32153240 None => "impl" . to_string ( ) ,
32163241 } ) ;
32173242 write ! ( w, "<h3 id='{}' class='impl'><span class='in-band'><code>{}</code>" ,
@@ -3243,30 +3268,7 @@ fn render_impl(w: &mut fmt::Formatter, cx: &Context, i: &Impl, link: AssocItemLi
32433268
32443269 let render_method_item: bool = match render_mode {
32453270 RenderMode :: Normal => true ,
3246- RenderMode :: ForDeref { mut_ : deref_mut_ } => {
3247- let self_type_opt = match item. inner {
3248- clean:: MethodItem ( ref method) => method. decl . self_type ( ) ,
3249- clean:: TyMethodItem ( ref method) => method. decl . self_type ( ) ,
3250- _ => None
3251- } ;
3252-
3253- if let Some ( self_ty) = self_type_opt {
3254- let ( by_mut_ref, by_box) = match self_ty {
3255- SelfTy :: SelfBorrowed ( _, mutability) |
3256- SelfTy :: SelfExplicit ( clean:: BorrowedRef { mutability, .. } ) => {
3257- ( mutability == Mutability :: Mutable , false )
3258- } ,
3259- SelfTy :: SelfExplicit ( clean:: ResolvedPath { did, .. } ) => {
3260- ( false , Some ( did) == cache ( ) . owned_box_did )
3261- } ,
3262- _ => ( false , false ) ,
3263- } ;
3264-
3265- ( deref_mut_ || !by_mut_ref) && !by_box
3266- } else {
3267- false
3268- }
3269- } ,
3271+ RenderMode :: ForDeref { mut_ : deref_mut_ } => should_render_item ( & item, deref_mut_) ,
32703272 } ;
32713273
32723274 match item. inner {
@@ -3513,12 +3515,16 @@ impl<'a> fmt::Display for Sidebar<'a> {
35133515 }
35143516}
35153517
3516- fn get_methods ( i : & clean:: Impl ) -> Vec < String > {
3518+ fn get_methods ( i : & clean:: Impl , for_deref : bool ) -> Vec < String > {
35173519 i. items . iter ( ) . filter_map ( |item| {
35183520 match item. name {
35193521 // Maybe check with clean::Visibility::Public as well?
35203522 Some ( ref name) if !name. is_empty ( ) && item. visibility . is_some ( ) && item. is_method ( ) => {
3521- Some ( format ! ( "<a href=\" #method.{name}\" >{name}</a>" , name = name) )
3523+ if !for_deref || should_render_item ( item, false ) {
3524+ Some ( format ! ( "<a href=\" #method.{name}\" >{name}</a>" , name = name) )
3525+ } else {
3526+ None
3527+ }
35223528 }
35233529 _ => None ,
35243530 }
@@ -3546,7 +3552,7 @@ fn sidebar_assoc_items(it: &clean::Item) -> String {
35463552 if let Some ( v) = c. impls . get ( & it. def_id ) {
35473553 let ret = v. iter ( )
35483554 . filter ( |i| i. inner_impl ( ) . trait_ . is_none ( ) )
3549- . flat_map ( |i| get_methods ( i. inner_impl ( ) ) )
3555+ . flat_map ( |i| get_methods ( i. inner_impl ( ) , false ) )
35503556 . collect :: < String > ( ) ;
35513557 if !ret. is_empty ( ) {
35523558 out. push_str ( & format ! ( "<a class=\" sidebar-title\" href=\" #methods\" >Methods\
@@ -3574,17 +3580,23 @@ fn sidebar_assoc_items(it: &clean::Item) -> String {
35743580 out. push_str ( "</a>" ) ;
35753581 let ret = impls. iter ( )
35763582 . filter ( |i| i. inner_impl ( ) . trait_ . is_none ( ) )
3577- . flat_map ( |i| get_methods ( i. inner_impl ( ) ) )
3583+ . flat_map ( |i| get_methods ( i. inner_impl ( ) , true ) )
35783584 . collect :: < String > ( ) ;
35793585 out. push_str ( & format ! ( "<div class=\" sidebar-links\" >{}</div>" , ret) ) ;
35803586 }
35813587 }
35823588 }
3589+ let mut links = HashSet :: new ( ) ;
35833590 let ret = v. iter ( )
35843591 . filter_map ( |i| if let Some ( ref i) = i. inner_impl ( ) . trait_ {
35853592 let out = format ! ( "{:#}" , i) . replace ( "<" , "<" ) . replace ( ">" , ">" ) ;
35863593 let encoded = small_url_encode ( & format ! ( "{:#}" , i) ) ;
3587- Some ( format ! ( "<a href=\" #impl-{:#}\" >{}</a>" , encoded, out) )
3594+ let generated = format ! ( "<a href=\" #impl-{}\" >{}</a>" , encoded, out) ;
3595+ if !links. contains ( & generated) && links. insert ( generated. clone ( ) ) {
3596+ Some ( generated)
3597+ } else {
3598+ None
3599+ }
35883600 } else {
35893601 None
35903602 } )
0 commit comments