使用 Vim 的 syn-include 和 syn-region 嵌入语法高亮时遇到问题
问题描述
我正在尝试让 Vim 通过以下方式语法高亮任何以扩展名 .Rtex
结尾的文件:
I am trying to get Vim to syntax highlight any file that ends with extension .Rtex
in the following way:
- 所有顶级文本都以 TeX 突出显示
- 例外:任何包含在
egin{python}...end{python}
中的文本都被高亮显示为 Python
- All top level text is highlighted as TeX
- Exception: any text enclosed in
egin{python}...end{python}
is highlighted as Python
我能够单独达到这些标准中的每一个,但无法同时达到这两个标准.我认为 TeX 突出显示会以某种方式覆盖我的 Python 突出显示区域,或者阻止它们生效,我一直在试图弄清楚如何.
I am able to achieve each of these criteria individually, but unable to achieve both simultaneously. I think that somehow the TeX highlighting overrides my Python-highlighted regions, or prevents them from taking effect, and I am stuck trying to figure out how.
第一步:编辑.vimrc
,给扩展名为.Rtex
的文件赋予rtex
文件类型:
First step: edit .vimrc
to give files with extension .Rtex
the filetype rtex
:
au BufRead *.Rtex setf rtex
第二步:创建~/.vim/syntax/rtex.vim
.该文件的内容将决定如何突出显示 .Rtex
文件.
Second step: create ~/.vim/syntax/rtex.vim
. It is the contents of this file that will determine how to highlight .Rtex
files.
第三步:通过使 rtex.vim
看起来像这样,启用通用的顶级 TeX 突出显示:
Third step: enable general top-level TeX highlighting, by making rtex.vim
look like this:
runtime! syntax/tex.vim
如果我现在打开一个 .Rtex
文件,整个文件将突出显示为 TeX,包括 egin{python}...end{python}
,正如预期的那样.
If I now open a .Rtex
file, the entire file is highlighted as TeX, including any text within egin{python}...end{python}
, as expected.
第四步: 按照 Vim 的 :help syn-include
中的说明包含 python 高亮并将其应用于由 egin{python} 分隔的所有区域
和 end{python}
.我的 rtex.vim
文件现在看起来像这样:
Fourth step: follow the instructions in Vim's :help syn-include
to include python highlighting and apply it to all regions delimited by egin{python}
and end{python}
. My rtex.vim
file now looks like this:
runtime! syntax/tex.vim
unlet! b:current_syntax
syntax include @Python syntax/python.vim
syntax region pythonCode start="\begin{python}" end="\end{python}" contains=@Python
unlet!b:current_syntax
命令旨在强制执行 python.vim
语法文件,即使现有语法 (TeX) 已经处于活动状态.
The unlet! b:current_syntax
command is meant to force the python.vim
syntax file to execute even though an existing syntax (TeX) is already active.
问题:如果我现在打开一个 .Rtex
文件,整个文件仍然仅突出显示为 TeX.egin{python}...end{python}
区域似乎没有效果.
Problem: If I now open a .Rtex
file, the entire file is still highlighted only as TeX. The egin{python}...end{python}
region seems to have no effect.
实验:如果我删除或注释掉 runtime!
命令,我确实会在 egin{python}...end{python}
区域,完全符合需要,但在文档的其余部分当然没有 TeX 突出显示.因此,我得出结论,TeX 突出显示在某种程度上是防止 python 区域生效的原因.
Experiment: If I remove or comment out the runtime!
command, I do get python highlighting, within the egin{python}...end{python}
regions, exactly as desired, but of course no TeX highlighting in the remainder of the document. I therefore conclude that the TeX highlighting is somehow responsible for preventing the python regions from taking effect.
Vim 大师能给我一些建议吗?我目前很难过.我查看了几个似乎相关的页面和 stackoverflow 问题,但到目前为止都没有找到解决方案:
Can a Master of Vim offer me any suggestions? I am currently stumped. I have looked at several pages and stackoverflow questions that seem relevant, but none of them have so far led to a solution:
- http://vim.wikia.com/wiki/Different_syntax_highlighting_within_regions_of_a_file
- Vim 中的嵌入式语法高亮显示
- yaml中嵌套html的VIM语法高亮
解决方案
在对手册进行了更多的研究,以及更多的尝试和错误之后,我终于回答了我自己的问题(一个同时令人尴尬和崇高的成就),我现在保存在这里以供后代使用.
After some more study of the manual, and much more trial and error, I have finally answered my own question (a simultaneously embarrassing and sublime accomplishment), which I now preserve here for posterity.
基本上,我认为问题在于 python 突出显示不会生效,因为 pythonCode
区域本身包含在 tex.vim
,所以它不是顶级的.解决方案是也include
(而不仅仅是runtime
)tex.vim
,给它一个类似@TeX
,然后将 containedin=@TeX
添加到我的 python 区域定义中.所以 syntax/rtex.vim
现在看起来像这样:
Basically, I think the problem is that the python highlighting wouldn't take effect because the pythonCode
region was itself contained in a region or highlight group defined by tex.vim
, so it wasn't top-level. The solution is to also include
(rather than just runtime
) tex.vim
, giving it a name like @TeX
, and then add containedin=@TeX
to my python region definition. So syntax/rtex.vim
now looks like this:
let b:current_syntax = ''
unlet b:current_syntax
runtime! syntax/tex.vim
let b:current_syntax = ''
unlet b:current_syntax
syntax include @TeX syntax/tex.vim
let b:current_syntax = ''
unlet b:current_syntax
syntax include @Python syntax/python.vim
syntax region pythonCode matchgroup=Snip start="\begin{python}" end="\end{python}" containedin=@TeX contains=@Python
hi link Snip SpecialComment
let b:current_syntax = 'rtex'
这行得通!我不确定是否所有这些 unlet b:current_syntax
命令都是绝对必要的.我还给了 python 区域分隔符一个匹配组(Snip
),以便它们可以自己突出显示(使用 SpecialComment
颜色),而不是简单地保留,这显然是什么默认情况下会发生,因为它们不再被视为 TeX 的一部分.
And this works! I'm not sure if all of those unlet b:current_syntax
commands are strictly necessary. I also gave the python region delimiters a matchgroup (Snip
) so that they can be highlighted themselves (with the SpecialComment
color), rather than left just plain, which is apparently what happens by default, since they are no longer considered part of the TeX.
现在为不同语言添加更多高亮区域是一件微不足道的事情(例如,egin{Scode}...end{Scode}
),如果你得到进入文学编程——我提出这个问题的最初动机.
Now it is a trivial thing to add more highlight regions for different languages (e.g., egin{Scode}...end{Scode}
), which is great if you're getting into literate programming -- the original motivation for my question.
这是一个屏幕截图,展示了它如何与嵌入在 TeX 文档中的 Python 和 R 代码一起工作:
here is a screenshot showing how it works with Python and R code embedded in a TeX document:
相关文章