Appendix E — The ggplot2 phrasebook

ggplot2 proved that a grammar of graphics could be a working tool and not only a theory. Most readers of this book arrive from it. gog makes its own choices inside that same idea, and this appendix translates between the two: which word to use, and what will feel different.

It assumes the plot you want can be drawn. To find out whether it can, read Coverage. That appendix reads ggplot2’s whole reference index against the kernel and says what gog refuses and what it does not draw.

E.1 Side by side

ggplot2 gog
Languages R R, Python, Julia and JavaScript, one engine under all of them
Naming geom_point, aes, alpha point, channels by plain name, opacity
Where x/y are written aes() at the plot or the layer, and a layer may override the plot’s aes() resolved by where the channel is written in the sentence
The histogram geom_histogram() or stat_bin(geom = "bar") bar * bin
Log axis scale_x_log10() x(gdp, scale = "log"), written on the binding
3-D external packages one more position: z
Animation gganimate, a separate package play is a channel of the kernel: + play(year)

E.2 Translations

You write in ggplot2 You write in gog
ggplot(df, aes(x = a, y = b)) data(df) + x(a) + y(b) + …
geom_point() point
geom_line() line
geom_step() step
geom_area() area
geom_col() bar
geom_bar(), which counts the rows for you bar * count, where the count is a word in the sentence
geom_histogram(bins = 30) bar * bin(30)
geom_freqpoly() line * bin
geom_density() line * density
geom_smooth() line * smooth
stat_summary(fun = mean, geom = "bar") bar * mean
aes(color = g) color(g)
aes(size = v) size(v)
aes(shape = g) shape(g)
aes(alpha = v) opacity(v)
aes(group = g) group(g)
scale_x_log10() x(v, scale = "log")
scale_color_viridis_c() color(v) + palette("viridis")
facet_grid(r ~ c) \| facet(c) / facet(r)
facet_wrap(~ g, ncol = 4) \| facet(g, wrap = 4); / runs the same line down instead, so one number replaces nrow and ncol
facet_*(scales = "free_y") y(v, free = TRUE), written on the axis it frees, so there is no free_x/free_y/free to choose between
patchwork’s p1 | p2, p1 / p2 plot_a | plot_b, plot_a / plot_b: the same two operators, and the operand decides which
patchwork’s plot_spacer(), plot_layout(widths =) theme(width =, height =) on the plot that needs more room; the blank corner of a marginal plot is the space a shared axis does not use
ggrepel’s geom_text_repel() text * repel, the collision modifier for overlapping labels, beside dodge, stack and jitter
ggExtra’s ggMarginal() top / (main | right), three ordinary plots (Composition)
coord_flip() swap the x and y bindings: orientation is read, not switched
labs(title = , x = , y = ) title(), x_label(), y_label(), z_label()
color = "red", alpha = 0.5 inside a geom_*() style(color = "red", opacity = 0.5)
theme(…) theme() sets the page; style() sets a layer’s constants
ggsave("plot.svg") the rendered plot is SVG; render_svg() returns it as text to write to a file, spelled the same way in all four languages

E.3 Six differences to expect

  • + is still +, and on purpose. ggplot2’s author has said the pipe would have been the better interface (Wickham, 2018), so it is fair to ask why gog kept +. The short answer has two parts. Python has no pipe operator of its own, so a pipe could not spell one syntax in all four languages, and a pipe makes every atom a function, which would leave bar * bin meaning nothing. Operators has the long version, including what commutes in gog that did not commute in ggplot2.e.
  • Nothing is computed unless you name it. bar draws your numbers as they arrive; if you want counting, you write countWhere a geom counts for you, gog computes nothing until you write the word.d.
  • There is one spelling. No geom/stat pairs, and no choice of which function to use. If you can say a plot two ways here, one of them is a bug. Use “Report an issue” in the margin.
  • The scale belongs to the binding. You name a channel once, and its scale is a property of that binding, not a second sentence about it.
  • Setting is not mapping. A constant maps no column, gets no legend, and belongs in style(). The quoted-string ambiguity (color("red")) does not exist here: it is refused, with the fix named.
  • Refusals give direction. A sentence gog cannot draw is refused, and the message names the sentence it would accept. If you are used to a warning and a plot, expect a stop instead. The errors are part of the book, and it renders them on purpose.