Vim syntax highlighting with $ and lstlisting's lstinline
Asked Answered
M

8

34

If I use the inline version of lstlisting as shown:

\lstinline{!$omp parallel for}

the syntax highlighting in vim goes wrong, and the remainder of the latex file is coloured red as if it is all part of the code listing. It's the dollar $ which causes the problem. How can I avoid this?

Mikey answered 18/7, 2011 at 20:19 Comment(2)
This seems to be a bug in the general vim syntax highlighting for tex as \verb{!$omp} produces the same result. You can try the newest syntax file from mysite.verizon.net/astronaut/vim/syntax/tex.vim.gz and contact its author Charles E. Campbell, Jr.Polka
50 rep for whoever answers with a fix for tex.vim.Dreibund
I
29

Let's finally solve this issue once and for all!

I mailed Charles E. Campbell, the maintainer of tex.vim, suggesting he'd add highlighting rules for the listings package. However it turns out lacking support for the listings package in tex.vim is actually intentional. The reasoning can be found :h tex-package. In short, you're supposed to create your own extended syntax highlighting rules (see bottom of post):

Tex: Want To Highlight More Commands?

LaTeX is a programmable language, and so there are thousands of packages full of specialized LaTeX commands, syntax, and fonts. If you're using such a package you'll often wish that the distributed syntax/tex.vim would support it. However, clearly this is impractical. So please consider using the techniques in mysyntaxfile-add to extend or modify the highlighting provided by syntax/tex.vim. Please consider uploading any extensions that you write, which typically would go in $HOME/after/syntax/tex/[pkgname].vim, to http://vim.sf.net/.

Personally I think it's a little unfortunate that it's not going to be included, as it surely increases the threshold for the average user to write his or hers LaTeX using Vim. Finding and adding syntax highlighting for lstlisting, lstinline etc. isn't too easy. It does not look like it's going to change anytime soon either when looking at this thread.

DevSolar seems to have already found it (and I appreciate the credit!), but Campbell offers a couple of example LaTeX package support vimballs. The first one, lstlisting.vba.gz, includes highlighting rules for lstlisting and lstinputlisting. It does however lack lstinline, which this topic is about.

Finally, here's my listings.vim resided in $HOME/.vim/after/syntax/tex/

syn region texZone start="\\begin{lstlisting}" end="\\end{lstlisting}\|%stopzone\>"
syn region texZone  start="\\lstinputlisting" end="{\s*[a-zA-Z/.0-9_^]\+\s*}"
syn match texInputFile "\\lstinline\s*\(\[.*\]\)\={.\{-}}" contains=texStatement,texInputCurlies,texInputFileOpt

-

Proper highlighting of verbatim, lstlisting and lstinline environments.

This seems to be the preferred solution. It does not require one to alter system wide files in /usr/share/vim/.., you don't have to download and source a vimball or alter environments rather than fixing the syntax highlighting itself. I might into look into releasing this as a simple plugin to make it more accessible.

Lastly, remember to check that you're actually running the tex filetype and not plaintex which lacks far too much to be viable. Already posted this in a comment above, but some more information can be found in a ticket I added to LaTeX-Box.

Inhere answered 8/2, 2014 at 20:16 Comment(6)
“As is shown in other answers, Konrad Rudolph's theory that Vim's syntax highlighter is not up for the job is also a little off.” – Wrong. You seem not to understand how LaTeX works. If you “fix” the problem, a simple \let\foo\verb reintroduces it. You cannot solve this problem in a general way, as I’ve explained in my answer. All you can ever hope to achieve are highly limited solutions (which is obviously fine if you customise it for your purposes; but providing a default is impractical if you use LaTeX correctly, i.e. when writing semantic code).Nur
@KonradRudolph Sorry if I misunderstood your answer. In what context would \let\foo\verb reintroduce the problem? I tried playing around with it, but to no avail. In what way would the minor changes to the tex syntax highlighting I have in my answer not work for "semantic code"?Inhere
Well once you use your own macros rather than predefined ones, the syntax highlighter doesn’t recognise verbatim code any more. You need to make explicitly aware of your macros.Nur
@KonradRudolph Hmm, I can't really see how. All the changes I've done is the three lines in my answer, and it's my understanding that it's working as intended (shown in picture). Not trying to deny anything, but can't really see what is the downside with adding those additional syntax rules.Inhere
To repeat, your changes of course work as long as you use bare \begin{lstlisting}. But often you wouldn’t do this, you would instead use lstlisting within a macro called, say, \terminal. If you then used \terminal{$ uname -a} this would screw up your highlighting. Of course you can now add a special syntax rule for \terminal. I’m just saying that this is not a general solution (although it may work well enough in practice) because \terminal might well be redefined during the execution of the script. And no, this is not just a theoretical problem, I have had this situation.Nur
@KonradRudolph That's a fair point, didn't think of it that way. I guess it's bothersome to have to into account macros based off lstlisting, but if you don't use said macros, or have a set you usually use, adding those wouldn't be too much of a problem.Inhere
R
7

