= self.inputs.iter().map(|ref t| {
+ format!("{}", t)
+ }).collect();
try!(write!(f, "{{\"inputs\":[{}],\"output\":", inputs.connect(",")));
match self.output {
@@ -1780,7 +1790,7 @@ fn item_trait(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
try!(write!(w, "{{\n"));
for t in &types {
try!(write!(w, " "));
- try!(render_method(w, t));
+ try!(render_method(w, t, MethodLink::Anchor));
try!(write!(w, ";\n"));
}
if types.len() > 0 && required.len() > 0 {
@@ -1788,7 +1798,7 @@ fn item_trait(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
}
for m in &required {
try!(write!(w, " "));
- try!(render_method(w, m));
+ try!(render_method(w, m, MethodLink::Anchor));
try!(write!(w, ";\n"));
}
if required.len() > 0 && provided.len() > 0 {
@@ -1796,7 +1806,7 @@ fn item_trait(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
}
for m in &provided {
try!(write!(w, " "));
- try!(render_method(w, m));
+ try!(render_method(w, m, MethodLink::Anchor));
try!(write!(w, " {{ ... }}\n"));
}
try!(write!(w, "}}"));
@@ -1812,7 +1822,7 @@ fn item_trait(w: &mut fmt::Formatter, cx: &Context, it: &clean::Item,
shortty(m),
*m.name.as_ref().unwrap(),
ConciseStability(&m.stability)));
- try!(render_method(w, m));
+ try!(render_method(w, m, MethodLink::Anchor));
try!(write!(w, ""));
try!(document(w, m));
Ok(())
@@ -1896,14 +1906,23 @@ fn assoc_type(w: &mut fmt::Formatter, it: &clean::Item,
Ok(())
}
-fn render_method(w: &mut fmt::Formatter, meth: &clean::Item) -> fmt::Result {
+fn render_method(w: &mut fmt::Formatter, meth: &clean::Item,
+ link: MethodLink) -> fmt::Result {
fn method(w: &mut fmt::Formatter, it: &clean::Item,
unsafety: ast::Unsafety, abi: abi::Abi,
g: &clean::Generics, selfty: &clean::SelfTy,
- d: &clean::FnDecl) -> fmt::Result {
+ d: &clean::FnDecl, link: MethodLink) -> fmt::Result {
use syntax::abi::Abi;
- write!(w, "{}{}fn {name}\
+ let name = it.name.as_ref().unwrap();
+ let anchor = format!("#{}.{}", shortty(it), name);
+ let href = match link {
+ MethodLink::Anchor => anchor,
+ MethodLink::GotoSource(did) => {
+ href(did).map(|p| format!("{}{}", p.0, anchor)).unwrap_or(anchor)
+ }
+ };
+ write!(w, "{}{}fn {name}\
{generics}{decl}{where_clause}",
match unsafety {
ast::Unsafety::Unsafe => "unsafe ",
@@ -1913,18 +1932,20 @@ fn render_method(w: &mut fmt::Formatter, meth: &clean::Item) -> fmt::Result {
Abi::Rust => String::new(),
a => format!("extern {} ", a.to_string())
},
- ty = shortty(it),
- name = it.name.as_ref().unwrap(),
+ href = href,
+ name = name,
generics = *g,
decl = Method(selfty, d),
where_clause = WhereClause(g))
}
match meth.inner {
clean::TyMethodItem(ref m) => {
- method(w, meth, m.unsafety, m.abi, &m.generics, &m.self_, &m.decl)
+ method(w, meth, m.unsafety, m.abi, &m.generics, &m.self_, &m.decl,
+ link)
}
clean::MethodItem(ref m) => {
- method(w, meth, m.unsafety, m.abi, &m.generics, &m.self_, &m.decl)
+ method(w, meth, m.unsafety, m.abi, &m.generics, &m.self_, &m.decl,
+ link)
}
clean::AssociatedTypeItem(ref bounds, ref default) => {
assoc_type(w, meth, bounds, default)
@@ -2151,6 +2172,12 @@ fn render_struct(w: &mut fmt::Formatter, it: &clean::Item,
Ok(())
}
+#[derive(Copy, Clone)]
+enum MethodLink {
+ Anchor,
+ GotoSource(ast::DefId),
+}
+
fn render_methods(w: &mut fmt::Formatter, it: &clean::Item) -> fmt::Result {
match cache().impls.get(&it.def_id) {
Some(v) => {
@@ -2159,7 +2186,7 @@ fn render_methods(w: &mut fmt::Formatter, it: &clean::Item) -> fmt::Result {
if non_trait.len() > 0 {
try!(write!(w, "Methods
"));
for i in &non_trait {
- try!(render_impl(w, i));
+ try!(render_impl(w, i, MethodLink::Anchor));
}
}
if traits.len() > 0 {
@@ -2168,13 +2195,16 @@ fn render_methods(w: &mut fmt::Formatter, it: &clean::Item) -> fmt::Result {
let (derived, manual): (Vec<_>, _) = traits.into_iter()
.partition(|i| i.impl_.derived);
for i in &manual {
- try!(render_impl(w, i));
+ let did = i.trait_did().unwrap();
+ try!(render_impl(w, i, MethodLink::GotoSource(did)));
}
if derived.len() > 0 {
- try!(write!(w, "Derived Implementations \
-
"));
+ try!(write!(w, "\
+ Derived Implementations \
+
"));
for i in &derived {
- try!(render_impl(w, i));
+ let did = i.trait_did().unwrap();
+ try!(render_impl(w, i, MethodLink::GotoSource(did)));
}
}
}
@@ -2184,36 +2214,32 @@ fn render_methods(w: &mut fmt::Formatter, it: &clean::Item) -> fmt::Result {
Ok(())
}
-fn render_impl(w: &mut fmt::Formatter, i: &Impl) -> fmt::Result {
+fn render_impl(w: &mut fmt::Formatter, i: &Impl, link: MethodLink)
+ -> fmt::Result {
try!(write!(w, "{}impl{} ",
ConciseStability(&i.stability),
i.impl_.generics));
- match i.impl_.polarity {
- Some(clean::ImplPolarity::Negative) => try!(write!(w, "!")),
- _ => {}
+ if let Some(clean::ImplPolarity::Negative) = i.impl_.polarity {
+ try!(write!(w, "!"));
}
- match i.impl_.trait_ {
- Some(ref ty) => try!(write!(w, "{} for ", *ty)),
- None => {}
+ if let Some(ref ty) = i.impl_.trait_ {
+ try!(write!(w, "{} for ", *ty));
}
- try!(write!(w, "{}{}
", i.impl_.for_, WhereClause(&i.impl_.generics)));
- match i.dox {
- Some(ref dox) => {
- try!(write!(w, "{}
",
- Markdown(dox)));
- }
- None => {}
+ try!(write!(w, "{}{}", i.impl_.for_,
+ WhereClause(&i.impl_.generics)));
+ if let Some(ref dox) = i.dox {
+ try!(write!(w, "{}
", Markdown(dox)));
}
- fn doctraititem(w: &mut fmt::Formatter, item: &clean::Item, dox: bool)
- -> fmt::Result {
+ fn doctraititem(w: &mut fmt::Formatter, item: &clean::Item,
+ dox: bool, link: MethodLink) -> fmt::Result {
match item.inner {
clean::MethodItem(..) | clean::TyMethodItem(..) => {
try!(write!(w, "{}",
*item.name.as_ref().unwrap(),
shortty(item),
ConciseStability(&item.stability)));
- try!(render_method(w, item));
+ try!(render_method(w, item, link));
try!(write!(w, "
\n"));
}
clean::TypedefItem(ref tydef) => {
@@ -2247,10 +2273,11 @@ fn render_impl(w: &mut fmt::Formatter, i: &Impl) -> fmt::Result {
try!(write!(w, ""));
for trait_item in i.impl_.items.iter() {
- try!(doctraititem(w, trait_item, true));
+ try!(doctraititem(w, trait_item, true, link));
}
fn render_default_methods(w: &mut fmt::Formatter,
+ did: ast::DefId,
t: &clean::Trait,
i: &clean::Impl) -> fmt::Result {
for trait_item in &t.items {
@@ -2260,7 +2287,8 @@ fn render_impl(w: &mut fmt::Formatter, i: &Impl) -> fmt::Result {
None => {}
}
- try!(doctraititem(w, trait_item, false));
+ try!(doctraititem(w, trait_item, false,
+ MethodLink::GotoSource(did)));
}
Ok(())
}
@@ -2271,7 +2299,7 @@ fn render_impl(w: &mut fmt::Formatter, i: &Impl) -> fmt::Result {
// for them work.
if let Some(clean::ResolvedPath { did, .. }) = i.impl_.trait_ {
if let Some(t) = cache().traits.get(&did) {
- try!(render_default_methods(w, t, &i.impl_));
+ try!(render_default_methods(w, did, t, &i.impl_));
}
}
try!(write!(w, "
"));
diff --git a/src/test/auxiliary/issue-17476.rs b/src/test/auxiliary/issue-17476.rs
new file mode 100644
index 00000000000..d3a86035742
--- /dev/null
+++ b/src/test/auxiliary/issue-17476.rs
@@ -0,0 +1,16 @@
+// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
+// file at the top-level directory of this distribution and at
+// http://rust-lang.org/COPYRIGHT.
+//
+// Licensed under the Apache License, Version 2.0 or the MIT license
+// , at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+
+#![doc(html_root_url = "http://example.com")]
+
+pub trait Foo {
+ fn foo(&self) {}
+}
diff --git a/src/test/rustdoc/issue-17476.rs b/src/test/rustdoc/issue-17476.rs
new file mode 100644
index 00000000000..cb224d66b44
--- /dev/null
+++ b/src/test/rustdoc/issue-17476.rs
@@ -0,0 +1,20 @@
+// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
+// file at the top-level directory of this distribution and at
+// http://rust-lang.org/COPYRIGHT.
+//
+// Licensed under the Apache License, Version 2.0 or the MIT license
+// , at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+// aux-build:issue-17476.rs
+
+extern crate issue_17476;
+
+pub struct Foo;
+
+// @has issue_17476/struct.Foo.html \
+// '//*[@href="http://example.com/issue_17476/trait.Foo.html#tymethod.foo"]' \
+// 'foo'
+impl issue_17476::Foo for Foo {}