Default knitr options and hooks

Published: March 12, 2021

Default knitr options and hooks

This is part four of our four part series

As with many aspects of programming, when you are working by yourself you can be (slightly) more lax with styles and set-up. However, as you start working in a team, different styles can quickly become a hindrance and lead to errors.

Using {knitr} is no different. When you work on documents with different team members, it’s helpful to have a consistent set of settings. If the default for eval changes, this can easily waste time as you try to track down an error. At Jumping Rivers, we use {knitr} a lot. From our training courses, to providing feedback to clients, to constructing monthly reports on clients infrastructure. The great thing about {knitr} is it’s really easy to customise. The bad thing is that without some care, it’s really easy for every member of the team to have different default options. This proliferation of different default options, means that when we pick up someone else document, mistakes may creep in.

We’ve found that to work effectively as team, we need a consistent set of global settings. To be honest, it isn’t really that important what the options are, it’s more crucial that they exist. In this post, we’ll describe the standard {knitr} we have and use.

Do you use RStudio Pro? If so, checkout out our managed RStudio services

Code Chunks

These options ensure that code chunks perform in a standard manner. The options below are relatively standard

  • echo: for our training courses, this is set toTRUE. For reports to clients, setting this to FALSE usually makes more sense.
  • collapse = TRUE: if possible, collapse all the source/output blocks from multiple chunk into a single block
  • comment = "#>": pre-pend result with #>. Default is ##

Graphics Options

We’ve just had three blog posts on graphics options, so clearly standardisation is a good thing here! Having a consistent set of {knitr} options makes standardising figures across documents (slightly) easier.

These options control the graphics options.

  • fig.path = "graphics/knitr-": create a standard directory where generated figures are stored. For our Hugo blog posts, we set fig.path = "" so the images are stored in the same directory as the md file.
  • fig.width = 6: the default of 7 is little large for most purposes. This is coupled with fig.asp = 0.7 to set the aspect ratio. If you decide you want to set fig.height in a code chunk, you also need to set fig.asp = NULL in that chunk. See the note at the end of this post for a further discussion on aspect ratios.
  • fig.pos = "t": when creating PDF documents, place the figures at the top of the page. Having figures placed where they appear in text can result in poorly pages, with dangling sentences at the bottom/top of the page.
  • fig.align = "center": centre the figure in the document. This gives the graph a more prominent place.
  • fig.retina = 2: use figures suitable for a retina display. The default if 2.
  • dpi differs for HTML and PDF documents. For PDF documents, we set dpi = 300, otherwise, we leave it at 72 (see our previous blog post on optimal figures for information). We can be clever, and set dpi = if (knitr::is_latex_output()) 72 else 300
  • out.width = 100%: We typically set this on a graph by graph basis.

Graphics Device

The graphics device is the default device for used to create and provide graphics. This options is controlled via the dev argument. For our training courses, where we produce PDF booklets of notes we set dev = "cairo_pdf" as the default. For blog post and HTML documents, such as this, we set dev = "svg". We also set dev.args = list(png = list(type = "cairo-png")), so that when we set dev = "png", we use the cairo-png variety.

{knitr} hooks

In our recent blog post on optimising PNG images, we discussed the optipng utility for reducing your file size. It’s actually straightforward to use optipng as a {knitr} hook, i.e. whenever you generate a PNG file, optipng automatically runs.

If you have optipng installed, you simply add the hook

knitr::knit_hooks$set(optipng = knitr::hook_optipng)

to the top of your document. You can also tweak the options via

# The args `-o1 -quiet' are passed to optipng
knitr::opts_chunk$set(optipng = "-o1 -quiet")

Putting it all together

When we put all of the above together, we end up with

knitr::opts_chunk$set(echo = FALSE, 
                      collapse = TRUE,
                      comment = "#>",
                      fig.path = "graphics/knitr-",
                      fig.retina = 2, # Control using dpi
                      fig.width = 6,  # generated images
                      fig.pos = "t",  # pdf mode
                      fig.align = "center",
                      dpi = if (knitr::is_latex_output()) 72 else 300, 
                      out.width = "100%",
                      dev = "svg",
                      dev.args = list(png = list(type = "cairo-png")),
                      optipng = "-o1 -quiet")

This can then be placed in an simple helper package to avoid duplication.

A note on aspect ratio: fig.asp

As with all graphic related options, there isn’t one single setting that is suitable for all situations. While fig.asp=0.7 gives a sensible default, you shouldn’t be frighted to change it. I found this article on when to use different aspect ratios very informative. R for Data Science also has a short section on figure sizing that’s worth reading.