blob: 89a936ad1746cb9bfc06d12208ae09b3e14f5444 [file] [log] [blame]
Bram Moolenaare4a3bcf2016-08-26 19:52:37 +02001" Vim syntax file
2" Language: Scala
3" Maintainer: Derek Wyatt
4" URL: https://github.com/derekwyatt/vim-scala
5" License: Same as Vim
Bram Moolenaar6aa57292021-08-14 21:25:52 +02006" Last Change: 2021 Aug 11
7" by Jesse Atkinson, PR #8746
Bram Moolenaare4a3bcf2016-08-26 19:52:37 +02008" ----------------------------------------------------------------------------
9
10if !exists('main_syntax')
Bram Moolenaar89bcfda2016-08-30 23:26:57 +020011 " quit when a syntax file was already loaded
12 if exists("b:current_syntax")
Bram Moolenaare4a3bcf2016-08-26 19:52:37 +020013 finish
14 endif
15 let main_syntax = 'scala'
16endif
17
18scriptencoding utf-8
19
20let b:current_syntax = "scala"
21
22" Allows for embedding, see #59; main_syntax convention instead? Refactor TOP
23"
24" The @Spell here is a weird hack, it means *exclude* if the first group is
25" TOP. Otherwise we get spelling errors highlighted on code elements that
26" match scalaBlock, even with `syn spell notoplevel`.
27function! s:ContainedGroup()
28 try
29 silent syn list @scala
30 return '@scala,@NoSpell'
31 catch /E392/
32 return 'TOP,@Spell'
33 endtry
34endfunction
35
36unlet! b:current_syntax
37
38syn case match
39syn sync minlines=200 maxlines=1000
40
41syn keyword scalaKeyword catch do else final finally for forSome if
42syn keyword scalaKeyword match return throw try while yield macro
43syn keyword scalaKeyword class trait object extends with nextgroup=scalaInstanceDeclaration skipwhite
44syn keyword scalaKeyword case nextgroup=scalaKeyword,scalaCaseFollowing skipwhite
45syn keyword scalaKeyword val nextgroup=scalaNameDefinition,scalaQuasiQuotes skipwhite
46syn keyword scalaKeyword def var nextgroup=scalaNameDefinition skipwhite
47hi link scalaKeyword Keyword
48
49exe 'syn region scalaBlock start=/{/ end=/}/ contains=' . s:ContainedGroup() . ' fold'
50
51syn keyword scalaAkkaSpecialWord when goto using startWith initialize onTransition stay become unbecome
52hi link scalaAkkaSpecialWord PreProc
53
54syn keyword scalatestSpecialWord shouldBe
55syn match scalatestShouldDSLA /^\s\+\zsit should/
56syn match scalatestShouldDSLB /\<should\>/
57hi link scalatestSpecialWord PreProc
58hi link scalatestShouldDSLA PreProc
59hi link scalatestShouldDSLB PreProc
60
61syn match scalaSymbol /'[_A-Za-z0-9$]\+/
62hi link scalaSymbol Number
63
64syn match scalaChar /'.'/
65syn match scalaChar /'\\[\\"'ntbrf]'/ contains=scalaEscapedChar
66syn match scalaChar /'\\u[A-Fa-f0-9]\{4}'/ contains=scalaUnicodeChar
67syn match scalaEscapedChar /\\[\\"'ntbrf]/
68syn match scalaUnicodeChar /\\u[A-Fa-f0-9]\{4}/
69hi link scalaChar Character
Bram Moolenaar6aa57292021-08-14 21:25:52 +020070hi link scalaEscapedChar Special
Bram Moolenaare4a3bcf2016-08-26 19:52:37 +020071hi link scalaUnicodeChar Special
72
73syn match scalaOperator "||"
74syn match scalaOperator "&&"
Bram Moolenaar036986f2017-03-16 17:41:02 +010075syn match scalaOperator "|"
76syn match scalaOperator "&"
Bram Moolenaare4a3bcf2016-08-26 19:52:37 +020077hi link scalaOperator Special
78
79syn match scalaNameDefinition /\<[_A-Za-z0-9$]\+\>/ contained nextgroup=scalaPostNameDefinition,scalaVariableDeclarationList
80syn match scalaNameDefinition /`[^`]\+`/ contained nextgroup=scalaPostNameDefinition
81syn match scalaVariableDeclarationList /\s*,\s*/ contained nextgroup=scalaNameDefinition
82syn match scalaPostNameDefinition /\_s*:\_s*/ contained nextgroup=scalaTypeDeclaration
83hi link scalaNameDefinition Function
84
85syn match scalaInstanceDeclaration /\<[_\.A-Za-z0-9$]\+\>/ contained nextgroup=scalaInstanceHash
86syn match scalaInstanceDeclaration /`[^`]\+`/ contained
87syn match scalaInstanceHash /#/ contained nextgroup=scalaInstanceDeclaration
88hi link scalaInstanceDeclaration Special
89hi link scalaInstanceHash Type
90
91syn match scalaUnimplemented /???/
92hi link scalaUnimplemented ERROR
93
94syn match scalaCapitalWord /\<[A-Z][A-Za-z0-9$]*\>/
95hi link scalaCapitalWord Special
96
97" Handle type declarations specially
98syn region scalaTypeStatement matchgroup=Keyword start=/\<type\_s\+\ze/ end=/$/ contains=scalaTypeTypeDeclaration,scalaSquareBrackets,scalaTypeTypeEquals,scalaTypeStatement
99
100" Ugh... duplication of all the scalaType* stuff to handle special highlighting
101" of `type X =` declarations
102syn match scalaTypeTypeDeclaration /(/ contained nextgroup=scalaTypeTypeExtension,scalaTypeTypeEquals contains=scalaRoundBrackets skipwhite
103syn match scalaTypeTypeDeclaration /\%(⇒\|=>\)\ze/ contained nextgroup=scalaTypeTypeDeclaration contains=scalaTypeTypeExtension skipwhite
104syn match scalaTypeTypeDeclaration /\<[_\.A-Za-z0-9$]\+\>/ contained nextgroup=scalaTypeTypeExtension,scalaTypeTypeEquals skipwhite
105syn match scalaTypeTypeEquals /=\ze[^>]/ contained nextgroup=scalaTypeTypePostDeclaration skipwhite
106syn match scalaTypeTypeExtension /)\?\_s*\zs\%(⇒\|=>\|<:\|:>\|=:=\|::\|#\)/ contained nextgroup=scalaTypeTypeDeclaration skipwhite
107syn match scalaTypeTypePostDeclaration /\<[_\.A-Za-z0-9$]\+\>/ contained nextgroup=scalaTypeTypePostExtension skipwhite
108syn match scalaTypeTypePostExtension /\%(⇒\|=>\|<:\|:>\|=:=\|::\)/ contained nextgroup=scalaTypeTypePostDeclaration skipwhite
109hi link scalaTypeTypeDeclaration Type
110hi link scalaTypeTypeExtension Keyword
111hi link scalaTypeTypePostDeclaration Special
112hi link scalaTypeTypePostExtension Keyword
113
114syn match scalaTypeDeclaration /(/ contained nextgroup=scalaTypeExtension contains=scalaRoundBrackets skipwhite
115syn match scalaTypeDeclaration /\%(⇒\|=>\)\ze/ contained nextgroup=scalaTypeDeclaration contains=scalaTypeExtension skipwhite
116syn match scalaTypeDeclaration /\<[_\.A-Za-z0-9$]\+\>/ contained nextgroup=scalaTypeExtension skipwhite
117syn match scalaTypeExtension /)\?\_s*\zs\%(⇒\|=>\|<:\|:>\|=:=\|::\|#\)/ contained nextgroup=scalaTypeDeclaration skipwhite
118hi link scalaTypeDeclaration Type
119hi link scalaTypeExtension Keyword
120hi link scalaTypePostExtension Keyword
121
122syn match scalaTypeAnnotation /\%([_a-zA-Z0-9$\s]:\_s*\)\ze[_=(\.A-Za-z0-9$]\+/ skipwhite nextgroup=scalaTypeDeclaration contains=scalaRoundBrackets
123syn match scalaTypeAnnotation /)\_s*:\_s*\ze[_=(\.A-Za-z0-9$]\+/ skipwhite nextgroup=scalaTypeDeclaration
124hi link scalaTypeAnnotation Normal
125
126syn match scalaCaseFollowing /\<[_\.A-Za-z0-9$]\+\>/ contained
127syn match scalaCaseFollowing /`[^`]\+`/ contained
128hi link scalaCaseFollowing Special
129
130syn keyword scalaKeywordModifier abstract override final lazy implicit implicitly private protected sealed null require super
131hi link scalaKeywordModifier Function
132
133syn keyword scalaSpecial this true false ne eq
134syn keyword scalaSpecial new nextgroup=scalaInstanceDeclaration skipwhite
135syn match scalaSpecial "\%(=>\|⇒\|<-\|←\|->\|→\)"
136syn match scalaSpecial /`[^`]\+`/ " Backtick literals
137hi link scalaSpecial PreProc
138
139syn keyword scalaExternal package import
140hi link scalaExternal Include
141
142syn match scalaStringEmbeddedQuote /\\"/ contained
143syn region scalaString start=/"/ end=/"/ contains=scalaStringEmbeddedQuote,scalaEscapedChar,scalaUnicodeChar
144hi link scalaString String
145hi link scalaStringEmbeddedQuote String
146
147syn region scalaIString matchgroup=scalaInterpolationBrackets start=/\<[a-zA-Z][a-zA-Z0-9_]*"/ skip=/\\"/ end=/"/ contains=scalaInterpolation,scalaInterpolationB,scalaEscapedChar,scalaUnicodeChar
Bram Moolenaar036986f2017-03-16 17:41:02 +0100148syn region scalaTripleIString matchgroup=scalaInterpolationBrackets start=/\<[a-zA-Z][a-zA-Z0-9_]*"""/ end=/"""\ze\%([^"]\|$\)/ contains=scalaInterpolation,scalaInterpolationB,scalaEscapedChar,scalaUnicodeChar
Bram Moolenaare4a3bcf2016-08-26 19:52:37 +0200149hi link scalaIString String
150hi link scalaTripleIString String
151
152syn match scalaInterpolation /\$[a-zA-Z0-9_$]\+/ contained
153exe 'syn region scalaInterpolationB matchgroup=scalaInterpolationBoundary start=/\${/ end=/}/ contained contains=' . s:ContainedGroup()
154hi link scalaInterpolation Function
155hi link scalaInterpolationB Normal
156
157syn region scalaFString matchgroup=scalaInterpolationBrackets start=/f"/ skip=/\\"/ end=/"/ contains=scalaFInterpolation,scalaFInterpolationB,scalaEscapedChar,scalaUnicodeChar
158syn match scalaFInterpolation /\$[a-zA-Z0-9_$]\+\(%[-A-Za-z0-9\.]\+\)\?/ contained
159exe 'syn region scalaFInterpolationB matchgroup=scalaInterpolationBoundary start=/${/ end=/}\(%[-A-Za-z0-9\.]\+\)\?/ contained contains=' . s:ContainedGroup()
160hi link scalaFString String
161hi link scalaFInterpolation Function
162hi link scalaFInterpolationB Normal
163
164syn region scalaTripleString start=/"""/ end=/"""\%([^"]\|$\)/ contains=scalaEscapedChar,scalaUnicodeChar
165syn region scalaTripleFString matchgroup=scalaInterpolationBrackets start=/f"""/ end=/"""\%([^"]\|$\)/ contains=scalaFInterpolation,scalaFInterpolationB,scalaEscapedChar,scalaUnicodeChar
166hi link scalaTripleString String
167hi link scalaTripleFString String
168
169hi link scalaInterpolationBrackets Special
170hi link scalaInterpolationBoundary Function
171
172syn match scalaNumber /\<0[dDfFlL]\?\>/ " Just a bare 0
173syn match scalaNumber /\<[1-9]\d*[dDfFlL]\?\>/ " A multi-digit number - octal numbers with leading 0's are deprecated in Scala
174syn match scalaNumber /\<0[xX][0-9a-fA-F]\+[dDfFlL]\?\>/ " Hex number
175syn match scalaNumber /\%(\<\d\+\.\d*\|\.\d\+\)\%([eE][-+]\=\d\+\)\=[fFdD]\=/ " exponential notation 1
176syn match scalaNumber /\<\d\+[eE][-+]\=\d\+[fFdD]\=\>/ " exponential notation 2
177syn match scalaNumber /\<\d\+\%([eE][-+]\=\d\+\)\=[fFdD]\>/ " exponential notation 3
178hi link scalaNumber Number
179
180syn region scalaRoundBrackets start="(" end=")" skipwhite contained contains=scalaTypeDeclaration,scalaSquareBrackets,scalaRoundBrackets
181
182syn region scalaSquareBrackets matchgroup=scalaSquareBracketsBrackets start="\[" end="\]" skipwhite nextgroup=scalaTypeExtension contains=scalaTypeDeclaration,scalaSquareBrackets,scalaTypeOperator,scalaTypeAnnotationParameter
183syn match scalaTypeOperator /[-+=:<>]\+/ contained
184syn match scalaTypeAnnotationParameter /@\<[`_A-Za-z0-9$]\+\>/ contained
185hi link scalaSquareBracketsBrackets Type
186hi link scalaTypeOperator Keyword
187hi link scalaTypeAnnotationParameter Function
188
189syn match scalaShebang "\%^#!.*" display
190syn region scalaMultilineComment start="/\*" end="\*/" contains=scalaMultilineComment,scalaDocLinks,scalaParameterAnnotation,scalaCommentAnnotation,scalaTodo,scalaCommentCodeBlock,@Spell keepend fold
191syn match scalaCommentAnnotation "@[_A-Za-z0-9$]\+" contained
192syn match scalaParameterAnnotation "\%(@tparam\|@param\|@see\)" nextgroup=scalaParamAnnotationValue skipwhite contained
193syn match scalaParamAnnotationValue /[.`_A-Za-z0-9$]\+/ contained
194syn region scalaDocLinks start="\[\[" end="\]\]" contained
195syn region scalaCommentCodeBlock matchgroup=Keyword start="{{{" end="}}}" contained
196syn match scalaTodo "\vTODO|FIXME|XXX" contained
197hi link scalaShebang Comment
198hi link scalaMultilineComment Comment
199hi link scalaDocLinks Function
200hi link scalaParameterAnnotation Function
201hi link scalaParamAnnotationValue Keyword
202hi link scalaCommentAnnotation Function
203hi link scalaCommentCodeBlockBrackets String
204hi link scalaCommentCodeBlock String
205hi link scalaTodo Todo
206
207syn match scalaAnnotation /@\<[`_A-Za-z0-9$]\+\>/
208hi link scalaAnnotation PreProc
209
210syn match scalaTrailingComment "//.*$" contains=scalaTodo,@Spell
211hi link scalaTrailingComment Comment
212
213syn match scalaAkkaFSM /goto([^)]*)\_s\+\<using\>/ contains=scalaAkkaFSMGotoUsing
214syn match scalaAkkaFSM /stay\_s\+using/
215syn match scalaAkkaFSM /^\s*stay\s*$/
216syn match scalaAkkaFSM /when\ze([^)]*)/
217syn match scalaAkkaFSM /startWith\ze([^)]*)/
218syn match scalaAkkaFSM /initialize\ze()/
219syn match scalaAkkaFSM /onTransition/
220syn match scalaAkkaFSM /onTermination/
221syn match scalaAkkaFSM /whenUnhandled/
222syn match scalaAkkaFSMGotoUsing /\<using\>/
223syn match scalaAkkaFSMGotoUsing /\<goto\>/
224hi link scalaAkkaFSM PreProc
225hi link scalaAkkaFSMGotoUsing PreProc
226
227let b:current_syntax = 'scala'
228
229if main_syntax ==# 'scala'
230 unlet main_syntax
231endif
232
233" vim:set sw=2 sts=2 ts=8 et: