Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

rustdoc: update formatting of fn signatures and where clauses to match style rfcs #41084

Merged
merged 9 commits into from
Apr 9, 2017
134 changes: 76 additions & 58 deletions src/librustdoc/html/format.rs
Original file line number Diff line number Diff line change
Expand Up @@ -41,22 +41,38 @@ pub struct UnsafetySpace(pub hir::Unsafety);
/// with a space after it.
#[derive(Copy, Clone)]
pub struct ConstnessSpace(pub hir::Constness);
/// Wrapper struct for properly emitting a method declaration.
pub struct Method<'a>(pub &'a clean::FnDecl, pub usize);
/// Similar to VisSpace, but used for mutability
#[derive(Copy, Clone)]
pub struct MutableSpace(pub clean::Mutability);
/// Similar to VisSpace, but used for mutability
#[derive(Copy, Clone)]
pub struct RawMutableSpace(pub clean::Mutability);
/// Wrapper struct for emitting a where clause from Generics.
pub struct WhereClause<'a>(pub &'a clean::Generics, pub usize);
/// Wrapper struct for emitting type parameter bounds.
pub struct TyParamBounds<'a>(pub &'a [clean::TyParamBound]);
/// Wrapper struct for emitting a comma-separated list of items
pub struct CommaSep<'a, T: 'a>(pub &'a [T]);
pub struct AbiSpace(pub Abi);

/// Wrapper struct for properly emitting a method declaration.
pub struct Method<'a> {
/// The declaration to emit.
pub decl: &'a clean::FnDecl,
/// The length of the function's "name", used to determine line-wrapping.
pub name_len: usize,
/// The number of spaces to indent each successive line with, if line-wrapping is necessary.
pub indent: usize,
}

/// Wrapper struct for emitting a where clause from Generics.
pub struct WhereClause<'a>{
/// The Generics from which to emit a where clause.
pub gens: &'a clean::Generics,
/// The number of spaces to indent each line with.
pub indent: usize,
/// Whether the where clause needs to add a comma and newline after the last bound.
pub end_newline: bool,
}

