Creating Documents from Outlines

Leo’s rst3 command converts Leo trees containing reStructuredText (rST) or Sphinx markup to HTML, PDF, LaTeX, and other kinds of output files. This tutorial gives step-by-step instructions for using the rst3 command.

Prerequisites: Please make sure you have read the first tutorial before reading this one. If you are new to rST, please read the rST primer. For full information about Sphinx, please read the Sphinx documentation.

The rst3 command makes using rST or Sphinx much easier by automatically creating underlining for rST sections. To reorganize a document, just reorganize the corresponding Leo outline: you don’t have to change underlining characters by hand.

The tutorial covers only the basic features of the rst3 command. This is enough to generate all of Leo’s documentation!

CheatSheet.leo contains an expanded version of the example used in this tutorial. You can open CheatSheet.leo from Leo’s help menu.

Install docutils and (optional) sphinx

The rst3 command requires the docutils Python package. You must also install the Sphinx package if you use sphinx markup. Sphinx gives Leo’s and Python’s websites their distinctive appearance and features. After installing docutils or sphinx, you must restart Leo so that the new installation will take effect.

Create the @rst node

  1. Create a node someplace in your outline.

  2. Type this in the headline:

    @rst myDocument.html
    

The @rst node, including its descendants, represents your document.

The output and intermediate files

The rst3 command applied to:

@rst myDocument.html

will generate an output file, myDocument.html, from this node and its children, grandchildren, etc. The rst3 command creates the output file in the same directory as the .leo file containing the @rst node. You can specify other directories using absolute or relative paths. Examples:

@rst myDocument.html        # in same folder as the .leo file
@rst html/myDocument.html   # in a subfolder
@rst ~/docs/myDocument.html # an absolute path to the folder

The rst3 command writes an intermediate file in the same directory as the output file. This intermediate file contains the reStructuredText markup generated by the rst3 command. It has the suffix .txt:

myDocument.html.txt

Choose docutils or sphinx

Put the rst3_call_docutils setting in the @settings tree in the .leo file containing the @rst node. This setting determines whether to use plain rST markup or full sphinx markup. To use plain reStructuredText markup:

@bool rst3_call_docutils = True

To use sphinx markup:

@bool rst3_call_docutils = False

Setting up conf.py for sphinx

When using sphinx you must ensure that sphinx’s conf.py file is configured so that it will find the intermediate files created by the rst3 command. For example, the conf.py file for Leo’s docs contains the following:

source_suffix = '.html.txt'

This “matches” the form of the intermediate files. For example, given:

@rst myDocument.html

and the default value for the rst3_write_intermediate_extension setting:

@string rst3_write_intermediate_extension = .txt

the name of the intermediate file will be:

myDocument.html.txt

myDocument.html.txt is the input file for sphinx.

Put a title in the @rst node

Put something like this in the body of the @rst node:

#############
War and Peace
#############

rST markup uses over/underlining to indicate chapter titles. Put an overline consisting of pounds signs above the title (War and Peace), and an identical underline of pound signs below as shown. rST markup for chapter titles is a bit picky:

  • under/overlines must be at least 4 characters long

  • under/overlines must be at least as long as the title.

  • The overline and underline must be identical.

Note: the rst3 command requires that the “#” character be used in the over/underlines for chapter titles.

Start the chapter

Put introductory words in the body of the @rst node itself:

“Well, Prince, so Genoa and Lucca are now just family estates of the Buonapartes. But I warn you, if you don’t tell me that this means war, if you still try to defend the infamies and horrors perpetrated by that Antichrist–I really believe he is Antichrist–I will have nothing more to do with you and you are no longer my friend, no longer my ‘faithful slave,’ as you call yourself! But how do you do? I see I have frightened you–sit down and tell me all the news.”

It was in July, 1805, and the speaker was the well-known Anna Pavlovna Scherer, maid of honor and favorite of the Empress Marya Fedorovna. With these words she greeted Prince Vasili Kuragin, a man of high rank and importance, who was the first to arrive at her reception. Anna Pavlovna had had a cough for some days. She was, as she said, suffering from la grippe; grippe being then a new word in St. Petersburg, used only by the elite.

Create sections and subsections

To create a new section, subsection, etc., in the output file:

  1. Create a new outline node, as some descendant of the @rst node.

  2. The new node’s headline becomes the section’s title.

  3. Type the contents of the section in the body text of the node.

