packages feed

pandoc-plot 1.0.1.0 → 1.0.2.0

raw patch · 32 files changed

+961/−549 lines, 32 filesPVP: major bump suggested

API removals or changes: PVP suggests a major version bump

API changes (from Hackage documentation)

- Text.Pandoc.Filter.Plot.Internal: ToolkitNotInstalled :: Toolkit -> ScriptResult
- Text.Pandoc.Filter.Plot.Internal: [toolkit] :: FigureSpec -> !Toolkit
- Text.Pandoc.Filter.Plot.Internal: capture :: Toolkit -> FigureSpec -> FilePath -> Script
- Text.Pandoc.Filter.Plot.Internal: command :: Toolkit -> OutputSpec -> Text -> Text
- Text.Pandoc.Filter.Plot.Internal: comment :: Toolkit -> Text -> Text
- Text.Pandoc.Filter.Plot.Internal: language :: Toolkit -> Text
- Text.Pandoc.Filter.Plot.Internal: scriptChecks :: Toolkit -> [Script -> CheckResult]
- Text.Pandoc.Filter.Plot.Internal: scriptExtension :: Toolkit -> String
- Text.Pandoc.Filter.Plot.Internal: toolkitAvailable :: Toolkit -> PlotM Bool
+ Text.Pandoc.Filter.Plot: [bokehCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [ggplot2CmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [gnuplotCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [graphvizCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [mathematicaCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [matlabCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [matplotlibCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [octaveCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [plotlyPythonCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [plotlyRCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [plotsjlCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot: [strictMode] :: Configuration -> !Bool
+ Text.Pandoc.Filter.Plot.Internal: CommandLineArgsK :: InclusionKey
+ Text.Pandoc.Filter.Plot.Internal: PlotState :: MVar (Map FilePath FileHash) -> MVar (Map Toolkit (Maybe Renderer)) -> PlotState
+ Text.Pandoc.Filter.Plot.Internal: Renderer :: Toolkit -> Executable -> (FigureSpec -> FilePath -> Script) -> (OutputSpec -> Text) -> [SaveFormat] -> [Script -> CheckResult] -> Text -> (Text -> Text) -> String -> Renderer
+ Text.Pandoc.Filter.Plot.Internal: StrictModeK :: InclusionKey
+ Text.Pandoc.Filter.Plot.Internal: [bokehCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [ggplot2CmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [gnuplotCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [graphvizCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [mathematicaCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [matlabCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [matplotlibCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [octaveCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [plotlyPythonCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [plotlyRCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [plotsjlCmdArgs] :: Configuration -> !Text
+ Text.Pandoc.Filter.Plot.Internal: [rendererCapture] :: Renderer -> FigureSpec -> FilePath -> Script
+ Text.Pandoc.Filter.Plot.Internal: [rendererChecks] :: Renderer -> [Script -> CheckResult]
+ Text.Pandoc.Filter.Plot.Internal: [rendererCommand] :: Renderer -> OutputSpec -> Text
+ Text.Pandoc.Filter.Plot.Internal: [rendererComment] :: Renderer -> Text -> Text
+ Text.Pandoc.Filter.Plot.Internal: [rendererExe] :: Renderer -> Executable
+ Text.Pandoc.Filter.Plot.Internal: [rendererLanguage] :: Renderer -> Text
+ Text.Pandoc.Filter.Plot.Internal: [rendererScriptExtension] :: Renderer -> String
+ Text.Pandoc.Filter.Plot.Internal: [rendererSupportedSaveFormats] :: Renderer -> [SaveFormat]
+ Text.Pandoc.Filter.Plot.Internal: [rendererToolkit] :: Renderer -> Toolkit
+ Text.Pandoc.Filter.Plot.Internal: [renderer_] :: FigureSpec -> !Renderer
+ Text.Pandoc.Filter.Plot.Internal: [strictMode] :: Configuration -> !Bool
+ Text.Pandoc.Filter.Plot.Internal: data PlotState
+ Text.Pandoc.Filter.Plot.Internal: data Renderer
+ Text.Pandoc.Filter.Plot.Internal: renderer :: Toolkit -> PlotM (Maybe Renderer)
+ Text.Pandoc.Filter.Plot.Internal: throwError :: Text -> PlotM ()
+ Text.Pandoc.Filter.Plot.Internal: whenStrict :: PlotM () -> PlotM ()
+ Text.Pandoc.Filter.Plot.Internal: withPrependedPath :: FilePath -> PlotM a -> PlotM a
- Text.Pandoc.Filter.Plot: Configuration :: !FilePath -> !Bool -> !Int -> !SaveFormat -> ![FilePath] -> !Format -> !Text -> !Verbosity -> !LogSink -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !Bool -> !Bool -> Configuration
+ Text.Pandoc.Filter.Plot: Configuration :: !FilePath -> !Bool -> !Int -> !SaveFormat -> ![FilePath] -> !Format -> !Text -> !Bool -> !Verbosity -> !LogSink -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Bool -> !Bool -> Configuration
- Text.Pandoc.Filter.Plot.Internal: Configuration :: !FilePath -> !Bool -> !Int -> !SaveFormat -> ![FilePath] -> !Format -> !Text -> !Verbosity -> !LogSink -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !Bool -> !Bool -> Configuration
+ Text.Pandoc.Filter.Plot.Internal: Configuration :: !FilePath -> !Bool -> !Int -> !SaveFormat -> ![FilePath] -> !Format -> !Text -> !Bool -> !Verbosity -> !LogSink -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !Script -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !FilePath -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Text -> !Bool -> !Bool -> Configuration
- Text.Pandoc.Filter.Plot.Internal: FigureSpec :: !Toolkit -> !Text -> !Bool -> !Script -> !SaveFormat -> !FilePath -> !Int -> ![FilePath] -> ![(Text, Text)] -> !Attr -> FigureSpec
+ Text.Pandoc.Filter.Plot.Internal: FigureSpec :: !Renderer -> !Text -> !Bool -> !Script -> !SaveFormat -> !FilePath -> !Int -> ![FilePath] -> ![(Text, Text)] -> !Attr -> FigureSpec

Files

CHANGELOG.md view
@@ -2,6 +2,37 @@ 
 pandoc-plot uses [Semantic Versioning](http://semver.org/spec/v2.0.0.html)
 
+Release 1.0.2.0
+---------------
+
+* Added the ability to run `pandoc-plot` in **strict mode**. By default, `pandoc-plot` leaves code blocks unchanged if a figure fails to be rendered.  In strict mode, `pandoc-plot` will immediately halt if it encounters a problem, such as a missing toolkit. You can activate strict mode via configuration:
+
+```yaml
+strict: true
+```
+
+* Added the ability to set command-line arguments for interpreters via configuration. For example, if you want to run the Matplotlib toolkit with all warnings shown:
+
+```yaml
+# Possible parameters for the Matplotlib toolkit
+matplotlib:
+  executable: python
+  command_line_arguments: -Wa
+```
+
+Or if you want `julia` to use more than one thread:
+
+```yaml
+# Possible parameters for the Plotsjl toolkit
+plotsjl:
+  executable: julia
+  command_line_arguments: --threads auto --optimize=0
+```
+
+* Fixed an issue where invoking the `plotsjl` toolkit on Windows would sometimes fail with the error: Unknown system error 50.
+* Fixed an issue with R-based toolkits on Windows not being detected properly.
+
+
 Release 1.0.1.0
 ---------------
 
MANUAL.md view
@@ -16,10 +16,21 @@ -   [Detailed usage](#detailed-usage)
     -   [As a filter](#as-a-filter)
     -   [Syntax](#syntax)
+        -   [Markdown](#markdown)
+        -   [LaTeX](#latex)
     -   [Parameters and options](#parameters-and-options)
+        -   [Code highlighting](#code-highlighting)
     -   [Interactive HTML figures](#interactive-html-figures)
     -   [Configuration](#configuration)
+        -   [Executables](#executables)
+        -   [Command-line arguments](#command-line-arguments)
+        -   [Toolkit-specific options](#toolkit-specific-options)
+        -   [Logging](#logging)
+        -   [Strict mode](#strict-mode)
     -   [Other commands](#other-commands)
+        -   [Finding installed toolkits](#finding-installed-toolkits)
+        -   [Cleaning output](#cleaning-output)
+        -   [Configuration template](#configuration-template)
 -   [Warning](#warning)
 
 ## Features Overview
@@ -159,7 +170,7 @@ `pandoc-plot` is a command line executable with a few functions. You can take a look at the help using the `-h`/`--help` flag:
 
 ``` bash
-pandoc-plot 1.0.1.0 - generate figures directly in documents
+pandoc-plot 1.0.2.0 - generate figures directly in documents
 
 Usage: pandoc-plot.EXE [(-v|--version) | --full-version | (-m|--manual)] 
                        [COMMAND] [AST]
@@ -193,7 +204,7 @@ pandoc --filter pandoc-plot -i input.md -o output.html
 ```
 
-If `pandoc-plot` fails to render a code block into a figure, the filtering will not stop. Your code blocks will stay unchanged.
+If `pandoc-plot` fails to render a code block into a figure, the filtering will not stop. Your code blocks will stay unchanged, unless you activate [strict mode](#strict-mode).
 
 You can chain other filters with it (e.g., [`pandoc-crossref`](https://github.com/lierdakil/pandoc-crossref)) like so:
 
@@ -340,6 +351,11 @@ # Particularly useful for HTML output.
 source: false
 
+# When `strict: false`, pandoc-plot will leave code blocks untouched if a plot
+# could not be generated. This could happen if, for example, a toolkit is not
+# installed. If you want pandoc-plot to fail instead, use `strict: true`.
+strict: false
+
 # Text label for links to source code.
 # You can change this label if you are writing a document in a non-English language. 
 # This only matters if `source` is set to `true`.
@@ -382,54 +398,65 @@   tight_bbox: false
   transparent: false
   executable: python
+  command_line_arguments:
 
 # The possible parameters for the MATLAB toolkit
 matlabplot:
   # preamble: matlab.m
   executable: matlab
+  command_line_arguments:
 
 # The possible parameters for the Plotly/Python toolkit
 plotly_python:
   # preamble: plotly-python.py
   executable: python
+  command_line_arguments:
 
 # The possible parameters for the Plotly/R toolkit
 plotly_r:
   # preamble: plotly-r.r
   executable: Rscript
+  command_line_arguments:
 
 # The possible parameters for the Mathematica toolkit
 mathplot:
   # preamble: mathematica.m
   executable: math
+  command_line_arguments:
 
 # The possible parameters for the GNU Octave toolkit
 octaveplot:
   # preamble: octave.m
   executable: octave
+  command_line_arguments:
 
 # The possible parameters for the ggplot2 toolkit
 ggplot2:
   # preamble: ggplot2.r
   executable: Rscript
+  command_line_arguments:
 
 # The possible parameters for the gnuplot toolkit
 gnuplot:
   # preamble: gnuplot.gp
   executable: gnuplot
+  command_line_arguments:
 
 # The possible parameters for the graphviz toolkit
 graphviz:
   # preamble: graphviz.dot
   executable: dot
+  command_line_arguments:
 
 bokeh:
   # preamble: bokeh.py
   executable: python
+  command_line_arguments:
 
 plotsjl:
   # preamble: plotsjl.jl
   executable: julia
+  command_line_arguments:
 ```
 
 A file like the above sets the **default** values; you can still override them in documents directly.
@@ -472,6 +499,28 @@   executable: "C:\Program Files\Matlab\R2019b\bin\matlab.exe"
 ```
 
+#### Command-line arguments
+
+*New in version 1.0.2.0*
+
+The `command_line_arguments` parameter available for all toolkits provides a way to customize the way interpreters are run. For example, if you want to run the `matplotlib` toolkit with all warnings shown:
+
+``` yaml
+# The possible parameters for the Matplotlib toolkit
+matplotlib:
+  executable: python
+  command_line_arguments: -Wa
+```
+
+Or if you want `julia` to use more than one thread:
+
+``` yaml
+# The possible parameters for the Matplotlib toolkit
+plotsjl:
+  executable: julia
+  command_line_arguments: --threads auto
+```
+
 #### Toolkit-specific options
 
 ##### Matplotlib
@@ -496,6 +545,18 @@ ```
 
 By default, `pandoc-plot` logs warnings and errors to the standard error stream only.
+
+#### Strict mode
+
+*New in version 1.0.2.0*
+
+By default, `pandoc-plot` leaves code blocks unchanged if a figure fails to be rendered. This might be the case if a plotting toolkit is not installed, or if running the code to render a figure returns an error. In **strict mode**, `pandoc-plot` will immediately halt if it encounters a problem. You can activate strict mode via configuration:
+
+``` yaml
+strict: true
+```
+
+Strict mode is ideal if you want to ensure that the figures are correctly rendered in the document.
 
 ### Other commands
 
README.md view
@@ -135,9 +135,6 @@ 
 ### From source
 
-[![Build
-Status](https://dev.azure.com/laurentdecotret/pandoc-plot/_apis/build/status/LaurentRDC.pandoc-plot?branchName=master)](https://dev.azure.com/laurentdecotret/pandoc-plot/_build/latest?definitionId=5&branchName=master)
-
 Building from source can be done using
 [`stack`](https://docs.haskellstack.org/en/stable/README/) or
 [`cabal`](https://www.haskell.org/cabal/):
docs/MANUAL.html view
@@ -4,7 +4,7 @@   <meta charset="utf-8" />
   <meta name="generator" content="pandoc" />
   <meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=yes" />
-  <title>pandoc-plot 1.0.1.0 manual</title>
+  <title>pandoc-plot 1.0.2.0 manual</title>
   <style>
     code{white-space: pre-wrap;}
     span.smallcaps{font-variant: small-caps;}
@@ -84,7 +84,7 @@ </head>
 <body>
 <header id="title-block-header">
-<h1 class="title">pandoc-plot 1.0.1.0 manual</h1>
+<h1 class="title">pandoc-plot 1.0.2.0 manual</h1>
 </header>
 <!--
 The file MANUAL.md is automatically generated by the tools/mkmanual.ps1 script. Do not edit manually.
@@ -104,12 +104,31 @@ <li><a href="#detailed-usage">Detailed usage</a>
 <ul>
 <li><a href="#as-a-filter">As a filter</a></li>
-<li><a href="#syntax">Syntax</a></li>
-<li><a href="#parameters-and-options">Parameters and options</a></li>
+<li><a href="#syntax">Syntax</a>
+<ul>
+<li><a href="#markdown">Markdown</a></li>
+<li><a href="#latex">LaTeX</a></li>
+</ul></li>
+<li><a href="#parameters-and-options">Parameters and options</a>
+<ul>
+<li><a href="#code-highlighting">Code highlighting</a></li>
+</ul></li>
 <li><a href="#interactive-html-figures">Interactive HTML figures</a></li>
-<li><a href="#configuration">Configuration</a></li>
-<li><a href="#other-commands">Other commands</a></li>
+<li><a href="#configuration">Configuration</a>
+<ul>
+<li><a href="#executables">Executables</a></li>
+<li><a href="#command-line-arguments">Command-line arguments</a></li>
+<li><a href="#toolkit-specific-options">Toolkit-specific options</a></li>
+<li><a href="#logging">Logging</a></li>
+<li><a href="#strict-mode">Strict mode</a></li>
 </ul></li>
+<li><a href="#other-commands">Other commands</a>
+<ul>
+<li><a href="#finding-installed-toolkits">Finding installed toolkits</a></li>
+<li><a href="#cleaning-output">Cleaning output</a></li>
+<li><a href="#configuration-template">Configuration template</a></li>
+</ul></li>
+</ul></li>
 <li><a href="#warning">Warning</a></li>
 </ul>
 <h2 id="features-overview">Features Overview</h2>
@@ -188,7 +207,7 @@ <div class="sourceCode" id="cb10"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb10-1"><a href="#cb10-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc</span> <span class="at">--filter</span> pandoc-plot <span class="at">--filter</span> pandoc-crossref <span class="at">-i</span> myfile.md <span class="at">-o</span> myfile.html</span></code></pre></div>
 <h2 id="detailed-usage">Detailed usage</h2>
 <p><code>pandoc-plot</code> is a command line executable with a few functions. You can take a look at the help using the <code>-h</code>/<code>--help</code> flag:</p>
-<div class="sourceCode" id="cb11"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb11-1"><a href="#cb11-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc-plot</span> 1.0.1.0 <span class="at">-</span> generate figures directly in documents</span>
+<div class="sourceCode" id="cb11"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb11-1"><a href="#cb11-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc-plot</span> 1.0.2.0 <span class="at">-</span> generate figures directly in documents</span>
 <span id="cb11-2"><a href="#cb11-2" aria-hidden="true" tabindex="-1"></a></span>
 <span id="cb11-3"><a href="#cb11-3" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE [<span class="er">(</span><span class="ex">-v</span><span class="kw">|</span><span class="ex">--version</span><span class="kw">)</span> <span class="kw">|</span> <span class="ex">--full-version</span> <span class="kw">|</span> <span class="kw">(</span><span class="ex">-m</span><span class="kw">|</span><span class="ex">--manual</span><span class="kw">)</span><span class="ex">]</span> </span>
 <span id="cb11-4"><a href="#cb11-4" aria-hidden="true" tabindex="-1"></a>                       <span class="ex">[COMMAND]</span> [AST]</span>
@@ -215,7 +234,7 @@ <h3 id="as-a-filter">As a filter</h3>
 <p>The most common use for <code>pandoc-plot</code> is as a pandoc filter, in which case it should be called without arguments. For example:</p>
 <div class="sourceCode" id="cb12"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb12-1"><a href="#cb12-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc</span> <span class="at">--filter</span> pandoc-plot <span class="at">-i</span> input.md <span class="at">-o</span> output.html</span></code></pre></div>
-<p>If <code>pandoc-plot</code> fails to render a code block into a figure, the filtering will not stop. Your code blocks will stay unchanged.</p>
+<p>If <code>pandoc-plot</code> fails to render a code block into a figure, the filtering will not stop. Your code blocks will stay unchanged, unless you activate <a href="#strict-mode">strict mode</a>.</p>
 <p>You can chain other filters with it (e.g., <a href="https://github.com/lierdakil/pandoc-crossref"><code>pandoc-crossref</code></a>) like so:</p>
 <div class="sourceCode" id="cb13"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb13-1"><a href="#cb13-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc</span> <span class="at">--filter</span> pandoc-plot <span class="at">--filter</span> pandoc-crossref <span class="at">-i</span> input.md <span class="at">-o</span> output.html</span></code></pre></div>
 <h3 id="syntax">Syntax</h3>
@@ -312,96 +331,112 @@ <span id="cb22-17"><a href="#cb22-17" aria-hidden="true" tabindex="-1"></a><span class="co"># Particularly useful for HTML output.</span></span>
 <span id="cb22-18"><a href="#cb22-18" aria-hidden="true" tabindex="-1"></a><span class="fu">source</span><span class="kw">:</span><span class="at"> </span><span class="ch">false</span></span>
 <span id="cb22-19"><a href="#cb22-19" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-20"><a href="#cb22-20" aria-hidden="true" tabindex="-1"></a><span class="co"># Text label for links to source code.</span></span>
-<span id="cb22-21"><a href="#cb22-21" aria-hidden="true" tabindex="-1"></a><span class="co"># You can change this label if you are writing a document in a non-English language. </span></span>
-<span id="cb22-22"><a href="#cb22-22" aria-hidden="true" tabindex="-1"></a><span class="co"># This only matters if `source` is set to `true`.</span></span>
-<span id="cb22-23"><a href="#cb22-23" aria-hidden="true" tabindex="-1"></a><span class="fu">source_label</span><span class="kw">:</span><span class="at"> Source code</span></span>
+<span id="cb22-20"><a href="#cb22-20" aria-hidden="true" tabindex="-1"></a><span class="co"># When `strict: false`, pandoc-plot will leave code blocks untouched if a plot</span></span>
+<span id="cb22-21"><a href="#cb22-21" aria-hidden="true" tabindex="-1"></a><span class="co"># could not be generated. This could happen if, for example, a toolkit is not</span></span>
+<span id="cb22-22"><a href="#cb22-22" aria-hidden="true" tabindex="-1"></a><span class="co"># installed. If you want pandoc-plot to fail instead, use `strict: true`.</span></span>
+<span id="cb22-23"><a href="#cb22-23" aria-hidden="true" tabindex="-1"></a><span class="fu">strict</span><span class="kw">:</span><span class="at"> </span><span class="ch">false</span></span>
 <span id="cb22-24"><a href="#cb22-24" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-25"><a href="#cb22-25" aria-hidden="true" tabindex="-1"></a><span class="co"># Default density of figures in dots per inches (DPI). </span></span>
-<span id="cb22-26"><a href="#cb22-26" aria-hidden="true" tabindex="-1"></a><span class="co"># This can be changed in the document specifically as well.</span></span>
-<span id="cb22-27"><a href="#cb22-27" aria-hidden="true" tabindex="-1"></a><span class="fu">dpi</span><span class="kw">:</span><span class="at"> </span><span class="dv">80</span></span>
-<span id="cb22-28"><a href="#cb22-28" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-29"><a href="#cb22-29" aria-hidden="true" tabindex="-1"></a><span class="co"># Default format in which to save the figures. This can be specified </span></span>
-<span id="cb22-30"><a href="#cb22-30" aria-hidden="true" tabindex="-1"></a><span class="co"># individually as well.</span></span>
-<span id="cb22-31"><a href="#cb22-31" aria-hidden="true" tabindex="-1"></a><span class="fu">format</span><span class="kw">:</span><span class="at"> PNG</span></span>
-<span id="cb22-32"><a href="#cb22-32" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-33"><a href="#cb22-33" aria-hidden="true" tabindex="-1"></a><span class="co"># Default files/directories on which all figures depend. If any of these files/directories</span></span>
-<span id="cb22-34"><a href="#cb22-34" aria-hidden="true" tabindex="-1"></a><span class="co"># changes, all figures will be re-rendered.</span></span>
-<span id="cb22-35"><a href="#cb22-35" aria-hidden="true" tabindex="-1"></a><span class="co"># Dependencies specified in code blocks will be appended to this list.</span></span>
-<span id="cb22-36"><a href="#cb22-36" aria-hidden="true" tabindex="-1"></a><span class="fu">dependencies</span><span class="kw">:</span></span>
-<span id="cb22-37"><a href="#cb22-37" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="kw">-</span><span class="at"> file1.txt</span></span>
-<span id="cb22-38"><a href="#cb22-38" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="kw">-</span><span class="at"> file2.txt</span></span>
-<span id="cb22-39"><a href="#cb22-39" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-40"><a href="#cb22-40" aria-hidden="true" tabindex="-1"></a><span class="co"># Text format for the captions. Unfortunately, there is no way to detect</span></span>
-<span id="cb22-41"><a href="#cb22-41" aria-hidden="true" tabindex="-1"></a><span class="co"># this automatically. You can use the same notation as Pandoc&#39;s --from </span></span>
-<span id="cb22-42"><a href="#cb22-42" aria-hidden="true" tabindex="-1"></a><span class="co"># parameter, specified here: </span></span>
-<span id="cb22-43"><a href="#cb22-43" aria-hidden="true" tabindex="-1"></a><span class="co">#     https://pandoc.org/MANUAL.html#option--from</span></span>
-<span id="cb22-44"><a href="#cb22-44" aria-hidden="true" tabindex="-1"></a><span class="co"># Example: markdown, rst+raw_tex</span></span>
-<span id="cb22-45"><a href="#cb22-45" aria-hidden="true" tabindex="-1"></a><span class="fu">caption_format</span><span class="kw">:</span><span class="at"> markdown+tex_math_dollars</span></span>
-<span id="cb22-46"><a href="#cb22-46" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-47"><a href="#cb22-47" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-48"><a href="#cb22-48" aria-hidden="true" tabindex="-1"></a><span class="co"># Logging configuration</span></span>
-<span id="cb22-49"><a href="#cb22-49" aria-hidden="true" tabindex="-1"></a><span class="fu">logging</span><span class="kw">:</span></span>
-<span id="cb22-50"><a href="#cb22-50" aria-hidden="true" tabindex="-1"></a><span class="co">  # Possible verbosity values: debug, error, warning, info, silent</span></span>
-<span id="cb22-51"><a href="#cb22-51" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">verbosity</span><span class="kw">:</span><span class="at"> warning</span></span>
-<span id="cb22-52"><a href="#cb22-52" aria-hidden="true" tabindex="-1"></a><span class="co">  # If the filepath below is not present, then pandoc-plot will log to stderr</span></span>
-<span id="cb22-53"><a href="#cb22-53" aria-hidden="true" tabindex="-1"></a><span class="co">  # Otherwise, log messages will be appended to the filepath.</span></span>
-<span id="cb22-54"><a href="#cb22-54" aria-hidden="true" tabindex="-1"></a><span class="co">  # filepath: path/to/file.txt</span></span>
-<span id="cb22-55"><a href="#cb22-55" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-56"><a href="#cb22-56" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Matplotlib toolkit</span></span>
-<span id="cb22-57"><a href="#cb22-57" aria-hidden="true" tabindex="-1"></a><span class="fu">matplotlib</span><span class="kw">:</span></span>
-<span id="cb22-58"><a href="#cb22-58" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: matplotlib.py</span></span>
-<span id="cb22-59"><a href="#cb22-59" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">tight_bbox</span><span class="kw">:</span><span class="at"> </span><span class="ch">false</span></span>
-<span id="cb22-60"><a href="#cb22-60" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">transparent</span><span class="kw">:</span><span class="at"> </span><span class="ch">false</span></span>
-<span id="cb22-61"><a href="#cb22-61" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
-<span id="cb22-62"><a href="#cb22-62" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-63"><a href="#cb22-63" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the MATLAB toolkit</span></span>
-<span id="cb22-64"><a href="#cb22-64" aria-hidden="true" tabindex="-1"></a><span class="fu">matlabplot</span><span class="kw">:</span></span>
-<span id="cb22-65"><a href="#cb22-65" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: matlab.m</span></span>
-<span id="cb22-66"><a href="#cb22-66" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> matlab</span></span>
-<span id="cb22-67"><a href="#cb22-67" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-68"><a href="#cb22-68" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Plotly/Python toolkit</span></span>
-<span id="cb22-69"><a href="#cb22-69" aria-hidden="true" tabindex="-1"></a><span class="fu">plotly_python</span><span class="kw">:</span></span>
-<span id="cb22-70"><a href="#cb22-70" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: plotly-python.py</span></span>
-<span id="cb22-71"><a href="#cb22-71" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
-<span id="cb22-72"><a href="#cb22-72" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-73"><a href="#cb22-73" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Plotly/R toolkit</span></span>
-<span id="cb22-74"><a href="#cb22-74" aria-hidden="true" tabindex="-1"></a><span class="fu">plotly_r</span><span class="kw">:</span></span>
-<span id="cb22-75"><a href="#cb22-75" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: plotly-r.r</span></span>
-<span id="cb22-76"><a href="#cb22-76" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> Rscript</span></span>
-<span id="cb22-77"><a href="#cb22-77" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-78"><a href="#cb22-78" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Mathematica toolkit</span></span>
-<span id="cb22-79"><a href="#cb22-79" aria-hidden="true" tabindex="-1"></a><span class="fu">mathplot</span><span class="kw">:</span></span>
-<span id="cb22-80"><a href="#cb22-80" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: mathematica.m</span></span>
-<span id="cb22-81"><a href="#cb22-81" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> math</span></span>
-<span id="cb22-82"><a href="#cb22-82" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-83"><a href="#cb22-83" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the GNU Octave toolkit</span></span>
-<span id="cb22-84"><a href="#cb22-84" aria-hidden="true" tabindex="-1"></a><span class="fu">octaveplot</span><span class="kw">:</span></span>
-<span id="cb22-85"><a href="#cb22-85" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: octave.m</span></span>
-<span id="cb22-86"><a href="#cb22-86" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> octave</span></span>
-<span id="cb22-87"><a href="#cb22-87" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-88"><a href="#cb22-88" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the ggplot2 toolkit</span></span>
-<span id="cb22-89"><a href="#cb22-89" aria-hidden="true" tabindex="-1"></a><span class="fu">ggplot2</span><span class="kw">:</span></span>
-<span id="cb22-90"><a href="#cb22-90" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: ggplot2.r</span></span>
-<span id="cb22-91"><a href="#cb22-91" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> Rscript</span></span>
+<span id="cb22-25"><a href="#cb22-25" aria-hidden="true" tabindex="-1"></a><span class="co"># Text label for links to source code.</span></span>
+<span id="cb22-26"><a href="#cb22-26" aria-hidden="true" tabindex="-1"></a><span class="co"># You can change this label if you are writing a document in a non-English language. </span></span>
+<span id="cb22-27"><a href="#cb22-27" aria-hidden="true" tabindex="-1"></a><span class="co"># This only matters if `source` is set to `true`.</span></span>
+<span id="cb22-28"><a href="#cb22-28" aria-hidden="true" tabindex="-1"></a><span class="fu">source_label</span><span class="kw">:</span><span class="at"> Source code</span></span>
+<span id="cb22-29"><a href="#cb22-29" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-30"><a href="#cb22-30" aria-hidden="true" tabindex="-1"></a><span class="co"># Default density of figures in dots per inches (DPI). </span></span>
+<span id="cb22-31"><a href="#cb22-31" aria-hidden="true" tabindex="-1"></a><span class="co"># This can be changed in the document specifically as well.</span></span>
+<span id="cb22-32"><a href="#cb22-32" aria-hidden="true" tabindex="-1"></a><span class="fu">dpi</span><span class="kw">:</span><span class="at"> </span><span class="dv">80</span></span>
+<span id="cb22-33"><a href="#cb22-33" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-34"><a href="#cb22-34" aria-hidden="true" tabindex="-1"></a><span class="co"># Default format in which to save the figures. This can be specified </span></span>
+<span id="cb22-35"><a href="#cb22-35" aria-hidden="true" tabindex="-1"></a><span class="co"># individually as well.</span></span>
+<span id="cb22-36"><a href="#cb22-36" aria-hidden="true" tabindex="-1"></a><span class="fu">format</span><span class="kw">:</span><span class="at"> PNG</span></span>
+<span id="cb22-37"><a href="#cb22-37" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-38"><a href="#cb22-38" aria-hidden="true" tabindex="-1"></a><span class="co"># Default files/directories on which all figures depend. If any of these files/directories</span></span>
+<span id="cb22-39"><a href="#cb22-39" aria-hidden="true" tabindex="-1"></a><span class="co"># changes, all figures will be re-rendered.</span></span>
+<span id="cb22-40"><a href="#cb22-40" aria-hidden="true" tabindex="-1"></a><span class="co"># Dependencies specified in code blocks will be appended to this list.</span></span>
+<span id="cb22-41"><a href="#cb22-41" aria-hidden="true" tabindex="-1"></a><span class="fu">dependencies</span><span class="kw">:</span></span>
+<span id="cb22-42"><a href="#cb22-42" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="kw">-</span><span class="at"> file1.txt</span></span>
+<span id="cb22-43"><a href="#cb22-43" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="kw">-</span><span class="at"> file2.txt</span></span>
+<span id="cb22-44"><a href="#cb22-44" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-45"><a href="#cb22-45" aria-hidden="true" tabindex="-1"></a><span class="co"># Text format for the captions. Unfortunately, there is no way to detect</span></span>
+<span id="cb22-46"><a href="#cb22-46" aria-hidden="true" tabindex="-1"></a><span class="co"># this automatically. You can use the same notation as Pandoc&#39;s --from </span></span>
+<span id="cb22-47"><a href="#cb22-47" aria-hidden="true" tabindex="-1"></a><span class="co"># parameter, specified here: </span></span>
+<span id="cb22-48"><a href="#cb22-48" aria-hidden="true" tabindex="-1"></a><span class="co">#     https://pandoc.org/MANUAL.html#option--from</span></span>
+<span id="cb22-49"><a href="#cb22-49" aria-hidden="true" tabindex="-1"></a><span class="co"># Example: markdown, rst+raw_tex</span></span>
+<span id="cb22-50"><a href="#cb22-50" aria-hidden="true" tabindex="-1"></a><span class="fu">caption_format</span><span class="kw">:</span><span class="at"> markdown+tex_math_dollars</span></span>
+<span id="cb22-51"><a href="#cb22-51" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-52"><a href="#cb22-52" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-53"><a href="#cb22-53" aria-hidden="true" tabindex="-1"></a><span class="co"># Logging configuration</span></span>
+<span id="cb22-54"><a href="#cb22-54" aria-hidden="true" tabindex="-1"></a><span class="fu">logging</span><span class="kw">:</span></span>
+<span id="cb22-55"><a href="#cb22-55" aria-hidden="true" tabindex="-1"></a><span class="co">  # Possible verbosity values: debug, error, warning, info, silent</span></span>
+<span id="cb22-56"><a href="#cb22-56" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">verbosity</span><span class="kw">:</span><span class="at"> warning</span></span>
+<span id="cb22-57"><a href="#cb22-57" aria-hidden="true" tabindex="-1"></a><span class="co">  # If the filepath below is not present, then pandoc-plot will log to stderr</span></span>
+<span id="cb22-58"><a href="#cb22-58" aria-hidden="true" tabindex="-1"></a><span class="co">  # Otherwise, log messages will be appended to the filepath.</span></span>
+<span id="cb22-59"><a href="#cb22-59" aria-hidden="true" tabindex="-1"></a><span class="co">  # filepath: path/to/file.txt</span></span>
+<span id="cb22-60"><a href="#cb22-60" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-61"><a href="#cb22-61" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Matplotlib toolkit</span></span>
+<span id="cb22-62"><a href="#cb22-62" aria-hidden="true" tabindex="-1"></a><span class="fu">matplotlib</span><span class="kw">:</span></span>
+<span id="cb22-63"><a href="#cb22-63" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: matplotlib.py</span></span>
+<span id="cb22-64"><a href="#cb22-64" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">tight_bbox</span><span class="kw">:</span><span class="at"> </span><span class="ch">false</span></span>
+<span id="cb22-65"><a href="#cb22-65" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">transparent</span><span class="kw">:</span><span class="at"> </span><span class="ch">false</span></span>
+<span id="cb22-66"><a href="#cb22-66" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
+<span id="cb22-67"><a href="#cb22-67" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-68"><a href="#cb22-68" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-69"><a href="#cb22-69" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the MATLAB toolkit</span></span>
+<span id="cb22-70"><a href="#cb22-70" aria-hidden="true" tabindex="-1"></a><span class="fu">matlabplot</span><span class="kw">:</span></span>
+<span id="cb22-71"><a href="#cb22-71" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: matlab.m</span></span>
+<span id="cb22-72"><a href="#cb22-72" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> matlab</span></span>
+<span id="cb22-73"><a href="#cb22-73" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-74"><a href="#cb22-74" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-75"><a href="#cb22-75" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Plotly/Python toolkit</span></span>
+<span id="cb22-76"><a href="#cb22-76" aria-hidden="true" tabindex="-1"></a><span class="fu">plotly_python</span><span class="kw">:</span></span>
+<span id="cb22-77"><a href="#cb22-77" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: plotly-python.py</span></span>
+<span id="cb22-78"><a href="#cb22-78" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
+<span id="cb22-79"><a href="#cb22-79" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-80"><a href="#cb22-80" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-81"><a href="#cb22-81" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Plotly/R toolkit</span></span>
+<span id="cb22-82"><a href="#cb22-82" aria-hidden="true" tabindex="-1"></a><span class="fu">plotly_r</span><span class="kw">:</span></span>
+<span id="cb22-83"><a href="#cb22-83" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: plotly-r.r</span></span>
+<span id="cb22-84"><a href="#cb22-84" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> Rscript</span></span>
+<span id="cb22-85"><a href="#cb22-85" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-86"><a href="#cb22-86" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-87"><a href="#cb22-87" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Mathematica toolkit</span></span>
+<span id="cb22-88"><a href="#cb22-88" aria-hidden="true" tabindex="-1"></a><span class="fu">mathplot</span><span class="kw">:</span></span>
+<span id="cb22-89"><a href="#cb22-89" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: mathematica.m</span></span>
+<span id="cb22-90"><a href="#cb22-90" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> math</span></span>
+<span id="cb22-91"><a href="#cb22-91" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
 <span id="cb22-92"><a href="#cb22-92" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-93"><a href="#cb22-93" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the gnuplot toolkit</span></span>
-<span id="cb22-94"><a href="#cb22-94" aria-hidden="true" tabindex="-1"></a><span class="fu">gnuplot</span><span class="kw">:</span></span>
-<span id="cb22-95"><a href="#cb22-95" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: gnuplot.gp</span></span>
-<span id="cb22-96"><a href="#cb22-96" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> gnuplot</span></span>
-<span id="cb22-97"><a href="#cb22-97" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-98"><a href="#cb22-98" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the graphviz toolkit</span></span>
-<span id="cb22-99"><a href="#cb22-99" aria-hidden="true" tabindex="-1"></a><span class="fu">graphviz</span><span class="kw">:</span></span>
-<span id="cb22-100"><a href="#cb22-100" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: graphviz.dot</span></span>
-<span id="cb22-101"><a href="#cb22-101" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> dot</span></span>
-<span id="cb22-102"><a href="#cb22-102" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-103"><a href="#cb22-103" aria-hidden="true" tabindex="-1"></a><span class="fu">bokeh</span><span class="kw">:</span></span>
-<span id="cb22-104"><a href="#cb22-104" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: bokeh.py</span></span>
-<span id="cb22-105"><a href="#cb22-105" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
-<span id="cb22-106"><a href="#cb22-106" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb22-107"><a href="#cb22-107" aria-hidden="true" tabindex="-1"></a><span class="fu">plotsjl</span><span class="kw">:</span></span>
-<span id="cb22-108"><a href="#cb22-108" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: plotsjl.jl</span></span>
-<span id="cb22-109"><a href="#cb22-109" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> julia</span></span></code></pre></div>
+<span id="cb22-93"><a href="#cb22-93" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the GNU Octave toolkit</span></span>
+<span id="cb22-94"><a href="#cb22-94" aria-hidden="true" tabindex="-1"></a><span class="fu">octaveplot</span><span class="kw">:</span></span>
+<span id="cb22-95"><a href="#cb22-95" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: octave.m</span></span>
+<span id="cb22-96"><a href="#cb22-96" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> octave</span></span>
+<span id="cb22-97"><a href="#cb22-97" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-98"><a href="#cb22-98" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-99"><a href="#cb22-99" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the ggplot2 toolkit</span></span>
+<span id="cb22-100"><a href="#cb22-100" aria-hidden="true" tabindex="-1"></a><span class="fu">ggplot2</span><span class="kw">:</span></span>
+<span id="cb22-101"><a href="#cb22-101" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: ggplot2.r</span></span>
+<span id="cb22-102"><a href="#cb22-102" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> Rscript</span></span>
+<span id="cb22-103"><a href="#cb22-103" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-104"><a href="#cb22-104" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-105"><a href="#cb22-105" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the gnuplot toolkit</span></span>
+<span id="cb22-106"><a href="#cb22-106" aria-hidden="true" tabindex="-1"></a><span class="fu">gnuplot</span><span class="kw">:</span></span>
+<span id="cb22-107"><a href="#cb22-107" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: gnuplot.gp</span></span>
+<span id="cb22-108"><a href="#cb22-108" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> gnuplot</span></span>
+<span id="cb22-109"><a href="#cb22-109" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-110"><a href="#cb22-110" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-111"><a href="#cb22-111" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the graphviz toolkit</span></span>
+<span id="cb22-112"><a href="#cb22-112" aria-hidden="true" tabindex="-1"></a><span class="fu">graphviz</span><span class="kw">:</span></span>
+<span id="cb22-113"><a href="#cb22-113" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: graphviz.dot</span></span>
+<span id="cb22-114"><a href="#cb22-114" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> dot</span></span>
+<span id="cb22-115"><a href="#cb22-115" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-116"><a href="#cb22-116" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-117"><a href="#cb22-117" aria-hidden="true" tabindex="-1"></a><span class="fu">bokeh</span><span class="kw">:</span></span>
+<span id="cb22-118"><a href="#cb22-118" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: bokeh.py</span></span>
+<span id="cb22-119"><a href="#cb22-119" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
+<span id="cb22-120"><a href="#cb22-120" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span>
+<span id="cb22-121"><a href="#cb22-121" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb22-122"><a href="#cb22-122" aria-hidden="true" tabindex="-1"></a><span class="fu">plotsjl</span><span class="kw">:</span></span>
+<span id="cb22-123"><a href="#cb22-123" aria-hidden="true" tabindex="-1"></a><span class="co">  # preamble: plotsjl.jl</span></span>
+<span id="cb22-124"><a href="#cb22-124" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> julia</span></span>
+<span id="cb22-125"><a href="#cb22-125" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span></span></code></pre></div>
 <p>A file like the above sets the <strong>default</strong> values; you can still override them in documents directly.</p>
 <p>The easiest way to specify configuration for <code>pandoc-plot</code> is to place a <code>.pandoc-plot.yml</code> file in the current working directory. You can also specify a configuration file in document metadata, under the <code>plot-configuration</code> key. For example, in Markdown:</p>
 <div class="sourceCode" id="cb23"><pre class="sourceCode markdown"><code class="sourceCode markdown"><span id="cb23-1"><a href="#cb23-1" aria-hidden="true" tabindex="-1"></a><span class="co">---</span></span>
@@ -424,6 +459,18 @@ <span id="cb25-2"><a href="#cb25-2" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python3</span></span></code></pre></div>
 <div class="sourceCode" id="cb26"><pre class="sourceCode yaml"><code class="sourceCode yaml"><span id="cb26-1"><a href="#cb26-1" aria-hidden="true" tabindex="-1"></a><span class="fu">matlabplot</span><span class="kw">:</span></span>
 <span id="cb26-2"><a href="#cb26-2" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> </span><span class="st">&quot;C:\Program Files\Matlab\R2019b</span><span class="sc">\b</span><span class="st">in\matlab.exe&quot;</span></span></code></pre></div>
+<h4 id="command-line-arguments">Command-line arguments</h4>
+<p><em>New in version 1.0.2.0</em></p>
+<p>The <code>command_line_arguments</code> parameter available for all toolkits provides a way to customize the way interpreters are run. For example, if you want to run the <code>matplotlib</code> toolkit with all warnings shown:</p>
+<div class="sourceCode" id="cb27"><pre class="sourceCode yaml"><code class="sourceCode yaml"><span id="cb27-1"><a href="#cb27-1" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Matplotlib toolkit</span></span>
+<span id="cb27-2"><a href="#cb27-2" aria-hidden="true" tabindex="-1"></a><span class="fu">matplotlib</span><span class="kw">:</span></span>
+<span id="cb27-3"><a href="#cb27-3" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> python</span></span>
+<span id="cb27-4"><a href="#cb27-4" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span><span class="at"> -Wa</span></span></code></pre></div>
+<p>Or if you want <code>julia</code> to use more than one thread:</p>
+<div class="sourceCode" id="cb28"><pre class="sourceCode yaml"><code class="sourceCode yaml"><span id="cb28-1"><a href="#cb28-1" aria-hidden="true" tabindex="-1"></a><span class="co"># The possible parameters for the Matplotlib toolkit</span></span>
+<span id="cb28-2"><a href="#cb28-2" aria-hidden="true" tabindex="-1"></a><span class="fu">plotsjl</span><span class="kw">:</span></span>
+<span id="cb28-3"><a href="#cb28-3" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">executable</span><span class="kw">:</span><span class="at"> julia</span></span>
+<span id="cb28-4"><a href="#cb28-4" aria-hidden="true" tabindex="-1"></a><span class="at">  </span><span class="fu">command_line_arguments</span><span class="kw">:</span><span class="at"> --threads auto</span></span></code></pre></div>
 <h4 id="toolkit-specific-options">Toolkit-specific options</h4>
 <h5 id="matplotlib">Matplotlib</h5>
 <ul>
@@ -432,49 +479,54 @@ </ul>
 <h4 id="logging">Logging</h4>
 <p>If you are running <code>pandoc-plot</code> on a large document, you might want to turn on logging. You can do so via the configuration file as follows:</p>
-<div class="sourceCode" id="cb27"><pre class="sourceCode yaml"><code class="sourceCode yaml"><span id="cb27-1"><a href="#cb27-1" aria-hidden="true" tabindex="-1"></a><span class="fu">logging</span><span class="kw">:</span></span>
-<span id="cb27-2"><a href="#cb27-2" aria-hidden="true" tabindex="-1"></a><span class="co">    # Possible verbosity values: debug, error, warning, info, silent</span></span>
-<span id="cb27-3"><a href="#cb27-3" aria-hidden="true" tabindex="-1"></a><span class="co">    # debug level shows all messages</span></span>
-<span id="cb27-4"><a href="#cb27-4" aria-hidden="true" tabindex="-1"></a><span class="co">    # error level shows all but debug messages, etc.</span></span>
-<span id="cb27-5"><a href="#cb27-5" aria-hidden="true" tabindex="-1"></a><span class="at">    </span><span class="fu">verbosity</span><span class="kw">:</span><span class="at"> info</span></span>
-<span id="cb27-6"><a href="#cb27-6" aria-hidden="true" tabindex="-1"></a><span class="at">    </span></span>
-<span id="cb27-7"><a href="#cb27-7" aria-hidden="true" tabindex="-1"></a><span class="co">    # OPTIONAL: log to file</span></span>
-<span id="cb27-8"><a href="#cb27-8" aria-hidden="true" tabindex="-1"></a><span class="co">    # Remove line below to log to stderr</span></span>
-<span id="cb27-9"><a href="#cb27-9" aria-hidden="true" tabindex="-1"></a><span class="at">    </span><span class="fu">filepath</span><span class="kw">:</span><span class="at"> log.txt</span></span></code></pre></div>
+<div class="sourceCode" id="cb29"><pre class="sourceCode yaml"><code class="sourceCode yaml"><span id="cb29-1"><a href="#cb29-1" aria-hidden="true" tabindex="-1"></a><span class="fu">logging</span><span class="kw">:</span></span>
+<span id="cb29-2"><a href="#cb29-2" aria-hidden="true" tabindex="-1"></a><span class="co">    # Possible verbosity values: debug, error, warning, info, silent</span></span>
+<span id="cb29-3"><a href="#cb29-3" aria-hidden="true" tabindex="-1"></a><span class="co">    # debug level shows all messages</span></span>
+<span id="cb29-4"><a href="#cb29-4" aria-hidden="true" tabindex="-1"></a><span class="co">    # error level shows all but debug messages, etc.</span></span>
+<span id="cb29-5"><a href="#cb29-5" aria-hidden="true" tabindex="-1"></a><span class="at">    </span><span class="fu">verbosity</span><span class="kw">:</span><span class="at"> info</span></span>
+<span id="cb29-6"><a href="#cb29-6" aria-hidden="true" tabindex="-1"></a><span class="at">    </span></span>
+<span id="cb29-7"><a href="#cb29-7" aria-hidden="true" tabindex="-1"></a><span class="co">    # OPTIONAL: log to file</span></span>
+<span id="cb29-8"><a href="#cb29-8" aria-hidden="true" tabindex="-1"></a><span class="co">    # Remove line below to log to stderr</span></span>
+<span id="cb29-9"><a href="#cb29-9" aria-hidden="true" tabindex="-1"></a><span class="at">    </span><span class="fu">filepath</span><span class="kw">:</span><span class="at"> log.txt</span></span></code></pre></div>
 <p>By default, <code>pandoc-plot</code> logs warnings and errors to the standard error stream only.</p>
+<h4 id="strict-mode">Strict mode</h4>
+<p><em>New in version 1.0.2.0</em></p>
+<p>By default, <code>pandoc-plot</code> leaves code blocks unchanged if a figure fails to be rendered. This might be the case if a plotting toolkit is not installed, or if running the code to render a figure returns an error. In <strong>strict mode</strong>, <code>pandoc-plot</code> will immediately halt if it encounters a problem. You can activate strict mode via configuration:</p>
+<div class="sourceCode" id="cb30"><pre class="sourceCode yaml"><code class="sourceCode yaml"><span id="cb30-1"><a href="#cb30-1" aria-hidden="true" tabindex="-1"></a><span class="fu">strict</span><span class="kw">:</span><span class="at"> </span><span class="ch">true</span></span></code></pre></div>
+<p>Strict mode is ideal if you want to ensure that the figures are correctly rendered in the document.</p>
 <h3 id="other-commands">Other commands</h3>
 <h4 id="finding-installed-toolkits">Finding installed toolkits</h4>
 <p>You can determine which toolkits are available on your current machine using the <code>pandoc-plot toolkits</code> command. Here is the full help text:</p>
-<div class="sourceCode" id="cb28"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb28-1"><a href="#cb28-1" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE toolkits [--config PATH]</span>
-<span id="cb28-2"><a href="#cb28-2" aria-hidden="true" tabindex="-1"></a>  <span class="ex">Show</span> information on toolkits and exit.</span>
-<span id="cb28-3"><a href="#cb28-3" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb28-4"><a href="#cb28-4" aria-hidden="true" tabindex="-1"></a><span class="ex">Available</span> options:</span>
-<span id="cb28-5"><a href="#cb28-5" aria-hidden="true" tabindex="-1"></a>  <span class="ex">--config</span> PATH            Path to optional configuration file.</span>
-<span id="cb28-6"><a href="#cb28-6" aria-hidden="true" tabindex="-1"></a>  <span class="ex">-h,--help</span>                Show this help text</span></code></pre></div>
+<div class="sourceCode" id="cb31"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb31-1"><a href="#cb31-1" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE toolkits [--config PATH]</span>
+<span id="cb31-2"><a href="#cb31-2" aria-hidden="true" tabindex="-1"></a>  <span class="ex">Show</span> information on toolkits and exit.</span>
+<span id="cb31-3"><a href="#cb31-3" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb31-4"><a href="#cb31-4" aria-hidden="true" tabindex="-1"></a><span class="ex">Available</span> options:</span>
+<span id="cb31-5"><a href="#cb31-5" aria-hidden="true" tabindex="-1"></a>  <span class="ex">--config</span> PATH            Path to optional configuration file.</span>
+<span id="cb31-6"><a href="#cb31-6" aria-hidden="true" tabindex="-1"></a>  <span class="ex">-h,--help</span>                Show this help text</span></code></pre></div>
 <h4 id="cleaning-output">Cleaning output</h4>
 <p>Figures produced by <code>pandoc-plot</code> can be placed in a few different locations. You can set a default location in the <a href="#configuration">Configuration</a>, but you can also re-direct specific figures in other directories if you use the <code>directory=...</code> argument in code blocks. These figures will build up over time. You can use the <code>clean</code> command to scan documents and delete the associated <code>pandoc-plot</code> output files. For example, to delete the figures generated from the <code>input.md</code> file:</p>
-<div class="sourceCode" id="cb29"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb29-1"><a href="#cb29-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc-plot</span> clean input.md</span></code></pre></div>
+<div class="sourceCode" id="cb32"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb32-1"><a href="#cb32-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc-plot</span> clean input.md</span></code></pre></div>
 <p>This sill remove all directories where a figure <em>could</em> have been placed. <strong>WARNING</strong>: all files will be removed.</p>
 <p>Here is the full help text for the <code>clean</code> command:</p>
-<div class="sourceCode" id="cb30"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb30-1"><a href="#cb30-1" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE clean [--config PATH] FILE</span>
-<span id="cb30-2"><a href="#cb30-2" aria-hidden="true" tabindex="-1"></a>  <span class="ex">Clean</span> output directories where figures from FILE and log files might be</span>
-<span id="cb30-3"><a href="#cb30-3" aria-hidden="true" tabindex="-1"></a>  <span class="ex">stored.</span> WARNING: All files in those directories will be deleted.</span>
-<span id="cb30-4"><a href="#cb30-4" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb30-5"><a href="#cb30-5" aria-hidden="true" tabindex="-1"></a><span class="ex">Available</span> options:</span>
-<span id="cb30-6"><a href="#cb30-6" aria-hidden="true" tabindex="-1"></a>  <span class="ex">--config</span> PATH            Path to optional configuration file.</span>
-<span id="cb30-7"><a href="#cb30-7" aria-hidden="true" tabindex="-1"></a>  <span class="ex">-h,--help</span>                Show this help text</span></code></pre></div>
+<div class="sourceCode" id="cb33"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb33-1"><a href="#cb33-1" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE clean [--config PATH] FILE</span>
+<span id="cb33-2"><a href="#cb33-2" aria-hidden="true" tabindex="-1"></a>  <span class="ex">Clean</span> output directories where figures from FILE and log files might be</span>
+<span id="cb33-3"><a href="#cb33-3" aria-hidden="true" tabindex="-1"></a>  <span class="ex">stored.</span> WARNING: All files in those directories will be deleted.</span>
+<span id="cb33-4"><a href="#cb33-4" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb33-5"><a href="#cb33-5" aria-hidden="true" tabindex="-1"></a><span class="ex">Available</span> options:</span>
+<span id="cb33-6"><a href="#cb33-6" aria-hidden="true" tabindex="-1"></a>  <span class="ex">--config</span> PATH            Path to optional configuration file.</span>
+<span id="cb33-7"><a href="#cb33-7" aria-hidden="true" tabindex="-1"></a>  <span class="ex">-h,--help</span>                Show this help text</span></code></pre></div>
 <h4 id="configuration-template">Configuration template</h4>
 <p>Because <code>pandoc-plot</code> supports a few toolkits, there are a lot of configuration options. Don’t start from scratch! The <code>write-example-config</code> command will create a file for you, which you can then modify:</p>
-<div class="sourceCode" id="cb31"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb31-1"><a href="#cb31-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc-plot</span> write-example-config</span></code></pre></div>
+<div class="sourceCode" id="cb34"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb34-1"><a href="#cb34-1" aria-hidden="true" tabindex="-1"></a><span class="ex">pandoc-plot</span> write-example-config</span></code></pre></div>
 <p>You will need to re-name the file to <code>.pandoc-ploy.yml</code> to be able to use it, so don’t worry about overwriting your own configuration.</p>
 <p>Here is the full help text for the <code>write-example-config</code> command:</p>
-<div class="sourceCode" id="cb32"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb32-1"><a href="#cb32-1" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE write-example-config [--path FILE]</span>
-<span id="cb32-2"><a href="#cb32-2" aria-hidden="true" tabindex="-1"></a>  <span class="ex">Write</span> example configuration to a file and exit.</span>
-<span id="cb32-3"><a href="#cb32-3" aria-hidden="true" tabindex="-1"></a></span>
-<span id="cb32-4"><a href="#cb32-4" aria-hidden="true" tabindex="-1"></a><span class="ex">Available</span> options:</span>
-<span id="cb32-5"><a href="#cb32-5" aria-hidden="true" tabindex="-1"></a>  <span class="ex">--path</span> FILE              Target location of the configuration file. Default is</span>
-<span id="cb32-6"><a href="#cb32-6" aria-hidden="true" tabindex="-1"></a>                           <span class="st">&quot;.example-pandoc-plot.yml&quot;</span></span>
-<span id="cb32-7"><a href="#cb32-7" aria-hidden="true" tabindex="-1"></a>  <span class="ex">-h,--help</span>                Show this help text</span></code></pre></div>
+<div class="sourceCode" id="cb35"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb35-1"><a href="#cb35-1" aria-hidden="true" tabindex="-1"></a><span class="ex">Usage:</span> pandoc-plot.EXE write-example-config [--path FILE]</span>
+<span id="cb35-2"><a href="#cb35-2" aria-hidden="true" tabindex="-1"></a>  <span class="ex">Write</span> example configuration to a file and exit.</span>
+<span id="cb35-3"><a href="#cb35-3" aria-hidden="true" tabindex="-1"></a></span>
+<span id="cb35-4"><a href="#cb35-4" aria-hidden="true" tabindex="-1"></a><span class="ex">Available</span> options:</span>
+<span id="cb35-5"><a href="#cb35-5" aria-hidden="true" tabindex="-1"></a>  <span class="ex">--path</span> FILE              Target location of the configuration file. Default is</span>
+<span id="cb35-6"><a href="#cb35-6" aria-hidden="true" tabindex="-1"></a>                           <span class="st">&quot;.example-pandoc-plot.yml&quot;</span></span>
+<span id="cb35-7"><a href="#cb35-7" aria-hidden="true" tabindex="-1"></a>  <span class="ex">-h,--help</span>                Show this help text</span></code></pre></div>
 <h2 id="warning">Warning</h2>
 <p>Do not run this filter on unknown documents. There is nothing in
 <code>pandoc-plot</code> that can stop a script from performing <strong>evil actions</strong>.</p>
example-config.yml view
@@ -18,6 +18,11 @@ # Particularly useful for HTML output.
 source: false
 
+# When `strict: false`, pandoc-plot will leave code blocks untouched if a plot
+# could not be generated. This could happen if, for example, a toolkit is not
+# installed. If you want pandoc-plot to fail instead, use `strict: true`.
+strict: false
+
 # Text label for links to source code.
 # You can change this label if you are writing a document in a non-English language. 
 # This only matters if `source` is set to `true`.
@@ -60,51 +65,62 @@   tight_bbox: false
   transparent: false
   executable: python
+  command_line_arguments:
 
 # The possible parameters for the MATLAB toolkit
 matlabplot:
   # preamble: matlab.m
   executable: matlab
+  command_line_arguments:
 
 # The possible parameters for the Plotly/Python toolkit
 plotly_python:
   # preamble: plotly-python.py
   executable: python
+  command_line_arguments:
 
 # The possible parameters for the Plotly/R toolkit
 plotly_r:
   # preamble: plotly-r.r
   executable: Rscript
+  command_line_arguments:
 
 # The possible parameters for the Mathematica toolkit
 mathplot:
   # preamble: mathematica.m
   executable: math
+  command_line_arguments:
 
 # The possible parameters for the GNU Octave toolkit
 octaveplot:
   # preamble: octave.m
   executable: octave
+  command_line_arguments:
 
 # The possible parameters for the ggplot2 toolkit
 ggplot2:
   # preamble: ggplot2.r
   executable: Rscript
+  command_line_arguments:
 
 # The possible parameters for the gnuplot toolkit
 gnuplot:
   # preamble: gnuplot.gp
   executable: gnuplot
+  command_line_arguments:
 
 # The possible parameters for the graphviz toolkit
 graphviz:
   # preamble: graphviz.dot
   executable: dot
+  command_line_arguments:
 
 bokeh:
   # preamble: bokeh.py
   executable: python
+  command_line_arguments:
 
 plotsjl:
   # preamble: plotsjl.jl
-  executable: julia+  executable: julia
+  command_line_arguments:
executable/OpenFile.hs view
@@ -1,6 +1,6 @@ -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
pandoc-plot.cabal view
@@ -1,12 +1,12 @@ cabal-version:  2.2
 name:           pandoc-plot
-version:        1.0.1.0
+version:        1.0.2.0
 synopsis:       A Pandoc filter to include figures generated from code blocks using your plotting toolkit of choice.
 description:    A Pandoc filter to include figures generated from code blocks. 
                 Keep the document and code in the same location. Output is 
                 captured and included as a figure.
 category:       Text
-copyright:      (c) 2019-2020 Laurent P. René de Cotret
+copyright:      (c) 2019-2021 Laurent P. René de Cotret
 homepage:       https://github.com/LaurentRDC/pandoc-plot#readme
 bug-reports:    https://github.com/LaurentRDC/pandoc-plot/issues
 author:         Laurent P. René de Cotret
src/Text/Pandoc/Filter/Plot.hs view
@@ -4,7 +4,7 @@ -- |
 -- Module      : $header$
 -- Description : Pandoc filter to create figures from code blocks using your plotting toolkit of choice
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : unstable
@@ -110,7 +110,8 @@ where
 
 import Control.Concurrent.Async.Lifted (mapConcurrently)
-import Data.Text (Text, unpack)
+import Data.Functor ((<&>))
+import Data.Text (Text, pack, unpack)
 import Data.Version (Version)
 import Paths_pandoc_plot (version)
 import Text.Pandoc.Definition (Block, Pandoc (..))
@@ -134,9 +135,11 @@     runPlotM,
     runScriptIfNecessary,
     supportedSaveFormats,
+    throwError,
     toFigure,
     toolkits,
     unavailableToolkits,
+    whenStrict,
   )
 
 -- | Walk over an entire Pandoc document, transforming appropriate code blocks
@@ -152,7 +155,7 @@   Pandoc ->
   IO Pandoc
 plotTransform conf (Pandoc meta blocks) =
-  runPlotM conf $ mapConcurrently make blocks >>= return . Pandoc meta
+  runPlotM conf $ mapConcurrently make blocks <&> Pandoc meta
 
 -- | The version of the pandoc-plot package.
 --
@@ -161,9 +164,14 @@ pandocPlotVersion = version
 
 -- | Try to process the block with `pandoc-plot`. If a failure happens (or the block)
--- was not meant to become a figure, return the block as-is.
+-- was not meant to become a figure, return the block as-is unless running in strict mode.
 make :: Block -> PlotM Block
-make blk = either (const (return blk)) return =<< makeEither blk
+make blk = either (onError blk) return =<< makeEither blk
+  where
+    onError :: Block -> PandocPlotError -> PlotM Block
+    onError b e = do
+      whenStrict $ throwError $ "[strict mode] " <> (pack . show $ e)
+      return b
 
 -- | Try to process the block with `pandoc-plot`, documenting the error.
 makeEither :: Block -> PlotM (Either PandocPlotError Block)
@@ -177,7 +185,6 @@     handleResult :: FigureSpec -> ScriptResult -> PlotM (Either PandocPlotError Block)
     handleResult _ (ScriptFailure msg code) = return $ Left (ScriptRuntimeError msg code)
     handleResult _ (ScriptChecksFailed msg) = return $ Left (ScriptChecksFailedError msg)
-    handleResult _ (ToolkitNotInstalled tk') = return $ Left (ToolkitNotInstalledError tk')
     handleResult spec ScriptSuccess = asks envConfig >>= \c -> Right <$> toFigure (captionFormat c) spec
 
 data PandocPlotError
src/Text/Pandoc/Filter/Plot/Clean.hs view
@@ -3,7 +3,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
src/Text/Pandoc/Filter/Plot/Configuration.hs view
@@ -3,7 +3,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -17,7 +17,6 @@   )
 where
 
-import Data.Maybe (fromMaybe)
 import Data.Text (Text, pack, unpack)
 import qualified Data.Text.IO as TIO
 import Data.Yaml (FromJSON (parseJSON), Value (Null, Object), (.!=), (.:?))
@@ -32,7 +31,7 @@ -- If a key is not present, its value will be set
 -- to the default value. Parsing errors result in thrown exceptions.
 configuration :: FilePath -> IO Configuration
-configuration fp = (loadYamlSettings [normalise fp] [] ignoreEnv) >>= renderConfig
+configuration fp = loadYamlSettings [normalise fp] [] ignoreEnv >>= renderConfig
 
 -- | Default configuration values.
 --
@@ -47,8 +46,10 @@       defaultDependencies = mempty,
       captionFormat = Format "markdown+tex_math_dollars",
       sourceCodeLabel = "Source code",
+      strictMode = False,
       logVerbosity = Warning,
       logSink = StdErr,
+      -- Preambles
       matplotlibPreamble = mempty,
       plotlyPythonPreamble = mempty,
       plotlyRPreamble = mempty,
@@ -60,6 +61,7 @@       graphvizPreamble = mempty,
       bokehPreamble = mempty,
       plotsjlPreamble = mempty,
+      -- Executables
       matplotlibExe = python,
       matlabExe = "matlab",
       plotlyPythonExe = python,
@@ -71,6 +73,19 @@       graphvizExe = "dot",
       bokehExe = python,
       plotsjlExe = "julia",
+      -- Command line arguments
+      matplotlibCmdArgs = mempty,
+      matlabCmdArgs = mempty,
+      plotlyPythonCmdArgs = mempty,
+      plotlyRCmdArgs = mempty,
+      mathematicaCmdArgs = mempty,
+      octaveCmdArgs = mempty,
+      ggplot2CmdArgs = mempty,
+      gnuplotCmdArgs = mempty,
+      graphvizCmdArgs = mempty,
+      bokehCmdArgs = mempty,
+      plotsjlCmdArgs = mempty,
+      -- Extras
       matplotlibTightBBox = False,
       matplotlibTransparent = False
     }
@@ -115,6 +130,7 @@     _defaultDependencies :: ![FilePath],
     _captionFormat :: !Format,
     _sourceCodeLabel :: !Text,
+    _strictMode :: !Bool,
     _logPrec :: !LoggingPrecursor,
     _matplotlibPrec :: !MatplotlibPrecursor,
     _matlabPrec :: !MatlabPrecursor,
@@ -139,18 +155,19 @@       _defaultDependencies = defaultDependencies defaultConfiguration,
       _captionFormat = captionFormat defaultConfiguration,
       _sourceCodeLabel = sourceCodeLabel defaultConfiguration,
+      _strictMode = strictMode defaultConfiguration,
       _logPrec = LoggingPrecursor (logVerbosity defaultConfiguration) Nothing, -- _logFilePath=Nothing implies log to stderr
-      _matplotlibPrec = MatplotlibPrecursor Nothing (matplotlibTightBBox defaultConfiguration) (matplotlibTransparent defaultConfiguration) (matplotlibExe defaultConfiguration),
-      _matlabPrec = MatlabPrecursor Nothing (matlabExe defaultConfiguration),
-      _plotlyPythonPrec = PlotlyPythonPrecursor Nothing (plotlyPythonExe defaultConfiguration),
-      _plotlyRPrec = PlotlyRPrecursor Nothing (plotlyRExe defaultConfiguration),
-      _mathematicaPrec = MathematicaPrecursor Nothing (mathematicaExe defaultConfiguration),
-      _octavePrec = OctavePrecursor Nothing (octaveExe defaultConfiguration),
-      _ggplot2Prec = GGPlot2Precursor Nothing (ggplot2Exe defaultConfiguration),
-      _gnuplotPrec = GNUPlotPrecursor Nothing (gnuplotExe defaultConfiguration),
-      _graphvizPrec = GraphvizPrecursor Nothing (graphvizExe defaultConfiguration),
-      _bokehPrec = BokehPrecursor Nothing (bokehExe defaultConfiguration),
-      _plotsjlPrec = PlotsjlPrecursor Nothing (plotsjlExe defaultConfiguration)
+      _matplotlibPrec = MatplotlibPrecursor Nothing (matplotlibTightBBox defaultConfiguration) (matplotlibTransparent defaultConfiguration) (matplotlibExe defaultConfiguration) (matplotlibCmdArgs defaultConfiguration),
+      _matlabPrec = MatlabPrecursor Nothing (matlabExe defaultConfiguration) (matlabCmdArgs defaultConfiguration),
+      _plotlyPythonPrec = PlotlyPythonPrecursor Nothing (plotlyPythonExe defaultConfiguration) (plotlyPythonCmdArgs defaultConfiguration),
+      _plotlyRPrec = PlotlyRPrecursor Nothing (plotlyRExe defaultConfiguration) (plotlyRCmdArgs defaultConfiguration),
+      _mathematicaPrec = MathematicaPrecursor Nothing (mathematicaExe defaultConfiguration) (mathematicaCmdArgs defaultConfiguration),
+      _octavePrec = OctavePrecursor Nothing (octaveExe defaultConfiguration) (octaveCmdArgs defaultConfiguration),
+      _ggplot2Prec = GGPlot2Precursor Nothing (ggplot2Exe defaultConfiguration) (ggplot2CmdArgs defaultConfiguration),
+      _gnuplotPrec = GNUPlotPrecursor Nothing (gnuplotExe defaultConfiguration) (gnuplotCmdArgs defaultConfiguration),
+      _graphvizPrec = GraphvizPrecursor Nothing (graphvizExe defaultConfiguration) (graphvizCmdArgs defaultConfiguration),
+      _bokehPrec = BokehPrecursor Nothing (bokehExe defaultConfiguration) (bokehCmdArgs defaultConfiguration),
+      _plotsjlPrec = PlotsjlPrecursor Nothing (plotsjlExe defaultConfiguration) (plotsjlCmdArgs defaultConfiguration)
     }
 
 data LoggingPrecursor = LoggingPrecursor
@@ -163,28 +180,29 @@   { _matplotlibPreamble :: !(Maybe FilePath),
     _matplotlibTightBBox :: !Bool,
     _matplotlibTransparent :: !Bool,
-    _matplotlibExe :: !FilePath
+    _matplotlibExe :: !FilePath,
+    _matplotlibCmdArgs :: !Text
   }
 
-data MatlabPrecursor = MatlabPrecursor {_matlabPreamble :: !(Maybe FilePath), _matlabExe :: !FilePath}
+data MatlabPrecursor = MatlabPrecursor {_matlabPreamble :: !(Maybe FilePath), _matlabExe :: !FilePath, _matlabCmdArgs :: !Text}
 
-data PlotlyPythonPrecursor = PlotlyPythonPrecursor {_plotlyPythonPreamble :: !(Maybe FilePath), _plotlyPythonExe :: !FilePath}
+data PlotlyPythonPrecursor = PlotlyPythonPrecursor {_plotlyPythonPreamble :: !(Maybe FilePath), _plotlyPythonExe :: !FilePath, _plotlyPythonCmdArgs :: !Text}
 
-data PlotlyRPrecursor = PlotlyRPrecursor {_plotlyRPreamble :: !(Maybe FilePath), _plotlyRExe :: !FilePath}
+data PlotlyRPrecursor = PlotlyRPrecursor {_plotlyRPreamble :: !(Maybe FilePath), _plotlyRExe :: !FilePath, _plotlyRCmdArgs :: !Text}
 
-data MathematicaPrecursor = MathematicaPrecursor {_mathematicaPreamble :: !(Maybe FilePath), _mathematicaExe :: !FilePath}
+data MathematicaPrecursor = MathematicaPrecursor {_mathematicaPreamble :: !(Maybe FilePath), _mathematicaExe :: !FilePath, _mathematicaCmdArgs :: !Text}
 
-data OctavePrecursor = OctavePrecursor {_octavePreamble :: !(Maybe FilePath), _octaveExe :: !FilePath}
+data OctavePrecursor = OctavePrecursor {_octavePreamble :: !(Maybe FilePath), _octaveExe :: !FilePath, _octaveCmdArgs :: !Text}
 
-data GGPlot2Precursor = GGPlot2Precursor {_ggplot2Preamble :: !(Maybe FilePath), _ggplot2Exe :: !FilePath}
+data GGPlot2Precursor = GGPlot2Precursor {_ggplot2Preamble :: !(Maybe FilePath), _ggplot2Exe :: !FilePath, _ggplot2CmdArgs :: !Text}
 
-data GNUPlotPrecursor = GNUPlotPrecursor {_gnuplotPreamble :: !(Maybe FilePath), _gnuplotExe :: !FilePath}
+data GNUPlotPrecursor = GNUPlotPrecursor {_gnuplotPreamble :: !(Maybe FilePath), _gnuplotExe :: !FilePath, _gnuplotCmdArgs :: !Text}
 
-data GraphvizPrecursor = GraphvizPrecursor {_graphvizPreamble :: !(Maybe FilePath), _graphvizExe :: !FilePath}
+data GraphvizPrecursor = GraphvizPrecursor {_graphvizPreamble :: !(Maybe FilePath), _graphvizExe :: !FilePath, _graphvizCmdArgs :: !Text}
 
-data BokehPrecursor = BokehPrecursor {_bokehPreamble :: !(Maybe FilePath), _bokehExe :: !FilePath}
+data BokehPrecursor = BokehPrecursor {_bokehPreamble :: !(Maybe FilePath), _bokehExe :: !FilePath, _bokehCmdArgs :: !Text}
 
-data PlotsjlPrecursor = PlotsjlPrecursor {_plotsjlPreamble :: !(Maybe FilePath), _plotsjlExe :: !FilePath}
+data PlotsjlPrecursor = PlotsjlPrecursor {_plotsjlPreamble :: !(Maybe FilePath), _plotsjlExe :: !FilePath, _plotsjlCmdArgs :: !Text}
 
 instance FromJSON LoggingPrecursor where
   parseJSON (Object v) =
@@ -199,46 +217,47 @@       <*> v .:? (tshow MatplotlibTightBBoxK) .!= (matplotlibTightBBox defaultConfiguration)
       <*> v .:? (tshow MatplotlibTransparentK) .!= (matplotlibTransparent defaultConfiguration)
       <*> v .:? (tshow ExecutableK) .!= (matplotlibExe defaultConfiguration)
+      <*> v .:? (tshow CommandLineArgsK) .!= (matplotlibCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Matplotlib, " configuration."]
 
 instance FromJSON MatlabPrecursor where
-  parseJSON (Object v) = MatlabPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (matlabExe defaultConfiguration)
+  parseJSON (Object v) = MatlabPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (matlabExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (matlabCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Matlab, " configuration."]
 
 instance FromJSON PlotlyPythonPrecursor where
-  parseJSON (Object v) = PlotlyPythonPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (plotlyPythonExe defaultConfiguration)
+  parseJSON (Object v) = PlotlyPythonPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (plotlyPythonExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (plotlyPythonCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show PlotlyPython, " configuration."]
 
 instance FromJSON PlotlyRPrecursor where
-  parseJSON (Object v) = PlotlyRPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (plotlyRExe defaultConfiguration)
+  parseJSON (Object v) = PlotlyRPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (plotlyRExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (plotlyRCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show PlotlyR, " configuration."]
 
 instance FromJSON MathematicaPrecursor where
-  parseJSON (Object v) = MathematicaPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (mathematicaExe defaultConfiguration)
+  parseJSON (Object v) = MathematicaPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (mathematicaExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (mathematicaCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Mathematica, " configuration."]
 
 instance FromJSON OctavePrecursor where
-  parseJSON (Object v) = OctavePrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (octaveExe defaultConfiguration)
+  parseJSON (Object v) = OctavePrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (octaveExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (octaveCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Octave, " configuration."]
 
 instance FromJSON GGPlot2Precursor where
-  parseJSON (Object v) = GGPlot2Precursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (ggplot2Exe defaultConfiguration)
+  parseJSON (Object v) = GGPlot2Precursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (ggplot2Exe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (ggplot2CmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show GGPlot2, " configuration."]
 
 instance FromJSON GNUPlotPrecursor where
-  parseJSON (Object v) = GNUPlotPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (gnuplotExe defaultConfiguration)
+  parseJSON (Object v) = GNUPlotPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (gnuplotExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (gnuplotCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show GNUPlot, " configuration."]
 
 instance FromJSON GraphvizPrecursor where
-  parseJSON (Object v) = GraphvizPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (graphvizExe defaultConfiguration)
+  parseJSON (Object v) = GraphvizPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (graphvizExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (graphvizCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Graphviz, " configuration."]
 
 instance FromJSON BokehPrecursor where
-  parseJSON (Object v) = BokehPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (bokehExe defaultConfiguration)
+  parseJSON (Object v) = BokehPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (bokehExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (bokehCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Bokeh, " configuration."]
 
 instance FromJSON PlotsjlPrecursor where
-  parseJSON (Object v) = PlotsjlPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (plotsjlExe defaultConfiguration)
+  parseJSON (Object v) = PlotsjlPrecursor <$> v .:? (tshow PreambleK) <*> v .:? (tshow ExecutableK) .!= (plotsjlExe defaultConfiguration) <*> v .:? (tshow CommandLineArgsK) .!= (plotsjlCmdArgs defaultConfiguration)
   parseJSON _ = fail $ mconcat ["Could not parse ", show Plotsjl, " configuration."]
 
 instance FromJSON ConfigPrecursor where
@@ -251,7 +270,7 @@     _defaultDependencies <- v .:? (tshow DependenciesK) .!= (_defaultDependencies defaultConfigPrecursor)
     _captionFormat <- v .:? (tshow CaptionFormatK) .!= (_captionFormat defaultConfigPrecursor)
     _sourceCodeLabel <- v .:? (tshow SourceCodeLabelK) .!= (_sourceCodeLabel defaultConfigPrecursor)
-
+    _strictMode <- v .:? tshow StrictModeK .!= (_strictMode defaultConfigPrecursor)
     _logPrec <- v .:? "logging" .!= _logPrec defaultConfigPrecursor
 
     _matplotlibPrec <- v .:? (cls Matplotlib) .!= _matplotlibPrec defaultConfigPrecursor
@@ -278,6 +297,7 @@       defaultDependencies = _defaultDependencies
       captionFormat = _captionFormat
       sourceCodeLabel = _sourceCodeLabel
+      strictMode = _strictMode
 
       logVerbosity = _logVerbosity _logPrec
       logSink = maybe StdErr LogFile (_logFilePath _logPrec)
@@ -297,6 +317,18 @@       bokehExe = _bokehExe _bokehPrec
       plotsjlExe = _plotsjlExe _plotsjlPrec
 
+      matplotlibCmdArgs = _matplotlibCmdArgs _matplotlibPrec
+      matlabCmdArgs = _matlabCmdArgs _matlabPrec
+      plotlyPythonCmdArgs = _plotlyPythonCmdArgs _plotlyPythonPrec
+      plotlyRCmdArgs = _plotlyRCmdArgs _plotlyRPrec
+      mathematicaCmdArgs = _mathematicaCmdArgs _mathematicaPrec
+      octaveCmdArgs = _octaveCmdArgs _octavePrec
+      ggplot2CmdArgs = _ggplot2CmdArgs _ggplot2Prec
+      gnuplotCmdArgs = _gnuplotCmdArgs _gnuplotPrec
+      graphvizCmdArgs = _graphvizCmdArgs _graphvizPrec
+      bokehCmdArgs = _bokehCmdArgs _bokehPrec
+      plotsjlCmdArgs = _plotsjlCmdArgs _plotsjlPrec
+
   matplotlibPreamble <- readPreamble (_matplotlibPreamble _matplotlibPrec)
   matlabPreamble <- readPreamble (_matlabPreamble _matlabPrec)
   plotlyPythonPreamble <- readPreamble (_plotlyPythonPreamble _plotlyPythonPrec)
@@ -311,7 +343,7 @@ 
   return Configuration {..}
   where
-    readPreamble fp = fromMaybe mempty $ TIO.readFile <$> fp
+    readPreamble fp = maybe mempty TIO.readFile fp
 
 tshow :: Show a => a -> Text
 tshow = pack . show
src/Text/Pandoc/Filter/Plot/Embed.hs view
@@ -3,7 +3,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
src/Text/Pandoc/Filter/Plot/Internal.hs view
@@ -1,6 +1,6 @@ -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
src/Text/Pandoc/Filter/Plot/Monad.hs view
@@ -2,7 +2,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,11 +13,17 @@   ( Configuration (..),
     PlotM,
     RuntimeEnv (..),
+    PlotState (..),
     runPlotM,
 
     -- * Running external commands
     runCommand,
+    withPrependedPath,
 
+    -- * Halting pandoc-plot
+    whenStrict,
+    throwError,
+
     -- * Getting file hashes
     fileHash,
 
@@ -46,9 +52,11 @@ 
 import Control.Concurrent.Chan (writeChan)
 import Control.Concurrent.MVar
+import Control.Exception.Lifted (bracket)
 import Control.Monad.Reader
 import Control.Monad.State.Strict
 import Data.ByteString.Lazy (toStrict)
+import Data.Functor ((<&>))
 import Data.Hashable (hash)
 import Data.Map.Strict (Map)
 import qualified Data.Map.Strict as M
@@ -62,12 +70,15 @@     getCurrentDirectory,
     getModificationTime,
   )
+import System.Environment (getEnv, setEnv)
 import System.Exit (ExitCode (..))
 import System.Process.Typed
-  ( byteStringOutput,
+  ( byteStringInput,
+    byteStringOutput,
     nullStream,
     readProcessStderr,
     setStderr,
+    setStdin,
     setStdout,
     setWorkingDir,
     shell,
@@ -139,10 +150,15 @@   (ec, processOutput') <-
     liftIO $
       readProcessStderr $
-        setStdout nullStream $
-          setStderr byteStringOutput $
-            setWorkingDir wordir $
-              shell (unpack command)
+        -- For Julia specifically, if the line below is not there,
+        -- The following error is thrown on Windows:
+        --    ERROR: error initializing stdin in uv_dup:
+        --           Unknown system error 50 (Unknown system error 50 50)
+        setStdin (byteStringInput "") $
+          setStdout nullStream $
+            setStderr byteStringOutput $
+              setWorkingDir wordir $
+                shell (unpack command)
   let processOutput = decodeUtf8With lenientDecode $ toStrict processOutput'
       logFunc =
         if ec == ExitSuccess
@@ -167,6 +183,30 @@   logFunc $ message <> errorMessage
   return (ec, processOutput)
 
+-- | Prepend a directory to the PATH environment variable for the duration
+-- of a computation.
+--
+-- This function is exception-safe; even if an exception happens during the
+-- computation, the PATH environment variable will be reverted back to
+-- its initial value.
+withPrependedPath :: FilePath -> PlotM a -> PlotM a
+withPrependedPath dir f = do
+  pathVar <- liftIO $ getEnv "PATH"
+  let pathVarPrepended = mconcat [dir, ";", pathVar]
+  bracket
+    (liftIO $ setEnv "PATH" pathVarPrepended)
+    (\_ -> liftIO $ setEnv "PATH" pathVar)
+    (const f)
+
+-- | Throw an error that halts the execution of pandoc-plot
+throwError :: Text -> PlotM ()
+throwError = liftIO . errorWithoutStackTrace . unpack
+
+-- | Conditional execution of a PlotM action if pandoc-plot is
+-- run in strict mode.
+whenStrict :: PlotM () -> PlotM ()
+whenStrict f = asksConfig strictMode >>= \s -> when s f
+
 -- Plot state is used for caching.
 -- One part consists of a map of filepaths to hashes
 -- This allows multiple plots to depend on the same file/directory, and the file hashes
@@ -174,14 +214,14 @@ -- We note that because figures are rendered possibly in parallel, access to
 -- the state must be synchronized; otherwise, each thread might compute its own
 -- hashes.
--- The other part is comprised of a map of toolkits to executables (possibly missing)
--- This means that executable will be search for only once.
+-- The other part is comprised of a map of toolkits to renderers (possibly missing)
+-- This means that checking if renderers are available will only be done once.
 type FileHash = Word
 
 data PlotState
   = PlotState
       (MVar (Map FilePath FileHash))
-      (MVar (Map Toolkit (Maybe Executable)))
+      (MVar (Map Toolkit (Maybe Renderer)))
 
 -- | Get a filehash. If the file hash has been computed before,
 -- it is reused. Otherwise, the filehash is calculated and stored.
@@ -211,25 +251,13 @@         then liftIO . fmap (fromIntegral . hash . show) . getModificationTime $ fp
         else err (mconcat ["Dependency ", pack fp, " does not exist."]) >> return 0
 
--- | Get an executable. If the executable has not been used before,
--- find it and store where it is. It will be re-used.
+-- | Find an executable.
 executable :: Toolkit -> PlotM (Maybe Executable)
-executable tk = do
-  name <- exeSelector tk
-  PlotState varHashes varExes <- get
-  exes <- liftIO $ takeMVar varExes
-  (exe', exes') <- case M.lookup tk exes of
-    Nothing -> do
-      debug $ mconcat ["Looking for executable \"", pack name, "\" for ", pack $ show tk]
-      exe' <- liftIO $ findExecutable name >>= return . fmap exeFromPath
-      let exes' = M.insert tk exe' exes
-      return (exe', exes')
-    Just e -> do
-      debug $ mconcat ["Executable \"", pack name, "\" already found."]
-      return (e, exes)
-  liftIO $ putMVar varExes exes'
-  put $ PlotState varHashes varExes
-  return exe'
+executable tk =
+  exeSelector tk
+    >>= \name ->
+      liftIO $
+        findExecutable name <&> fmap exeFromPath
   where
     exeSelector Matplotlib = asksConfig matplotlibExe
     exeSelector PlotlyPython = asksConfig plotlyPythonExe
@@ -278,6 +306,8 @@     captionFormat :: !Format,
     -- | The text label to which the source code is linked. Change this if you are writing non-english documents.
     sourceCodeLabel :: !Text,
+    -- | Whether to halt pandoc-plot when an error is encountered or not.
+    strictMode :: !Bool,
     -- | Level of logging verbosity.
     logVerbosity :: !Verbosity,
     -- | Method of logging, i.e. printing to stderr or file.
@@ -326,6 +356,28 @@     bokehExe :: !FilePath,
     -- | The executable to use to generate figures using the Julia/Plots.jl toolkit.
     plotsjlExe :: !FilePath,
+    -- | Command-line arguments to pass to the Python interpreter for the Matplotlib toolkit
+    matplotlibCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the MATLAB toolkit.
+    matlabCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the Plotly/Python toolkit.
+    plotlyPythonCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the Plotly/R toolkit.
+    plotlyRCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the Mathematica toolkit.
+    mathematicaCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the GNU Octave toolkit.
+    octaveCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the GGPlot2 toolkit.
+    ggplot2CmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the gnuplot toolkit.
+    gnuplotCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the Graphviz toolkit.
+    graphvizCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the Python/Bokeh toolkit.
+    bokehCmdArgs :: !Text,
+    -- | Command-line arguments to pass to the interpreter for the Julia/Plots.jl toolkit.
+    plotsjlCmdArgs :: !Text,
     -- | Whether or not to make Matplotlib figures tight by default.
     matplotlibTightBBox :: !Bool,
     -- | Whether or not to make Matplotlib figures transparent by default.
src/Text/Pandoc/Filter/Plot/Monad/Logging.hs view
@@ -3,7 +3,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
src/Text/Pandoc/Filter/Plot/Monad/Types.hs view
@@ -4,7 +4,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,10 +13,12 @@ -- This module defines base types in use in pandoc-plot
 module Text.Pandoc.Filter.Plot.Monad.Types
   ( Toolkit (..),
+    Renderer (..),
     Script,
     CheckResult (..),
     InclusionKey (..),
     FigureSpec (..),
+    OutputSpec (..),
     SaveFormat (..),
     cls,
     extension,
@@ -122,7 +124,9 @@   | PreambleK
   | DpiK
   | SourceCodeLabelK
+  | StrictModeK
   | ExecutableK
+  | CommandLineArgsK
   | DependenciesK
   | FileK
   | MatplotlibTightBBoxK
@@ -140,7 +144,9 @@   show PreambleK = "preamble"
   show DpiK = "dpi"
   show SourceCodeLabelK = "source_label"
+  show StrictModeK = "strict"
   show ExecutableK = "executable"
+  show CommandLineArgsK = "command_line_arguments"
   show DependenciesK = "dependencies"
   show FileK = "file"
   show MatplotlibTightBBoxK = "tight_bbox"
@@ -156,8 +162,8 @@ -- It is assumed that once a @FigureSpec@ has been created, no configuration
 -- can overload it; hence, a @FigureSpec@ completely encodes a particular figure.
 data FigureSpec = FigureSpec
-  { -- | Plotting toolkit to use for this figure.
-    toolkit :: !Toolkit,
+  { -- | Renderer to use for this figure.
+    renderer_ :: !Renderer,
     -- | Figure caption.
     caption :: !Text,
     -- | Append link to source code in caption.
@@ -220,7 +226,7 @@             mconcat $ intersperse ", " $ show <$> saveFormats
           ]
     where
-      saveFormats = (enumFromTo minBound maxBound) :: [SaveFormat]
+      saveFormats = enumFromTo minBound maxBound :: [SaveFormat]
 
 instance FromJSON SaveFormat -- TODO: test this parsing
 
@@ -233,3 +239,26 @@ 
 isWindows :: Bool
 isWindows = os `elem` ["mingw32", "win32", "cygwin32"] -- Aliases taken from cabal's Distribution.System module
+
+-- | Internal description of all information
+-- needed to output a figure.
+data OutputSpec = OutputSpec
+  { -- | Figure spec
+    oFigureSpec :: FigureSpec,
+    -- | Path to the script to render
+    oScriptPath :: FilePath,
+    -- | Figure output path
+    oFigurePath :: FilePath
+  }
+
+data Renderer = Renderer
+  { rendererToolkit :: Toolkit,
+    rendererExe :: Executable,
+    rendererCapture :: FigureSpec -> FilePath -> Script,
+    rendererCommand :: OutputSpec -> Text,
+    rendererSupportedSaveFormats :: [SaveFormat],
+    rendererChecks :: [Script -> CheckResult],
+    rendererLanguage :: Text,
+    rendererComment :: Text -> Text,
+    rendererScriptExtension :: String
+  }
src/Text/Pandoc/Filter/Plot/Parse.hs view
@@ -3,7 +3,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -18,12 +18,12 @@   )
 where
 
-import Control.Monad (join, when)
+import Control.Monad (join, unless, when)
 import Data.Char (isSpace)
 import Data.Default (def)
-import Data.List (intersperse)
+import Data.List (find, intersperse)
 import qualified Data.Map.Strict as Map
-import Data.Maybe (fromJust, fromMaybe, isJust, listToMaybe)
+import Data.Maybe (fromJust, fromMaybe, isJust)
 import Data.String (fromString)
 import Data.Text (Text, pack, unpack)
 import qualified Data.Text as T
@@ -50,26 +50,39 @@ -- If an environment is detected, but the save format is incompatible,
 -- an error will be thrown.
 parseFigureSpec :: Block -> PlotM (Maybe FigureSpec)
-parseFigureSpec block@(CodeBlock (id', classes, attrs) _) =
-  sequence $
-    fmap figureSpec $
-      plotToolkit block >>= hasToolkit
+parseFigureSpec block@(CodeBlock (id', classes, attrs) _) = do
+  -- The following would be a good case for the use of MaybeT
+  -- but I don't want to bring in another dependency
+  let mtk = plotToolkit block
+  case mtk of
+    Nothing -> return Nothing
+    Just tk -> do
+      r <- renderer tk
+      case r of
+        Nothing -> do
+          let msg = mconcat ["Renderer for ", tshow tk, " needed but is not installed"]
+          whenStrict $ throwError $ "[strict mode] " <> msg
+          warning msg
+          return Nothing
+        Just r' -> do
+          Just <$> figureSpec r'
   where
-    hasToolkit = \tk -> if cls tk `elem` classes then return tk else Nothing
     attrs' = Map.fromList attrs
     preamblePath = unpack <$> Map.lookup (tshow PreambleK) attrs'
 
-    figureSpec :: Toolkit -> PlotM FigureSpec
-    figureSpec toolkit = do
+    figureSpec :: Renderer -> PlotM FigureSpec
+    figureSpec renderer_@Renderer {..} = do
       conf <- asks envConfig
+      let toolkit = rendererToolkit
       let extraAttrs' = parseExtraAttrs toolkit attrs'
-          header = comment toolkit $ "Generated by pandoc-plot " <> ((pack . showVersion) version)
+          header = rendererComment $ "Generated by pandoc-plot " <> (pack . showVersion) version
           defaultPreamble = preambleSelector toolkit conf
 
       includeScript <-
-        fromMaybe
+        maybe
           (return defaultPreamble)
-          ((liftIO . TIO.readFile) <$> preamblePath)
+          (liftIO . TIO.readFile)
+          preamblePath
       let -- Filtered attributes that are not relevant to pandoc-plot
           -- This presumes that inclusionKeys includes ALL possible keys, for all toolkits
           filteredAttrs = filter (\(k, _) -> k `notElem` (tshow <$> inclusionKeys)) attrs
@@ -81,22 +94,22 @@       content <- parseContent block
 
       let caption = Map.findWithDefault mempty (tshow CaptionK) attrs'
-          withSource = fromMaybe defWithSource $ readBool <$> Map.lookup (tshow WithSourceK) attrs'
+          withSource = maybe defWithSource readBool (Map.lookup (tshow WithSourceK) attrs')
           script = mconcat $ intersperse "\n" [header, includeScript, content]
-          saveFormat = fromMaybe defSaveFmt $ (fromString . unpack) <$> Map.lookup (tshow SaveFormatK) attrs'
+          saveFormat = maybe defSaveFmt (fromString . unpack) (Map.lookup (tshow SaveFormatK) attrs')
           directory = makeValid $ unpack $ Map.findWithDefault (pack $ defaultDirectory conf) (tshow DirectoryK) attrs'
-          dpi = fromMaybe defDPI $ (read . unpack) <$> Map.lookup (tshow DpiK) attrs'
+          dpi = maybe defDPI (read . unpack) (Map.lookup (tshow DpiK) attrs')
           extraAttrs = Map.toList extraAttrs'
           blockAttrs = (id', filter (/= cls toolkit) classes, filteredAttrs)
 
       let blockDependencies = parseFileDependencies $ fromMaybe mempty $ Map.lookup (tshow DependenciesK) attrs'
-          dependencies = (defaultDependencies conf) <> blockDependencies
+          dependencies = defaultDependencies conf <> blockDependencies
 
       -- This is the first opportunity to check save format compatibility
-      let saveFormatSupported = saveFormat `elem` (supportedSaveFormats toolkit)
-      when (not saveFormatSupported) $ do
-        let msg = pack $ mconcat ["Save format ", show saveFormat, " not supported by ", show toolkit]
-        err msg
+      _' <-
+        unless (saveFormat `elem` rendererSupportedSaveFormats) $
+          let msg = pack $ mconcat ["Save format ", show saveFormat, " not supported by ", show toolkit]
+           in err msg
       return FigureSpec {..}
 parseFigureSpec _ = return Nothing
 
@@ -125,7 +138,7 @@ -- from a code block, if any.
 plotToolkit :: Block -> Maybe Toolkit
 plotToolkit (CodeBlock (_, classes, _) _) =
-  listToMaybe $ filter (\tk -> cls tk `elem` classes) toolkits
+  find (\tk -> cls tk `elem` classes) toolkits
 plotToolkit _ = Nothing
 
 -- | Reader a caption, based on input document format
@@ -158,9 +171,7 @@ parseFileDependencies t
   | t == mempty = mempty
   | otherwise =
-    fmap normalise
-      . fmap unpack
-      . fmap (T.dropAround isSpace) -- Remove leading/trailing whitespace on filenames
+    fmap (normalise . unpack . T.dropAround isSpace)
       . T.splitOn ","
       . T.dropAround (\c -> c `elem` ['[', ']'])
       $ t
src/Text/Pandoc/Filter/Plot/Renderers.hs view
@@ -3,7 +3,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -11,31 +11,30 @@ --
 -- Specification of renderers.
 module Text.Pandoc.Filter.Plot.Renderers
-  ( scriptExtension,
-    comment,
-    language,
+  ( renderer,
     preambleSelector,
-    supportedSaveFormats,
-    scriptChecks,
     parseExtraAttrs,
-    command,
-    capture,
     executable,
-    toolkitAvailable,
     availableToolkits,
     availableToolkitsM,
     unavailableToolkits,
     unavailableToolkitsM,
+    supportedSaveFormats,
     OutputSpec (..),
     Executable (..),
+    Renderer (..),
   )
 where
 
 import Control.Concurrent.Async.Lifted (forConcurrently)
+import Control.Concurrent.MVar
+import Control.Monad.Reader (local)
+import Control.Monad.State.Strict
 import Data.List ((\\))
 import Data.Map.Strict (Map)
-import Data.Maybe (catMaybes)
-import Data.Text (Text)
+import qualified Data.Map.Strict as M
+import Data.Maybe (catMaybes, isJust)
+import Data.Text (Text, pack)
 import Text.Pandoc.Filter.Plot.Monad
 import Text.Pandoc.Filter.Plot.Renderers.Bokeh
 import Text.Pandoc.Filter.Plot.Renderers.GGPlot2
@@ -48,64 +47,39 @@ import Text.Pandoc.Filter.Plot.Renderers.PlotlyPython
 import Text.Pandoc.Filter.Plot.Renderers.PlotlyR
 import Text.Pandoc.Filter.Plot.Renderers.Plotsjl
-import Text.Pandoc.Filter.Plot.Renderers.Prelude (OutputSpec (..))
 
--- Extension for script files, e.g. ".py", or ".m".
-scriptExtension :: Toolkit -> String
-scriptExtension Matplotlib = ".py"
-scriptExtension PlotlyPython = ".py"
-scriptExtension PlotlyR = ".r"
-scriptExtension Matlab = ".m"
-scriptExtension Mathematica = ".m"
-scriptExtension Octave = ".m"
-scriptExtension GGPlot2 = ".r"
-scriptExtension GNUPlot = ".gp"
-scriptExtension Graphviz = ".dot"
-scriptExtension Bokeh = ".py"
-scriptExtension Plotsjl = ".jl"
-
--- | Language that is used by a toolkit. Specifically used
--- to highlight the appropriate language in the external source code.
-language :: Toolkit -> Text
-language Matplotlib = "python"
-language PlotlyPython = "python"
-language PlotlyR = "r"
-language Matlab = "matlab"
-language Mathematica = "mathematica"
-language Octave = "matlab"
-language GGPlot2 = "r"
-language GNUPlot = "gnuplot"
-language Graphviz = "dot"
-language Bokeh = "python"
-language Plotsjl = "julia"
-
--- Make a string into a comment
-comment :: Toolkit -> (Text -> Text)
-comment Matplotlib = mappend "# "
-comment PlotlyPython = mappend "# "
-comment PlotlyR = mappend "# "
-comment Matlab = mappend "% "
-comment Mathematica = \t -> mconcat ["(*", t, "*)"]
-comment Octave = mappend "% "
-comment GGPlot2 = mappend "# "
-comment GNUPlot = mappend "# "
-comment Graphviz = mappend "// "
-comment Bokeh = mappend "# "
-comment Plotsjl = mappend "# "
-
--- | The function that maps from configuration to the preamble.
-preambleSelector :: Toolkit -> (Configuration -> Script)
-preambleSelector Matplotlib = matplotlibPreamble
-preambleSelector PlotlyPython = plotlyPythonPreamble
-preambleSelector PlotlyR = plotlyRPreamble
-preambleSelector Matlab = matlabPreamble
-preambleSelector Mathematica = mathematicaPreamble
-preambleSelector Octave = octavePreamble
-preambleSelector GGPlot2 = ggplot2Preamble
-preambleSelector GNUPlot = gnuplotPreamble
-preambleSelector Graphviz = graphvizPreamble
-preambleSelector Bokeh = bokehPreamble
-preambleSelector Plotsjl = plotsjlPreamble
+-- | Get the renderer associated with a toolkit.
+-- If the renderer has not been used before,
+-- initialize it and store where it is. It will be re-used.
+renderer :: Toolkit -> PlotM (Maybe Renderer)
+renderer tk = do
+  PlotState varHashes varRenderers <- get
+  renderers <- liftIO $ takeMVar varRenderers
+  (r', rs') <- case M.lookup tk renderers of
+    Nothing -> do
+      debug $ mconcat ["Looking for renderer for ", pack $ show tk]
+      r' <- sel tk
+      let rs' = M.insert tk r' renderers
+      return (r', rs')
+    Just e -> do
+      debug $ mconcat ["Renderer for \"", pack $ show tk, "\" already initialized."]
+      return (e, renderers)
+  liftIO $ putMVar varRenderers rs'
+  put $ PlotState varHashes varRenderers
+  return r'
+  where
+    sel :: Toolkit -> PlotM (Maybe Renderer)
+    sel Matplotlib = matplotlib
+    sel PlotlyPython = plotlyPython
+    sel PlotlyR = plotlyR
+    sel Matlab = matlab
+    sel Mathematica = mathematica
+    sel Octave = octave
+    sel GGPlot2 = ggplot2
+    sel GNUPlot = gnuplot
+    sel Graphviz = graphviz
+    sel Bokeh = bokeh
+    sel Plotsjl = plotsjl
 
 -- | Save formats supported by this renderer.
 supportedSaveFormats :: Toolkit -> [SaveFormat]
@@ -121,67 +95,26 @@ supportedSaveFormats Bokeh = bokehSupportedSaveFormats
 supportedSaveFormats Plotsjl = plotsjlSupportedSaveFormats
 
--- Checks to perform before running a script. If ANY check fails,
--- the figure is not rendered. This is to prevent, for example,
--- blocking operations to occur.
-scriptChecks :: Toolkit -> [Script -> CheckResult]
-scriptChecks Matplotlib = [matplotlibCheckIfShow]
-scriptChecks Bokeh = [bokehCheckIfShow]
-scriptChecks _ = mempty
+-- | The function that maps from configuration to the preamble.
+preambleSelector :: Toolkit -> (Configuration -> Script)
+preambleSelector Matplotlib = matplotlibPreamble
+preambleSelector PlotlyPython = plotlyPythonPreamble
+preambleSelector PlotlyR = plotlyRPreamble
+preambleSelector Matlab = matlabPreamble
+preambleSelector Mathematica = mathematicaPreamble
+preambleSelector Octave = octavePreamble
+preambleSelector GGPlot2 = ggplot2Preamble
+preambleSelector GNUPlot = gnuplotPreamble
+preambleSelector Graphviz = graphvizPreamble
+preambleSelector Bokeh = bokehPreamble
+preambleSelector Plotsjl = plotsjlPreamble
 
 -- | Parse code block headers for extra attributes that are specific
 -- to this renderer. By default, no extra attributes are parsed.
 parseExtraAttrs :: Toolkit -> Map Text Text -> Map Text Text
-parseExtraAttrs Matplotlib = matplotlibExtraAttrs
+parseExtraAttrs Matplotlib = M.filterWithKey (\k _ -> k `elem` ["tight_bbox", "transparent"])
 parseExtraAttrs _ = return mempty
 
--- | Generate the appropriate command-line command to generate a figure.
--- The executable will need to be found first, hence the IO monad.
-command ::
-  Toolkit ->
-  OutputSpec ->
-  Text -> -- Executable name (e.g. "python3")
-  Text
-command Matplotlib = matplotlibCommand
-command PlotlyPython = plotlyPythonCommand
-command PlotlyR = plotlyRCommand
-command Matlab = matlabCommand
-command Mathematica = mathematicaCommand
-command Octave = octaveCommand
-command GGPlot2 = ggplot2Command
-command GNUPlot = gnuplotCommand
-command Graphviz = graphvizCommand
-command Bokeh = bokehCommand
-command Plotsjl = plotsjlCommand
-
--- | Script fragment required to capture a figure.
-capture :: Toolkit -> (FigureSpec -> FilePath -> Script)
-capture Matplotlib = matplotlibCapture
-capture PlotlyPython = plotlyPythonCapture
-capture PlotlyR = plotlyRCapture
-capture Matlab = matlabCapture
-capture Mathematica = mathematicaCapture
-capture Octave = octaveCapture
-capture GGPlot2 = ggplot2Capture
-capture GNUPlot = gnuplotCapture
-capture Graphviz = graphvizCapture
-capture Bokeh = bokehCapture
-capture Plotsjl = plotsjlCapture
-
--- | Check if a toolkit is available, based on the current configuration
-toolkitAvailable :: Toolkit -> PlotM Bool
-toolkitAvailable Matplotlib = matplotlibAvailable
-toolkitAvailable PlotlyPython = plotlyPythonAvailable
-toolkitAvailable PlotlyR = plotlyRAvailable
-toolkitAvailable Matlab = matlabAvailable
-toolkitAvailable Mathematica = mathematicaAvailable
-toolkitAvailable Octave = octaveAvailable
-toolkitAvailable GGPlot2 = ggplot2Available
-toolkitAvailable GNUPlot = gnuplotAvailable
-toolkitAvailable Graphviz = graphvizAvailable
-toolkitAvailable Bokeh = bokehAvailable
-toolkitAvailable Plotsjl = plotsjlAvailable
-
 -- | List of toolkits available on this machine.
 -- The executables to look for are taken from the configuration.
 availableToolkits :: Configuration -> IO [Toolkit]
@@ -196,13 +129,16 @@ --
 -- Note that logging is disabled
 availableToolkitsM :: PlotM [Toolkit]
-availableToolkitsM = silence $ do
-  mtks <- forConcurrently toolkits $ \tk -> do
-    available <- toolkitAvailable tk
-    if available
-      then return $ Just tk
-      else return Nothing
-  return $ catMaybes mtks
+availableToolkitsM = silence $
+  asNonStrict $ do
+    mtks <- forConcurrently toolkits $ \tk -> do
+      available <- isJust <$> renderer tk
+      if available
+        then return $ Just tk
+        else return Nothing
+    return $ catMaybes mtks
+  where
+    asNonStrict = local (\(RuntimeEnv c l d) -> RuntimeEnv c {strictMode = False} l d)
 
 -- | Monadic version of @unavailableToolkits@
 unavailableToolkitsM :: PlotM [Toolkit]
src/Text/Pandoc/Filter/Plot/Renderers/Bokeh.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,11 +13,8 @@ --
 -- Rendering Bokeh code blocks
 module Text.Pandoc.Filter.Plot.Renderers.Bokeh
-  ( bokehSupportedSaveFormats,
-    bokehCommand,
-    bokehCapture,
-    bokehAvailable,
-    bokehCheckIfShow,
+  ( bokeh,
+    bokehSupportedSaveFormats,
   )
 where
 
@@ -25,20 +22,43 @@ import qualified Data.Text as T
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+bokeh :: PlotM (Maybe Renderer)
+bokeh = do
+  avail <- bokehAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig bokehCmdArgs
+      mexe <- executable Bokeh
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Bokeh,
+                rendererExe = exe,
+                rendererCapture = appendCapture bokehCaptureFragment,
+                rendererCommand = bokehCommand cmdargs exename,
+                rendererSupportedSaveFormats = bokehSupportedSaveFormats,
+                rendererChecks = [bokehCheckIfShow],
+                rendererLanguage = "python",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".py"
+              }
+
 bokehSupportedSaveFormats :: [SaveFormat]
 bokehSupportedSaveFormats = [PNG, SVG, HTML]
 
-bokehCommand :: OutputSpec -> Text -> Text
-bokehCommand OutputSpec {..} exe = [st|#{exe} "#{oScriptPath}"|]
+bokehCommand :: Text -> Text -> OutputSpec -> Text
+bokehCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} "#{oScriptPath}"|]
 
 bokehAvailable :: PlotM Bool
 bokehAvailable = do
   mexe <- executable Bokeh
   case mexe of
     Nothing -> return False
-    Just (Executable dir exe) -> commandSuccess dir [st|#{exe} -c "import bokeh; import selenium"|]
+    Just (Executable dir exe) -> withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|#{exe} -c "import bokeh; import selenium"|]
 
--- | Check if `matplotlib.pyplot.show()` calls are present in the script,
+-- | Check if `bokeh.io.show()` calls are present in the script,
 -- which would halt pandoc-plot
 bokehCheckIfShow :: Script -> CheckResult
 bokehCheckIfShow s =
@@ -51,9 +71,6 @@         <$> [ "bokeh.io.show(",
               "show("
             ]
-
-bokehCapture :: FigureSpec -> FilePath -> Script
-bokehCapture = appendCapture bokehCaptureFragment
 
 bokehCaptureFragment :: FigureSpec -> FilePath -> Script
 bokehCaptureFragment FigureSpec {..} fname =
src/Text/Pandoc/Filter/Plot/Renderers/GGPlot2.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,21 +13,42 @@ --
 -- Rendering GGPlot2 plots code blocks
 module Text.Pandoc.Filter.Plot.Renderers.GGPlot2
-  ( ggplot2SupportedSaveFormats,
-    ggplot2Command,
-    ggplot2Capture,
-    ggplot2Available,
+  ( ggplot2,
+    ggplot2SupportedSaveFormats,
   )
 where
 
 import qualified Data.Text as T
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+ggplot2 :: PlotM (Maybe Renderer)
+ggplot2 = do
+  avail <- ggplot2Available
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig ggplot2CmdArgs
+      mexe <- executable GGPlot2
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = GGPlot2,
+                rendererExe = exe,
+                rendererCapture = ggplot2Capture,
+                rendererCommand = ggplot2Command cmdargs exename,
+                rendererSupportedSaveFormats = ggplot2SupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "r",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".r"
+              }
+
 ggplot2SupportedSaveFormats :: [SaveFormat]
 ggplot2SupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, TIF]
 
-ggplot2Command :: OutputSpec -> Text -> Text
-ggplot2Command OutputSpec {..} exe = [st|#{exe} "#{oScriptPath}"|]
+ggplot2Command :: Text -> Text -> OutputSpec -> Text
+ggplot2Command cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} "#{oScriptPath}"|]
 
 ggplot2Available :: PlotM Bool
 ggplot2Available = do
@@ -35,7 +56,7 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -e 'if(!require("ggplot2")) {quit(status=1)}'|]
+      withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|#{exe} -e "if(!require('ggplot2')) {quit(status=1)}"|]
 
 ggplot2Capture :: FigureSpec -> FilePath -> Script
 ggplot2Capture fs fp =
src/Text/Pandoc/Filter/Plot/Renderers/GNUPlot.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,20 +13,41 @@ --
 -- Rendering gnuplot plots code blocks
 module Text.Pandoc.Filter.Plot.Renderers.GNUPlot
-  ( gnuplotSupportedSaveFormats,
-    gnuplotCommand,
-    gnuplotCapture,
-    gnuplotAvailable,
+  ( gnuplot,
+    gnuplotSupportedSaveFormats,
   )
 where
 
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+gnuplot :: PlotM (Maybe Renderer)
+gnuplot = do
+  avail <- gnuplotAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig gnuplotCmdArgs
+      mexe <- executable GNUPlot
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = GNUPlot,
+                rendererExe = exe,
+                rendererCapture = gnuplotCapture,
+                rendererCommand = gnuplotCommand cmdargs exename,
+                rendererSupportedSaveFormats = gnuplotSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "gnuplot",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".gp"
+              }
+
 gnuplotSupportedSaveFormats :: [SaveFormat]
 gnuplotSupportedSaveFormats = [PNG, SVG, EPS, GIF, JPG, PDF]
 
-gnuplotCommand :: OutputSpec -> Text -> Text
-gnuplotCommand OutputSpec {..} exe = [st|#{exe} -c "#{oScriptPath}"|]
+gnuplotCommand :: Text -> Text -> OutputSpec -> Text
+gnuplotCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} -c "#{oScriptPath}"|]
 
 gnuplotAvailable :: PlotM Bool
 gnuplotAvailable = do
@@ -34,7 +55,7 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|"#{exe}" -h|]
+      withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|"#{exe}" -h|]
 
 gnuplotCapture :: FigureSpec -> FilePath -> Script
 gnuplotCapture = prependCapture gnuplotCaptureFragment
src/Text/Pandoc/Filter/Plot/Renderers/Graphviz.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,24 +13,45 @@ --
 -- Rendering Graphviz plots code blocks
 module Text.Pandoc.Filter.Plot.Renderers.Graphviz
-  ( graphvizSupportedSaveFormats,
-    graphvizCommand,
-    graphvizCapture,
-    graphvizAvailable,
+  ( graphviz,
+    graphvizSupportedSaveFormats,
   )
 where
 
 import Data.Char
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+graphviz :: PlotM (Maybe Renderer)
+graphviz = do
+  avail <- graphvizAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig graphvizCmdArgs
+      mexe <- executable Graphviz
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Graphviz,
+                rendererExe = exe,
+                rendererCapture = graphvizCapture,
+                rendererCommand = graphvizCommand cmdargs exename,
+                rendererSupportedSaveFormats = graphvizSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "dot",
+                rendererComment = mappend "// ",
+                rendererScriptExtension = ".dot"
+              }
+
 graphvizSupportedSaveFormats :: [SaveFormat]
 graphvizSupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, WEBP, GIF]
 
-graphvizCommand :: OutputSpec -> Text -> Text
-graphvizCommand OutputSpec {..} exe =
+graphvizCommand :: Text -> Text -> OutputSpec -> Text
+graphvizCommand cmdargs exe OutputSpec {..} =
   let fmt = fmap toLower . show . saveFormat $ oFigureSpec
       dpi' = dpi oFigureSpec
-   in [st|#{exe} -T#{fmt} -Gdpi=#{dpi'} -o "#{oFigurePath}" "#{oScriptPath}"|]
+   in [st|#{exe} #{cmdargs} -T#{fmt} -Gdpi=#{dpi'} -o "#{oFigurePath}" "#{oScriptPath}"|]
 
 graphvizAvailable :: PlotM Bool
 graphvizAvailable = do
@@ -38,7 +59,7 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -?|]
+      withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|#{exe} -?|]
 
 -- Graphviz export is entirely based on command-line arguments
 -- so there is no need to modify the script itself.
src/Text/Pandoc/Filter/Plot/Renderers/Mathematica.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,20 +13,41 @@ --
 -- Rendering Mathematica plots code blocks
 module Text.Pandoc.Filter.Plot.Renderers.Mathematica
-  ( mathematicaSupportedSaveFormats,
-    mathematicaCommand,
-    mathematicaCapture,
-    mathematicaAvailable,
+  ( mathematica,
+    mathematicaSupportedSaveFormats,
   )
 where
 
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+mathematica :: PlotM (Maybe Renderer)
+mathematica = do
+  avail <- mathematicaAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig mathematicaCmdArgs
+      mexe <- executable Mathematica
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Mathematica,
+                rendererExe = exe,
+                rendererCapture = mathematicaCapture,
+                rendererCommand = mathematicaCommand cmdargs exename,
+                rendererSupportedSaveFormats = mathematicaSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "mathematica",
+                rendererComment = \t -> mconcat ["(*", t, "*)"],
+                rendererScriptExtension = ".m"
+              }
+
 mathematicaSupportedSaveFormats :: [SaveFormat]
 mathematicaSupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, GIF, TIF]
 
-mathematicaCommand :: OutputSpec -> Text -> Text
-mathematicaCommand OutputSpec {..} exe = [st|#{exe} -script "#{oScriptPath}"|]
+mathematicaCommand :: Text -> Text -> OutputSpec -> Text
+mathematicaCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} -script "#{oScriptPath}"|]
 
 mathematicaAvailable :: PlotM Bool
 mathematicaAvailable = do
@@ -34,7 +55,7 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -h|] -- TODO: test this
+      withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|#{exe} -h|] -- TODO: test this
 
 mathematicaCapture :: FigureSpec -> FilePath -> Script
 mathematicaCapture = appendCapture mathematicaCaptureFragment
src/Text/Pandoc/Filter/Plot/Renderers/Matlab.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,21 +13,42 @@ --
 -- Rendering Matlab code blocks
 module Text.Pandoc.Filter.Plot.Renderers.Matlab
-  ( matlabSupportedSaveFormats,
-    matlabCommand,
-    matlabCapture,
-    matlabAvailable,
+  ( matlab,
+    matlabSupportedSaveFormats,
   )
 where
 
 import System.Directory (exeExtension)
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+matlab :: PlotM (Maybe Renderer)
+matlab = do
+  avail <- matlabAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig matlabCmdArgs
+      mexe <- executable Matlab
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Matlab,
+                rendererExe = exe,
+                rendererCapture = matlabCapture,
+                rendererCommand = matlabCommand cmdargs exename,
+                rendererSupportedSaveFormats = matlabSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "matlab",
+                rendererComment = mappend "% ",
+                rendererScriptExtension = ".m"
+              }
+
 matlabSupportedSaveFormats :: [SaveFormat]
 matlabSupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, GIF, TIF]
 
-matlabCommand :: OutputSpec -> Text -> Text
-matlabCommand OutputSpec {..} exe = [st|#{exe} -batch "run('#{oScriptPath}')"|]
+matlabCommand :: Text -> Text -> OutputSpec -> Text
+matlabCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} -batch "run('#{oScriptPath}')"|]
 
 -- On Windows at least, "matlab -help"  actually returns -1, even though the
 -- help text is shown successfully!
src/Text/Pandoc/Filter/Plot/Renderers/Matplotlib.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -17,12 +17,8 @@ --     * @tight_bbox=True|False@ : Make plot bounding box tight. Default is False
 --     * @transparent=True|False@ : Make plot background transparent (perfect for web pages). Default is False.
 module Text.Pandoc.Filter.Plot.Renderers.Matplotlib
-  ( matplotlibSupportedSaveFormats,
-    matplotlibCommand,
-    matplotlibCapture,
-    matplotlibExtraAttrs,
-    matplotlibAvailable,
-    matplotlibCheckIfShow,
+  ( matplotlib,
+    matplotlibSupportedSaveFormats,
   )
 where
 
@@ -31,11 +27,34 @@ import qualified Data.Text as T
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+matplotlib :: PlotM (Maybe Renderer)
+matplotlib = do
+  avail <- matplotlibAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig matplotlibCmdArgs
+      mexe <- executable Matplotlib
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Matplotlib,
+                rendererExe = exe,
+                rendererCapture = matplotlibCapture,
+                rendererCommand = matplotlibCommand cmdargs exename,
+                rendererSupportedSaveFormats = matplotlibSupportedSaveFormats,
+                rendererChecks = [matplotlibCheckIfShow],
+                rendererLanguage = "python",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".py"
+              }
+
 matplotlibSupportedSaveFormats :: [SaveFormat]
 matplotlibSupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, GIF, TIF]
 
-matplotlibCommand :: OutputSpec -> Text -> Text
-matplotlibCommand OutputSpec {..} exe = [st|#{exe} "#{oScriptPath}"|]
+matplotlibCommand :: Text -> Text -> OutputSpec -> Text
+matplotlibCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} "#{oScriptPath}"|]
 
 matplotlibCapture :: FigureSpec -> FilePath -> Script
 matplotlibCapture = appendCapture matplotlibCaptureFragment
@@ -53,16 +72,13 @@     tightBox = if tight_ then ("'tight'" :: Text) else ("None" :: Text)
     transparent = if transparent_ then ("True" :: Text) else ("False" :: Text)
 
-matplotlibExtraAttrs :: M.Map Text Text -> (M.Map Text Text)
-matplotlibExtraAttrs kv = M.filterWithKey (\k _ -> k `elem` ["tight_bbox", "transparent"]) kv
-
 matplotlibAvailable :: PlotM Bool
 matplotlibAvailable = do
   mexe <- executable Matplotlib
   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -c "import matplotlib"|]
+      withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|#{exe} -c "import matplotlib"|]
 
 -- | Check if `matplotlib.pyplot.show()` calls are present in the script,
 -- which would halt pandoc-plot
src/Text/Pandoc/Filter/Plot/Renderers/Octave.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,20 +13,41 @@ --
 -- Rendering Octave plots code blocks
 module Text.Pandoc.Filter.Plot.Renderers.Octave
-  ( octaveSupportedSaveFormats,
-    octaveCommand,
-    octaveCapture,
-    octaveAvailable,
+  ( octave,
+    octaveSupportedSaveFormats,
   )
 where
 
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+octave :: PlotM (Maybe Renderer)
+octave = do
+  avail <- octaveAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig octaveCmdArgs
+      mexe <- executable Octave
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Octave,
+                rendererExe = exe,
+                rendererCapture = octaveCapture,
+                rendererCommand = octaveCommand cmdargs exename,
+                rendererSupportedSaveFormats = octaveSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "matlab",
+                rendererComment = mappend "% ",
+                rendererScriptExtension = ".m"
+              }
+
 octaveSupportedSaveFormats :: [SaveFormat]
 octaveSupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, GIF, TIF]
 
-octaveCommand :: OutputSpec -> Text -> Text
-octaveCommand OutputSpec {..} exe = [st|#{exe} --no-gui --no-window-system "#{oScriptPath}"|]
+octaveCommand :: Text -> Text -> OutputSpec -> Text
+octaveCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} --no-gui --no-window-system "#{oScriptPath}"|]
 
 octaveAvailable :: PlotM Bool
 octaveAvailable = do
@@ -34,7 +55,7 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -h|]
+      withPrependedPath dir $ asks envCWD >>= flip commandSuccess [st|#{exe} -h|]
 
 octaveCapture :: FigureSpec -> FilePath -> Script
 octaveCapture = appendCapture octaveCaptureFragment
src/Text/Pandoc/Filter/Plot/Renderers/PlotlyPython.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,28 +13,50 @@ --
 -- Rendering Plotly-python code blocks
 module Text.Pandoc.Filter.Plot.Renderers.PlotlyPython
-  ( plotlyPythonSupportedSaveFormats,
-    plotlyPythonCommand,
-    plotlyPythonCapture,
-    plotlyPythonAvailable,
+  ( plotlyPython,
+    plotlyPythonSupportedSaveFormats,
   )
 where
 
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+plotlyPython :: PlotM (Maybe Renderer)
+plotlyPython = do
+  avail <- plotlyPythonAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig plotlyPythonCmdArgs
+      mexe <- executable PlotlyPython
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = PlotlyPython,
+                rendererExe = exe,
+                rendererCapture = plotlyPythonCapture,
+                rendererCommand = plotlyPythonCommand cmdargs exename,
+                rendererSupportedSaveFormats = plotlyPythonSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "python",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".py"
+              }
+
 plotlyPythonSupportedSaveFormats :: [SaveFormat]
 plotlyPythonSupportedSaveFormats = [PNG, JPG, WEBP, PDF, SVG, EPS, HTML]
 
-plotlyPythonCommand :: OutputSpec -> Text -> Text
-plotlyPythonCommand OutputSpec {..} exe = [st|#{exe} "#{oScriptPath}"|]
+plotlyPythonCommand :: Text -> Text -> OutputSpec -> Text
+plotlyPythonCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} "#{oScriptPath}"|]
 
 plotlyPythonAvailable :: PlotM Bool
 plotlyPythonAvailable = do
-  mexe <- executable Matplotlib
+  mexe <- executable PlotlyPython
   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -c "import plotly.graph_objects"|]
+      withPrependedPath dir $
+        asks envCWD >>= flip commandSuccess [st|#{exe} -c "import plotly.graph_objects"|]
 
 plotlyPythonCapture :: FigureSpec -> FilePath -> Script
 plotlyPythonCapture = appendCapture plotlyPythonCaptureFragment
src/Text/Pandoc/Filter/Plot/Renderers/PlotlyR.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,21 +13,42 @@ --
 -- Rendering Plotly/R plots code blocks
 module Text.Pandoc.Filter.Plot.Renderers.PlotlyR
-  ( plotlyRSupportedSaveFormats,
-    plotlyRCommand,
-    plotlyRCapture,
-    plotlyRAvailable,
+  ( plotlyR,
+    plotlyRSupportedSaveFormats,
   )
 where
 
 import qualified Data.Text as T
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+plotlyR :: PlotM (Maybe Renderer)
+plotlyR = do
+  avail <- plotlyRAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig plotlyRCmdArgs
+      mexe <- executable PlotlyR
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = PlotlyR,
+                rendererExe = exe,
+                rendererCapture = plotlyRCapture,
+                rendererCommand = plotlyRCommand cmdargs exename,
+                rendererSupportedSaveFormats = plotlyRSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "r",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".r"
+              }
+
 plotlyRSupportedSaveFormats :: [SaveFormat]
 plotlyRSupportedSaveFormats = [PNG, PDF, SVG, JPG, EPS, HTML]
 
-plotlyRCommand :: OutputSpec -> Text -> Text
-plotlyRCommand OutputSpec {..} exe = [st|#{exe} "#{oScriptPath}"|]
+plotlyRCommand :: Text -> Text -> OutputSpec -> Text
+plotlyRCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} "#{oScriptPath}"|]
 
 plotlyRAvailable :: PlotM Bool
 plotlyRAvailable = do
@@ -35,7 +56,8 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -e 'if(!require("plotly")) {quit(status=1)}'|]
+      withPrependedPath dir $
+        asks envCWD >>= flip commandSuccess [st|#{exe} -e "if(!require('plotly')) {quit(status=1)}"|]
 
 plotlyRCapture :: FigureSpec -> FilePath -> Script
 plotlyRCapture fs fp =
src/Text/Pandoc/Filter/Plot/Renderers/Plotsjl.hs view
@@ -5,7 +5,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -13,22 +13,43 @@ --
 -- Rendering Julia/Plots.jl code blocks
 module Text.Pandoc.Filter.Plot.Renderers.Plotsjl
-  ( plotsjlSupportedSaveFormats,
-    plotsjlCommand,
-    plotsjlCapture,
-    plotsjlAvailable,
+  ( plotsjl,
+    plotsjlSupportedSaveFormats,
   )
 where
 
 import Text.Pandoc.Filter.Plot.Renderers.Prelude
 
+plotsjl :: PlotM (Maybe Renderer)
+plotsjl = do
+  avail <- plotsjlAvailable
+  if not avail
+    then return Nothing
+    else do
+      cmdargs <- asksConfig plotsjlCmdArgs
+      mexe <- executable Plotsjl
+      return $
+        mexe >>= \exe@(Executable _ exename) ->
+          return
+            Renderer
+              { rendererToolkit = Plotsjl,
+                rendererExe = exe,
+                rendererCapture = plotsjlCapture,
+                rendererCommand = plotsjlCommand cmdargs exename,
+                rendererSupportedSaveFormats = plotsjlSupportedSaveFormats,
+                rendererChecks = mempty,
+                rendererLanguage = "julia",
+                rendererComment = mappend "# ",
+                rendererScriptExtension = ".jl"
+              }
+
 -- Save formats support by most backends
 -- https://docs.plotsjl.org/latest/output/#Supported-output-file-formats-1
 plotsjlSupportedSaveFormats :: [SaveFormat]
 plotsjlSupportedSaveFormats = [PNG, SVG, PDF]
 
-plotsjlCommand :: OutputSpec -> Text -> Text
-plotsjlCommand OutputSpec {..} exe = [st|#{exe} "#{oScriptPath}"|]
+plotsjlCommand :: Text -> Text -> OutputSpec -> Text
+plotsjlCommand cmdargs exe OutputSpec {..} = [st|#{exe} #{cmdargs} "#{oScriptPath}"|]
 
 plotsjlAvailable :: PlotM Bool
 plotsjlAvailable = do
@@ -36,7 +57,8 @@   case mexe of
     Nothing -> return False
     Just (Executable dir exe) ->
-      commandSuccess dir [st|#{exe} -e "using Plots"|]
+      withPrependedPath dir $
+        asks envCWD >>= flip commandSuccess [st|#{exe} -e "using Plots"|]
 
 plotsjlCapture :: FigureSpec -> FilePath -> Script
 plotsjlCapture = appendCapture plotsjlCaptureFragment
src/Text/Pandoc/Filter/Plot/Renderers/Prelude.hs view
@@ -2,7 +2,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -17,7 +17,6 @@     unpack,
     commandSuccess,
     existsOnPath,
-    OutputSpec (..),
     appendCapture,
     toRPath,
   )
@@ -52,17 +51,6 @@   FilePath ->
   Script
 appendCapture f s fp = mconcat [script s, "\n", f s fp]
-
--- | Internal description of all information
--- needed to output a figure.
-data OutputSpec = OutputSpec
-  { -- | Figure spec
-    oFigureSpec :: FigureSpec,
-    -- | Path to the script to render
-    oScriptPath :: FilePath,
-    -- | Figure output path
-    oFigurePath :: FilePath
-  }
 
 -- | R paths use the '/' path separator
 toRPath :: FilePath -> FilePath
src/Text/Pandoc/Filter/Plot/Scripting.hs view
@@ -4,7 +4,7 @@ 
 -- |
 -- Module      : $header$
--- Copyright   : (c) Laurent P René de Cotret, 2020
+-- Copyright   : (c) Laurent P René de Cotret, 2019 - 2021
 -- License     : GNU GPL, version 2 or above
 -- Maintainer  : laurent.decotret@outlook.com
 -- Stability   : internal
@@ -20,7 +20,6 @@   )
 where
 
-import Control.Exception.Lifted (bracket)
 import Control.Monad.Reader
 import Data.Default (def)
 import Data.Functor.Identity (Identity (..))
@@ -33,7 +32,6 @@     doesFileExist,
     getTemporaryDirectory,
   )
-import System.Environment (getEnv, setEnv)
 import System.Exit (ExitCode (..))
 import System.FilePath
   ( addExtension,
@@ -45,7 +43,6 @@ import Text.Pandoc.Class (runPure)
 import Text.Pandoc.Definition
 import Text.Pandoc.Filter.Plot.Monad
-import Text.Pandoc.Filter.Plot.Renderers
 import Text.Pandoc.Filter.Plot.Scripting.Template
 import Text.Pandoc.Options (WriterOptions (..))
 import Text.Pandoc.SelfContained (makeSelfContained)
@@ -78,13 +75,11 @@   = ScriptSuccess
   | ScriptChecksFailed Text -- Message
   | ScriptFailure Text Int -- Command and exit code
-  | ToolkitNotInstalled Toolkit -- Script failed because toolkit is not installed
 
 instance Show ScriptResult where
   show ScriptSuccess = "Script success."
   show (ScriptChecksFailed msg) = unpack $ "Script checks failed: " <> msg
   show (ScriptFailure msg ec) = mconcat ["Script failed with exit code ", show ec, " and the following message: ", unpack msg]
-  show (ToolkitNotInstalled tk) = (show tk) <> " toolkit not installed."
 
 -- Run script as described by the spec
 -- Checks are performed, according to the renderer
@@ -92,7 +87,7 @@ -- stderr.
 runTempScript :: FigureSpec -> PlotM ScriptResult
 runTempScript spec@FigureSpec {..} = do
-  let checks = scriptChecks toolkit
+  let checks = rendererChecks renderer_
       checkResult = mconcat $ checks <*> [script]
   case checkResult of
     CheckFailed msg -> return $ ScriptChecksFailed msg
@@ -100,49 +95,35 @@       scriptPath <- tempScriptPath spec
       target <- figurePath spec
 
-      -- Check if executable is present
-      -- Note that checking if the toolkit if fully configured is much more involved,
-      -- and so we only check if the toolkit is appropriately installed if there is
-      -- an error.
-      exe <- executable toolkit
-      case exe of
-        Nothing -> error $ "Toolkit " <> show toolkit <> " is not installed."
-        Just (Executable exedir exename) ->
-          -- Change the PATH environment variable so the appropriate executable is
-          -- found first
-          withPrependedPath exedir $ do
-            let scriptWithCapture = (capture toolkit) spec target
+      let scriptWithCapture = rendererCapture renderer_ spec target
 
-            liftIO $ T.writeFile scriptPath scriptWithCapture
-            let outputSpec =
-                  OutputSpec
-                    { oFigureSpec = spec,
-                      oScriptPath = scriptPath,
-                      oFigurePath = target
-                    }
+      liftIO $ T.writeFile scriptPath scriptWithCapture
+      let outputSpec =
+            OutputSpec
+              { oFigureSpec = spec,
+                oScriptPath = scriptPath,
+                oFigurePath = target
+              }
+      let command_ = rendererCommand renderer_ outputSpec
 
-            let command_ = command toolkit outputSpec exename
-            -- It is important that the CWD be inherited from the
-            -- parent process. See #2.
-            cwd <- asks envCWD
-            (ec, _) <- runCommand cwd command_
-            case ec of
-              ExitSuccess -> return ScriptSuccess
-              ExitFailure code -> do
-                -- Two possible types of failures: either the script
-                -- failed because the toolkit was not available, or
-                -- because of a genuine error
-                toolkitInstalled <- toolkitAvailable toolkit
-                if toolkitInstalled
-                  then return $ ScriptFailure command_ code
-                  else return $ ToolkitNotInstalled toolkit
+      -- Change the PATH environment variable so the appropriate executable is
+      -- found first
+      let (Executable exedir _) = rendererExe renderer_
+      withPrependedPath exedir $ do
+        -- It is important that the CWD be inherited from the
+        -- parent process. See #2.
+        cwd <- asks envCWD
+        (ec, _) <- runCommand cwd command_
+        case ec of
+          ExitSuccess -> return ScriptSuccess
+          ExitFailure code -> return $ ScriptFailure command_ code
 
 -- | Determine the temp script path from Figure specifications
 -- Note that for certain renderers, the appropriate file extension
 -- is important.
 tempScriptPath :: FigureSpec -> PlotM FilePath
 tempScriptPath FigureSpec {..} = do
-  let ext = scriptExtension toolkit
+  let ext = rendererScriptExtension renderer_
   -- MATLAB will refuse to process files that don't start with
   -- a letter
   -- Note that this hash is only so that we are running scripts from unique
@@ -154,7 +135,7 @@ -- | Determine the path to the source code that generated the figure.
 -- To ensure that the source code path is distinguished from HTML figures, we use the extension .src.html.
 sourceCodePath :: FigureSpec -> PlotM FilePath
-sourceCodePath = fmap normalise . fmap (flip replaceExtension ".src.html") . figurePath
+sourceCodePath = fmap (normalise . flip replaceExtension ".src.html") . figurePath
 
 -- | Hash of the content of a @FigureSpec@. Note that unlike usual hashes,
 -- two @FigureSpec@ with the same @figureContentHash@ does not mean that they are equal!
@@ -168,7 +149,7 @@   return $
     fromIntegral $
       hash
-        ( ( fromEnum toolkit,
+        ( ( fromEnum (rendererToolkit renderer_),
             script,
             fromEnum saveFormat,
             directory
@@ -191,34 +172,21 @@       stem = flip addExtension ext . show $ fh
   return $ normalise $ directory spec </> stem
 
--- | Prepend a directory to the PATH environment variable for the duration
--- of a computation.
---
--- This function is exception-safe; even if an exception happens during the
--- computation, the PATH environment variable will be reverted back to
--- its initial value.
-withPrependedPath :: FilePath -> PlotM a -> PlotM a
-withPrependedPath dir f = do
-  pathVar <- liftIO $ getEnv "PATH"
-  let pathVarPrepended = mconcat [dir, ";", pathVar]
-  bracket
-    (liftIO $ setEnv "PATH" pathVarPrepended)
-    (\_ -> liftIO $ setEnv "PATH" pathVar)
-    (\_ -> f)
-
 -- | Write the source code of a figure to an HTML file with appropriate syntax highlighting.
 writeSource :: FigureSpec -> PlotM ()
 writeSource spec = do
+  let rdr = renderer_ spec
+      language = rendererLanguage rdr
   scp <- sourceCodePath spec
-  let doc = Pandoc mempty [CodeBlock (mempty, [language (toolkit spec)], mempty) (script spec)]
+  let doc = Pandoc mempty [CodeBlock (mempty, [language], mempty) (script spec)]
       renderSource = \template -> do
         let opts = def {writerTemplate = Just template}
             -- Note that making the document self-contained is absolutely required so that the CSS for
             -- syntax highlighting is included directly in the document.
-            t = either (const mempty) id $ runPure $ (writeHtml5String opts doc >>= makeSelfContained)
+            t = either (const mempty) id $ runPure (writeHtml5String opts doc >>= makeSelfContained)
         liftIO $ T.writeFile scp t
 
-  either (err . pack) (renderSource) $ runIdentity $ compileTemplate mempty sourceTemplate
+  either (err . pack) renderSource $ runIdentity $ compileTemplate mempty sourceTemplate
 
 sourceTemplate :: Text
 sourceTemplate = pack $(sourceTemplate_)
stack.yaml view
@@ -5,11 +5,12 @@ 
 # GHC 8.10.2 is broken on Windows:
 #   https://gitlab.haskell.org/ghc/ghc/-/issues/18550
-compiler: ghc-8.10.1
+compiler: ghc-8.10.3
 
 extra-deps:
-- pandoc-2.11.3.1
-- citeproc-0.3.0.1@sha256:1860a6757d5bc3ec149a434ed4011edb30155cb6ae92a1d83ccf3bd163bca0f1,5590
+- pandoc-2.11.3.2
+- citeproc-0.3.0.3@sha256:273b4935b18079fb666e53419dbf31e1edb7c7bdf7ea4295ff7ba6da22dc61b3,5590
+- texmath-0.12.1@sha256:57d2ff00f89da2a56f10eda28c6c502e1314a35090c7f63600f6d7b0adedbc29,6563
 - commonmark-0.1.1.2@sha256:c06ab05f0f224ab7982502a96e17952823a9b6dae8505fb35194b0baa9e2a975,3278
 - commonmark-extensions-0.2.0.4@sha256:6a437bcfa3c757af4262b71336513619990eafb5cfdc33e57a499c93ad225608,3184
 - commonmark-pandoc-0.2.0.1@sha256:529c6e2c6cabf61558b66a28123eafc1d90d3324be29819f59f024e430312c1f,1105
@@ -20,7 +21,6 @@ # For development
 - git: https://github.com/owickstrom/pandoc-include-code.git
   commit: 89c8465549960872257da993a399d978a269d6a6
-- ghc-check-0.3.0.1@sha256:651d9b2b75a5cbdb3c942117801bfa566079bcaf20360e4d0959f9e575c30b39,1070
   
 # Faster compilation.
 # See here: 
tests/fixtures/.verbose-config.yml view
@@ -1,3 +1,10 @@+strict: true
+
 logging:
   verbosity: debug
-  filepath: log.txt+
+matplotlib:
+  command_line_arguments: -Wa
+
+plotsjl:
+  command_line_arguments: --optimize=0