Making paper writing easier with TextMate

Update (02/23/2010) : A nice side effect of this change means I don't see the Mailplane or Google Reader icon with "unread counts" because I don't have to Apple+Tab to compile/review the PDF.


I've made some modifications to the default "Typset and View" command in TextMate's LaTeX bundle. 

Before these changes I would:

  1. Make and save edits in TextMate 
  2. Go to a Terminal window and run a shell script
  3. View the updated PDF in a Preview window

This was annoying. Lots of Apple+Tab'ing to do something that is very routine. So my new process is:

  1. Make edits in TextMate and press Apple+R

This runs the following shell script:

#!/bin/bash

osascript -e "tell application \"System Events\" to keystroke \"\`\" using {command down}"

cd "$TM_DIRECTORY"

BASENAME="${TM_FILEPATH##*/}"
PDF_FILE="${BASENAME%.*}.pdf" 
PDF_FULL_PATH="${TM_FILEPATH%/*}/$PDF_FILE"

echo "<pre>" > textmate.log
pdflatex -file-line-error -halt-on-error $BASENAME >> textmate.log
bibtex $BASENAME >> textmate.log
pdflatex -file-line-error -halt-on-error $BASENAME >> textmate.log
pdflatex -file-line-error -halt-on-error $BASENAME >> textmate.log
echo "</pre>" >> textmate.log

if [[ -e "$PDF_FILE" ]] # does the file exist?
   then echo "<meta http-equiv=\"refresh\" content=\"0; file://$PDF_FULL_PATH\">"
   else cat textmate.log
fi

rm textmate.log

Before the script runs, TextMate saves the file I'm editing and opens an output window which I leave open. TextMate switches focus to this output window automatically so the first thing the script does is switch back. This allows me to continue typing while the PDF is being compiled. Then I run pdflatex and bibtex enough times to get everything worked out. And finally, if the PDF compiled cleaning I add a meta tag to the output so that the stdout results of pdflatex disappear and everything is replaced by the PDF. If the PDF doesn't compile the output of pdflatex is left in the window so I can track down the error. I use "textmate.log" as a temp file to prevent the streaming output from distracting me.