28

I just saw a similar question about Emacs/AUCTeX so this one was coming. I use nvi for all my editing including TeX and it would not change it for anything. However, even after almost 20 years of use I never stop to be amazed by clever trick people show me of and on.

This is my favorite list of nvi tricks (to be edited and improved over next couple of days):

1) Do not forget to use key mappings! Don't forget also that the whole power of Unix is on your fingertips as there is nothing easier than to invoke shell commands in nvi. Combination of this two ideas is very potent.

a) Even though nvi has no built in spell checker it doesn't mean that we can't do a spell checking. Actually it is even easier than in most "user friendly editors". This is the most useful line in my .exrc for TeX editing.

map v :w^M:!ispell %^M:e!^M^M

The spell checking is done by pressing ESC+v. Note that people who prefer aspell over ispell can put something like

map v :w^M:!aspell check  %^M:e!^M^M

b) Another useful keyboard mapping specifically for TeX users.

map ^X :w^M:!make pdf clean %^M^M

What is does it enables you to tex your most recent edit by pressing Ctrl+X which pending on your pdf-viewer is automatically updated. Almost WYSIWYG for nvi users. Ok for people who want to add this into their .exrc files note that tex-ing is actually done with make utility. So I do have my own home cooked Makefile in my working directory. Targets pdf and clean are described in the Makefile.

2) nvi comes with pretty sensible sets of default values. However a carefully crafted .exrc can dramatically increase productivity of editing. This is my complete .exrc.

set autoindent
set autoprint
set cedit=^[
set extended
set file=^[
set number
set ruler
set shiftwidth=4
set showmatch
set showmode
set tabstop=8
set verbose
set wrapmargin=8

map V !}fmt -w 72 ^M
map v :w^M:!ispell %^M:e!^M^M
map ^X :w^M:!make pdf clean-ps %^M^M

Probably two of the most underappreciated options which were not present in the original vi editor are extended option which allows you to use extended regular expressions (think egrep) and cedit=^[ (^[ which is ESC in the verbose mode) allows you to use command history in ex mode.

There are two other options which I do not have in my .exrc file but I find it very useful. By default nvi search is case sensitive. We can override this behavior by setting option ignorecase (ic). Since I tend to use extended regular expressions this is not essential feature for me. Second non default option which is very useful is incremental search. Just set searchincr and you will see what nvi matches words as you type in each letter of your search string.

3) Using abbreviations coming soon.

4) Buffers, markers and similar coming soon

5) Batch editing for beginners coming soon.

Edit:

This edit is inspired by Stefan Kottwitz comment. My favorite thread on vi/vim from stackexchange is "What is your most productive shortcut with VIM?". I almost fall of the chair after reading the first answer "Your problem with Vim is that you don't grok vi".

2
  • 3
    See What are your favorite Vim tricks on SO, with currently 142 answers.
    – Stefan Kottwitz
    Apr 21, 2012 at 9:50
  • 1
    +1 for using nvi! :-D (and the spell checker tip) too bad vim doesn’t have all the repetition goodness of the originals.
    – morbusg
    Apr 22, 2012 at 16:29

4 Answers 4

24

Disclaimer: I usually edit .tex files in Vim, but I don't use the Vim-LaTeX suite.

I wouldn't say the following suggestions are tricks per se - they are provided by third-party plugins - but they actually help me with my usual TeX workflow:

snipMate

Created by Michael Sanders

From the manual: snipMate.vim aims to be an unobtrusive, concise vim script that implements some of TextMate's snippets features in Vim. A snippet is a piece of often-typed text that you can insert into your document using a trigger word followed by a <tab>.

snipMate helps me a lot, mainly because it offers snippets for several languages out of the box, including TeX. For example, when editing a file mydoc.tex, typing

begin<tab>

will expand to an environment block of the form

\begin{env}

\end{env}

with the cursor selecting the word env. After typing the environment name, hitting <tab> again will take the cursor to

\begin{env}
   |        
\end{env}

for me to type. The snippets list for TeX is not that big, but the plugin seems to have a fairly easy syntax for us to create custom snippets. Here's the code used to create the above snippet:

# \begin{}...\end{}
snippet begin
\begin{${1:env}}
    ${2}
\end{$1}

So far, so good.

Tabular

Created by Matt Wozniski

From the manual: Sometimes, it's useful to line up text. Naturally, it's nicer to have the computer do this for you, since aligning things by hand quickly becomes unpleasant. While there are other plugins for aligning text, the ones I've tried are either impossibly difficult to understand and use, or too simplistic to handle complicated tasks. This plugin aims to make the easy things easy and the hard things possible, without providing an unnecessarily obtuse interface. It's still a work in progress, and criticisms are welcome.

Tabular helps me a lot when I'm trying to add elements in a tabular environment. It organizes the columns in a human-readable format. Let's suppose we have the following mess entries:

\begin{tabular}{lll}
    Hello world & I love ducks & Vim rocks\\
    Think of a very long entry & How was your day & Quack!
\end{tabular}

It's quite confusing, but Tabular can help us. I usually enter in Visual mode, select the two rows and then issue

:'<,'>Tabularize /&

and we are done. The new rows now look like

\begin{tabular}{lll}
    Hello world                & I love ducks     & Vim rocks\\
    Think of a very long entry & How was your day & Quack!
\end{tabular}

I can also apply :Tabularize /&, but I prefer to delimit my scope. A similar plugin Align can also be used for this purpose, see my answer to Which text editor to make tables scripts human readable.

surround

Created by Tim Pope

From the manual: Surround.vim is all about "surroundings": parentheses, brackets, quotes, XML tags, and more. The plugin provides mappings to easily delete, change and add such surroundings in pairs.

I usually use this plugin when editing source code from other languages. Let's suppose I have the following text enclosed between double quotes:

"Hello world"

By calling cs"', the double quotes are automatically replaced by single quotes. I decided to make a different use of surround, so I took an example from the documentation and adapted to my TeX needs. First of all, I have the following line in my .vimrc:

autocmd FileType tex let b:surround_45 = "``\r''"

Note that 45 is the ASCII code of -. Now I can simply call cs"- and my text

"Hello world"

becomes

``Hello world''

The documentation has a few examples on TeX snippets.


For those who want to try the plugins I listed above, I highly recommend the use of the awesome pathogen plugin created by Tim Pope.

From the manual: Manage your runtimepath with ease. In practical terms, pathogen.vim makes it super easy to install plugins and runtime files in their own private directories.

Hope it helps. :)

