You got LaTeX in my Markdown!
Tuesday, October 21, 2014
Working title: You got Markdown in my LaTeX!
I hate writing documents in Microsoft Word and Apple Pages. I spend way too much time fiddling with formatting, page layout, and typesetting before everything looks the way I want it. And writing math equations, even with Word's GUI equation editor, is tedious and takes too much clicking. I'm a programmer—just let me use LaTeX's equation format instead!
tl;dr
If you want to write documents in Markdown, embed LaTeX, and generate PDFs, use Pandoc.
Skip down to Kung Fu Pandoc to get started!
So just use LaTeX, they said. It'll be fun, they said.
I like typesetting tools, and I like LaTeX... with reservations. Some of my complaints:
- The boilerplate needed to get a TeX document up and running is pretty massive.
- LaTeX is a pain in the ass to write. There is so much character overhead behind basic formatting.
- Bold?
\textbf{bolded text}
. - Inline code?
\texttt{for (int i = 0; i < 42; i++)}
- Basic tables? Here's a short reference.
- Bold?
- Holy reserved characters, Batman! Here are things you can't write in LaTeX without escaping:
# $ % ^ & _ { } ~ \
It's not like I'd ever want to use a dollar sign in my budget report or an underscore in my C code.
- If you don't escape a character properly, you'll probably get a syntax error. LaTeX's syntax errors are cryptic and terrifying:
Missing $ inserted
: could mean just about anything, such as: you put too many lines inside an equation block, or you forgot to close a curly bracket.No line here to end
: means that you tried to continue a line when LaTeX "didn't expect it". When does LaTeX expect it? God only knows.- Not confusing enough for you? There are more errors where those came from.
Wouldn't it be nice if...
This semester, I tried to write an assignment for class and found out my LaTeX build chain in Sublime broke. Instead of trying to troubleshoot it, I started thinking about what I'd like to use instead.
Here's why I love LaTeX:
- It lets me write equations quickly. Its equation syntax makes sense to me, and it's easy to
stealimport equations from Wikipedia pages. - It's a typesetting program, not a WYSIWYG. No more screwing around with weird margin sliders and page layout tools and header settings: simply throw in your text, edit the settings once, and watch all your text reflow into place.
- It's easy to generate a PDF from a LaTeX file.
Here's why I prefer Markdown as a language to write formatted text:
- It's SUPER lightweight.
**bold**
,*italic*
, ```inline code` ``. - GitHub-flavored Markdown is super cool. It adds support for syntax-highlighted code blocks and tables! I like it so much I built a tool to generate Markdown tables from CSV files.
- You probably already know its syntax if you use GitHub or Reddit frequently.
I asked myself: "Self, wouldn't it be great if there were a typesetting tool that let you write documents in Markdown, embed LaTeX where you needed it, and generate PDFs?" And it turns out that already exists.
Kung-Fu Pandoc
If you need to convert files from one markup format into another, pandoc is your swiss-army knife.
—John MacFarlane, author of pandoc
We'll use this Swiss Army knife called Pandoc to compile and export our Markdown-LaTeX docs. Let's try it out!
Install Pandoc and LaTeX
You'll need Pandoc and pdfTeX installed. If you can run pandoc
and pdflatex
from a terminal, you're probably good to go.
If you're on a Mac, install Pandoc using Homebrew (brew install pandoc
) and install MacTeX using their .pkg
installer.
Get Your Source Doc
Here's a sample Markdown-plus-LaTeX document you can try to compile. Save that file somewhere as example.md
.
Compile Your Doc
Here's the command I used to compile example.md
—> example.pdf
:
pandoc -o example.pdf example.md
See? It's that easy. Now open your PDF and you should see something like this:
Awesome. You're one step closer to well-documented world domination.
Automate That Ish with Sublime Text's Build Systems
Great! Now you can build Pandoc Markdown docs manually from the command line.
If you use Sublime Text like me, you might use the Build command (F7
or Cmd+B
) to build and run your scripts. When I used LaTeXTools, I got really used to checking how my LaTex looked when it was rendered by hitting Cmd+B
. The LaTeX build command rendered my source document and opened a PDF viewer with the results.
I duplicated this in Sublime Text. Here's how you can too!
Create a new Sublime-Build file
Sublime-Build files tell Sublime Text how you want to build a document when you hit Ctrl-B.
Create a new Sublime-Build file by selecting Tools —> Build System —> New Build System...
You'll get a document named untitled.sublime-build
that looks like this:
{
"shell_cmd": "make"
}
Write Your Pandoc Build Command
Replace the contents of your new document with the following:
{
"shell_cmd": "pandoc -o \"$file.pdf\" \"$file\" && open -a Preview \"$file.pdf\"",
"selector": "text.html.markdown",
"path": "/usr/texbin:$PATH"
}
Then change a few things:
If you're not on a Mac, remove the open -a
command.
open -a Preview \"$file.pdf\""
is just for Macs—it opens the rendered file in Preview.app.
If you're not on a Mac, strip off the &&
characters and everything after them. Your shell_cmd
will look like this:
{
"shell_cmd": "pandoc -o \"$file.pdf\" \"$file\"",
...
Remove the path
setting if you don't want it. Easier: just leave it in.
I found my Sublime install couldn't find pdflatex
unless I added this directory to the build system's path directly. You can probably leave it in—it shouldn't do any harm as long as Sublime can find pdflatex
.
Save Your New Build Command
The default save location will be Sublime Text 3/Packages/User
. Save the file you just created into that directory as Markdown to PDF.sublime-build
.
Set "Build System" to "Automatic"
Select Tools —> Build System —> Automatic
to ensure Sublime picks your new Markdown build system.
Build a Markdown File!
Open the example.md
file you downloaded earlier in Sublime, then hit F7
or Cmd-B
. The Sublime Text console should open as it starts compiling your document, then print something like this when it's done:
[Finished in 2.4s]
Check the directory holding example.md
and look for a brand-new example.md.pdf
file!
You did it! I am very proud of you.
Bonus Round: Custom LaTeX Templates
You're a cool guy who knows cool stuff. Want to make your LaTeX docs even cooler? Add your own custom template.
Say I hate the default LaTeX monospace font and I want to add \usepackage{inconsolata}
to fancy up my code blocks. Here's how I can do that:
- Save a LaTeX template somewhere on my computer
- Edit that template and add the LaTeX packages I want
- Ask Pandoc to use that template every time I compile my documents
Get a LaTeX template
I used this default.latex
template provided by jgm. Seems to work great!
I saved mine as ~/.pandoc/default.latex
because I think that's where Pandoc templates usually go.
Edit that template
At line 134, I added some text to remind me where I can safely put \usepackage
commands, as well as my custom command:
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % ADD YOUR \usepackage{...} COMMANDS HERE %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\usepackage{inconsolata}
Make Pandoc use that template
I edited my shell_cmd
inside my .sublime-build
file from the following:
"shell_cmd": "pandoc -o \"$file.pdf\" \"$file\" && open -a Preview \"$file.pdf\"",
I added a command-line argument pointing Pandoc to my default template as shown:
"shell_cmd": "pandoc --template=\"/Users/mplewis/.pandoc/default.latex\" -o \"$file.pdf\" \"$file\" && open -a Preview \"$file.pdf\"",
Now Pandoc uses my new template and makes my typewriter text not suck. Hooray!
I'd love to hear what you think about this post. Email me!