diff --git a/.gitignore b/.gitignore index 1377554..f6e1a80 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,16 @@ -*.swp +# Swap +[._]*.s[a-v][a-z] +[._]*.sw[a-p] +[._]s[a-v][a-z] +[._]sw[a-p] + +# Session +Session.vim + +# Temporary +.netrwhist +*~ +temp_stash + +# Auto-generated tag files +doc/tags diff --git a/ftdetect/karel.vim b/ftdetect/karel.vim index 00af346..102a7d1 100644 --- a/ftdetect/karel.vim +++ b/ftdetect/karel.vim @@ -1 +1 @@ -au BufNewFile,BufRead *.kl setf karel +au BufNewFile,BufRead \c*.kl setf karel diff --git a/ftplugin/karel.vim b/ftplugin/karel.vim new file mode 100644 index 0000000..56d5c48 --- /dev/null +++ b/ftplugin/karel.vim @@ -0,0 +1,21 @@ +" Fanuc Karel file type plugin for Vim +" Language: KAREL +" Maintainer: Patrick Meiser-Knosowski +" Credits: Kirill Morozov +" Version: 1.0.1 +" Last Change: 28. May 2026 +" +" Suggestions of improvement are very welcome. Please email me! +" + +" Only do this when not done yet for this buffer +if exists("b:did_ftplugin") + finish +endif +let b:did_ftplugin = 1 + +setlocal comments=:-- +setlocal commentstring=--\ %s +setlocal suffixesadd+=.kl,.KL,.ls,.LS + +let b:undo_ftplugin = "setlocal com< cms< sua<" diff --git a/indent/karel.vim b/indent/karel.vim new file mode 100644 index 0000000..9913607 --- /dev/null +++ b/indent/karel.vim @@ -0,0 +1,121 @@ +" Vim indent file +" Language: Fanuc Karel +" Maintainer: Patrick Meiser-Knosowski +" Version: 1.0.0 +" Last Change: 28. May 2026 + +" Only load this indent file when no other was loaded. +if exists("b:did_indent") + finish +endif +let b:did_indent = 1 + +setlocal nolisp +setlocal nocindent +setlocal nosmartindent +setlocal autoindent +setlocal indentexpr=GetKarelIndent() +setlocal indentkeys=!^F,o,O,=~end,0=~else,0=~case,0=~until,0=~const,0=~type,0=~var,0=~begin +let b:undo_indent = "setlocal lisp< cindent< smartindent< autoindent< indentexpr< indentkeys<" + +if get(g:,'karelSpaceIndent',1) + " Use spaces, not tabs, for indention, 2 is enough. + " More or even tabs would waste valuable space on the teach pendant. + setlocal softtabstop=2 + setlocal shiftwidth=2 + setlocal expandtab + setlocal shiftround + let b:undo_indent = b:undo_indent." softtabstop< shiftwidth< expandtab< shiftround<" +endif + +" Only define the function once. +if exists("*GetKarelIndent") + finish +endif +let s:keepcpo = &cpo +set cpo&vim + +function GetKarelIndent() abort + + let currentLine = getline(v:lnum) + if currentLine =~? '\v^--' && !get(g:, 'karelCommentIndent', 0) + " If current line has a -- in column 1, keep zero indent. + " This may be useful if code is commented out at the first column. + return 0 + endif + + " Find a non-blank line above the current line. + let preNoneBlankLineNum = s:karelPreNoneBlank(v:lnum - 1) + if preNoneBlankLineNum == 0 + " At the start of the file use zero indent. + return 0 + endif + + let preNoneBlankLine = getline(preNoneBlankLineNum) + let ind = indent(preNoneBlankLineNum) + + " Define add 'shiftwidth' pattern + let addShiftwidthPattern = '\v^\s*(' + let addShiftwidthPattern ..= 'if>|while>|for>|using>|condition>|.*' + let addShiftwidthPattern ..= '|else>' + let addShiftwidthPattern ..= '|case>' + let addShiftwidthPattern ..= '|repeat>' + let addShiftwidthPattern ..= '|const>' + let addShiftwidthPattern ..= '|type>' + let addShiftwidthPattern ..= '|var>' + let addShiftwidthPattern ..= '|begin>' + let addShiftwidthPattern ..= '|routine>' + if get(g:, 'karelIndentBetweenPrg', 1) + let addShiftwidthPattern ..= '|program>' + endif + let addShiftwidthPattern ..= ')' + + " Define Subtract 'shiftwidth' pattern + let subtractShiftwidthPattern = '\v^\s*(' + let subtractShiftwidthPattern ..= 'end(if|while|for|using|condition|structure)?>' + let subtractShiftwidthPattern ..= '|else>' + let subtractShiftwidthPattern ..= '|case>|endselect>' + let subtractShiftwidthPattern ..= '|until>' + let subtractShiftwidthPattern ..= '|const>' + let subtractShiftwidthPattern ..= '|type>' + let subtractShiftwidthPattern ..= '|var>' + let subtractShiftwidthPattern ..= '|begin>' + let subtractShiftwidthPattern ..= ')' + + " Add shiftwidth + if preNoneBlankLine =~? addShiftwidthPattern + let ind += &sw + endif + + " Subtract shiftwidth + if currentLine =~? subtractShiftwidthPattern + let ind = ind - &sw + endif + + " First case after a select gets the indent of the select. + if currentLine =~? '\v^\s*case>' + \&& preNoneBlankLine =~? '\v^\s*select>' + let ind = ind + &sw + endif + + return ind +endfunction + +" This function works almost like prevnonblank() but handles &-headers, +" comments and continue instructions like blank lines +function s:karelPreNoneBlank(lnum) abort + + let nPreNoneBlank = prevnonblank(a:lnum) + + while nPreNoneBlank > 0 && getline(nPreNoneBlank) =~? '\v^\s*(\&\w\+|--)' + " Previous none blank line irrelevant. Look further aback. + let nPreNoneBlank = prevnonblank(nPreNoneBlank - 1) + endwhile + + return nPreNoneBlank +endfunction + +let &cpo = s:keepcpo +unlet s:keepcpo + +" vim:sw=2 sts=2 et diff --git a/syntax/karel.vim b/syntax/karel.vim index 72b1a02..3d8fefd 100644 --- a/syntax/karel.vim +++ b/syntax/karel.vim @@ -1,17 +1,14 @@ " Vim syntax file -" Language: KAREL -" Maintainer: Jay Strybis -" URL: http://github.com/onerobotics/vim-karel -" License: MIT +" Language: KAREL +" Last Change: 2024-11-17 +" Maintainer: Kirill Morozov +" Credits: Jay Strybis for the initial implementation and Patrick Knosowski +" for a couple of fixes. if exists("b:current_syntax") finish endif -if version < 600 - syntax clear -endif - " KAREL is case-insensitive syntax case ignore @@ -64,10 +61,10 @@ hi def link karelFunction Function syn keyword karelClause EVAL FROM IN WHEN WITH hi def link karelClause Keyword -syn keyword karelConditional IF THEN ELSE ENDIF SELECT ENDSELECT +syn keyword karelConditional IF THEN ELSE ENDIF SELECT ENDSELECT CASE OF hi def link karelConditional Conditional -syn keyword karelRepeat WHILE DO ENDWHILE FOR +syn keyword karelRepeat WHILE DO ENDWHILE FOR TO DOWNTO hi def link karelRepeat Repeat syn keyword karelProcedure ABORT_TASK ACT_SCREEN ACT_TBL ADD_BYNAMEPC ADD_DICT ADD_INTPC ADD_REALPC ADD_STRINGPC APPEND_NODE APPEND_QUEUE @@ -112,5 +109,4 @@ hi def link karelKeyword Keyword syn region karelComment start="--" end="$" hi def link karelComment Comment - let b:current_syntax = "karel"