1
  • I started using vim-operator-surround rather than surround, so I could add custom brackets such as $\langle\rangle$ with cs(<. I didn't know normal surround could do customization. Do you think it could work in my case as well? Also, can you now do things like da" to remove the double quoted sentence? Oct 7, 2015 at 10:42
7

I use the vim-latex suite, and absolutely love it. However, I've found the following tweaks quite useful to help me compile my documents.

(These commands will be most useful to Linux users)

  1. I like to 'toggle' between seeing the compiler output and not. With the setup below, I simply press t which toggles between 'silent' and 'verbose' mode

  2. I like to be able to choose which compile method I use- either latex, pdflatex, etc. I can use

    • f just to latex the main file
    • F to use latex->dvips->ps2pdf the main file
    • P to use pdflatex on the main file
    • F6 to view the main pdf file (calling evince)
    • F4 to view the main dvi file (calling xdvi)
  3. Choosing the main file with the vim-latex suite requires creation of a separate file in the current working directory. The script below greps the current file and searches for %*** mainfilename.tex; if it doesn't find any, then the current file is the main file, if it does find one, then the matched expression is the main file

~/.vim/after/ftplugin/tex.vim

" by default make the compile verbose
let g:Myvar="noisy"

" function to compile the mainfile, either verbosely or not
function! CompileMainfile()
    if g:Myvar=="noisy"
    :! MakepdfMainfile.sh %
   else
    "echo "quiet"
    :! MakepdfMainfile.sh % noshow
   endif
endfunction

" latex => dvips => ps2pdf
function! DvipsMainfile()
    if g:Myvar=="noisy"
    :! compileMainfile.sh -d %
   else
    "echo "quiet"
    :! compileMainfile.sh -dq %
   endif
endfunction

" pdflatex
function! PdflatexMainfile()
    if g:Myvar=="noisy"
    :! compileMainfile.sh -p %
   else
    "echo "quiet"
    :! compileMainfile.sh -pq %
   endif
endfunction

" just latex
function! Justlatex()
    if g:Myvar=="noisy"
    :! compileMainfile.sh %
   else
    "echo "quiet"
    :! compileMainfile.sh -q %
   endif
endfunction

" function to toggle between Noisy and Quiet
function! ToggleNQ()
    if g:Myvar=="noisy"
     let g:Myvar="quiet"
     echo "Silent mode ON"
    else
     let g:Myvar="noisy"
     echo "Silent mode OFF"
    endif
endfunction

:map f :w<CR>:call Justlatex()<CR>
:map F :w<CR>:call DvipsMainfile()<CR>
:map P :w<CR>:call PdflatexMainfile()<CR>
:map <F4> :! viewMainDVI.sh %<CR>
:map <F6> :! viewMainPDF.sh %<CR>
:map t :call ToggleNQ() <CR>

/usr/local/bin/compileMainfile.sh

#! /bin/bash
#
# compileMainfile.sh
#
#   December 2011
#
#   Purpose: compile a .tex file either using latex, pdflatex, or
#               latex=> dvips=> ps2pdf, in silent mode or verbose mode
#   examples
#           compileMainfile myfile.tex          # just latex myfile
#           compileMainfile -d myfile.tex       # latex => dvips => ps2pdf
#           compileMainfile -p myfile.tex       # pdflatex myfile
#
#           add the -q flag for SILENT (or quiet) mode
#           compileMainfile -q myfile.tex
#           compileMainfile -qd myfile.tex
#           compileMainfile -qp myfile.tex
#
# See pgs 249 & 250 of BASH COOKBOOK for examples of getopts- really useful!


# argument check
ERROR="Too few arguments : no file name specified"
[[ $# -eq 0 ]] && echo $ERROR && exit  # no args? ... print error and exit

# define functions
function makepdf ()
{
    echo "======================================="
    echo "Main file is $mainFile.tex"
    echo "======================================="
    if [ $quiet -eq 0 ]
    then
        echo "VERBOSE mode on"
        # latex mainFile.tex
        [[ $uselatex -eq 1 ]] && [[ $convertdvips -ne 1 ]] && latex $mainFile
        # latex => dvips => ps2pdf mainFile.tex
        [[ $convertdvips -eq 1 ]] && makepdf.sh $mainFile 1 && echo "DVIPS"
        # pdflatex
        [[ $usepdflatex -eq 1 ]] && pdflatex $mainFile && echo "PDFLATEX"
        egrep 'undefined' $mainFile.log
        egrep 'multiply-defined' $mainFile.log
        egrep '\\end occurred when \\iftrue' $mainFile.log
    else
        echo "SILENT mode on"
        if [ $convertdvips -eq 1 ]
        then
            # latex => dvips => ps2pdf mainFile.tex
            echo "DVIPS"
            nohup makepdf.sh $mainFile 1 &
        elif [ $uselatex -eq 1  ]
        then
            # latex mainFile.tex
            echo "just LaTeX"
            nohup latex $mainFile &
        elif [ $usepdflatex -eq 1 ]
        then
            # pdflatex
            echo "PDFlatex"
            nohup pdflatex $mainFile &
        fi
    fi
}


# set default values of flags
quiet=0
uselatex=1
usepdflatex=0
convertdvips=0

# check flags, and change defaults appropriately
while getopts 'abpqd' OPTION
do
 case $OPTION in 
  q)    quiet=1
   echo "Silent mode ON"
   ;;
  p)    usepdflatex=1
        uselatex=0
   ;;
  d)    convertdvips=1
   ;;
  ?)    printf "Usage: %s: [-a] [-b value] args\n" $(basename $0) >&2
        exit 2
        ;;
 esac 
