= Asciidoctor PDF: A _native_ PDF converter for AsciiDoc
Dan Allen <https://github.com/mojavelinux[@mojavelinux]>; Sarah White <https://github.com/graphitefriction[@graphitefriction]>
// Settings:
:compat-mode!:
:experimental:
:idprefix:
:idseparator: -
ifdef::env-github[:relfileprefix: /blob/master]
//:pdf-page-size: [8.25in, 11.69in]
//:pdf-page-size: A4
// Aliases:
:project-name: Asciidoctor PDF
:project-handle: asciidoctor-pdf
// URIs:
:uri-project: https://github.com/asciidoctor/asciidoctor-pdf
:uri-project-repo: {uri-project}
:uri-project-issues: {uri-project-repo}/issues
:uri-project-list: http://discuss.asciidoctor.org
:uri-prawn: http://prawn.majesticseacreature.com
:uri-rvm: http://rvm.io
:uri-asciidoctor: http://asciidoctor.org

:original-outfilesuffix: {outfilesuffix}
:outfilesuffix: .adoc

_Lo and behold_, a native PDF converter for AsciiDoc built with {uri-asciidoctor}[Asciidoctor] and {uri-prawn}[Prawn]! +
_No more middleman._ +
_No more DocBook toolchain._ +
It's AsciiDoc straight to PDF!

[caption='Status']
CAUTION: {project-name} is currently _alpha_ software.
While it handles most of the AsciiDoc content, there's still work needed to fill in gaps where conversion is incomplete, incorrect or not implemented.
See the milestone v1.5.0 in the {uri-project-issues}[issue tracker] for details.

== Prawn, the majestic PDF generator

{uri-project}[{project-name}] is made possible by an amazing Ruby Gem named Prawn.
And what a Gem it is!

{uri-prawn}[Prawn] is a nimble PDF writer for Ruby.
More important, it's a hackable platform that offers both high level APIs for the most common needs and low level APIs for bending the document model to accomodate special circumstances.

With Prawn, you can write text, draw lines and shapes and place images _anywhere_ on the page and add as much color as you like.
In addition, it brings a fluent API and aggressive code re-use to the printable document space.

Here's an example that demonstrates how to use Prawn to create a basic PDF document.

.Create a basic PDF document using Prawn
[source,ruby]
----
require 'prawn'

Prawn::Document.generate 'example.pdf' do
  text 'Hello, PDF creation!'
end
----

It's that easy.
And that's just the beginning.
Skip ahead to <<Getting started>> to start putting it use.

*Prawn is the killer library for PDF generation* we've needed to close this critical gap in Asciidoctor.
It absolutely takes the pain out of creating printable documents.
Picking up from there, {project-name} takes the pain out of creating printable documents _from AsciiDoc_.

== Notable features

* Direct AsciiDoc to PDF conversion
* Configuration-driven style and layout
* PDF document outline (i.e., bookmarks)
* Document metadata (title, authors, subject, keywords, etc)
* Internal cross reference links
* Syntax highlighting with CodeRay or Pygments
* Page breaks avoided in block content
* Orphan section titles avoided
* Table border settings honored

=== Missing features

See <<WORKLOG.adoc#,WORKLOG>>.

== Prerequisites

All that's needed is Ruby 1.9.3 or better (2.1.2 recommended) and a few RubyGems, which we explain how to install in the next section.

To check you have Ruby available, use the `ruby` command to query the version installed:

 $ ruby --version

If you're using {uri-rvm}[RVM], we recommend creating a new gemset to work with Asciidoctor and {project-name}:

 $ rvm use 2.1@asciidoctor-pdf --create

We like RVM because it keeps the dependencies required by various projects isolated.

== Getting started

The {project-name} project is published in pre-release on RubyGems.org.
You can either install the pre-release version using the following command:

 $ gem install --pre asciidoctor-pdf
 
If you want to syntax highlight source listings, you'll also want to install CodeRay or Pygments.
To be safe, go ahead and install both gems:

 $ gem install coderay pygments.rb

Assuming all the required gems install properly, verify you can run the `asciidoctor-pdf` script:

 $ asciidoctor-pdf -v

If you see the version of Asciidoctor PDF printed, you're ready to use {project-name}!

Skip ahead to the <<example-asciidoc-document>> section to start putting {project-name} to use.
Alternatively, you can follow the steps below to install the project from source.

=== Retrieve the source code

You can retrieve the {project-name} project in one of two ways:

. Clone the git repository
. Download a zip archive of the repository

==== Option 1: Fetch using git clone

If you want to clone the git repository, simply copy the {uri-project-repo}[GitHub repository URL] and pass it to `git clone` command:

 $ git clone https://github.com/asciidoctor/asciidoctor-pdf

Next, change to the project directory:

 $ cd asciidoctor-pdf

==== Option 2: Download the archive

If you want to download a zip archive, click the btn:[Download Zip] button on the right-hand side of the repository page on GitHub.
Once the download finishes, extract the archive, open a console and change to that directory.

TIP: Instead of working out of the {project-handle} directory, you can simply add the absolute path of the [path]_bin_ directory to your `PATH` environment variable.

We'll leverage the project configuration to install the necessary dependencies.

=== Install the dependencies

The dependencies needed to use {project-name} are defined in the [file]_Gemfile_ at the root of the project.
We can use Bundler to install the dependencies for us.

To check you have Bundler available, use the `bundle` command to query the version installed:

 $ bundle --version

If it's not installed, use the `gem` command to install it.

 $ gem install bundler

Then use the `bundle` command to install the project dependencies:

 $ bundle

