Skip to content

Commit 76c4a48

Browse files
authored
Merge pull request #552 from Microsoft/multiLineArrowParameters
Treat ( followed by new line as parameter context for arrow, falling back to expression
2 parents c4d834c + 0213331 commit 76c4a48

23 files changed

+1896
-108
lines changed

TypeScript.YAML-tmLanguage

Lines changed: 65 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ variables:
3131
matchingBraces: (\{([^\{\}]|(\{[^\{\}]*\}))*\})
3232
matchingBrackets: (\[([^\[\]]|(\[[^\[\]]*\]))*\])
3333
inlineComment: \/\*([^\*]|(\*[^\/]))*\*\/
34+
lookBehindOfPossiblyMultilineArrow: (?<=[(=,]|=>)
3435
# Identifier start | matching braces | matching parenthesis | matching square brackets
3536
typeParamersStart: ([_$[:alpha:]]|{{matchingBraces}}|{{matchingParenthesis}}|{{matchingBrackets}})
3637
typeParameters: (<\s*{{typeParamersStart}}([^=<>]|=[^<]|\<\s*{{typeParamersStart}}([^=<>]|=[^<])*\>)*>\s*)
@@ -39,6 +40,7 @@ variables:
3940
typeArgumentsInnerExpressionPart: '[^<>\(]|{{matchingParenthesis}}|(?<==)\>'
4041
typeArguments: '<\s*{{typeArgumentsStart}}({{typeArgumentsInnerExpressionPart}}|\<\s*{{typeArgumentsStart}}({{typeArgumentsInnerExpressionPart}})*(?!=)\>)*(?!=)>'
4142
functionCallLookup: \s*(\?\.\s*)?({{typeArguments}}\s*)?\(
43+
returnTypeOfArrow: \s*([^<>\(\)]|\<[^<>]+\>|\([^\(\)]+\))+
4244
arrowLookup: |-
4345
# sure shot arrow functions even if => is on new line
4446
(
@@ -55,9 +57,10 @@ variables:
5557
(
5658
{{typeParameters}}? # typeparameters
5759
\(\s*(([_$[:alpha:]]|{{matchingBraces}}|{{matchingBrackets}})([^()]|{{matchingParenthesis}})*)?\) # parameters
58-
(\s*:\s*([^<>\(\)]|\<[^<>]+\>|\([^\(\)]+\))+)? # return type
60+
(\s*:{{returnTypeOfArrow}})? # return type
5961
\s*=> # arrow operator
6062
)
63+
possiblyMultilineArrow: ({{typeParameters}}?[\(]\s*$) # during lookup treat <typeparameters>?( followed by line end as arrow
6164
functionOrArrowLookup: |-
6265
\s*(
6366
((async\s+)?(
@@ -66,6 +69,7 @@ variables:
6669
({{identifier}}\s*=>)
6770
)) |
6871
((async\s*)?(
72+
{{possiblyMultilineArrow}} |
6973
{{arrowLookup}}
7074
))
7175
)
@@ -86,6 +90,7 @@ variables:
8690
))
8791
)) |
8892
(:\s*(=>|{{matchingParenthesis}}|(<[^<>]*>)|[^<>(),=])+={{functionOrArrowLookup}})
93+
arrowFunctionEnd: (?==>|\{|(^\s*(export|function|class|interface|let|var|const|import|enum|namespace|module|type|abstract|declare)\s+))
8994

9095
patterns:
9196
- include: '#directives'
@@ -159,6 +164,7 @@ repository:
159164
- include: '#function-expression'
160165
- include: '#class-expression'
161166
- include: '#arrow-function'
167+
- include: '#paren-expression-possibly-arrow'
162168
- include: '#cast'
163169
- include: '#ternary-expression'
164170
- include: '#new-expr'
@@ -580,7 +586,7 @@ repository:
580586
)
581587
beginCaptures:
582588
'1': { name: storage.modifier.async.ts }
583-
end: (?==>|\{|(^\s*(export|function|class|interface|let|var|const|import|enum|namespace|module|type|abstract|declare)\s+))
589+
end: '{{arrowFunctionEnd}}'
584590
patterns:
585591
- include: '#comment'
586592
- include: '#type-parameters'
@@ -637,6 +643,10 @@ repository:
637643
endCaptures:
638644
'0': { name: punctuation.definition.parameters.end.ts }
639645
patterns:
646+
- include: '#function-parameters-body'
647+
648+
function-parameters-body:
649+
patterns:
640650
- include: '#comment'
641651
- include: '#decorator'
642652
- include: '#destructuring-parameter'
@@ -1098,9 +1108,9 @@ repository:
10981108
begin: (?!\?\.\s*[^[:digit:]])(\?)
10991109
beginCaptures:
11001110
'1': { name: keyword.operator.ternary.ts }
1101-
end: (:)
1111+
end: \s*(:)
11021112
endCaptures:
1103-
'0': { name: keyword.operator.ternary.ts }
1113+
'1': { name: keyword.operator.ternary.ts }
11041114
patterns:
11051115
- include: '#expression'
11061116

@@ -1146,6 +1156,42 @@ repository:
11461156
patterns:
11471157
- include: '#type'
11481158

1159+
# when ( is followed by end of line, it could be arrow parameter decarations, so inside this match as if parameter falling back to expression
1160+
# but do this only from expression and as last resort
1161+
paren-expression-possibly-arrow:
1162+
patterns:
1163+
- begin: '{{lookBehindOfPossiblyMultilineArrow}}\s*(async)?(?=\s*{{typeParameters}}\(\s*$)'
1164+
beginCaptures:
1165+
'1': { name: storage.modifier.async.ts }
1166+
end: (?<=\))
1167+
patterns:
1168+
- include: '#type-parameters'
1169+
- begin: \(
1170+
beginCaptures:
1171+
'0': { name: meta.brace.round.ts }
1172+
end: \)
1173+
endCaptures:
1174+
'0': { name: meta.brace.round.ts }
1175+
patterns:
1176+
- include: '#expression-inside-possibly-arrow-parens'
1177+
- begin: '{{lookBehindOfPossiblyMultilineArrow}}\s*(async)?\s*(\()(?=\s*$)'
1178+
beginCaptures:
1179+
'1': { name: storage.modifier.async.ts }
1180+
'2': { name: meta.brace.round.ts }
1181+
end: \)
1182+
endCaptures:
1183+
'0': { name: meta.brace.round.ts }
1184+
patterns:
1185+
- include: '#expression-inside-possibly-arrow-parens'
1186+
- include: '#possibly-arrow-return-type'
1187+
1188+
expression-inside-possibly-arrow-parens:
1189+
patterns:
1190+
- include: '#expressionWithoutIdentifiers'
1191+
- include: '#function-parameters-body'
1192+
- include: '#identifiers'
1193+
- include: '#expressionPunctuations'
1194+
11491195
paren-expression:
11501196
begin: \(
11511197
beginCaptures:
@@ -1155,7 +1201,6 @@ repository:
11551201
'0': {name: meta.brace.round.ts }
11561202
patterns:
11571203
- include: '#expression'
1158-
- include: '#punctuation-comma'
11591204

11601205
#cast expression
11611206
cast:
@@ -1735,7 +1780,21 @@ repository:
17351780
begin: '(?<=\))\s*(:)'
17361781
beginCaptures:
17371782
'1': { name: keyword.operator.type.annotation.ts }
1738-
end: (?==>|\{|(^\s*(export|function|class|interface|let|var|const|import|enum|namespace|module|type|abstract|declare)\s+))
1783+
end: '{{arrowFunctionEnd}}'
1784+
patterns:
1785+
- include: '#arrow-return-type-body'
1786+
1787+
#This is the check if the exoression '): something =>'' can be matched as return type of arrow
1788+
possibly-arrow-return-type:
1789+
begin: (?<=\))\s*(:)(?={{returnTypeOfArrow}}\s*=>)
1790+
beginCaptures:
1791+
'1': { name: meta.arrow.ts meta.return.type.arrow.ts keyword.operator.type.annotation.ts }
1792+
end: '{{arrowFunctionEnd}}'
1793+
contentName: meta.arrow.ts meta.return.type.arrow.ts
1794+
patterns:
1795+
- include: '#arrow-return-type-body'
1796+
1797+
arrow-return-type-body:
17391798
patterns:
17401799
# TODO: handle the fn and constructor type specifically.
17411800
# Handle returning of object type specifically here so as to not confuse it with the start of function block

0 commit comments

Comments
 (0)