Search code examples
rggplot2legend-properties

Adjust Height and Width of Legend Glyphs Generated by key_glyph ggplot


I was thrilled to discover that I can change the glyph used in the legend by adding key_glyph = draw_key_rect to my geom layer. I want to make the legend wider and shorter to resemble the legend in this map by Timo Grossenbacher:

I've tried adjusting scale_fill_manual(guide = guide_legend(keyheight = unit(0.01, units = "mm") , keywidth = unit(40, units = "mm"))) which changes the dimensions of the legend, but only seems to work when I make the glyphs bigger. I can't seem to make the keyheight any smaller.

Is there a better method of adjusting the legend glyphs' dimensions?

enter image description here

Simplified code here:

df <- data_frame(x_value = c(1:10),
                 y_value = c(rev(1:10)),
                 value = c("a","a","a","a","b","b","b","b","c","c"))
library(ggplot2)

ggplot(data = df) + 
  geom_point(aes(x_value, y_value, fill = value),
             shape = 21,
             size = 9,
             key_glyph = draw_key_rect) +
  theme(legend.justification = c(0,0), # set which corner of legend legen.position references
        legend.position = c(0.05, 0.04)) +
  scale_fill_manual(values = c("red", "green", "blue"),
                    guide = guide_legend(direction = "horizontal",
                                         keyheight = unit(0.01, units = "mm"),
                                         keywidth = unit(40, units = "mm"),
                                         title.position = 'top',
                                         label.position = "bottom"))

Solution

  • You could create a fake legend. Or here's another mildly hacky solution.

    The problem seems to be the size argument in geom_point, so you could make a fake aesthetic, in particular using lines, e.g. like this:

    • draw transparent lines (geom_line(alpha = 0))
    • make a color legend for geom_line with the same colors as your fill.
    • set the alpha to 1 for your color legend (override.aes)
    • remove the fill legend.
    • control the legend height in theme
    library(ggplot2)
    
    df <- data.frame(x_value = c(1:10),
                     y_value = c(rev(1:10)),
                     value = c("a","a","a","a","b","b","b","b","c","c"))
    
    ggplot(data = df) + 
      geom_point(aes(x_value, y_value, fill = value), shape = 21, size = 7, 
                 show.legend = FALSE) + # remove fill legend
      geom_line(aes(x_value, y_value, color = value), 
                alpha = 0, #invisible line. If your data is big, you could create a very small data frame for that
                key_glyph = draw_key_rect) +
      theme(legend.justification = c(0,0), 
            legend.position = c(0.05, 0.04), 
            legend.key.height = unit(0.1, 'in')) + # control height
      scale_fill_manual(values = c("red", "green", "blue")) +
      scale_color_manual(values = c("red", "green", "blue")) +
      guides(color = guide_legend(override.aes = list(alpha = 1), # make line visible in legend 
                                  direction = "horizontal",
                                  keywidth = unit(20, units = "mm"),
                                  title.position = 'top',
                                  label.position = "bottom"))
    

    Created on 2020-02-20 by the reprex package (v0.3.0)

    Another option is to remove your key_glyph argument and control the glyph height with the size argument in geom_line