@@ -344,7 +344,7 @@ namespace ts.formatting {
344
344
}
345
345
346
346
export function formatNodeGivenIndentation ( node : Node , sourceFileLike : SourceFileLike , languageVariant : LanguageVariant , initialIndentation : number , delta : number , formatContext : FormatContext ) : TextChange [ ] {
347
- const range = { pos : 0 , end : sourceFileLike . text . length } ;
347
+ const range = { pos : node . pos , end : node . end } ;
348
348
return getFormattingScanner ( sourceFileLike . text , languageVariant , range . pos , range . end , scanner => formatSpanWorker (
349
349
range ,
350
350
node ,
@@ -438,6 +438,25 @@ namespace ts.formatting {
438
438
}
439
439
}
440
440
441
+ if ( previousRange ! && formattingScanner . getStartPos ( ) >= originalRange . end ) {
442
+ const token =
443
+ formattingScanner . isOnEOF ( ) ? formattingScanner . readEOFTokenRange ( ) :
444
+ formattingScanner . isOnToken ( ) ? formattingScanner . readTokenInfo ( enclosingNode ) . token :
445
+ undefined ;
446
+
447
+ if ( token ) {
448
+ processPair (
449
+ token ,
450
+ sourceFile . getLineAndCharacterOfPosition ( token . pos ) . line ,
451
+ enclosingNode ,
452
+ previousRange ,
453
+ previousRangeStartLine ! ,
454
+ previousParent ! ,
455
+ enclosingNode ,
456
+ /*dynamicIndentation*/ undefined ) ;
457
+ }
458
+ }
459
+
441
460
return edits ;
442
461
443
462
// local functions
@@ -653,29 +672,14 @@ namespace ts.formatting {
653
672
} ) ;
654
673
655
674
// proceed any tokens in the node that are located after child nodes
656
- while ( formattingScanner . isOnToken ( ) ) {
675
+ while ( formattingScanner . isOnToken ( ) && formattingScanner . getStartPos ( ) < originalRange . end ) {
657
676
const tokenInfo = formattingScanner . readTokenInfo ( node ) ;
658
- if ( tokenInfo . token . end > node . end ) {
677
+ if ( tokenInfo . token . end > Math . min ( node . end , originalRange . end ) ) {
659
678
break ;
660
679
}
661
680
consumeTokenAndAdvanceScanner ( tokenInfo , node , nodeDynamicIndentation , node ) ;
662
681
}
663
682
664
- if ( ! node . parent && formattingScanner . isOnEOF ( ) ) {
665
- const token = formattingScanner . readEOFTokenRange ( ) ;
666
- if ( token . end <= node . end && previousRange ) {
667
- processPair (
668
- token ,
669
- sourceFile . getLineAndCharacterOfPosition ( token . pos ) . line ,
670
- node ,
671
- previousRange ,
672
- previousRangeStartLine ,
673
- previousParent ,
674
- contextNode ,
675
- nodeDynamicIndentation ) ;
676
- }
677
- }
678
-
679
683
function processChildNode (
680
684
child : Node ,
681
685
inheritedIndentation : number ,
@@ -717,9 +721,12 @@ namespace ts.formatting {
717
721
return inheritedIndentation ;
718
722
}
719
723
720
- while ( formattingScanner . isOnToken ( ) ) {
724
+ while ( formattingScanner . isOnToken ( ) && formattingScanner . getStartPos ( ) < originalRange . end ) {
721
725
// proceed any parent tokens that are located prior to child.getStart()
722
726
const tokenInfo = formattingScanner . readTokenInfo ( node ) ;
727
+ if ( tokenInfo . token . end > originalRange . end ) {
728
+ return inheritedIndentation ;
729
+ }
723
730
if ( tokenInfo . token . end > childStartPos ) {
724
731
if ( tokenInfo . token . pos > childStartPos ) {
725
732
formattingScanner . skipToStartOf ( child ) ;
@@ -731,7 +738,7 @@ namespace ts.formatting {
731
738
consumeTokenAndAdvanceScanner ( tokenInfo , node , parentDynamicIndentation , node ) ;
732
739
}
733
740
734
- if ( ! formattingScanner . isOnToken ( ) ) {
741
+ if ( ! formattingScanner . isOnToken ( ) || formattingScanner . getStartPos ( ) >= originalRange . end ) {
735
742
return inheritedIndentation ;
736
743
}
737
744
@@ -773,7 +780,7 @@ namespace ts.formatting {
773
780
774
781
if ( listStartToken !== SyntaxKind . Unknown ) {
775
782
// introduce a new indentation scope for lists (including list start and end tokens)
776
- while ( formattingScanner . isOnToken ( ) ) {
783
+ while ( formattingScanner . isOnToken ( ) && formattingScanner . getStartPos ( ) < originalRange . end ) {
777
784
const tokenInfo = formattingScanner . readTokenInfo ( parent ) ;
778
785
if ( tokenInfo . token . end > nodes . pos ) {
779
786
// stop when formatting scanner moves past the beginning of node list
@@ -814,7 +821,7 @@ namespace ts.formatting {
814
821
}
815
822
816
823
const listEndToken = getCloseTokenForOpenToken ( listStartToken ) ;
817
- if ( listEndToken !== SyntaxKind . Unknown && formattingScanner . isOnToken ( ) ) {
824
+ if ( listEndToken !== SyntaxKind . Unknown && formattingScanner . isOnToken ( ) && formattingScanner . getStartPos ( ) < originalRange . end ) {
818
825
let tokenInfo : TokenInfo | undefined = formattingScanner . readTokenInfo ( parent ) ;
819
826
if ( tokenInfo . token . kind === SyntaxKind . CommaToken && isCallLikeExpression ( parent ) ) {
820
827
const commaTokenLine = sourceFile . getLineAndCharacterOfPosition ( tokenInfo . token . pos ) . line ;
@@ -969,7 +976,7 @@ namespace ts.formatting {
969
976
previousStartLine : number ,
970
977
previousParent : Node ,
971
978
contextNode : Node ,
972
- dynamicIndentation : DynamicIndentation ) : LineAction {
979
+ dynamicIndentation : DynamicIndentation | undefined ) : LineAction {
973
980
974
981
formattingContext . updateContext ( previousItem , previousParent , currentItem , currentParent , contextNode ) ;
975
982
@@ -982,24 +989,26 @@ namespace ts.formatting {
982
989
// win in a conflict with lower priority rules.
983
990
forEachRight ( rules , rule => {
984
991
lineAction = applyRuleEdits ( rule , previousItem , previousStartLine , currentItem , currentStartLine ) ;
985
- switch ( lineAction ) {
986
- case LineAction . LineRemoved :
987
- // Handle the case where the next line is moved to be the end of this line.
988
- // In this case we don't indent the next line in the next pass.
989
- if ( currentParent . getStart ( sourceFile ) === currentItem . pos ) {
990
- dynamicIndentation . recomputeIndentation ( /*lineAddedByFormatting*/ false , contextNode ) ;
991
- }
992
- break ;
993
- case LineAction . LineAdded :
994
- // Handle the case where token2 is moved to the new line.
995
- // In this case we indent token2 in the next pass but we set
996
- // sameLineIndent flag to notify the indenter that the indentation is within the line.
997
- if ( currentParent . getStart ( sourceFile ) === currentItem . pos ) {
998
- dynamicIndentation . recomputeIndentation ( /*lineAddedByFormatting*/ true , contextNode ) ;
999
- }
1000
- break ;
1001
- default :
1002
- Debug . assert ( lineAction === LineAction . None ) ;
992
+ if ( dynamicIndentation ) {
993
+ switch ( lineAction ) {
994
+ case LineAction . LineRemoved :
995
+ // Handle the case where the next line is moved to be the end of this line.
996
+ // In this case we don't indent the next line in the next pass.
997
+ if ( currentParent . getStart ( sourceFile ) === currentItem . pos ) {
998
+ dynamicIndentation . recomputeIndentation ( /*lineAddedByFormatting*/ false , contextNode ) ;
999
+ }
1000
+ break ;
1001
+ case LineAction . LineAdded :
1002
+ // Handle the case where token2 is moved to the new line.
1003
+ // In this case we indent token2 in the next pass but we set
1004
+ // sameLineIndent flag to notify the indenter that the indentation is within the line.
1005
+ if ( currentParent . getStart ( sourceFile ) === currentItem . pos ) {
1006
+ dynamicIndentation . recomputeIndentation ( /*lineAddedByFormatting*/ true , contextNode ) ;
1007
+ }
1008
+ break ;
1009
+ default :
1010
+ Debug . assert ( lineAction === LineAction . None ) ;
1011
+ }
1003
1012
}
1004
1013
1005
1014
// We need to trim trailing whitespace between the tokens if they were on different lines, and no rule was applied to put them on the same line
0 commit comments