The initial Problem seemed to me, that the rest of the tex-File is shown with messed-up syntax highlighting. So maybe the easy and practicable Solution could be to use a

%stopzone

after the lstlisting-Region.

Rhamnaceous answered 28/5, 2014 at 7:38 Comment(0)
N
6

This isn’t really a bug – it’s by design. In order to highlight this correctly, Vim would have to parse and interpret the whole TeX document up until the point where this code occurs, since TeX is a context-sensitive language. This is both too complex and too time-consuming for a syntax highlighting plugin.

The only acceptable fix would be to rewrite the syntax highlighter from scratch, using a complete implementation of TeX that emits meta information for each token in the source code. This is a huge project. As far as I know, no currently available TeX implementation gives such information, which means that one would really have to write this oneself.

Nur answered 27/8, 2011 at 16:0 Comment(1)
Well it would be sufficient if it handled \lstinline{...} blocks just like e.g. \begin{lstlisting}...\end{lstlisting} where everything works fine.Dreibund
P
4

This works for me:

\lstinline[mathescape]{!$\$$omp parallel for}

As far as I understand, it typesets the dollar symbol in math mode, but I couldn't see any visible difference.

Prophets answered 9/6, 2012 at 11:48 Comment(0)
G
3

I had a similar problem with inserting R commands for knitr in tex files. I had a lot of $ and other special characters within \rinline{}. And I fixed it so that Vim ignores text within this command.

You want to edit tex.vim file, on my distribution it is sudo vim /usr/share/vim/vim73/syntax/tex.vim

At ca. line line 228:

syn match texInputFile      "\\\(epsfig\|input\|usepackage\)\s*\(\[.*\]\)\={.\{-}}"     contains=texStatement,texInputCurlies,texInputFileOpt

Change to:

syn match texInputFile      "\\\(epsfig\|input\|usepackage\|rinline\)\s*\(\[.*\]\)\={.\{-}}"        contains=texStatement,texInputCurlies,texInputFileOpt

... or for lstinline:

syn match texInputFile      "\\\(epsfig\|input\|usepackage\|lstinline\)\s*\(\[.*\]\)\={.\{-}}"      contains=texStatement,texInputCurlies,texInputFileOpt
Gusgusba answered 28/8, 2013 at 16:56 Comment(1)
Optionally add syn match texInputFile "\\lstinline\s*\(\[.*\]\)\={.\{-}}" contains=texStatement,texInputCurlies,texInputFileOpt to $HOME/.vim/after/syntax/tex/lstinline.vim (or similar). For more information see github.com/LaTeX-Box-Team/LaTeX-Box/issues/124Inhere
P
1

Based on timss' answer, create a file named ~/.vim/after/syntax/tex/listings.tex and add the following rule. Replace YOURENV with the environment you want to make the highlighting exception for!

syn region texZone start="\\begin{YOURENV}" end="\\end{YOURENV}\|%stopzone\>"

This rule should now automatically be loaded next time you open Vim with an existing .tex file.

screenshot of the highlighting before and after adding the rule

Percheron answered 2/12, 2020 at 14:31 Comment(2)
I think the syntax file should be named tex.vim not listings.vim, don't you?Attainture
@Attainture For me it worked like this, though I can double check and edit the answer if you say it doesn't work for you with a filename other than tex.vim. It might also just depend on if you have a custom file there for (la)tex already, you can append to that file instead of creating a new one to keep the directory cleaner.Percheron
E
0

I don't have this issue. I am running Vim 7.3.46 with filetype=tex. (Mine defaults to "plaintex" on .tex files; you might want to check filetype with :set ft?)

Eby answered 25/8, 2011 at 23:32 Comment(1)
Lucky you. I use Vim 7.3 and :set ft? gives filetype=tex.Mikey
D
0

Going through the link posted by timss on user1174052's answer, I found Dr Chip's Vim Page, which provides the lstlisting.vba.gz Vimball plugin. Download, open in Vim...

vim lstlisting.vba.gz

...execute the vimball...

:so %

...and the next time you open a LaTeX file, contents of lstlisting environments are completely ignored by the syntax highlighting.

Credit goes to user timss, who posted the link to the LaTeX-Box ticket, where he also posted the link to Dr Chip's page. I added this answer merely as a "direct link" shortcut.

Devault answered 14/1, 2014 at 13:7 Comment(1)
Thanks for the credit! I think I finally concluded this issue so please take a look at my new (big) post.Inhere

© 2022 - 2024 — McMap. All rights reserved.