+title: Vim, LaTeX, Evince, and Forward Search
+After writing the [previous post](2013-05-09-latex-vim-plugins-part2.html) (see also [part
+1](2013-04-05-latex-vim-plugins.html)), I started looking into a better forward search for LaTeX and
+Vim, specifically controlling evince via the dbus API. These instructions work with GNOME 3.8
+(specifically evince 3.8.0 and gedit-plugins-3.8.1) and should work for future versions. I am
+unsure if they will work for GNOME 3.6 and earlier.
+The way SyncTex works is that when compiling with pdflatex, you specify "-synctex=1" on the command
+line and a \<filename\>.synctex.gz file is then generated. This synctex.gz file contains
+information about the input files and how the lines of the input file map to items in the pdf.
+Evince has code to parse these .synctex.gz files, so we just need to tell evince the pdf file, the
+input file, and the line number via a dbus method.
+I use rubber (see [the first post](2013-04-05-latex-vim-plugins.html)) to compile. There is a [bug
+report](https://bugs.launchpad.net/ubuntu/+source/rubber/+bug/414431) for adding synctex support to
+rubber. For now, I took the approach suggested by Smeuuh in the bug report. In ~/bin, I added a
+file called pdflatex with the contents:
+exec /usr/bin/pdflatex -synctex=1 "$@"
+I also added *.synctex.gz to "make clean" in my generic makefile.
+Evince has a dbus method called SyncTex which takes the pdf filename, the input filename, a
+line number, and a timestamp. We could make this dbus call directly from Vim using python, execute
+dbus-send from the command line, or run some external python script. The main issue is in the
+future evince might change the dbus API. Thankfully, the gedit synctex plugin contains a python
+which makes the dbus call and can be called on the command line. Presumably this script will be
+kept up to date since it is part of gedit, and so we can just directly call the latest version of
+the script from Vim. I did make one minor change to the script. The current version (as of May 11)
+hangs after sending the message when run from the command line. The following minor change fixes
+--- /usr/lib/gedit/plugins/synctex/evince_dbus.py 2013-04-15 13:42:37.000000000 -0500
++++ evince_dbus.py 2013-05-11 15:35:31.991411344 -0500
+ a = EvinceWindowProxy('file://' + path_output, True,logger=logger)
++ loop = GObject.MainLoop()
+ def sync_view(ev_window, path_input, line_number):
+ ev_window.SyncView (path_input, (line_number, 1),0)
+ GObject.timeout_add(400, sync_view, a, path_input, line_number)
+- loop = GObject.MainLoop()
+I just installed the gedit-plugins Arch Linux package and made the above small change, but you could
+also download the evince_dbus.py file directly from git, it has no other dependencies on other files
+To wire up Vim, I added the following to tex ftplugin script (located for me at
+ let filename = bufname("%")
+ for syncfile in split(system('zgrep -l "' . filename . '" *.synctex.gz'), "\n")
+ let pdffile = substitute(syncfile, ".synctex.gz$", ".pdf", "")
+ exec 'silent ! python /usr/lib/gedit/plugins/synctex/evince_dbus.py ' .
+ \ '"' . pdffile . '" ' . lineno . ' "' . filename . '"'
+map <buffer> <LocalLeader>e :call SyncTex()<CR>
+Almost all my papers are made up of multiple tex files which I \\input into one main file which is
+then compiled using rubber and make, so I needed a way to find the pdf given the currently open
+file. The \<filename\>.synctex.gz contains all the filenames that went into building the
+corresponding pdf, so I use zgrep to find the synctex.gz file containing the current file. I even
+have one project where the same source file is imported into two different compilations (the full
+paper and an executive summary), so the vimscript above will open both pdfs because it loops through
+all the lines returned by zgrep.
+I do not use backward search (clicking in evince to change vim to the cooresponding line) because
+[CtrlP](https://github.com/kien/ctrlp.vim) on tags (which the makefile generates from LaTeX labels)
+plus normal Vim movement commands like forward/back paragraph is very fast to navigate anywhere in
+my input, even for my 50+ page papers where the input is spread over 12-15 files. Therefore I keep
+my fingers on the keyboard and use Vim forward search to scroll evince. If I want to scroll evince
+down or move evince to a different section, I use vim movement commands like page down, paragraph
+down, and/or CtrlP, and then \\e to update the evince position. This way I keep my fingers on the
+keyboard and moving around large pdfs is very fast, faster even than scrolling with the mouse. Also
+focus never leaves the vim window so at any time I can just type a vim command. It feels a little
+strange at first to scroll evince by moving in Vim, but I quickly got the hang of it. Having said
+that, evince does support backward search and the evince_dbus.py script has some code for it which
+could be the basis for a vim plugin, perhaps importing evince_dbus.py from python vimscript.