Skip to content

Commit 78ba6e7

Browse files
feat: support closure block indent_style
1 parent a15e97f commit 78ba6e7

File tree

5 files changed

+117
-4
lines changed

5 files changed

+117
-4
lines changed

src/closures.rs

+35-4
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ use syntax::{ast, ptr};
33

44
use crate::attr::get_attrs_from_stmt;
55
use crate::config::lists::*;
6-
use crate::config::Version;
6+
use crate::config::{IndentStyle, Version};
77
use crate::expr::{block_contains_comment, is_simple_block, is_unsafe_block, rewrite_cond};
88
use crate::items::{span_hi_for_param, span_lo_for_param};
99
use crate::lists::{definitive_tactic, itemize_list, write_list, ListFormatting, Separator};
@@ -238,9 +238,21 @@ fn rewrite_closure_fn_decl(
238238
.shrink_left(is_async.len() + mover.len() + immovable.len())?
239239
.sub_width(4)?;
240240

241+
let indent_style = context.config.indent_style();
242+
let version = context.config.version();
243+
241244
// 1 = |
242245
let param_offset = nested_shape.indent + 1;
243-
let param_shape = nested_shape.offset_left(1)?.visual_indent(0);
246+
let param_shape = match indent_style {
247+
IndentStyle::Block => {
248+
if version == Version::Two {
249+
Shape::indented(shape.indent.block_indent(context.config), context.config)
250+
} else {
251+
nested_shape.offset_left(1)?.visual_indent(0)
252+
}
253+
}
254+
IndentStyle::Visual => nested_shape.offset_left(1)?.visual_indent(0),
255+
};
244256
let ret_str = fn_decl.output.rewrite(context, param_shape)?;
245257

246258
let param_items = itemize_list(
@@ -273,10 +285,29 @@ fn rewrite_closure_fn_decl(
273285
.tactic(tactic)
274286
.preserve_newline(true);
275287
let list_str = write_list(&item_vec, &fmt)?;
276-
let mut prefix = format!("{}{}{}|{}|", is_async, immovable, mover, list_str);
288+
let one_line_budget = context.budget(param_shape.indent.width());
289+
let (param_str, put_params_in_block) = if match indent_style {
290+
IndentStyle::Block => list_str.contains('\n') || list_str.len() > one_line_budget,
291+
_ => false,
292+
} && !item_vec.is_empty()
293+
&& version == Version::Two
294+
{
295+
(
296+
format!(
297+
"{}{}{}",
298+
param_shape.indent.to_string_with_newline(context.config),
299+
&list_str,
300+
shape.indent.to_string_with_newline(context.config)
301+
),
302+
true,
303+
)
304+
} else {
305+
(list_str, false)
306+
};
307+
let mut prefix = format!("{}{}{}|{}|", is_async, immovable, mover, param_str);
277308

278309
if !ret_str.is_empty() {
279-
if prefix.contains('\n') {
310+
if prefix.contains('\n') && !put_params_in_block {
280311
prefix.push('\n');
281312
prefix.push_str(&param_offset.to_string(context.config));
282313
} else {

tests/source/closure_block_style.rs

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// rustfmt-indent_style: Block
2+
// rustfmt-version: Two
3+
4+
fn foo() {
5+
{
6+
let write_status = |status: &mut Vec<ansi_term::ANSIString>,
7+
diff: &Diff,
8+
heading: &str,
9+
color: &Style,
10+
show_hints: bool,
11+
hints: &[&str]|-> Option<bool> { Some(true) };}
12+
}
13+
14+
fn bar() {
15+
let write_status = |status: &mut Vec<ansi_term::ANSIString>,diff: &Diff,heading: &str,color: &Style,| -> Option<bool> { Some(true) };
16+
let baz = |foo: bool| -> Option<bool> { Some(true) };
17+
}

tests/source/closure_visual_style.rs

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// rustfmt-indent_style: Visual
2+
// rustfmt-version: Two
3+
4+
fn foo() {
5+
{
6+
let write_status = |status: &mut Vec<ansi_term::ANSIString>,
7+
diff: &Diff,
8+
heading: &str,
9+
color: &Style,
10+
show_hints: bool,
11+
hints: &[&str]|-> Option<bool> { Some(true) };}
12+
}
13+
14+
fn bar() {
15+
let write_status = |status: &mut Vec<ansi_term::ANSIString>,diff: &Diff,heading: &str,color: &Style,| -> Option<bool> { Some(true) };
16+
let baz = |foo: bool| -> Option<bool> { Some(true) };
17+
}

tests/target/closure_block_style.rs

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
// rustfmt-indent_style: Block
2+
// rustfmt-version: Two
3+
4+
fn foo() {
5+
{
6+
let write_status = |
7+
status: &mut Vec<ansi_term::ANSIString>,
8+
diff: &Diff,
9+
heading: &str,
10+
color: &Style,
11+
show_hints: bool,
12+
hints: &[&str]
13+
| -> Option<bool> { Some(true) };
14+
}
15+
}
16+
17+
fn bar() {
18+
let write_status = |
19+
status: &mut Vec<ansi_term::ANSIString>,
20+
diff: &Diff,
21+
heading: &str,
22+
color: &Style
23+
| -> Option<bool> { Some(true) };
24+
let baz = |foo: bool| -> Option<bool> { Some(true) };
25+
}

tests/target/closure_visual_style.rs

+23
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// rustfmt-indent_style: Visual
2+
// rustfmt-version: Two
3+
4+
fn foo() {
5+
{
6+
let write_status = |status: &mut Vec<ansi_term::ANSIString>,
7+
diff: &Diff,
8+
heading: &str,
9+
color: &Style,
10+
show_hints: bool,
11+
hints: &[&str]|
12+
-> Option<bool> { Some(true) };
13+
}
14+
}
15+
16+
fn bar() {
17+
let write_status = |status: &mut Vec<ansi_term::ANSIString>,
18+
diff: &Diff,
19+
heading: &str,
20+
color: &Style|
21+
-> Option<bool> { Some(true) };
22+
let baz = |foo: bool| -> Option<bool> { Some(true) };
23+
}

0 commit comments

Comments
 (0)