done

shift $(($OPTIND - 1))

# check we haven't called with -dp 
# which would mean dvips and pdflatex
[[ $usepdflatex -eq 1 ]] && [[ $convertdvips -eq 1 ]] && echo "Option clash: cannot be called with -dp" && exit

# name of MAINFILE
mainFile=$1

# incase we're compiling from within the CHAPTER file
set `grep -F %*** $1 | tr -d "%*" `""
dummy=$1

# delete the file extension
mainFile=${mainFile/%.tex/}
dummy=${dummy/\.*/}

# check the length of the dummy string, if it's 0 then latex the current file
# otherwise latex the referenced latex file
if [ $dummy ]
then
 mainFile=$dummy
fi

# call the makepdf function
makepdf
exit

/usr/local/bin/MakepdfMainfile.sh

#! /bin/bash
#
# December 2011
#
# Purpose:  compile latex->dvips->ps2pdf
#       either silently or verbosely
#
# Options:  noshow
#
# examples: MakepdfMainfile.sh myfile.tex noshow    # silent mode
#       MakepdfMainfile.sh myfile.tex       # verbose mode

# argument check
ERROR="Too few arguments : no file name specified"
[[ $# -eq 0 ]] && echo $ERROR && exit  # no args? ... print error and exit

# assume VERBOSE mode by default
noshow=0
[[ $# -eq 2 ]] && [[ $2 == "noshow" ]] && noshow=1  # otherwise turn on SILENT mode

# name of MAINFILE
mainFile=$1

# incase we're compiling from within the CHAPTER file
set `grep -F %*** $1 | tr -d "%*" `""
dummy=$1

# delete the file extension
mainFile=${mainFile/%.tex/}
dummy=${dummy/\.*/}

# check the length of the dummy string, if it's 0 then latex the current file
# otherwise latex the referenced latex file
if [ $dummy ]
then
 mainFile=$dummy
fi

echo "======================================="
echo "Making PDF : Main file is $mainFile"
echo "======================================="
if [ $noshow -eq 1 ]
then
    echo "SILENT mode on"
    nohup makepdf.sh $mainFile 1 &
else
    echo "VERBOSE mode on"
    makepdf.sh $mainFile 1
    echo "======================================="
    echo "Made PDF : Main file is $mainFile".tex
    echo "======================================="
    egrep 'undefined' $mainFile.log
    egrep 'multiply-defined' $mainFile.log
    egrep '\\end occurred when \\iftrue' $mainFile.log
fi
1
  • Fantastic answer, Chris! I'm updating my Vim configuration. :) Apr 23, 2012 at 0:29
5

Tables

I write a lot of tables which are all pretty much the same. I bind most of my commands to ;word , table being bound to ;tab. It asks for number of columns, caption, and whether or not it's fixed width. I of course use the Tabularize plugin as well for formatting.

function! TableCreator()
        let curline=getline('.')
        call inputsave()
        let cols = input('Enter number of columns: ')
        let caption = input('Caption: ')
        let centering = input('Fixed width? (y/n) :')
        call inputrestore()
        exe "normal a\\begin{table}[!h]\r\\caption{" . caption . "\\label{tab:}}\r\\begin{center}\r\\begin{tabular}{\e"
        let numcols = cols
        while cols > 0
                if centering == 'y'
                        exe "normal ap{4cm}\e"
                else
                        exe "normal ac\e"
                endif
                let cols = cols-1
        endwhile
        exe "normal a}\e"
        let cols = numcols - 1
        exe "normal a\r\r\r\e"
        exe "normal a\\end{tabular}\r\\end{center}\r\\end{table}\\ \\\\"
endfunction

Spell Checking

I write a couple different languages, and depending on my target audience. I use this to conveniently switch between them.

" Spell Check
let b:myLang=0
let g:myLangList=["nospell","de","en_gb","en_us"]
function! ToggleSpell()
  let b:myLang=b:myLang+1
  if b:myLang>=len(g:myLangList) | let b:myLang=0 | endif
  if b:myLang==0
    setlocal nospell
  else
    execute "setlocal spell spelllang=".get(g:myLangList, b:myLang)
  endif
  echo "spell checking language:" g:myLangList[b:myLang]
endfunction
3
  • Cool tricks! :) Apr 23, 2012 at 0:30
  • @EricR: How do you use the script? Apr 30, 2012 at 11:20
  • @MarcoDaniel, the two scripts I have shown here I have bound as follows: imap ;tab <ESC>:call TableCreator()<cr> and nmap <silent><F7> :call ToggleSpell()<CR>
    – EricR
    Apr 30, 2012 at 17:43
3

Keeping it down to the plugins the most relevant for LaTeX editing.

NERD Commenter

By Martin Greenfell, aka scrooloose

Quick commenting of blocks of text, automatically using correct comment notation for the detected language (including TeX).

It is either used in single line mode, where

  • \CC will comment the current line
  • \CU will uncomment the current line
  • \CSpace will toggle the comment status of the current line.

\ is the default "leader" key; you might have it configured differently (I personally use Space). The command can of course be mapped to whatever one wants, but these are the default mappings.

I also often (perhaps more often) use it in visual multiline mode by moving to the first line, pressing Shift+V for visual line selection, moving to the last and then commenting the whole block with the above mappings.

There are more functions and commands available; see the documentation in the above link.

Gundo

By Steve Losh

"Graphical undo". Modern Vim versions actually keep undo trees in memory that are directly traversable by g+ and g-. This can be a "life saver" to rescue file modifications even after accidentally issuing input after having walked backwards in the undo history, but walking the tree is mostly a blind trial and error process using these commands.

Gundo opens a split where it draws the actual undo tree and lets you traverse it graphically. It is not something that I use every day, but the times when I need to walk in the undo forest, it is massively useful, not least when writing LaTeX.

Vundle

By gmarik

Pathogen used to be absolutely essential for handling plugins, and all Vim users should be thankful for it. Vundle is a noteworthy improvement of the concept, directly plugging into primarily Github and the official Vim script catalogue.

This might not seem like much, but it allows you to keep the full information on installed plugins within ~/.vimrc, which makes it a lot easier to synchronize setups across machines and keep everything tidy in version control itself in a more straightforward way than can be done with Pathogen.

Better Rainbow Parentheses

By kien

There are many versions of this type of plugin. It highlights matching parentheses in different colors per matching pair.

I do not have it activated by default, but have a mapping to toggle it on and off in case I feel lost in the land of brackets and braces, which can certainly happen in LaTeX.

LaTeX-Box

I have noticed that I am not alone in finding Vim-LaTeX (aka LaTeX-suite) too heavy and intrusive while editing. I actually had it enabled by default for years, but the only functions I used intentionally was the folding and perhaps the "smart quotes". On the other hand, several of its functions was a direct and recurring hindrance for my editing.

Some might like the Vim-LaTeX method, but for me LaTeX-Box lightweight and non-intrusive approach fits much better, and it is never in my way.

LaTeX-Box enables "smart completion" (context aware of bibliography entries, labels, environments, etc.), Latexmk integration (e.g. continuous compilation on file changes), folding, and more. See the documentation.

3
  • 2
    Thanks for the mention of LaTeX-Box; I've also found that Vim-LaTeX can be a hindrance to me at times! Jun 19, 2014 at 14:17
  • Afaik vim already saves all your changes as a tree, but it is a bit tricky to traverse it. Does this mean I don't need to install Gundo before I actually really need it? Oct 7, 2015 at 10:47
  • @ThomasAhle: Yes, as mentioned above Vim saves undo trees by default, that you can traverse with g+ and g-, though it is quite flaky to do it blindly like that, since the trees easily become complex with several branches. Gundo helps with the visualization. Once installed, it lies latent until you activate it, which opens up a pane with the graphical undo-tree, so it does not hurt just to have it installed. I suppose you could try to install it "live" upon demand, but it seems like something you would not want to do if you are in the situation that you really need it. Oct 8, 2015 at 16:00

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .