Say you want to write your very own software or coding book. The first option to proceed is, of course, a text processor like LibreOffice Writer. Don’t use that; that’s not hacky enough for you. You may use instead use a more complex toolchain, like LaTeX. If you are as lazy as me, you probably don’t want to learn how to layout a book using LaTeX. So… what’s left?

Here’s the best and easiest way: use Markdown. Of course, it’s not as powerful as LaTeX, but it’s fast, easy and lightweight.

## Where do we start?

If you don’t know Markdown, I recommend you to read this tutorial. Since we’re not serving the book as is (some scattered .md files) we need something to transform those source .md files into a convenient format like .pdf or .pub. Please, greet your new friend Pandoc.

## Installing

sudo apt-get install pandoc


Also, we’ll be using make to build the output files, so don’t forget to install it too:

sudo apt-get install make


## Folder structure

Before creating scattered files like a maniac, let’s create a folder tree structure to keep files organized. For example:

my-book/         # Root directory.
|- build/        # Folder used to store builded (output) files.
|- chapters/     # Markdowns files; one for each chapter.
|- images/       # Images folder.
|  |- cover.png  # Cover page for epub.
|- Makefile      # Makefile used for building our books.


Simple, isn’t it? Don’t worry about the files’ content; I’ll explain each file on the following sections.

You can find the template used on this post in this GitHub repository.

## Setup generic data

First, we need a title and an author, don’t we? That’s the purpose of metadata.yml. Here’s a example:

---
title: My book title
author: Daniel Herzog
rights:  Creative Commons Attribution 4.0 International
language: en-US
tags: [book, my-book, etc]
abstract: |
---


You get the idea, right? You can find the list of all available keys on this page.

## Creating chapters

Creating a new chapter is as simple as creating a new markdown file in the chapters/ folder; you’ll end up with something like this:

chapters/01-introduction.md
chapters/02-installation.md
chapters/03-usage.md
chapters/04-references.md


Pandoc and Make will join them automatically ordered by name; that’s why the numeric prefixes are being used.

All you need to specify for each chapter is at least a title:

# Introduction

This is the first paragraph of the introduction chapter.

## First

This is the first subsection.

## Second

This is the second subsection.


Each title (#) will represent a chapter, while each subtitle (##) will represent a chapter’s section. You can use as many levels of sections as markdown supports (I guess the limit is 5 or 6).

Imagine you want to reference a chapter from another; when the link is clicked, it will redirect you to that section. It can be achieved with anchor links:

// chapters/01-introduction.md
# Introduction

// chapters/02-installation.md
# Usage

...


Just use the chapter’s title name. If you want to rename the reference, use this syntax:

For more information, check [this](#usage) chapter.


Anchor names should be downcased, and spaces, colons, semicolons… should be replaced with hyphens. Instead of Chapter title: A new era, you have: #chapter-title-a-new-era.

It’s the same as chapters’ links:

# Introduction

## First

## Second

...


Or, renamed:

For more information, check [this](#second) section.


Same rules apply here as above.

## Inserting objects

Text. That’s cool. What about images and tables?

### Insert an image

Use Markdown syntax to insert an image with a caption:

![A cool seagull.](images/seagull.png)


Pandoc will automatically convert the image into a figure (image + caption).

If you want to resize the image, you may use this syntax, available in Pando 1.16:

![A cool seagull.](images/seagull.png){ width=50% height=50% }


Also, to reference an image, use LaTeX labels:

Please, admire the gloriousnes of Figure \ref{seagull_image}.

![A cool seagull.\label{seagull_image}](images/seagull.png)


### Insert a table

Just insert a Markdown table, and use the Table: Your table description syntax to add a caption:

| Index | Name |
| ----- | ---- |
| 0     | AAA  |
| 1     | BBB  |
| ...   | ...  |

Table: This is an example table.


If you want to reference a table, use LaTeX labels:

Please, check Table /ref{example_table}.

| Index | Name |
| ----- | ---- |
| 0     | AAA  |
| 1     | BBB  |
| ...   | ...  |

Table: This is an example table.\label{example_table}


Wrap a LaTeX math equation between $ delimiters for inline (tiny) formulas: This,$\mu = \sum_{i=0}^{N} \frac{x_i}{N}$, the mean equation, ...  Pandoc will transform them automatically into images using online services. If you want to center the equation instead of inlining it, use double $$ delimiters: $$\mu = \sum_{i=0}^{N} \frac{x_i}{N}$$ Here’s an online equation editor. ## Output We’ll be using a Makefile to automatize the building process. Instead of using the pandoc cli util, we’re going to use some make commands. The Makefile looks like this: BUILD = build OUTPUT_FILENAME = book METADATA = metadata.yml CHAPTERS = chapters/*.md TOC = --toc --toc-depth=2 COVER_IMAGE = images/cover.png LATEX_CLASS = report MATH_FORMULAS = --webtex all: book book: epub html pdf clean: rm -r$(BUILD)

epub: $(BUILD)/epub/$(OUTPUT_FILENAME).epub

html: $(BUILD)/html/$(OUTPUT_FILENAME).html

pdf: $(BUILD)/pdf/$(OUTPUT_FILENAME).pdf

$(BUILD)/epub/$(OUTPUT_FILENAME).epub: $(METADATA)$(CHAPTERS)
mkdir -p $(BUILD)/epub pandoc$(TOC) -S $(MATH_FORMULAS) --epub-metadata=$(METADATA) --epub-cover-image=$(COVER_IMAGE) -o [email protected]$^

$(BUILD)/html/$(OUTPUT_FILENAME).html: $(CHAPTERS) mkdir -p$(BUILD)/html
pandoc $(TOC)$(MATH_FORMULAS) --standalone --to=html5 -o [email protected] $^$(BUILD)/pdf/$(OUTPUT_FILENAME).pdf:$(METADATA) $(CHAPTERS) mkdir -p$(BUILD)/pdf
pandoc $(TOC)$(MATH_FORMULAS) -V documentclass=$(LATEX_CLASS) -o [email protected]$^


Don’t worry! If you’re not familiarized with make, you don’t need to actually understand how that works.

### Export to PDF

Use this command:

make pdf


The generated file will be placed in build/pdf.

Please, note that PDF file generation requires some extra dependencies (~ 800 MB):

sudo apt-get install texlive-latex-base texlive-fonts-recommended texlive-latex-extra


### Export to EPUB

Use this command:

make epub


The generated file will be placed in build/epub.

### Export to HTML

Use this command:

make html


The generated file(s) will be placed in build/html.

### Extra configuration

If you want to configure the output, you’ll probably have to look the Pandoc Manual for further information about pdf (LaTeX) generation, custom styles, etc.

Happy coding!