MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 1 | " Vim syntax file |
| 2 | " Language: Tera |
| 3 | " Maintainer: Muntasir Mahmud <muntasir.joypurhat@gmail.com> |
MuntasirSZN | a8aeeeb | 2025-03-11 21:17:45 +0100 | [diff] [blame] | 4 | " Last Change: 2025 Mar 11 |
MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 5 | |
| 6 | if exists("b:current_syntax") |
| 7 | finish |
| 8 | endif |
| 9 | |
| 10 | " Detect the underlying language based on filename pattern |
| 11 | " For files like file.html.tera, we want to load html syntax |
| 12 | let s:filename = expand("%:t") |
| 13 | let s:dotpos = strridx(s:filename, '.', strridx(s:filename, '.tera') - 1) |
| 14 | let s:underlying_filetype = "" |
| 15 | |
| 16 | if s:dotpos != -1 |
| 17 | let s:underlying_ext = s:filename[s:dotpos+1:strridx(s:filename, '.tera')-1] |
| 18 | if s:underlying_ext != "" && s:underlying_ext != "tera" |
| 19 | let s:underlying_filetype = s:underlying_ext |
| 20 | endif |
| 21 | endif |
| 22 | |
| 23 | " Load the underlying language syntax if detected |
| 24 | if s:underlying_filetype != "" |
| 25 | execute "runtime! syntax/" . s:underlying_filetype . ".vim" |
| 26 | unlet! b:current_syntax |
| 27 | else |
| 28 | " Default to HTML if no specific language detected |
| 29 | runtime! syntax/html.vim |
| 30 | unlet! b:current_syntax |
| 31 | endif |
| 32 | |
| 33 | " Tera comment blocks: {# comment #} |
MuntasirSZN | a8aeeeb | 2025-03-11 21:17:45 +0100 | [diff] [blame] | 34 | syn region teraCommentBlock start="{#" end="#}" contains=@Spell |
MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 35 | |
| 36 | " Tera statements: {% if condition %} |
MuntasirSZN | a8aeeeb | 2025-03-11 21:17:45 +0100 | [diff] [blame] | 37 | syn region teraStatement start="{%" end="%}" contains=teraKeyword,teraString,teraNumber,teraFunction,teraBoolean,teraFilter,teraOperator |
MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 38 | |
| 39 | " Tera expressions: {{ variable }} |
MuntasirSZN | a8aeeeb | 2025-03-11 21:17:45 +0100 | [diff] [blame] | 40 | syn region teraExpression start="{{" end="}}" contains=teraString,teraNumber,teraFunction,teraBoolean,teraFilter,teraOperator,teraIdentifier |
MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 41 | |
| 42 | " Special handling for raw blocks - content inside shouldn't be processed |
| 43 | syn region teraRawBlock start="{% raw %}" end="{% endraw %}" contains=TOP,teraCommentBlock,teraStatement,teraExpression |
| 44 | |
| 45 | " Control structure keywords |
| 46 | syn keyword teraKeyword contained if else elif endif for endfor in macro endmacro |
| 47 | syn keyword teraKeyword contained block endblock extends include import set endset |
MuntasirSZN | a8aeeeb | 2025-03-11 21:17:45 +0100 | [diff] [blame] | 48 | syn keyword teraKeyword contained break continue filter endfilter raw endraw |
MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 49 | |
| 50 | " Identifiers - define before operators for correct priority |
| 51 | syn match teraIdentifier contained "\<\w\+\>" |
| 52 | |
| 53 | " Operators used in expressions and statements |
| 54 | syn match teraOperator contained "==\|!=\|>=\|<=\|>\|<\|+\|-\|*\|/" |
| 55 | syn match teraOperator contained "{\@<!%}\@!" " Match % but not when part of {% or %} |
| 56 | syn keyword teraOperator contained and or not is as |
| 57 | |
| 58 | " Functions and filters |
| 59 | syn match teraFunction contained "\<\w\+\ze(" |
| 60 | syn match teraFilter contained "|\_s*\w\+" |
| 61 | |
| 62 | " String literals - both single and double quoted |
| 63 | syn region teraString contained start=+"+ skip=+\\"+ end=+"+ contains=@Spell |
| 64 | syn region teraString contained start=+'+ skip=+\\'+ end=+'+ contains=@Spell |
| 65 | |
| 66 | " Numeric literals - both integer and float |
| 67 | syn match teraNumber contained "\<\d\+\>" |
| 68 | syn match teraNumber contained "\<\d\+\.\d\+\>" |
| 69 | |
| 70 | " Boolean values |
| 71 | syn keyword teraBoolean contained true false |
| 72 | |
| 73 | " Highlighting links |
| 74 | hi def link teraCommentBlock Comment |
| 75 | hi def link teraKeyword Statement |
| 76 | hi def link teraOperator Operator |
| 77 | hi def link teraFunction Function |
| 78 | hi def link teraIdentifier Identifier |
| 79 | hi def link teraString String |
| 80 | hi def link teraNumber Number |
| 81 | hi def link teraBoolean Boolean |
MuntasirSZN | a8aeeeb | 2025-03-11 21:17:45 +0100 | [diff] [blame] | 82 | hi def link teraFilter Function |
| 83 | hi def link teraStatement Statement |
| 84 | hi def link teraExpression Statement |
MuntasirSZN | 14da0fb | 2025-03-09 08:49:14 +0100 | [diff] [blame] | 85 | |
| 86 | " Clean up script-local variables |
| 87 | unlet s:filename |
| 88 | unlet s:dotpos |
| 89 | if exists("s:underlying_ext") |
| 90 | unlet s:underlying_ext |
| 91 | endif |
| 92 | unlet s:underlying_filetype |
| 93 | |
| 94 | let b:current_syntax = "tera" |