rggplot2

How to set the same width of the multiple plots in R ggplot2?


I'm trying to draw the three bar plots in one image.
For the example data, I have a question about setting the width of each plot.

df <- data.frame(group=c('A', 'B', 'C', 'D', 'E'),
                 valueA=c(0.1, 0.06, 0.02, 0.09, 0.12),
                 valueB=c(0.4, 0.6, 0.55, 0.45, 0.52),
                 valueC=c(0.76, 0.79, 0.85, 0.94, 0.89))

A_bar <- ggplot(df, aes(x=group, y=valueA, fill=group))+
  geom_bar(stat='identity')+
  theme_bw()+
  labs(x = "Group", y = "ValueA", fill = "Group") +
  scale_y_continuous(limits=c(0,0.2),oob = rescale_none)+
  coord_flip()

A_bar <- A_bar + theme(legend.position="none", 
                       axis.text=element_text(size=12), 
                       axis.title=element_text(size=14))


B_bar <- ggplot(df, aes(x=group, y=valueB, fill=group))+
  geom_bar(stat='identity')+
  theme_bw()+
  labs(x = "Group", y = "ValueB", fill = "Group") +
  scale_y_continuous(limits=c(0.4,0.65),oob = rescale_none)+
  theme(axis.title.y = element_blank())+
  coord_flip()

B_bar <- B_bar + theme(legend.position="none", 
                           axis.text=element_text(size=12), 
                           axis.title=element_text(size=14),
                           axis.text.y=element_blank())


C_bar <- ggplot(df, aes(x=group, y=valueC, fill=group))+
  geom_bar(stat='identity')+
  theme_bw()+
  labs(x = "Group", y = "ValueC", fill = "Group") +
  scale_y_continuous(limits=c(0.7,1),oob = rescale_none)+
  theme(axis.title.y = element_blank())+
  coord_flip()

C_bar <- C_bar + theme(legend.position="none", 
                         axis.text=element_text(size=12), 
                         axis.title=element_text(size=14),
                         axis.text.y=element_blank())

ggarrange(A_bar, B_bar, C_bar, ncol=3, nrow=1)

Let the result figure follows as below: enter image description here

You can see that the width of the first and the other plots are slightly different because of the y-axis title and labels in the first plot.
I want to unify the width of them like this. enter image description here I also tried to use facet_grid or facet_wrap, but it was confused because of the variables.

For the minor question, how can I insert the margin between the y-axis and bar plot as same as the ValueA plot?
Also, how can I change the order of the barplots from E~A to A~E?


Solution

  • You could create a fourth panel containing just the y-axis group labels:

    old_bw <- theme_set(theme_bw())
    
    theme_update(legend.position="none",                                   
                 axis.title.y=element_blank(),
                 axis.title.x=element_text(size=14),
                 axis.text.y=element_blank(),
                 axis.ticks.y=element_blank(),
                 plot.margin = unit(c(0.2,0.1,0.2,0.1), "cm"))
    
    Y_axis <- ggplot(df, aes(x=group, y=valueA, fill=group)) +
      labs(x = "Group", y="") +
      theme_minimal() +
      theme(axis.title.y=element_text(size=14),
            axis.text.y=element_text(size=14),
            axis.text.x=element_text(size=14, color=0),
            plot.margin = unit(c(0.2,0,0.2,0.2), "cm")) +
      scale_y_continuous(limits=c(0,0), oob = scales::rescale_none)+
      coord_flip(); Y_axis
      
    A_bar <- ggplot(df, aes(x=group, y=valueA, fill=group))+
      geom_bar(stat='identity')+
      labs(x = "", y = "ValueA", fill = "Group") +
      scale_y_continuous(limits=c(0,0.2), oob = scales::rescale_none)+
      coord_flip()
    
    B_bar <- ggplot(df, aes(x=group, y=valueB, fill=group))+
      geom_bar(stat='identity')+
      labs(x = "", y = "ValueB", fill = "Group") +
      scale_y_continuous(limits=c(0.4,0.65), oob = scales::rescale_none)+
      coord_flip()
    
    C_bar <- ggplot(df, aes(x=group, y=valueC, fill=group))+
      geom_bar(stat='identity')+
      labs(x = "", y = "ValueC", fill = "Group") +
      scale_y_continuous(limits=c(0.7,1),oob = scales::rescale_none)+
      coord_flip() 
    

    Then use ggarrange to force equal widths on the 3 plots.

    ggpubr::ggarrange(Y_axis, A_bar, B_bar, C_bar, ncol=4, nrow=1, 
            widths=c(1,6,6,6))
    
    theme_set(old_bw)
    

    enter image description here