Building a nice legend with R and ggplot2

This post describes all the available options to customize the chart legend with R and ggplot2. It shows how to control the title, text, location, symbols and more.

ggplot2 section Data to Viz

Default legend with ggplot2

By default, ggplot2 will automatically build a legend on your chart as soon as a shape feature is mapped to a variable in aes() part of the ggplot() call. So if you use color, shape or alpha, a legend will be available.

Here is an example based on the mtcars dataset. This post is gonna show how to use the theme() function to apply all type of customization on this default legend.

Note : this post is strongly inspired by the doc you get typiinig ??ggplot2::theme, give it a go!

# Load ggplot2

# Very basic chart
basic <- ggplot(mtcars, aes(wt, mpg, colour = factor(cyl), shape = factor(vs) )) +

Change legend title with labs()

The labs() function allows to change the legend titles. You can specify one title per section of the legend, i.e. per aesthetics in use in the chart.

         colour = "name1",
         shape = "name2"

Get rid of the legend: guides() and theme()

It is possible to remove a specific part or the whole legend thanks to the theme() and the guides() function. See code below:

# Left -> get rid of one part of the legend
basic + guides(shape=FALSE)
# Right -> only the x axis is modified
basic + theme(legend.position = "none")

Control legend position with legend.position

You can place the legend literally anywhere.

To put it around the chart, use the legend.position option and specify top, right, bottom, or left. To put it inside the plot area, specify a vector of length 2, both values going between 0 and 1 and giving the x and y coordinates.

Note: the command legend.justification sets the corner that the position refers to.

# Left -> legend around the plot
basic + theme(legend.position = "bottom")
# Right -> inside the plot area
basic + theme(
    legend.position = c(.95, .95),
    legend.justification = c("right", "top"), = "right",
    legend.margin = margin(6, 6, 6, 6)

Legend appearance

Here are 4 examples showing how to customize the legend main features:

# custom box around legend
basic + theme( = element_rect(color="red", size=2), = margin(116, 6, 6, 6)
# custom the key
basic + theme(legend.key = element_rect(fill = "white", colour = "black"))
# custom the text
basic + theme(legend.text = element_text(size = 8, colour = "red"))
# custom the title
basic + theme(legend.title = element_text(face = "bold"))

Related chart types

Grouped and Stacked barplot
Pie chart
Circular packing


This document is a work by Yan Holtz. Any feedback is highly encouraged. You can fill an issue on Github, drop me a message on Twitter, or send an email pasting with

Github Twitter