NOTE: You need to call `bundle` from the project directory so that it can find the [file]_Gemfile_.

Assuming all the required gems install properly, verify you can run the `asciidoctor-pdf` script using Ruby:

 $ ruby ./bin/asciidoctor-pdf -v

If you see the version of Asciidoctor PDF printed, you're ready to use {project-name}!

If you get an error message--and you're not using a Ruby manager like RVM--you may need to invoke the script through `bundle exec`:

 $ bundle exec ./bin/asciidoctor-pdf -v

If this works, be sure to use `bundle exec` whenever invoking the `./bin/asciidoctor-pdf` script.

Next, let's grab an AsciiDoc document to distill.

=== Example AsciiDoc document

If you don't already have an AsciiDoc document, you can use the [file]_example.adoc_ file found in the examples directory of this project.

.example.adoc
[source,asciidoc]
....
= Document Title
Doc Writer <doc@example.com>
:doctype: book
:source-highlighter: coderay
:listing-caption: Listing

A simple http://asciidoc.org[AsciiDoc] document.

== Introduction

A paragraph followed by a simple list with square bullets.

[square]
* item 1
* item 2

Here's how you say "`Hello, World!`" in Prawn:

.Create a basic PDF document using Prawn
[source,ruby]
----
require 'prawn'

Prawn::Document.generate 'example.pdf' do
  text 'Hello, World!'
end
----
....

It's time to convert the AsciiDoc document directly to PDF.

=== Convert AsciiDoc to PDF

Converting to PDF is a simple as running the `./bin/asciidoctor-pdf` script using Ruby and passing our AsciiDoc document as the first argument.

 $ ruby ./bin/asciidoctor-pdf example.adoc

When the script completes, you should see the file [file]_example.pdf_ in the same directory.

IMPORTANT: You'll need to the `coderay` gem installed to run this example since it uses the `source-highlighter` attribute with the value of `coderay`.

Open the [file]_example.pdf_ file with a PDF viewer to see the result.

.Example PDF document rendered in a PDF viewer
image::examples/example-pdf-screenshot.png[Screenshot of PDF document,width=800,scaledwidth=100%]

You're also encouraged to try converting this link:README.adoc[README] as well as the documents in the examples directory to see more of what {project-name} can do.
Another good example is the https://github.com/cdi-spec/cdi/tree/master/spec[CDI Specification].

The pain of the DocBook toolchain should be melting away about now.

== Themes

The layout and styling of the PDF is driven by a YAML configuration file.
To learn how the theming system works and how to create and apply custom themes, refer to the <<docs/theming-guide.adoc#,Asciidoctor PDF Theme Guide>>.

You can use the built-in theme files, [file]_default-theme.yml_ and [file]_asciidoctor-theme.yml_, found in the [file]_data/themes_ directory, as examples.

Specify the path to an alternate theme file with the `pdf-style` attribute.
For example to use the built-in _asciidoctor_ theme:

 $ ./bin/asciidoctor-pdf -a pdf-style=asciidoctor examples/example.adoc
 
To refer to a theme at another location you can use the `pdf-stylesdir` attribute to specify the location of themes.
If the `pdf-style` value does not end in `.yml`, then the file name is calculated as `{pdf-style}-theme.yml` located in the `pdf-stylesdir` directory (which defaults to the built-in `data/themes` directory).

== Optional scripts

{project-name} also provides a shell script that invokes GhostScript (`gs`) to optimize and compress the generated PDF with minimal impact on quality.
You must have Ghostscript installed to use it.

Here's an example usage:

 $ ./bin/optimize-pdf example.pdf

The command will generate the file [file]_example-optimized.pdf_ in the current directory.

WARNING: The `optimize-pdf` script currently requires a Bash shell (Linux, OSX, etc).
We plan to rewrite the script in Ruby so it works across platforms (see https://github.com/asciidoctor/asciidoctor-pdf/issues/1[issue #1])

IMPORTANT: The `optimize-pdf` script relies on Ghostscript >= 9.10.
Otherwise, it may actually make the PDF larger.
Also, you should only consider using it if the file size of the original PDF is > 5MB.

If a file is found with the extension `.pdfmarks` and the same rootname as the input file, it is used to add metadata to the generated PDF document.
This file is necessary to preserve the document metadata since Ghostscript will otherwise drop it.
That's why Asciidoctor PDF always creates this file in addition to the PDF.

== Contributing

In the spirit of free software, _everyone_ is encouraged to help improve this project.

To contribute code, simply fork the project on GitHub, hack away and send a pull request with your proposed changes.

Feel free to use the {uri-project-issues}[issue tracker] or {uri-project-list}[Asciidoctor mailing list] to provide feedback or suggestions in other ways.

[[resources,Links]]
== Resources

* https://groups.google.com/forum/#!msg/prawn-ruby/MbMsCx862iY/6ImCsvLGfVcJ[Discussion about image quality in PDFs]

== Authors

{project-name} was written by https://github.com/mojavelinux[Dan Allen] and https://github.com/graphitefriction[Sarah White] of OpenDevise Inc. on behalf of the Asciidoctor Project.

== Copyright

Copyright (C) 2014 OpenDevise Inc. and the Asciidoctor Project.
Free use of this software is granted under the terms of the MIT License.

For the full text of the license, see the <<LICENSE.adoc#,LICENSE>> file.
Refer to the <<NOTICE.adoc#,NOTICE>> file for information about third-party Open Source software in use.

// FIXME Asciidoctor should be using outfilesuffix defined in header
:outfilesuffix: {original-outfilesuffix}
