2

I would like to adjust the spacing between plots that are aligned in a panel using the cowplot package when some plots contain axis titles/labels, and others don't.

Example

Let's create three plots:

library(tidyverse)
library(cowplot)

set.seed(123)

df <- data.frame(x = rnorm(n = 100), 
                 y = rnorm(n = 100))

plot <- ggplot(data = df, aes(x, y)) + geom_point()

plot_grid(plot, plot, plot, nrow = 1, align = "vh") 

enter image description here

These plots are aligned perfectly! But often, I have a scenario in which I would like to create a 'cleaner' panel figure. One way to do this is to remove the titles/text of the y-axis of the second and third plots.

Like this:

plot2 <- plot + theme(axis.title.y = element_blank(),  
                      axis.text.y = element_blank())

plot_grid(plot, plot2, plot2, nrow = 1, align = "vh")

enter image description here

Again, perfectly aligned, but the spacing between the first and the second plot (and the second and third plot) is quite large. I would like to reduce the spacing to create a more compact plot, while the axis remain exactly the same size.

Expected output

enter image description here

Is this possible with cowplot? Or is there another way to do this?

user213544
  • 2,046
  • 3
  • 22
  • 52

2 Answers2

2

Referencing this post on github, plot_grid() doesn't add any space by default and uses the margins of your plot. To remove the space outside your plot area, you can use them(plot.margin=...) to remove.

With that being said... that's not what's going on here! Printing either plot or plot2 will yield a plot with no margins. It appears the issue is with the use of the align= argument in plot_grid(). I'm not sure why, but setting it to anything other than the default values (align="none") results in the extra whitespace around the plots. Very strange... needless to say, removing that argument fixes your problem:

Original code using align="vh"

plot_grid(plot, plot2, plot2, nrow = 1, align="vh")

enter image description here

Using align="none"

plot_grid(plot, plot2, plot2, nrow = 1, align="none")

enter image description here

Any further space would be added according to your graphics device, since the actual plot you get depends on the size and resolution of that device.

chemdork123
  • 12,369
  • 2
  • 16
  • 32
  • Thanks! Intriguing behavior... The answer is indeed a step towards what I'm looking for, however, when omitting the alignment argument, the axis do not stay the same size. I'm wondering if there is a way to omit the argument, while keeping the axis the same size... (Now, it seems that plots 2 and 3 have an x-axis that is the size of the x-axis of plot 1 + axis.title.y + axis.text.y) – user213544 Jul 24 '20 at 18:42
  • 1
    I see what you mean. Well, there's the `rel_widths` argument. You can set the relative width of the first plot larger than the others, but the actual amount will be decided by trial and error. – chemdork123 Jul 24 '20 at 21:58
0

Here is a solution using the patchwork package

library(tidyverse)

set.seed(123)

df <- data.frame(x = rnorm(n = 100), 
                 y = rnorm(n = 100))

plot1 <- ggplot(data = df, aes(x, y)) + geom_point()

plot2 <- plot1 + theme(axis.title.y = element_blank(),  
                      axis.text.y = element_blank())

# install.packages("patchwork", dependencies = TRUE)
library(patchwork)

plot1 + plot2 + plot2 +
  plot_layout(ncol = 3) 

Created on 2020-07-24 by the reprex package (v0.3.0)

Tung
  • 26,371
  • 7
  • 91
  • 115