pub struct HRef<'a> {
pub did: DefId,
pub text: &'a str,
Expand Down Expand Up @@ -167,24 +183,27 @@ impl fmt::Display for clean::Generics {

impl<'a> fmt::Display for WhereClause<'a> {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let &WhereClause(gens, pad) = self;
let &WhereClause { gens, indent, end_newline } = self;
if gens.where_predicates.is_empty() {
return Ok(());
}
let mut clause = String::new();
if f.alternate() {
clause.push_str(" where ");
clause.push_str(" where");
} else {
clause.push_str(" <span class=\"where fmt-newline\">where ");
if end_newline {
clause.push_str(" <span class=\"where fmt-newline\">where");
} else {
clause.push_str(" <span class=\"where\">where");
}
}
for (i, pred) in gens.where_predicates.iter().enumerate() {
if i > 0 {
if f.alternate() {
clause.push_str(", ");
} else {
clause.push_str(",<br>");
}
if f.alternate() {
clause.push(' ');
} else {
clause.push_str("<br>");
}

match pred {
&clean::WherePredicate::BoundPredicate { ref ty, ref bounds } => {
let bounds = bounds;
Expand Down Expand Up @@ -213,21 +232,29 @@ impl<'a> fmt::Display for WhereClause<'a> {
}
}
}

if i < gens.where_predicates.len() - 1 || end_newline {
clause.push(',');
}
}

if end_newline {
//add a space so stripping <br> tags and breaking spaces still renders properly
if f.alternate() {
clause.push(' ');
} else {
clause.push_str("&nbsp;");
}
}

if !f.alternate() {
clause.push_str("</span>");
let plain = format!("{:#}", self);
if plain.len() + pad > 80 {
// break it onto its own line regardless, but make sure method impls and trait
// blocks keep their fixed padding (2 and 9, respectively)
let padding = if pad > 10 {
repeat("&nbsp;").take(8).collect::<String>()
} else {
repeat("&nbsp;").take(pad + 6).collect::<String>()
};
clause = clause.replace("<br>", &format!("<br>{}", padding));
} else {
clause = clause.replace("<br>", " ");
let padding = repeat("&nbsp;").take(indent + 4).collect::<String>();
clause = clause.replace("<br>", &format!("<br>{}", padding));
clause.insert_str(0, &repeat("&nbsp;").take(indent.saturating_sub(1))
.collect::<String>());
if !end_newline {
clause.insert_str(0, "<br>");
}
}
write!(f, "{}", clause)
Expand Down Expand Up @@ -838,43 +865,35 @@ fn fmt_impl(i: &clean::Impl,
f: &mut fmt::Formatter,
link_trait: bool,
use_absolute: bool) -> fmt::Result {
let mut plain = String::new();

if f.alternate() {
write!(f, "impl{:#} ", i.generics)?;
} else {
write!(f, "impl{} ", i.generics)?;
}
plain.push_str(&format!("impl{:#} ", i.generics));

if let Some(ref ty) = i.trait_ {
if i.polarity == Some(clean::ImplPolarity::Negative) {
write!(f, "!")?;
plain.push_str("!");
}

if link_trait {
fmt::Display::fmt(ty, f)?;
plain.push_str(&format!("{:#}", ty));
} else {
match *ty {
clean::ResolvedPath { typarams: None, ref path, is_generic: false, .. } => {
let last = path.segments.last().unwrap();
fmt::Display::fmt(&last.name, f)?;
fmt::Display::fmt(&last.params, f)?;
plain.push_str(&format!("{:#}{:#}", last.name, last.params));
}
_ => unreachable!(),
}
}
write!(f, " for ")?;
plain.push_str(" for ");
}

fmt_type(&i.for_, f, use_absolute, true)?;
plain.push_str(&format!("{:#}", i.for_));

fmt::Display::fmt(&WhereClause(&i.generics, plain.len() + 1), f)?;
fmt::Display::fmt(&WhereClause { gens: &i.generics, indent: 0, end_newline: true }, f)?;
Ok(())
}

Expand Down Expand Up @@ -939,12 +958,15 @@ impl fmt::Display for clean::FnDecl {

impl<'a> fmt::Display for Method<'a> {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let decl = self.0;
let indent = self.1;
let &Method { decl, name_len, indent } = self;
let amp = if f.alternate() { "&" } else { "&amp;" };
let mut args = String::new();
let mut args_plain = String::new();
for (i, input) in decl.inputs.values.iter().enumerate() {
if i == 0 {
args.push_str("<br>");
}

if let Some(selfty) = input.to_self() {
match selfty {
clean::SelfValue => {
Expand All @@ -970,7 +992,7 @@ impl<'a> fmt::Display for Method<'a> {
}
} else {
if i > 0 {
args.push_str("<br> ");
args.push_str(" <br>");
args_plain.push_str(" ");
}
if !input.name.is_empty() {
Expand All @@ -986,8 +1008,8 @@ impl<'a> fmt::Display for Method<'a> {
args_plain.push_str(&format!("{:#}", input.type_));
}
if i + 1 < decl.inputs.values.len() {
args.push_str(",");
args_plain.push_str(",");
args.push(',');
args_plain.push(',');
}
}

Expand All @@ -1003,27 +1025,23 @@ impl<'a> fmt::Display for Method<'a> {
format!("{}", decl.output)
};

let mut output: String;
let plain: String;
let pad = repeat(" ").take(indent).collect::<String>();
if arrow.is_empty() {
output = format!("({})", args);
plain = format!("{}({})", pad, args_plain);
let pad = repeat(" ").take(name_len).collect::<String>();
let plain = format!("{pad}({args}){arrow}",
pad = pad,
args = args_plain,
arrow = arrow_plain);

let output = if plain.len() > 80 {
let full_pad = format!("<br>{}", repeat("&nbsp;").take(indent + 4).collect::<String>());
let close_pad = format!("<br>{}", repeat("&nbsp;").take(indent).collect::<String>());
format!("({args}{close}){arrow}",
args = args.replace("<br>", &full_pad),
close = close_pad,
arrow = arrow)
} else {
output = format!("({args})<br>{arrow}", args = args, arrow = arrow);
plain = format!("{pad}({args}){arrow}",
pad = pad,
args = args_plain,
arrow = arrow_plain);
}
format!("({args}){arrow}", args = args.replace("<br>", ""), arrow = arrow)
};

if plain.len() > 80 {
let pad = repeat("&nbsp;").take(indent).collect::<String>();
let pad = format!("<br>{}", pad);
output = output.replace("<br>", &pad);
} else {
output = output.replace("<br>", "");
}
if f.alternate() {
write!(f, "{}", output.replace("<br>", "\n"))
} else {
Expand Down
Loading