CINXE.COM
Asciidoctor EPUB3 Documentation | Asciidoctor Docs
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <meta name="viewport" content="width=device-width,initial-scale=1"> <title>Asciidoctor EPUB3 Documentation | Asciidoctor Docs</title> <link rel="stylesheet" href="../../_/css/site.css"> <link rel="stylesheet" href="../../_/css/vendor/tabs.css"> <meta name="generator" content="Antora 3.1.8"> <link rel="canonical" href="https://docs.asciidoctor.org/epub3-converter/latest/"> <meta property="og:url" content="https://docs.asciidoctor.org/epub3-converter/latest/"> <meta property="og:description" content="A documentation page for Asciidoctor EPUB3."> <meta property="og:site_name" content="Asciidoctor Docs"> <meta name="twitter:card" content="summary_large_image"> <meta property="og:title" content="Asciidoctor EPUB3 - Asciidoctor EPUB3 Documentation"> <meta property="og:image" content="https://docs.asciidoctor.org/_/img/asciidoctor-og.png"> <meta name="twitter:site" content="@asciidoctor"> <meta name="page-spec" content="epub3-converter::index.adoc"> <link rel="icon" href="../../_/img/favicon.ico" type="image/x-icon"> </head> <body class="article"> <header class="header"> <nav class="navbar"> <div class="navbar-brand"> <a class="navbar-item logo" title="Asciidoctor" href="https://asciidoctor.org"><img src="../../_/img/asciidoctor-logo.svg" alt="Asciidoctor" width="48"></a> <a class="navbar-item title" href="https://docs.asciidoctor.org/">Asciidoctor Docs</a> <button class="navbar-burger" aria-controls="topbar-nav" aria-expanded="false" aria-label="Toggle main menu"> <span></span> <span></span> <span></span> </button> </div> <div id="topbar-nav" class="navbar-menu"> <div class="navbar-end"> <div class="navbar-item search hide-for-print"> <div id="search" class="field has-filter"> <input class="query" type="text" placeholder="Search the docs"> <label class="filter checkbox"> <input type="checkbox" data-facet-filter="component:epub3-converter"> In this project </label> </div> </div> <div class="navbar-item has-dropdown is-hoverable"> <div class="navbar-link">AsciiDoc</div> <div class="navbar-dropdown"> <a class="navbar-item" href="../../asciidoc/latest/">Language</a> <a class="navbar-item" href="../../asciidoc/latest/syntax-quick-reference/">Syntax Quick Reference</a> </div> </div> <div class="navbar-item has-dropdown is-hoverable"> <div class="navbar-link">Processing</div> <div class="navbar-dropdown"> <a class="navbar-item" href="../../asciidoctor/latest/">Asciidoctor <small>Ruby</small></a> <a class="navbar-item" href="../../asciidoctor.js/latest/">Asciidoctor.js <small>JavaScript</small></a> <a class="navbar-item" href="../../asciidoctorj/latest/">AsciidoctorJ <small>Java</small></a> </div> </div> <div class="navbar-item has-dropdown is-hoverable"> <div class="navbar-link">Extensions</div> <div class="navbar-dropdown"> <div class="navbar-item">Add-on Converters</div> <a class="navbar-item" href="../../pdf-converter/latest/">PDF <small>Ruby</small></a> <a class="navbar-item" href="./">EPUB3 <small>Ruby</small></a> <a class="navbar-item" href="../../reveal.js-converter/latest/">reveal.js <small>Ruby, JavaScript</small></a> <hr class="navbar-divider"> <div class="navbar-item">Extended Syntax</div> <a class="navbar-item" href="../../diagram-extension/latest/">Asciidoctor Diagram <small>Ruby</small></a> </div> </div> <div class="navbar-item has-dropdown is-hoverable"> <div class="navbar-link">Tooling</div> <div class="navbar-dropdown is-right"> <div class="navbar-item">Build Automation</div> <a class="navbar-item" href="../../maven-tools/latest/">Maven Tools <small>Java</small></a> <a class="navbar-item" href="../../gradle-plugin/latest/">Gradle Plugin <small>Java</small></a> <a class="navbar-item" href="../../asciidoclet/latest/">Asciidoclet <small>Java</small></a> <hr class="navbar-divider"> <div class="navbar-item">Text Editors / Viewers</div> <a class="navbar-item" href="../../browser-extension/">Browser Extension</a> <a class="navbar-item" href="https://intellij-asciidoc-plugin.ahus1.de/docs" target="_blank" rel="noopener">IntelliJ Plugin</a> </div> </div> <div class="navbar-item has-dropdown is-hoverable"> <a class="navbar-item" href="../../about/get-help/" data-title="Support"> <span class="icon"><img src="../../_/img/octicons-24.svg#view-comment-discussion"></span> </a> <div class="navbar-dropdown is-right"> <a class="navbar-item has-icon" href="https://chat.asciidoctor.org" target="_blank" rel="noopener"> <span class="icon"><img src="../../_/img/octicons-16.svg#view-comment-discussion"></span> <span>Chat</span> </a> <!-- <a class="navbar-item has-icon" href="https://discuss.asciidoctor.org" target="_blank" rel="noopener"> <span class="icon"><img src="../../_/img/octicons-16.svg#view-mail"></span> <span>List</span> </a> --> <a class="navbar-item has-icon" href="https://github.com/asciidoctor" target="_blank" rel="noopener"> <span class="icon"><img src="../../_/img/octicons-16.svg#view-mark-github"></span> <span>Source</span> </a> <a class="navbar-item has-icon" href="https://twitter.com/asciidoctor" target="_blank" rel="noopener"> <span class="icon"><img src="../../_/img/octicons-16.svg#view-hash"></span> <span>Tweets</span> </a> </div> </div> </div> </div> </nav> </header> <div class="body"> <div class="nav-container"> <aside class="nav"> <div class="panels"> <div class="nav-panel-explore is-active" data-panel="explore"> <div class="context"> <span class="title">Asciidoctor EPUB3</span> <span class="version">2.1</span> </div> <ul class="components"> <li class="component"> <a class="title" href="../../asciidoc/latest/">AsciiDoc</a> </li> <li class="component"> <a class="title" href="../../asciidoctor/latest/">Asciidoctor</a> <ul class="versions"> <li class="version is-latest"> <a href="../../asciidoctor/latest/">2.0</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../asciidoctor.js/latest/">Asciidoctor.js</a> <ul class="versions"> <li class="version is-latest"> <a href="../../asciidoctor.js/latest/">3.0</a> </li> <li class="version"> <a href="../../asciidoctor.js/2.2/">2.2</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../asciidoctorj/latest/">AsciidoctorJ</a> <ul class="versions"> <li class="version is-latest"> <a href="../../asciidoctorj/latest/">3.0</a> </li> <li class="version"> <a href="../../asciidoctorj/2.5/">2.5</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../pdf-converter/latest/">Asciidoctor PDF</a> <ul class="versions"> <li class="version is-latest"> <a href="../../pdf-converter/latest/">2.3</a> </li> <li class="version"> <a href="../../pdf-converter/2.2/">2.2</a> </li> <li class="version"> <a href="../../pdf-converter/2.1/">2.1</a> </li> <li class="version"> <a href="../../pdf-converter/2.0/">2.0</a> </li> </ul> </li> <li class="component is-current"> <a class="title" href="./">Asciidoctor EPUB3</a> <ul class="versions"> <li class="version is-current is-latest"> <a href="./">2.1</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../reveal.js-converter/latest/">Asciidoctor reveal.js</a> <ul class="versions"> <li class="version is-latest"> <a href="../../reveal.js-converter/latest/">5.0</a> </li> <li class="version"> <a href="../../reveal.js-converter/4.1/">4.1</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../maven-tools/latest/">Maven Tools</a> <ul class="versions"> <li class="version is-latest"> <a href="../../maven-tools/latest/">3.1</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../gradle-plugin/latest/">Gradle Plugin Suite</a> <ul class="versions"> <li class="version is-latest"> <a href="../../gradle-plugin/latest/">4.0</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../asciidoclet/latest/">Asciidoclet</a> <ul class="versions"> <li class="version is-latest"> <a href="../../asciidoclet/latest/">2.0</a> </li> <li class="version"> <a href="../../asciidoclet/1.5.6/">1.5.6</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../diagram-extension/latest/">Asciidoctor Diagram</a> <ul class="versions"> <li class="version is-latest"> <a href="../../diagram-extension/latest/">2.2</a> </li> </ul> </li> <li class="component"> <a class="title" href="../../browser-extension/">Browser Extension</a> </li> <li class="component"> <a class="title" href="../../about/">Community</a> </li> </ul> </div> </div> </aside> </div> <main class="article"> <div class="toolbar" role="navigation"> <button class="nav-toggle"></button> <a href="../../" class="home-link" title="Home"></a> <nav class="breadcrumbs" aria-label="breadcrumbs"> </nav> <a class="project-link" href="https://github.com/asciidoctor/asciidoctor-epub3" title="Project home"><span class="icon"><img src="../../_/img/octicons-16.svg#view-mark-github"></span></a> <div class="edit-this-page"><a href="https://github.com/asciidoctor/asciidoctor-epub3/edit/main/docs/modules/ROOT/pages/index.adoc">Edit this Page</a></div> </div> <div class="content"> <aside class="toc sidebar" data-title="Contents" data-levels="2"> <div class="toc-menu"></div> </aside> <article class="doc epub3-converter"> <h1 class="page">Asciidoctor EPUB3 Documentation</h1> <div id="preamble"> <div class="sectionbody"> <div class="paragraph"> <p>Asciidoctor EPUB3 is a set of Asciidoctor extensions for converting AsciiDoc documents directly to the EPUB3 e-book format.</p> </div> </div> </div> <div class="sect1"> <h2 id="introduction"><a class="anchor" href="#introduction"></a>Introduction</h2> <div class="sectionbody"> <div class="paragraph"> <p>Asciidoctor EPUB3 is not merely a converter from AsciiDoc to EPUB3. Rather, it’s a tool for creating highly aesthetic, professional, <em>easy-to-read</em> e-books. Let’s face it, many of the technical e-books out there—​especially those produced from software documentation—​are <strong><em>hideous</em></strong>. Asciidoctor EPUB3 is on a mission to disrupt the status quo.</p> </div> <div class="imageblock"> <div class="content"> <img src="_images/text.png" alt="text"> </div> <div class="title">Figure 1. An excerpt from an e-book produced by Asciidoctor EPUB3 shown in Day, Night, and Sepia modes.</div> </div> <div class="sect2"> <h3 id="project-mission"><a class="anchor" href="#project-mission"></a>Project Mission</h3> <div class="paragraph"> <p>The Asciidoctor EPUB3 project aims to produce EPUB3 documents that meet the following objectives:</p> </div> <div class="dlist itemized"> <dl> <dt>Fully Semantic</dt> <dd> <p>Produce deeply semantic XHTML5 documents, including use of the recommended <code>epub:type</code> attribute.</p> </dd> <dt>Exceptional Readability</dt> <dd> <p>Readers should be drawn into the text so that they read and absorb it. Maximize the readability of the text using carefully crafted styles that are focused on:</p> <div class="ulist"> <ul> <li> <p>Custom, readable fonts with strong UTF-8 character support</p> </li> <li> <p>Sufficient line spacing and margins</p> </li> <li> <p>Modular font size scale</p> </li> <li> <p>Subtle, pleasing colors with good contrast</p> </li> <li> <p>A responsive design that scales well from small to large screens</p> </li> <li> <p>Widowed and orphaned content avoided where possible</p> </li> </ul> </div> </dd> <dt>Complete and Accurate Metadata</dt> <dd> <p>Fully populate the EPUB3 package metadata using information in the AsciiDoc source document.</p> </dd> <dt>Consistent Rendering</dt> <dd> <p>Render consistently across a broad range of EPUB3 (and select EPUB2+) e-readers and respond to any size screen.</p> </dd> <dt>Polish, Polish, and More Polish</dt> <dd> <p>Add polish to the final product such as font-based icons and callout numbers.</p> </dd> </dl> </div> <div class="paragraph"> <p>We believe that the e-books produced by Asciidoctor EPUB3 are the <em>very best</em> output you can expect to find in digital publishing today. Of course, there’s always room for improvement, so we’ll continue to work with you to achieve and maintain this goal.</p> </div> <div class="paragraph"> <p>Asciidoctor EPUB3 only produces variable layout (i.e., reflowable) EPUB3 documents since this layout is best suited for the types of documents typically written in AsciiDoc. We may explore the use of fixed layout documents in the future if the need arises.</p> </div> </div> <div class="sect2"> <h3 id="notable-features"><a class="anchor" href="#notable-features"></a>Notable Features</h3> <div class="ulist"> <ul> <li> <p>Direct AsciiDoc to EPUB3 conversion</p> </li> <li> <p>Highly-aesthetic and readable styles with optimized text legibility</p> </li> <li> <p>Respects font settings (if supported by the e-reader) without altering headings, code or icons</p> </li> <li> <p>EPUB3 metadata, manifest and spine (assembled by Gepub)</p> </li> <li> <p>Document metadata (title, authors, subject, keywords, etc.)</p> </li> <li> <p>Internal cross-reference links</p> </li> <li> <p>Syntax highlighting with Rouge, CodeRay or Pygments</p> </li> <li> <p>Unicode callout numbers</p> </li> <li> <p>Page breaks avoided in block content (so much as it’s supported by the e-reader)</p> </li> <li> <p>Orphan section titles avoided (so much as it’s supported by the e-reader)</p> </li> <li> <p>Table border settings honored</p> </li> <li> <p>Support for SVG images in the content</p> </li> <li> <p>Stem blocks via AsciiMath</p> </li> </ul> </div> </div> </div> </div> <div class="sect1"> <h2 id="structuring-your-manuscript"><a class="anchor" href="#structuring-your-manuscript"></a>Structuring your Manuscript</h2> <div class="sectionbody"> <div class="paragraph"> <p>An EPUB3 archive is composed of multiple files. The content of each “chapter” is typically stored in a dedicated XHTML file. Therefore, the Asciidoctor EPUB3 converter “chunks” the AsciiDoc source document into multiple XHTML files to add to the EPUB3 archive. Like other converters, Asciidoctor EPUB3 handles this chunking task by automatically slicing up the XHTML output at predetermined heading levels.</p> </div> <div class="paragraph"> <p>When the <code>doctype</code> attribute is set to <code>book</code>, each top-level section will become a separate e-book "chapter" file. This includes preface, bibliography, appendix, etc. This behavior can be configured via the <code>epub-chapter-level</code> document attribute.</p> </div> <div class="paragraph"> <p>Otherwise, the whole document is converted to a single ebook chapter.</p> </div> <div class="paragraph"> <p>You may specify custom chapter filenames by assigning IDs to sections:</p> </div> <div class="listingblock"> <div class="content"> <pre class="highlightjs highlight"><code class="language-asciidoc hljs" data-lang="asciidoc">[#custom-chapter-id] = Chapter</code></pre> </div> </div> <div class="paragraph"> <p>Here’s an example showing the structure of a book:</p> </div> <div class="listingblock"> <div class="content"> <pre class="highlightjs highlight"><code class="language-asciidoc hljs" data-lang="asciidoc">= Book Title Author Name :doctype: book :imagesdir: images //...and so on == Chapter One Some interesting text here. == Chapter Two Even more exciting stuff.</code></pre> </div> </div> <div class="paragraph"> <p>In older Asciidoctor EPUB3 versions, there were strict rules on document organization: a 'spine' master document with chapter includes. This is no longer the case. If you followed the old rules, chances are your document will work with the newer Asciidoctor EPUB3 either as-is or after minor adjustments.</p> </div> </div> </div> <div class="sect1"> <h2 id="prerequisites"><a class="anchor" href="#prerequisites"></a>Prerequisites</h2> <div class="sectionbody"> <div class="paragraph"> <p>All that’s needed to use Asciidoctor EPUB3 is Ruby 2.7 or newer and a few Ruby gems, which we’ll explain how to install in the next section.</p> </div> <div class="paragraph"> <p>To check if you have Ruby available, use the <code>ruby</code> command to query the installed version:</p> </div> <div class="literalblock"> <div class="content"> <pre>$ ruby --version</pre> </div> </div> </div> </div> <div class="sect1"> <h2 id="getting-started"><a class="anchor" href="#getting-started"></a>Getting Started</h2> <div class="sectionbody"> <div class="paragraph"> <p>You can get Asciidoctor EPUB3 by <a href="#install-the-published-gem">installing the published gem</a>.</p> </div> <div class="sect2"> <h3 id="install-the-published-gem"><a class="anchor" href="#install-the-published-gem"></a>Install the Published Gem</h3> <div class="paragraph"> <p>Asciidoctor EPUB3 is published on RubyGems.org. You can install the published gem using the following command:</p> </div> <div class="literalblock"> <div class="content"> <pre>$ NOKOGIRI_USE_SYSTEM_LIBRARIES=1 gem install asciidoctor-epub3</pre> </div> </div> <div class="paragraph"> <p>This optional environment variable tells the gem installer to link against the C libraries on the system, if available, instead of compiling the libraries from scratch. This speeds up the installation of Nokogiri considerably.</p> </div> <div class="paragraph"> <p>If you want to syntax highlight source listings, you’ll also want to install Rouge, CodeRay, or Pygments. Choose one (or more) of the following:</p> </div> <div class="literalblock"> <div class="title">Rouge</div> <div class="content"> <pre>$ gem install rouge</pre> </div> </div> <div class="literalblock"> <div class="title">CodeRay</div> <div class="content"> <pre>$ gem install coderay</pre> </div> </div> <div class="literalblock"> <div class="title">Pygments</div> <div class="content"> <pre>$ gem install pygments.rb</pre> </div> </div> <div class="paragraph"> <p>You then activate syntax highlighting for a given document by adding the <code>source-highlighter</code> attribute to the document header (Rouge shown):</p> </div> <div class="listingblock"> <div class="content"> <pre class="highlightjs highlight"><code class="language-asciidoc hljs" data-lang="asciidoc">:source-highlighter: rouge</code></pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> If a style is not specified, the black and white theme (i.e., bw) is used. This default is used so that the syntax highlighting is legible regardless of which reading mode the reader selects (white, black, sepia, etc). To override this default, you must set <code><highlighter>-style</code> document header attribute to a valid highlighter style name (e.g., <code>:rouge-style: pastie</code>). </td> </tr> </table> </div> <div class="paragraph"> <p>Assuming all the required gems install properly, verify you can run the <code>asciidoctor-epub3</code> script:</p> </div> <div class="literalblock"> <div class="content"> <pre>$ asciidoctor-epub3 -v</pre> </div> </div> <div class="paragraph"> <p>If you see the version of Asciidoctor EPUB3 printed, you’re ready to use Asciidoctor EPUB3. Let’s get an AsciiDoc document ready to convert to EPUB3.</p> </div> </div> <div class="sect2"> <h3 id="epub-related-asciidoc-attributes"><a class="anchor" href="#epub-related-asciidoc-attributes"></a>EPUB-related AsciiDoc Attributes</h3> <div class="paragraph"> <p>The metadata in the generated EPUB3 file is populated from attributes in the AsciiDoc document. The names of the attributes and the metadata elements to which they map are documented in this section.</p> </div> <div class="paragraph"> <p>The term <em class="term">package metadata</em> in Table 1 is in reference to the <a href="http://www.idpf.org/epub/30/spec/epub30-publications.html#sec-metadata-elem"><metadata> element</a> in the EPUB3 package document (e.g., <em class="file">package.opf</em>). The <code>dc</code> namespace prefix is in reference to the <a href="https://www.dublincore.org/specifications/dublin-core/dces/2004-12-20/">Dublin Core Metadata Element Set</a>.</p> </div> <table class="tableblock frame-none grid-rows stretch"> <caption class="title">AsciiDoc attributes that control the EPUB3 metadata (i.e., package.opf)</caption> <colgroup> <col style="width: 25%;"> <col style="width: 75%;"> </colgroup> <thead> <tr> <th class="tableblock halign-left valign-top">Name</th> <th class="tableblock halign-left valign-top">Description</th> </tr> </thead> <tbody> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>uuid</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the <strong>required</strong> unique identifier (<code><dc:identifier></code>) in the package metadata. An id will be generated automatically from the doctitle if not specified. The recommended practice is to identify the document by means of a string or number conforming to a formal identification system.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>lang</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the content language / locale (<code><dc:language></code>) in the package metadata.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>scripts</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Controls the font subsets that are selected based on the specified scripts (e.g., alphabets). (values: <strong>latin</strong>, latin-ext, latin-cyrillic or multilingual)</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>revdate</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the publication date (<code><dc:date></code>) in the package metadata. The date should be specified in a parsable format, such as <code>2014-01-01</code>.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>doctitle</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the title (<code><dc:title></code>) in the package metadata. The title is added to the metadata in plain text format.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>author</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the contributors (<code><dc:contributor></code>) in the package metadata. The authors in each chapter document are aggregated together with the authors in the master file.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>username</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Used to resolve an avatar for the author that is displayed in the header of a chapter when the <code>doctype</code> is set to a value other than <code>book</code>. The avatar image should be located at the path <em>{imagesdir}/avatars/{username}.jpg</em>, where <code>{username}</code> is the value of this attribute.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>producer</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the publisher (<code><dc:publisher></code>) in the package metadata.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>creator</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the creator (<code><dc:creator></code>) in the package metadata. <strong>If the creator is not specified, Asciidoctor is set as the creator with the role "mfr" (an abbreviation for manufacturer).</strong></p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>description</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the description (<code><dc:description></code>) in the package metadata.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>keywords</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the subjects (i.e., <code><dc:subject></code>) in the package metadata. The keywords should be represented as comma-separated values (CSV).</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>front-cover-image</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the front cover image and the image on the cover page (EPUB3 only) in the package metadata. The image is also added to the e-book archive. The value may be specified as a path or inline image macro. Using the inline image macro is preferred as it allows the height and width to be specified.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>copyright</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the rights statement (<code><dc:rights></code>) in the package metadata.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>source</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the source reference (<code><dc:source></code>) in the package metadata. The recommended practice is to identify the referenced resource by means of a string or number conforming to a formal identification system.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>epub-properties</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">An optional override of the properties attribute for this document’s item in the manifest. <em>Only applies to a chapter document.</em></p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>epub-chapter-level</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Specify the section level at which to split the EPUB into separate "chapter" files. This attribute only affects documents with <code>:doctype: book</code>. The default is to split into chapters at level-1 sections. This attribute only affects the internal composition of the EPUB, not the way chapters and sections are displayed to users. Some readers may be slow if the chapter files are too large, so for large documents with few level-1 headings, one might want to use a chapter level of 2 or 3.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>series-name, series-volume, series-id</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Populates the series statements (<code>belongs-to-collection</code>) in the package metadata. Volume is a number, ID probably a UUID that is constant for all volumes in the series.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>epub3-frontmatterdir</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">The path to a directory that contains frontmatter files. The file names must match <code>front-matter*.html</code> and will be included in alphabetic order. The files are expected to be valid EPUB HTML files. <em>If only one front matter page is required, the default 'front-matter.html' file can be used instead.</em></p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>epub3-stylesdir</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">The path to a directory that contains alternate epub3.css and epub3-css3-only.css files to customize the look and feel.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>doctype</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Used to control the inclusion of special content in the generated HTML. If set to a value other than book, the byline information (author and avatar) is included below the chapter header and a typographic end mark is added at the end of the last paragraph. Suggested values include: book (default), article.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>toc</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Adds table of contents at the beginning of the book. Depth is controlled by <code>:toclevels:</code> attribute.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock"><code>outlinelevels</code></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Sets the depth of table of contents metadata. If not set, defaults to <code>:toclevels:</code></p></td> </tr> </tbody> </table> <div class="paragraph"> <p>With that out of the way, it’s time to convert the AsciiDoc document directly to EPUB3.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="performing-the-conversion"><a class="anchor" href="#performing-the-conversion"></a>Performing the Conversion</h2> <div class="sectionbody"> <div class="paragraph"> <p>You can convert AsciiDoc documents to EPUB3 from the command line using the <code>asciidoctor-epub3</code> script provided with the Asciidoctor EPUB3 project.</p> </div> <div class="sect2"> <h3 id="convert-asciidoc-to-epub3"><a class="anchor" href="#convert-asciidoc-to-epub3"></a>Convert AsciiDoc to EPUB3</h3> <div class="paragraph"> <p>Converting an AsciiDoc document to EPUB3 is as simple as passing your document to the <code>asciidoctor-epub3</code> command. This command should be available on your PATH if you installed the <code>asciidoctor-epub3</code> gem. Otherwise, you can find the command in the <em class="path">bin</em> folder of the project. We also recommend specifying an output directory using the <code>-D</code> option flag.</p> </div> <div class="literalblock"> <div class="content"> <pre>$ asciidoctor-epub3 -D output samples/sample-book.adoc</pre> </div> </div> <div class="paragraph"> <p>When the script completes, you’ll see the file <em class="file">sample-book.epub</em> appear in the <em class="path">output</em> directory. Open that file with an EPUB reader (aka e-reader) to view the result.</p> </div> <div class="paragraph"> <p>Below are several screenshots of this sample book as it appears on an Android phone.</p> </div> <div class="imageblock"> <div class="content"> <img src="_images/chapter-title.png" alt="chapter title"> </div> <div class="title">Figure 2. An example of a chapter title and abstract shown side-by-side in Day and Night modes</div> </div> <div class="imageblock"> <div class="content"> <img src="_images/section-title-paragraph.png" alt="section title paragraph"> </div> <div class="title">Figure 3. An example of a section title followed by paragraph text separated by a literal block</div> </div> <div class="imageblock"> <div class="content"> <img src="_images/figure-admonition.png" alt="figure admonition"> </div> <div class="title">Figure 4. An example of a figure and an admonition</div> </div> <div class="imageblock"> <div class="content"> <img src="_images/sidebar.png" alt="sidebar"> </div> <div class="title">Figure 5. An example of a sidebar</div> </div> <div class="imageblock"> <div class="content"> <img src="_images/table.png" alt="table"> </div> <div class="title">Figure 6. An example of a table</div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> The <code>asciidoctor-epub3</code> command is a temporary solution for invoking the Asciidoctor EPUB3 converter. We plan to remove this script once we have completed proper integration with the <code>asciidoctor</code> command. </td> </tr> </table> </div> <div class="admonitionblock tip"> <table> <tr> <td class="icon"> <i class="fa icon-tip" title="Tip"></i> </td> <td class="content"> As another example, point <code>asciidoctor-epub3</code> at the <a href="https://github.com/opendevise/github-guides-asciidoc">GitHub Guides</a> that we’ve ported to AsciiDoc, then compare the output to the real <a href="https://guides.github.com">GitHub Guides</a>. </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="validate-the-epub3-archive"><a class="anchor" href="#validate-the-epub3-archive"></a>Validate the EPUB3 Archive</h3> <div class="paragraph"> <p>Next, let’s validate the EPUB3 archive to ensure it built correctly.</p> </div> <div class="literalblock"> <div class="title">EPUB3 with validation</div> <div class="content"> <pre>$ asciidoctor-epub3 -D output -a ebook-validate samples/sample-book.adoc</pre> </div> </div> <div class="literalblock output"> <div class="title">Validation success</div> <div class="content"> <pre>Validating using EPUB version 3.0.1 rules. No errors or warnings detected. Messages: 0 fatal / 0 errors / 0 warnings / 0 info EPUBCheck completed</pre> </div> </div> <div class="paragraph"> <p>If the EPUB3 archive contains any errors, they will be output in your terminal.</p> </div> <div class="sidebarblock"> <div class="content"> <div class="title">EPUB Standard & Validator</div> <div class="paragraph"> <p>The electronic publication (EPUB) standard is developed by the <a href="http://www.idpf.org/">International Digital Publishing Forum (IDPF)</a>. <a href="http://www.idpf.org/epub/31/spec/epub-spec.html">EPUB 3.1</a>, released in January 2017, is the latest version of this standard.</p> </div> <div class="paragraph"> <p>An EPUB3 archive contains:</p> </div> <div class="ulist"> <ul> <li> <p>a package document (metadata, file manifest, spine)</p> </li> <li> <p>a navigation document (table of contents)</p> </li> <li> <p>one or more content documents</p> </li> <li> <p>assets (images, fonts, stylesheets, etc.)</p> </li> </ul> </div> <div class="paragraph"> <p>The IDPF also supports <a href="https://github.com/w3c/epubcheck">EPUBCheck</a>. EPUBCheck parses and validates the file against the EPUB schema.</p> </div> </div> </div> <div class="paragraph"> <p>If you want to browse the contents of the EPUB3 file that is generated, or preview the XHTML files in a regular web browser, add the <code>-a ebook-extract</code> flag to the <code>asciidoctor-epub3</code> command. The EPUB3 file will be extracted to a directory adjacent to the generated file, but without the file extension.</p> </div> <div class="literalblock"> <div class="content"> <pre>$ asciidoctor-epub3 -D output -a ebook-extract samples/sample-book.adoc</pre> </div> </div> <div class="paragraph"> <p>In this example, the contents of the EPUB3 will be extracted to the <em class="path">output/sample-book</em> directory.</p> </div> </div> <div class="sect2"> <h3 id="tuning-listing-captions"><a class="anchor" href="#tuning-listing-captions"></a>Tuning Listing Captions</h3> <div class="paragraph"> <p>Unlike the built-in converters, the EPUB3 converter is configured to add a signifier (e.g., <code>Listing</code>) at the start of the caption for all listing and source blocks that have a title. This behavior is triggered because the <code>listing-caption</code> attribute is set by default.</p> </div> <div class="paragraph"> <p>If you don’t want the signifier to be included at the beginning of the caption on listing and source blocks, simply unset the <code>listing-caption</code> when invoking Asciidoctor EPUB3.</p> </div> <div class="literalblock"> <div class="content"> <pre>$ asciidoctor-epub3 -a listing-caption! book.adoc</pre> </div> </div> <div class="paragraph"> <p>Now the behavior will match that of the built-in converters. For more information about this attribute and other related attributes, see <a href="https://asciidoctor.org/docs/user-manual/#builtin-attributes-i18n">internationalization and numbering</a>.</p> </div> </div> <div class="sect2"> <h3 id="command-arguments"><a class="anchor" href="#command-arguments"></a>Command Arguments</h3> <div class="dlist"> <dl> <dt class="hdlist1"><strong>-h, --help</strong> </dt> <dd> <p>Show the usage message</p> </dd> <dt class="hdlist1"><strong>-D, --destination-dir</strong> </dt> <dd> <p>Writes files to specified directory (defaults to the current directory)</p> </dd> <dt class="hdlist1"><strong>-a ebook-epubcheck-path=<path></strong></dt> <dd> <p>Specifies path to EPUBCheck executable to use with <code>-a ebook-validate</code>. This attribute takes precedence over <code>EPUBCHECK</code> environment variable.</p> </dd> <dt class="hdlist1"><strong>-a ebook-extract</strong> </dt> <dd> <p>Extracts the EPUB3 to a folder in the destination directory after the file is generated</p> </dd> <dt class="hdlist1"><strong>-a ebook-validate</strong> </dt> <dd> <p>Runs <a href="https://github.com/w3c/epubcheck">EPUBCheck</a> to validate output file against the EPUB3 specification</p> </dd> <dt class="hdlist1"><strong>-v, --version</strong> </dt> <dd> <p>Display the program version</p> </dd> </dl> </div> </div> <div class="sect2"> <h3 id="environment-variables"><a class="anchor" href="#environment-variables"></a>Environment variables</h3> <div class="dlist"> <dl> <dt class="hdlist1"><strong>EPUBCHECK</strong></dt> <dd> <p>Specifies path to EPUBCheck executable to use with <code>-a ebook-validate</code>. Effect of this variable can be overriden with <code>-a ebook-epubcheck-path</code> attribute.</p> </dd> </dl> </div> </div> <div class="sect2"> <h3 id="epub3-archive-structure"><a class="anchor" href="#epub3-archive-structure"></a>EPUB3 Archive Structure</h3> <div class="paragraph"> <p>Here’s a sample manifest of files found in an EPUB3 document produced by Asciidoctor EPUB3.</p> </div> <div class="literalblock"> <div class="content"> <pre>META-INF/ container.xml EPUB/ fonts/ awesome/ fa-solid-900.ttf font-icons.ttf mplus-1mn-latin-bold.ttf mplus-1mn-latin-light.ttf mplus-1mn-latin-medium.ttf mplus-1mn-latin-regular.ttf mplus-1p-latin-bold.ttf mplus-1p-latin-light.ttf mplus-1p-latin-regular.ttf noto-serif-bold-italic.ttf noto-serif-bold.ttf noto-serif-italic.ttf noto-serif-regular.ttf images/ avatars/ default.png figure-01.png figure-02.png styles/ epub3-css3-only.css epub3.css chapter-01.xhtml chapter-02.xhtml ... cover.xhtml nav.xhtml package.opf toc.ncx mimetype</pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="working-with-images"><a class="anchor" href="#working-with-images"></a>Working with Images</h2> <div class="sectionbody"> <div class="paragraph"> <p>Images referenced in your AsciiDoc document must be stored in the images catalog. The images catalog is defined by the <code>imagesdir</code> attribute. If set, the value of this attribute is resolved relative to the document and must be at or below (i.e., within) the directory of that document. (In other words, it cannot point to a location outside the document directory). If this attribute is not set, the images catalog defaults to the directory of the document. Asciidoctor EPUB3 will discover all local image references and insert those images into the EPUB3 archive at the same relative path.</p> </div> <div class="sect2"> <h3 id="default-images"><a class="anchor" href="#default-images"></a>Default Images</h3> <div class="paragraph"> <p>The sample book contains a placeholder image for the author avatar.</p> </div> </div> <div class="sect2"> <h3 id="adding-the-cover-image"><a class="anchor" href="#adding-the-cover-image"></a>Adding the Cover Image</h3> <div class="paragraph"> <p>E-readers have different image resolution and file size limits regarding a book’s cover. Kindle covers tend to be 1050x1600 (16:9 aspect ratio). To ensure your cover displays correctly, you’ll want to review the documentation or publisher guidelines for the e-reading platform you’re targeting.</p> </div> <div class="admonitionblock warning"> <table> <tr> <td class="icon"> <i class="fa icon-warning" title="Warning"></i> </td> <td class="content"> We’ve found that if the book cover is more than 1600px on any side, Aldiko will not render it and may even crash. </td> </tr> </table> </div> <div class="paragraph"> <p>Feel free to use the SVG of the sample cover in the <em class="path">data/images</em> folder as a template for creating your own cover. Once your image is ready, you can set the cover image by defining the <code>front-cover-image</code> attribute in the header of the master document.</p> </div> <div class="listingblock"> <div class="content"> <pre class="highlightjs highlight"><code class="language-asciidoc hljs" data-lang="asciidoc">:front-cover-image: image:cover.png[Front Cover,1050,1600]</code></pre> </div> </div> <div class="paragraph"> <p>The image is resolved relative to the directory specified in the <code>imagesdir</code> attribute, which defaults to the directory of the3 document. The image can be in any format, though we recommend using PNG, JPG, or SVG as they are the most portable formats.</p> </div> <div class="admonitionblock important"> <table> <tr> <td class="icon"> <i class="fa icon-important" title="Important"></i> </td> <td class="content"> <strong>You should always specify the dimensions of the cover image.</strong> This ensures the viewer will preserve the aspect ratio if it needs to be scaled to fit the screen. If you don’t specify a width and height, then the dimensions are assumed to be 1050x1600. </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="how-to-organize-images-by-chapter"><a class="anchor" href="#how-to-organize-images-by-chapter"></a>How to Organize Images by Chapter</h3> <div class="paragraph"> <p>You can set the <code>imagesdir</code> attribute by chapter (as long as the attribute is not overridden by the API). To do so, use an attribute entry to set the value of the <code>imagesdir</code> attribute on the line above the include directive for a chapter.</p> </div> <div class="listingblock"> <div class="content"> <pre class="highlightjs highlight"><code class="language-asciidoc hljs" data-lang="asciidoc">:imagesdir: chapter-one/images include::chapter-one.adoc[] :imagesdir: chapter-two/images include::chapter-two.adoc[]</code></pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="about-the-theme"><a class="anchor" href="#about-the-theme"></a>About the Theme</h2> <div class="sectionbody"> <div class="paragraph"> <p>EPUB3 files are styled using CSS3. However, each e-reading platform honors a reduced set of CSS3 styles, and the styles they allow and how they implement them are rarely documented. All we’ve got to say is <em>thank goodness for CSS hacks, media queries and years of CSS experience!</em></p> </div> <div class="paragraph"> <p>The theme provided with Asciidoctor EPUB3 has been crafted to display EPUB3 files as consistently as possible across the most common EPUB3 platforms and to degrade gracefully in select EPUB2 platforms. The theme maintains readability regardless of the reading mode (i.e., day, night or sepia) or the display device’s pixel density and screen resolution.</p> </div> <div class="paragraph"> <p>The theme’s CSS files are located in the <em class="path">data/style</em> directory.</p> </div> <div class="admonitionblock important"> <table> <tr> <td class="icon"> <i class="fa icon-important" title="Important"></i> </td> <td class="content"> Asciidoctor EPUB3 only provides one theme, and, at this time, you can not replace it with a custom theme using the <code>stylesheet</code> attribute. However, you can use your own <em class="path">epub3.css</em> and <em class="path">epub3-css3-only.css</em> files by specifying the directory where they are located using the <code>epub3-stylesdir</code> attribute. </td> </tr> </table> </div> <div class="sect2"> <h3 id="device-specific-styles"><a class="anchor" href="#device-specific-styles"></a>Device-specific Styles</h3> <div class="paragraph"> <p>For readers that support JavaScript, Asciidoctor EPUB3 adds a CSS class to the body element of each chapter that corresponds to the name of the reader as reported by the <a href="http://www.idpf.org/epub/301/spec/epub-contentdocs.html#app-epubReadingSystem">epubReadingSystem</a> JavaScript object. This enhancement allows you to use styles targeted specifically at that reader.</p> </div> <div class="paragraph"> <p>Below you can find the readers that are known to support this feature and the CSS class name that gets added to the body element.</p> </div> <table class="tableblock frame-none grid-rows stretch"> <colgroup> <col style="width: 33.3333%;"> <col style="width: 33.3333%;"> <col style="width: 33.3334%;"> </colgroup> <thead> <tr> <th class="tableblock halign-left valign-top">Reader</th> <th class="tableblock halign-left valign-top">HTML Element</th> <th class="tableblock halign-left valign-top">CSS Class Name</th> </tr> </thead> <tbody> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Gitden</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">body</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">gitden-reader</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Namo PubTreeViewer</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">body</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">namo-epub-library</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Readium</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">body</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">readium-js-viewer</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">iBooks</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">body</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">ibooks</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Adobe RMSDK >= 11</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">body</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">rmsdk</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Google Books</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">div</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">gb-reader-container</p></td> </tr> </tbody> </table> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> Kobo does not support the epubReadingSystem JavaScript object, despite the fact that it does support JavaScript. </td> </tr> </table> </div> </div> </div> </div> <div class="sect1"> <h2 id="pushing-to-android"><a class="anchor" href="#pushing-to-android"></a>Pushing to Android</h2> <div class="sectionbody"> <div class="paragraph"> <p>While it’s certainly possible to view the EPUB3 on your desktop/laptop, you’ll probably want to test it where it’s most likely going to be read—​on a reading device such as a smartphone or a tablet. Assuming you have an Android device available, transferring the EPUB3 to the device is easy once you get a bit of setup out of the way.</p> </div> <div class="paragraph"> <p>You transfer files from your computer to an Android phone over a USB connection using a command from the Android SDK Tools called <code>adb</code>. Follow these steps to get it set up:</p> </div> <div class="olist arabic"> <ol class="arabic"> <li> <p>Download the Android SDK Tools zip from the table labeled <strong>SDK Tools Only</strong> on the <a href="https://developer.android.com/sdk/index.html">Get the Android SDK</a> page</p> </li> <li> <p>Extract the archive</p> </li> <li> <p>Locate the path to the <code>adb</code> command (Hint: Look in the platform-tools folder)</p> </li> <li> <p>Set the environment variable named ADB to the path of the <code>adb</code> command</p> <div class="literalblock"> <div class="content"> <pre>$ export ADB=~/apps/android-sdk/platform-tools/adb</pre> </div> </div> </li> </ol> </div> <div class="paragraph"> <p>Now you can use the <code>adb push</code> to push the EPUB3 files to your Android device.</p> </div> <div class="literalblock"> <div class="title">Publish EPUB3 file to Android device</div> <div class="content"> <pre>$ adb push output/sample-book.epub /sdcard</pre> </div> </div> <div class="paragraph"> <p>You’ll have to manually import the EPUB3 into your e-reader of choice.</p> </div> </div> </div> <div class="sect1"> <h2 id="e-book-reader-recommendations-and-quirks"><a class="anchor" href="#e-book-reader-recommendations-and-quirks"></a>E-book Reader Recommendations and Quirks</h2> <div class="sectionbody"> <div class="paragraph"> <p>EPUB3 e-readers will provide the best reading experience when viewing a book generated by Asciidoctor EPUB3. Here’s a list of some of the e-readers we know to have good EPUB3 support and the systems on which they run:</p> </div> <div class="ulist"> <ul> <li> <p><a href="http://www.amazon.com/gp/feature.html?docId=1000493771">Amazon Kindle</a> (most platforms)</p> </li> <li> <p><a href="http://gitden.com/gitdenreader">Gitden</a> (Android and iOS)</p> </li> <li> <p><a href="http://www.apple.com/ibooks">iBooks</a> (iOS, OSX)</p> </li> <li> <p><a href="https://chrome.google.com/webstore/detail/readium/fepbnnnkkadjhjahcafoaglimekefifl?hl=en-US">Readium</a> (Chrome)</p> </li> <li> <p><a href="http://www.kobo.com/apps">Kobo</a> (Android, iOS, OSX and Windows)</p> </li> <li> <p><a href="http://www.namo.com/site/namo/menu/5074.do">Namo PubTreeViewer</a> (Android, iOS and Windows)</p> </li> <li> <p><a href="http://calibre-ebook.com">Calibre (ebook-viewer)</a> (Linux, OSX, Windows)</p> </li> </ul> </div> <div class="admonitionblock important"> <table> <tr> <td class="icon"> <i class="fa icon-important" title="Important"></i> </td> <td class="content"> To get the full experience, <strong>ensure that the e-reader is configured to use the publisher’s styles</strong>. Different e-readers word this setting in different ways. Look for the option screen that allows you to set the fonts and font colors and disable it. With publisher’s styles active, you’ll still be able to adjust the relative size of the fonts and margins and toggle between day, night and sepia mode. </td> </tr> </table> </div> <div class="paragraph"> <p>When the book is viewed in EPUB2 e-readers and Kindle apps/devices which have reached their end-of-life (EOL), the e-book relies on the strong semantics of HTML and some fallback styles to render properly. EPUB2 e-readers, such as Aldiko, don’t understand CSS3 styles and therefore miss out on some of the subtleties in the formatting.</p> </div> <div class="paragraph"> <p>As mentioned in the <a href="#about-the-theme">theme section</a>, the stylesheet attempts to provide as consistent a reading experience as possible in the common EPUB3 e-readers, despite the different CSS implementation rules and limitations unique to each e-book application. Most of these obstacles were addressed using media queries or explicit classes. Some we haven’t conquered. Yet.</p> </div> <div class="paragraph"> <p>The <a href="#kindle-quirks">Kindle quirks list</a> shows you just a few of the constraints we encountered. To see all the workarounds and why we chose certain style options, check out the code and comments in the <em class="file">epub3.css</em> and <em class="file">epub3-css-only.css</em> files.</p> </div> <div id="kindle-quirks" class="ulist"> <div class="title">Kindle Quirks</div> <ul> <li> <p>overrules margins and line heights like a medieval tyrant</p> </li> <li> <p><code>font-family</code> can’t be set on <code><body></code></p> </li> <li> <p>requires <code>!important</code> on text-decoration</p> </li> <li> <p><code>position: relative</code> isn’t permitted</p> </li> <li> <p>strips (or unwraps) <code><header></code> tags</p> </li> <li> <p><code>@page</code> isn’t supported</p> </li> <li> <p><code>page-break: avoid</code> isn’t supported</p> </li> <li> <p><code>page-break-*</code> cannot be applied using a compound or nested CSS selector; must be a simple ID or class</p> </li> <li> <p><code>max-width</code> isn’t supported</p> </li> <li> <p><code>widows</code> are left in the cold</p> </li> <li> <p>won’t style footers without an explicit class</p> </li> <li> <p><code>-webkit-hyphens: auto</code> causes Kindle for Mac (and perhaps others) to crash</p> </li> <li> <p><code>text-rendering: optimizeLegibility</code> causes file to be rejected by KFP (and causes the text to disappear in some previewers)</p> </li> <li> <p>Kindle Direct Publishing (KDP) strips out select font-related CSS rules (e.g., <code>font-family</code>) under certain conditions (for reasons that have proved nearly impossible to reverse engineer); the known workaround is to add a layer of indirection by using <code>@import</code> to hide the CSS files from the script</p> </li> </ul> </div> </div> </div> </article> </div> </main> </div> <footer class="footer"> <div class="footer-main"> <figure class="footer-brand"> <a class="logo" href="https://asciidoctor.org" target="_blank" rel="noopener"><img src="../../_/img/asciidoctor-logo.svg" alt="Asciidoctor" width="48"></a> <figcaption class="footer-brand-name"><a href="https://asciidoctor.org" target="_blank" rel="noopener">Asciidoctor</a></figcaption> </figure> <ul class="footer-brand-links"> <!-- <li><a href="https://asciidoctor.org" target="_blank" rel="noopener">Home</a></li> --> <li><a href="https://docs.asciidoctor.org">Docs</a></li> <li><a href="https://chat.asciidoctor.org" target="_blank" rel="noopener">Chat</a></li> <li><a href="https://github.com/asciidoctor" target="_blank" rel="noopener">Source</a></li> <li><a href="https://discuss.asciidoctor.org" target="_blank" rel="noopener">List (archive)</a></li> </ul> <p class="footer-brand-follow"> <a href="https://twitter.com/asciidoctor" title="Follow us on Twitter" target="_blank" rel="noopener"><img src="../../_/img/twitter-logo.svg" alt="Twitter logo" class="logo" width="28"><span class="handle">@asciidoctor</span></a> </p> </div> <div class="footer-legal"> <p>Copyright © 2025 Dan Allen, Sarah White, and individual Asciidoctor contributors. Except where noted, the content is licensed under a Creative Commons Attribution 4.0 International (CC BY 4.0) license.</p> <p>The <a href="https://github.com/asciidoctor/asciidoctor-docs-ui" target="_blank" rel="noopener">UI for this site</a> is derived from the Antora default UI and is licensed under the MPL-2.0 license. Several icons are imported from <a href="https://primer.style/octicons/" target="_blank" rel="noopener">Octicons</a> and are licensed under the MIT license.</p> <p>AsciiDoc® and AsciiDoc Language™ are trademarks of the Eclipse Foundation, Inc.</p> </div> <div class="footer-thanks"> <p>Thanks to our <a href="https://asciidoctor.org/supporters/" target="_blank" rel="noopener">backers</a> and <a href="https://asciidoctor.org/contributors/" target="_blank" rel="noopener">contributors</a> for helping to make this project possible. Additional thanks to:</p> <p class="badges"> <a href="https://opendevise.com" title="Development support by OpenDevise" target="_blank" rel="noopener"><img src="https://secure.gravatar.com/avatar/823717a797dbd78ceff7b26aa397f383.png?size=80" alt="OpenDevise Logo" width="30"></a> <a href="https://zulip.com" title="Chat powered by Zulip" target="_blank" rel="noopener"><img src="../../_/img/zulip-logo.svg" alt="Zulip logo" width="30"></a> <a href="https://algolia.com/docsearch" title="Search by Algolia DocSearch" target="_blank" rel="noopener"><img src="../../_/img/algolia-logo.svg" alt="Algolia logo" width="30"></a> <a href="https://netlify.com" title="Deploys by Netlify" target="_blank" rel="noopener"><img src="../../_/img/netlify-logo.svg" alt="Deploys by Netlify" width="67"></a> </p> <p>Authored in <a href="https://asciidoc.org" target="_blank" rel="noopener">AsciiDoc</a>.<br>Produced by <a href="https://antora.org" target="_blank" rel="noopener">Antora</a> and <a href="https://asciidoctor.org" target="_blank" rel="noopener">Asciidoctor</a>.</p> </div> </footer> <script id="site-script" src="../../_/js/site.js" data-ui-root-path="../../_"></script> <script async src="../../_/js/vendor/tabs.js"></script> <script async src="../../_/js/vendor/highlight.js"></script> <script async id="search-script" src="../../_/js/vendor/docsearch.js" data-app-id="V1SEVEBOXX" data-api-key="02ab3d2d0cab4dec119447e14abdd3bc" data-index-name="asciidoctor-docs" data-stylesheet="../../_/css/vendor/docsearch.css"></script> </body> </html>