That’s all there is to it:

  • The rst3 command generates rST underlining automatically.

  • You reorganize your document by reorganizing nodes.

There is no need to change markup when reorganizing your document, a huge improvement over writing “raw” rST.

Write your document

Now you write your novel, short story, documentation, or whatever. Organize your work as always:

nodes create sections, subsections, sub-sub-sections, etc.
depending on their position in the outline.

Run the rst3 command

<Alt-X>rst3<Return> runs the rst3 command.

  • If the present node is an @rst node (or a descendant of an @rst node) the rst3 command applies to the nearest ancestor @rst node.

  • Otherwise, the rst3 command applies to all descendant @rst trees.

If @bool rst3_call_docutils is True, the rst3 command will call docutils automatically to create the output files. For more information about Leo’s settings, see this section.

When using sphinx, run sphinx’s “make” utility after running the rst3 command to create the final output files.

Errors and warnings:

  1. Install docutils and then restart Leo if you see this error:

    writeToDocutils: docutils not present
    
  2. ​Leo has a default stylesheet ​​that centers titles and makes them big and bold, so you can disregard messages such as:

    stylesheet not found <path-to>default.css
    

Other topics

@rst-no-head suppresses sections

Sometimes you want to organize text without creating sections:

  1. Create an outline node to organize your text.

  2. Type the following in the headline:

    @rst-no-head <any text: it is ignored>
    

The rst3 command adds the body text of this node to the previous section:

  • The headline is ignored.

  • The @rst-no-head node does not change the rST section structure in any way.

@rst-ignore & @rst-ignore-tree ignore text

It is often useful to put reference material in your @rst tree that will not be included in the actual output. To have the rst3 command ignore a single node, type this in the node’s headline:

@rst-ignore <ignored-text>

Neither the headline nor body text will be part of the output file.

To have the rst3 command ignore a node and all its descendants, type this in the node’s headline:

@rst-ignore-tree <ignored-text>

Inserting raw markup

The rST manual tells how to insert “raw” markup into the output. For example, Leo’s documentation defines the following:

.. |---| unicode:: U+02015 .. for quotes
   :trim:

Now --- inserts —, the unicode “quotation dash” used to indicate the author of quotations. Note that rST automatically turns -- into a dash: –.

The rST | markup breaks text into specific lines, but there are times when it can’t be used. The following inserts a line break into text:

.. |br| raw:: html

   <br />

Filtering contents

Plugins may define filters that alter the output of any node. When writing the headline of a node p, the rst3 command calls the body filter to change the p.b. Similarly, the rst3 command calls the headline filter to change p.h. By default, these filters do nothing. That is, they return p.b and p.b respectively. However, the signatures of these filters are:

def headline_filter(c, p)
def body_filter(c, p)

so these filters have full access to all nodes of the entire outline. As a result, these filters can return arbitrary text that comes from anywhere in the outline.

The leo/plugins/example_rst_filter.py shows how to define and register these filters.

Summary

  • The rst3 command converts an @rst tree to an output file and an intermediate file.

  • docutils uses the output file; sphinx uses the intermediate file.

  • Settings starting with “rst3” control how the rst3 command works.

  • Within @rst trees, headlines become rST sections.

  • Sections levels in the generated rST correspond to outline levels in Leo.

  • You reorganize your rST documents just by reorganizing the corresponding @rst tree.

  • The rst3 command works acts on the nearest ancestor @rst node, if any, or on all descendant @rst nodes.

  • @rst-no-head nodes insert text (or markup) without an rST headline.

  • The rst3 command ignores @rst-ignore nodes and @rst-ignore-tree trees.

  • The @button make-sphinx node in LeoDocs.leo calls sphinx automatically.

  • CheatSheet.leo contains an expanded version of the example used in this tutorial.
    You can open CheatSheet.leo from Leo’s help menu.

Further study

You now know enough to get started with the rst3 command. Some possible next steps are:

  • Look at Leo’s own documentation in LeoDocs.leo. Discover how the nodes in this tree correspond to the documentation you see before you.

  • LeoDocs.leo has an @button make-sphinx script that calls sphinx automatically.

  • Create your own @rst nodes. Run the rst3 command on them and see what happens.

  • If you get stuck, please ask for help at https://groups.google.com/forum/#!forum/leo-editor.