@@ -236,79 +236,96 @@ impl<'b, 'a: 'b> FmtVisitor<'a> {
236236 fn close_block ( & mut self , span : Span , unindent_comment : bool ) {
237237 let config = self . config ;
238238
239- let mut last_hi = span . lo ( ) ;
240- let mut unindented = false ;
239+ let mut prev_kind = CodeCharKind :: Normal ;
240+ let mut newline_inserted = false ;
241241
242242 let skip_normal = |s : & str | {
243243 let trimmed = s. trim ( ) ;
244- trimmed. is_empty ( ) || trimmed. chars ( ) . all ( |c| c == ';' )
244+ ! trimmed. is_empty ( ) && trimmed. chars ( ) . all ( |c| c == ';' )
245245 } ;
246246
247247 let last_line_offset = if last_line_contains_single_line_comment ( & self . buffer ) {
248248 0
249249 } else {
250- last_line_width ( & self . buffer )
250+ last_line_width ( & self . buffer ) + 1
251251 } ;
252- for ( kind, offset, sub_slice) in CommentCodeSlices :: with_offset (
252+
253+ if unindent_comment {
254+ self . block_indent = self . block_indent . block_unindent ( config) ;
255+ }
256+
257+ let mut iter = CommentCodeSlices :: with_offset (
253258 self . snippet ( span) ,
254259 last_line_offset,
255260 self . config . tab_spaces ( ) ,
256- ) {
261+ )
262+ . peekable ( ) ;
263+ while let Some ( ( kind, offset, sub_slice) ) = iter. next ( ) {
257264 let sub_slice = transform_missing_snippet ( config, sub_slice) ;
258265
259266 debug ! ( "close_block: {:?} {:?} {:?}" , kind, offset, sub_slice) ;
260267
261268 match kind {
262269 CodeCharKind :: Comment => {
263- if !unindented && unindent_comment {
264- unindented = true ;
265- self . block_indent = self . block_indent . block_unindent ( config) ;
266- }
267- let span_in_between = mk_sp ( last_hi, span. lo ( ) + BytePos :: from_usize ( offset) ) ;
268- let snippet_in_between = self . snippet ( span_in_between) ;
269- let mut comment_on_same_line = !snippet_in_between. contains ( "\n " )
270- && !last_line_contains_single_line_comment ( & self . buffer ) ;
271-
272- let comment_shape = Shape :: indented ( self . block_indent , config) . comment ( config) ;
273- if comment_on_same_line {
274- // 1 = a space before `//`
275- let offset_len = 1 + last_line_width ( & self . buffer )
276- . saturating_sub ( self . block_indent . width ( ) ) ;
277- match comment_shape
278- . visual_indent ( offset_len)
279- . sub_width ( offset_len)
280- {
281- Some ( shp) => comment_shape = shp,
282- None => comment_on_same_line = false ,
270+ let comment_shape = if newline_inserted {
271+ self . shape ( ) . comment ( self . config )
272+ } else {
273+ Shape {
274+ width : self . config . comment_width ( ) ,
275+ indent : Indent :: from_width ( self . config , last_line_offset) ,
276+ offset : 0 ,
283277 }
284278 } ;
285-
286- if comment_on_same_line {
279+ let comment_str = rewrite_comment ( & sub_slice, false , comment_shape, config) ;
280+ if self
281+ . buffer
282+ . chars ( )
283+ . last ( )
284+ . map_or ( false , |c| !c. is_whitespace ( ) && c != '/' )
285+ {
287286 self . push_str ( " " ) ;
288- } else {
289- if count_newlines ( snippet_in_between) >= 2 || extra_newline {
290- self . push_str ( "\n " ) ;
291- }
292- self . push_str ( & self . block_indent . to_string_with_newline ( config) ) ;
293287 }
294-
295- let comment_str = rewrite_comment ( & sub_slice, false , comment_shape, config) ;
296288 match comment_str {
297289 Some ( ref s) => self . push_str ( s) ,
298290 None => self . push_str ( & sub_slice) ,
299291 }
300292 }
301293 CodeCharKind :: Normal if skip_normal ( & sub_slice) => {
294+ prev_kind = kind;
302295 continue ;
303296 }
304297 CodeCharKind :: Normal => {
298+ let prev_is_comment = prev_kind == CodeCharKind :: Comment ;
299+ prev_kind = kind;
300+
301+ if iter. peek ( ) . is_none ( ) {
302+ continue ;
303+ }
304+
305+ match count_newlines ( & sub_slice) {
306+ 0 if !prev_is_comment
307+ || !last_line_contains_single_line_comment ( & self . buffer ) =>
308+ {
309+ self . push_str ( " " ) ;
310+ continue ;
311+ }
312+ 0 => ( ) ,
313+ 1 if prev_is_comment
314+ && last_line_contains_single_line_comment ( & self . buffer ) =>
315+ {
316+ self . push_str ( "\n " )
317+ }
318+ 1 => ( ) ,
319+ _ => self . push_str ( "\n " ) ,
320+ }
321+ newline_inserted = true ;
322+
305323 self . push_str ( & self . block_indent . to_string_with_newline ( config) ) ;
306- self . push_str ( sub_slice. trim ( ) ) ;
307324 }
308325 }
309- last_hi = span . lo ( ) + BytePos :: from_usize ( offset + sub_slice . len ( ) ) ;
326+ prev_kind = kind ;
310327 }
311- if unindented {
328+ if unindent_comment {
312329 self . block_indent = self . block_indent . block_indent ( self . config ) ;
313330 }
314331 self . block_indent = self . block_indent . block_unindent ( self . config ) ;
0 commit comments