%YAML 1.2 --- # http://www.sublimetext.com/docs/3/syntax.html name: TypeScriptReact file_extensions: - tsx scope: source.tsx contexts: main: - include: directives - include: statements - match: \A(#!).*(?=$) scope: comment.line.shebang.ts captures: 1: punctuation.definition.comment.ts comment: - match: /\*\*(?!/) captures: 0: punctuation.definition.comment.tsx push: - meta_scope: comment.block.documentation.tsx - match: \*/ captures: 0: punctuation.definition.comment.tsx pop: true - include: docblock - match: /\* captures: 0: punctuation.definition.comment.tsx push: - meta_scope: comment.block.tsx - match: \*/ captures: 0: punctuation.definition.comment.tsx pop: true - match: '(^[ \t]+)?(?=//)' captures: 1: punctuation.whitespace.comment.leading.tsx push: - match: (?=$) pop: true - match: // captures: 0: punctuation.definition.comment.tsx push: - meta_scope: comment.line.double-slash.tsx - match: (?=$) pop: true access-modifier: - match: (?)' scope: meta.arrow.tsx captures: 1: storage.modifier.async.tsx 2: variable.parameter.tsx - match: |- (?x) (?: (? is on new line ( [(]\s* ( ([)]\s*:) | # (): ([_$[:alpha:]][_$[:alnum:]]*\s*:) | # [(]param: (\.\.\.) # [(]... ) ) | ( [<]\s*[_$[:alpha:]][_$[:alnum:]]*\s+extends\s*[^=>] # < typeparam extends ) | # arrow function possible to detect only with => on same line ( (<([^<>]|\<[^<>]+\>)+>\s*)? # typeparameters \(([^()]|\([^()]*\))*\) # parameteres (\s*:\s*(.)*)? # return type \s*=> # arrow operator ) ) ) captures: 1: storage.modifier.async.tsx push: - meta_scope: meta.arrow.tsx - match: '(?==>|\{)' pop: true - include: comment - include: type-parameters - include: function-parameters - include: arrow-return-type - match: "=>" captures: 0: storage.type.function.arrow.tsx push: - meta_scope: meta.arrow.tsx - match: '(?<=\})|((?!\{)(?=\S))' pop: true - include: decl-block - include: expression arrow-return-type: - match: (?<=\))\s*(:) captures: 1: keyword.operator.type.annotation.tsx push: - meta_scope: meta.return.type.arrow.tsx - match: '(?==>|\{)' pop: true - match: '(?<=:)\s*(\{)' captures: 1: punctuation.definition.block.tsx push: - meta_scope: meta.object.type.tsx - match: '\}' captures: 0: punctuation.definition.block.tsx pop: true - include: type-object-members - include: type-predicate-operator - include: type binding-element: - include: comment - include: object-binding-pattern - include: array-binding-pattern - include: destructuring-variable-rest - include: variable-initializer boolean-literal: - match: (?\s*$)' captures: 1: punctuation.definition.comment.tsx push: - meta_scope: comment.line.triple-slash.directive.tsx - match: (?=$) pop: true - match: (<)(reference|amd-dependency|amd-module) captures: 1: punctuation.definition.tag.directive.tsx 2: entity.name.tag.directive.tsx push: - meta_scope: meta.tag.tsx - match: /> captures: 0: punctuation.definition.tag.directive.tsx pop: true - match: path|types|no-default-lib|name scope: entity.other.attribute-name.directive.tsx - match: "=" scope: keyword.operator.assignment.tsx - include: string docblock: - match: |- (?x)(? # {Array} or {Object} type application (optional .) ) (?: [\.|~] # {Foo.bar} namespaced, {string|number} multiple, {Foo~bar} class-specific callback [a-zA-Z_$]+ (?: (?: [\w$]* (?:\[\])? # {(string|number[])} type application, a string or an array of numbers ) | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) )* \) | [a-zA-Z_$]+ (?: (?: [\w$]* (?:\[\])? # {(string|number[])} type application, a string or an array of numbers ) | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) (?: [\.|~] # {Foo.bar} namespaced, {string|number} multiple, {Foo~bar} class-specific callback [a-zA-Z_$]+ (?: [\w$]* | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) )* ) ) # Check for suffix (?:\[\])? # {string[]} type application, an array of strings =? # {string=} optional parameter ) )}) \s+ ( \[ # [foo] optional parameter \s* (?: [a-zA-Z_$][\w$]* (?: (?:\[\])? # Foo[].bar properties within an array \. # Foo.Bar namespaced parameter [a-zA-Z_$][\w$]* )* (?: \s* = # [foo=bar] Default parameter value \s* [\w$\s]* )? ) \s* \] | (?: [a-zA-Z_$][\w$]* (?: (?:\[\])? # Foo[].bar properties within an array \. # Foo.Bar namespaced parameter [a-zA-Z_$][\w$]* )* )? ) \s+ (?:-\s+)? # optional hyphen before the description ((?:(?!\*\/).)*) # The type description captures: 0: other.meta.jsdoc 1: entity.name.type.instance.jsdoc 2: variable.other.jsdoc 3: other.description.jsdoc - match: |- (?x) ({(?: \* | # {*} any type \? | # {?} unknown type (?: (?: # Check for a prefix \? | # {?string} nullable type ! | # {!string} non-nullable type \.{3} # {...string} variable number of parameters )? (?: (?: function # {function(string, number)} function type \s* \( \s* (?: [a-zA-Z_$][\w$]* (?: \s*,\s* [a-zA-Z_$][\w$]* )* )? \s* \) (?: # {function(): string} function return type \s*:\s* [a-zA-Z_$][\w$]* )? )? | (?: \( # Opening bracket of multiple types with parenthesis {(string|number)} [a-zA-Z_$]+ (?: [\w$]* | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) (?: [\.|~] # {Foo.bar} namespaced, {string|number} multiple, {Foo~bar} class-specific callback [a-zA-Z_$]+ (?: [\w$]* | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) )* \) | [a-zA-Z_$]+ (?: [\w$]* | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) (?: [\.|~] # {Foo.bar} namespaced, {string|number} multiple, {Foo~bar} class-specific callback [a-zA-Z_$]+ (?: [\w$]* | \.?<[\w$]+(?:,\s+[\w$]+)*> # {Array} or {Object} type application (optional .) ) )* ) ) # Check for suffix (?:\[\])? # {string[]} type application, an array of strings =? # {string=} optional parameter ) )}) \s+ (?:-\s+)? # optional hyphen before the description ((?:(?!\*\/).)*) # The type description captures: 0: other.meta.jsdoc 1: entity.name.type.instance.jsdoc 2: other.description.jsdoc enum-declaration: - match: '(?>=|>>>=|\|= scope: keyword.operator.assignment.compound.bitwise.tsx - match: "<<|>>>|>>" scope: keyword.operator.bitwise.shift.tsx - match: "===|!==|==|!=" scope: keyword.operator.comparison.tsx - match: <=|>=|<>|<|> scope: keyword.operator.relational.tsx - match: \!|&&|\|\| scope: keyword.operator.logical.tsx - match: \&|~|\^|\| scope: keyword.operator.bitwise.tsx - match: \= scope: keyword.operator.assignment.tsx - match: "--" scope: keyword.operator.decrement.tsx - match: \+\+ scope: keyword.operator.increment.tsx - match: '%|\*|/|-|\+' scope: keyword.operator.arithmetic.tsx - match: '(?<=[_$[:alnum:])])\s*(/)(?![/*])' captures: 1: keyword.operator.arithmetic.tsx field-declaration: - match: '(?) | ([(]\s*(([)]\s*:)|([_$[:alpha:]][_$[:alnum:]]*\s*:)|(\.\.\.) )) | ([<]\s*[_$[:alpha:]][_$[:alnum:]]*((\s+extends\s*[^=>])|(\s*[,]))) | ((<([^<>]|\<[^<>]+\>)+>\s*)?\(([^()]|\([^()]*\))*\)(\s*:\s*(.)*)?\s*=>)) ) | (:\s*( (<) | ([(]\s*( ([)]) | (\.\.\.) | ([_$[:alnum:]]+\s*( ([:,?=])| ([)]\s*=>) )) ))) ) ) scope: meta.definition.property.tsx entity.name.function.tsx - match: "[_$[:alpha:]][_$[:alnum:]]*" scope: meta.definition.property.tsx variable.object.property.tsx - match: \? scope: keyword.operator.optional.tsx for-loop: - match: (?]|\<[^<>]+\>)+>\s*)?\()' push: - match: '(?<=\))(?!(([_$[:alpha:]][_$[:alnum:]]*\s*\.\s*)*|(\.\s*)?)([_$[:alpha:]][_$[:alnum:]]*)\s*(<([^<>]|\<[^<>]+\>)+>\s*)?\()' pop: true - include: literal - include: support-objects - include: object-identifiers - include: punctuation-accessor - match: "([_$[:alpha:]][_$[:alnum:]]*)" scope: entity.name.function.tsx - include: comment - match: \< captures: 0: punctuation.definition.typeparameters.begin.tsx push: - meta_scope: meta.type.parameters.tsx - match: \> captures: 0: punctuation.definition.typeparameters.end.tsx pop: true - include: type - include: punctuation-comma - include: paren-expression function-declaration: - match: '(?)| ([(]\s*(([)]\s*:)|([_$[:alpha:]][_$[:alnum:]]*\s*:)|(\.\.\.) )) | ([<]\s*[_$[:alpha:]][_$[:alnum:]]*((\s+extends\s*[^=>])|(\s*[,]))) | ((<([^<>]|\<[^<>]+\>)+>\s*)?\(([^()]|\([^()]*\))*\)(\s*:\s*(.)*)?\s*=>))) captures: 1: punctuation.accessor.tsx 2: entity.name.function.tsx - match: '(\.)\s*([[:upper:]][_$[:digit:][:upper:]]*)(?![_$[:alnum:]])' captures: 1: punctuation.accessor.tsx 2: variable.other.constant.property.tsx - match: '(\.)\s*([_$[:alpha:]][_$[:alnum:]]*)' captures: 1: punctuation.accessor.tsx 2: variable.other.property.tsx - match: "([[:upper:]][_$[:digit:][:upper:]]*)(?![_$[:alnum:]])" scope: variable.other.constant.tsx - match: "[_$[:alpha:]][_$[:alnum:]]*" scope: variable.other.readwrite.tsx import-declaration: - match: (?)) push: - match: '(/>)|(?:())' captures: 0: meta.tag.tsx 1: punctuation.definition.tag.end.tsx 2: punctuation.definition.tag.begin.tsx 3: entity.name.tag.tsx 4: punctuation.definition.tag.end.tsx pop: true - include: jsx-tag jsx-children: - include: jsx-tag-without-attributes - include: jsx-child-tag - include: jsx-tag-invalid - include: jsx-evaluated-code - include: jsx-entities jsx-entities: - match: "(&)([a-zA-Z0-9]+|#[0-9]+|#x[0-9a-fA-F]+)(;)" scope: constant.character.entity.tsx captures: 1: punctuation.definition.entity.tsx 3: punctuation.definition.entity.tsx - match: "&" scope: invalid.illegal.bad-ampersand.tsx jsx-evaluated-code: - match: '\{' captures: 0: punctuation.section.embedded.begin.tsx push: - meta_scope: meta.embedded.expression.tsx - match: '\}' captures: 0: punctuation.section.embedded.end.tsx pop: true - include: expression jsx-string-double-quoted: - match: '"' captures: 0: punctuation.definition.string.begin.tsx push: - meta_scope: string.quoted.double.tsx - match: '"' captures: 0: punctuation.definition.string.end.tsx pop: true - include: jsx-entities jsx-string-single-quoted: - match: "'" captures: 0: punctuation.definition.string.begin.tsx push: - meta_scope: string.quoted.single.tsx - match: "'" captures: 0: punctuation.definition.string.end.tsx pop: true - include: jsx-entities jsx-tag: - match: |- (?x) (?=(<)\s* ([_$a-zA-Z][-$\w.]*(?)) push: - meta_scope: meta.tag.tsx - match: '(?=(/>)|(?:()))' pop: true - match: |- (?x) (<)\s* ([_$a-zA-Z][-$\w.]*(?) captures: 1: punctuation.definition.tag.begin.tsx 2: entity.name.tag.tsx push: - match: "(?=[/]?>)" pop: true - include: comment - include: jsx-tag-attributes - include: jsx-tag-attributes-illegal - match: (>) captures: 1: punctuation.definition.tag.end.tsx push: - meta_content_scope: meta.jsx.children.tsx - match: (?=|/\*|//) captures: 1: entity.other.attribute-name.tsx jsx-tag-attributes: - include: jsx-tag-attribute-name - include: jsx-tag-attribute-assignment - include: jsx-string-double-quoted - include: jsx-string-single-quoted - include: jsx-evaluated-code jsx-tag-attributes-illegal: - match: \S+ scope: invalid.illegal.attribute.tsx jsx-tag-in-expression: - match: |- (?x) (?<=[({\[,?=>:*]|&&|\|\||\?|\Wreturn|^return|\Wdefault|^)\s* (?!(<)\s*([_$a-zA-Z][-$\w.]*(?)) #look ahead is not start of tag without attributes (?!<\s*[_$[:alpha:]][_$[:alnum:]]*((\s+extends\s+[^=>])|,)) # look ahead is not type parameter of arrow (?=(<)\s* ([_$a-zA-Z][-$\w.]*(?)) push: - match: '(/>)|(?:())' captures: 0: meta.tag.tsx 1: punctuation.definition.tag.end.tsx 2: punctuation.definition.tag.begin.tsx 3: entity.name.tag.tsx 4: punctuation.definition.tag.end.tsx pop: true - include: jsx-tag jsx-tag-invalid: - match: <\s*> scope: invalid.illegal.tag.incomplete.tsx jsx-tag-without-attributes: - match: '(<)\s*([_$a-zA-Z][-$\w.]*(?)' captures: 1: punctuation.definition.tag.begin.tsx 2: entity.name.tag.tsx 3: punctuation.definition.tag.end.tsx push: - meta_scope: meta.tag.without-attributes.tsx - meta_content_scope: meta.jsx.children.tsx - match: '()' captures: 1: punctuation.definition.tag.begin.tsx 2: entity.name.tag.tsx 3: punctuation.definition.tag.end.tsx pop: true - include: jsx-children literal: - include: numeric-literal - include: boolean-literal - include: null-literal - include: undefined-literal - include: numericConstant-literal - include: array-literal - include: this-literal - include: super-literal method-declaration: - match: '(?)| ([(]\s*(([)]\s*:)|([_$[:alpha:]][_$[:alnum:]]*\s*:)|(\.\.\.) )) | ([<]\s*[_$[:alpha:]][_$[:alnum:]]*((\s+extends\s*[^=>])|(\s*[,]))) | ((<([^<>]|\<[^<>]+\>)+>\s*)?\(([^()]|\([^()]*\))*\)(\s*:\s*(.)*)?\s*=>)))) captures: 0: meta.object-literal.key.tsx 1: entity.name.function.tsx 2: punctuation.separator.key-value.tsx push: - meta_scope: meta.object.member.tsx - match: '(?=,|\})' pop: true - include: expression - match: '(?:[_$[:alpha:]][_$[:alnum:]]*)\s*(:)' captures: 0: meta.object-literal.key.tsx 1: punctuation.separator.key-value.tsx push: - meta_scope: meta.object.member.tsx - match: '(?=,|\})' pop: true - include: expression - match: \.\.\. captures: 0: keyword.operator.spread.tsx push: - meta_scope: meta.object.member.tsx - match: '(?=,|\})' pop: true - include: expression - match: '([_$[:alpha:]][_$[:alnum:]]*)\s*(?=,|\}|$)' scope: meta.object.member.tsx captures: 1: variable.other.readwrite.tsx - include: punctuation-comma parameter-array-binding-pattern: - match: '(?:(\.\.\.)\s*)?(\[)' captures: 1: keyword.operator.rest.tsx 2: punctuation.definition.binding-pattern.array.tsx push: - match: '\]' captures: 0: punctuation.definition.binding-pattern.array.tsx pop: true - include: parameter-binding-element - include: punctuation-comma parameter-binding-element: - include: comment - include: parameter-object-binding-pattern - include: parameter-array-binding-pattern - include: destructuring-parameter-rest - include: variable-initializer parameter-name: - match: \s*\b(public|protected|private|readonly)(?=\s+(public|protected|private|readonly)\s+) captures: 1: storage.modifier.tsx - match: |- (?x)(?:\s*\b(public|private|protected|readonly)\s+)?(\.\.\.)?\s*(?) | ([(]\s*(([)]\s*:)|([_$[:alpha:]][_$[:alnum:]]*\s*:)|(\.\.\.) )) | ([<]\s*[_$[:alpha:]][_$[:alnum:]]*((\s+extends\s*[^=>])|(\s*[,]))) | ((<([^<>]|\<[^<>]+\>)+>\s*)?\(([^()]|\([^()]*\))*\)(\s*:\s*(.)*)?\s*=>)) ) | (:\s*( (<) | ([(]\s*( ([)]) | (\.\.\.) | ([_$[:alnum:]]+\s*( ([:,?=])| ([)]\s*=>) )) ))) ) ) captures: 1: storage.modifier.tsx 2: keyword.operator.rest.tsx 3: entity.name.function.tsx 4: keyword.operator.optional.tsx - match: '(?:\s*\b(public|private|protected|readonly)\s+)?(\.\.\.)?\s*(?|&&|\|\||\*\/)\s*(/)(?![/*])(?=(?:[^/\\\[]|\\.|\[([^\]\\]|\\.)+\])+/(?![/*])[gimy]*(?!\s*[a-zA-Z0-9_$]))' captures: 1: punctuation.definition.string.begin.tsx push: - meta_scope: string.regexp.tsx - match: "(/)([gimuy]*)" captures: 1: punctuation.definition.string.end.tsx 2: keyword.other.tsx pop: true - include: regexp - match: '(?]|\<[^<>]+\>)+>\s*)?\() captures: 1: punctuation.accessor.tsx 2: support.constant.dom.tsx 3: support.variable.property.dom.tsx - match: |- (?x)(?])|(?<=[\}>\]\)]|[_$[:alpha:]])\s*(?=\{)' pop: true - include: comment - include: type type-builtin-literals: - match: (?) )) ) ) ) push: - meta_scope: meta.type.function.tsx - match: (?<=\)) pop: true - include: function-parameters type-function-return-type: - match: "=>" captures: 0: storage.type.function.arrow.tsx push: - meta_scope: meta.type.function.return.tsx - match: '(?)(?=[,\]\)\{\}=;>]|//|$)' pop: true - include: comment - match: '(?<==>)\s*(\{)' captures: 1: punctuation.definition.block.tsx push: - meta_scope: meta.object.type.tsx - match: '\}' captures: 0: punctuation.definition.block.tsx pop: true - include: type-object-members - include: type-predicate-operator - include: type type-name: - match: '([_$[:alpha:]][_$[:alnum:]]*)\s*(\.)' captures: 1: entity.name.type.module.tsx 2: punctuation.accessor.tsx - match: "[_$[:alpha:]][_$[:alnum:]]*" scope: entity.name.type.tsx type-object: - match: '\{' captures: 0: punctuation.definition.block.tsx push: - meta_scope: meta.object.type.tsx - match: '\}' captures: 0: punctuation.definition.block.tsx pop: true - include: type-object-members type-object-members: - include: comment - include: method-declaration - include: indexer-declaration - include: indexer-mapped-type-declaration - include: field-declaration - include: type-annotation - match: \.\.\. captures: 0: keyword.operator.spread.tsx push: - match: '(?=\}|;|,|$)|(?<=\})' pop: true - include: type - include: punctuation-comma - include: punctuation-semicolon - include: type type-operators: - include: typeof-operator - match: "[&|]" scope: keyword.operator.type.tsx - match: (?) captures: 1: punctuation.definition.typeparameters.end.tsx pop: true - include: comment - match: (?) scope: keyword.operator.assignment.tsx - include: type - include: punctuation-comma type-paren-or-function-parameters: - match: \( captures: 0: meta.brace.round.tsx push: - meta_scope: meta.type.paren.cover.tsx - match: \) captures: 0: meta.brace.round.tsx pop: true - include: type - include: function-parameters type-predicate-operator: - match: (?) | ([(]\s*(([)]\s*:)|([_$[:alpha:]][_$[:alnum:]]*\s*:)|(\.\.\.) )) | ([<]\s*[_$[:alpha:]][_$[:alnum:]]*((\s+extends\s*[^=>])|(\s*[,]))) | ((<([^<>]|\<[^<>]+\>)+>\s*)?\(([^()]|\([^()]*\))*\)(\s*:\s*(.)*)?\s*=>)) ) | (:\s*( (<) | ([(]\s*( ([)]) | (\.\.\.) | ([_$[:alnum:]]+\s*( ([:,?=])| ([)]\s*=>) )) ))) ) ) captures: 1: meta.definition.variable.tsx entity.name.function.tsx push: - meta_scope: meta.var-single-variable.expr.tsx - match: '(?=$|[;,=}]|(\s+(of|in)\s+))' pop: true - include: var-single-variable-type-annotation - match: "([[:upper:]][_$[:digit:][:upper:]]*)(?![_$[:alnum:]])" captures: 1: meta.definition.variable.tsx variable.other.constant.tsx push: - meta_scope: meta.var-single-variable.expr.tsx - match: '(?=$|[;,=}]|(\s+(of|in)\s+))' pop: true - include: var-single-variable-type-annotation - match: "([_$[:alpha:]][_$[:alnum:]]*)" captures: 1: meta.definition.variable.tsx variable.other.readwrite.tsx push: - meta_scope: meta.var-single-variable.expr.tsx - match: '(?=$|[;,=}]|(\s+(of|in)\s+))' pop: true - include: var-single-variable-type-annotation var-single-variable-type-annotation: - include: type-annotation - include: string - include: comment variable-initializer: - match: (?