Sorted bar graph in facet_grid

In the following plot, how do I obtain sorted bar across all facet? That is, region will be sorted according to measure values in all grids.

suppressWarnings(suppressMessages(library(tidyverse)))
# Data
m <- c(0.27, 0.27, 0.39, 0.21, 0.06, 0.18, 0.09, 0.11, 0.26, 0.17, 
       0.25, 0.18, 0.13, 0.11, 0.25, 0.15, 0.13, 0.21, 0.24, 0.19, 0.14, 
       0.12, 0.27, 0.23)
toy_df <- tibble(
  region = rep(c("A", "B", "C", "D", "E", "F"), each = 4),
  type = rep(c("X", "Y"), each = 2, times = 6),
  fact = rep(c("Good", "Bad"), times = 12),
  measure = m
)
# Plot
toy_df %>% 
  ggplot(aes(x = region, y = measure, fill = region)) +
  geom_bar(stat = "identity") +
  facet_grid(`type` ~ `fact`)

Created on 2020-10-19 by the reprex package (v0.3.0)

As far as I understand, there isn't a straightforward way of reordering the X-axis levels within each panel according to another variable, especially when doing so according to two other variables, as it is your case (type~fact).

This issue may be similar to: https://forum.posit.co/t/how-can-we-arrange-the-bars-for-each-facets-grid-in-ggplot/31512

These discussions may be of help I you feel like trying a workaround:

library(tidyverse)

m <- c(0.27, 0.27, 0.39, 0.21, 0.06, 0.18, 0.09, 0.11, 0.26, 0.17, 
       0.25, 0.18, 0.13, 0.11, 0.25, 0.15, 0.13, 0.21, 0.24, 0.19, 0.14, 
       0.12, 0.27, 0.23)
toy_df <- tibble(
  region = rep(c("A", "B", "C", "D", "E", "F"), each = 4),
  type = rep(c("X", "Y"), each = 2, times = 6),
  fact = rep(c("Good", "Bad"), times = 12),
  measure = m
)

(list_of_toy_df <- group_by(toy_df,type,fact) %>% 
  group_map(.f=~arrange(tibble(.),
                        desc(measure)) %>%
              mutate(region=forcats::as_factor(region)),.keep=TRUE))
# Plot
list_of_plots <- map(list_of_toy_df,
                      ~{ggplot(data = .,
                               aes(x = region, y = measure, fill = region)) +
                          geom_bar(stat = "identity")+
                          scale_fill_manual(values=
                                              c("A"="#F8766D", 
                                                "B"="#B79F00", 
                                                "C" = "#00BA38", 
                                                "D" = "#00BFC4",
                                                "E"= "#619CFF",
                                                "F" = "#F564E3"))+
                                               theme(legend.position="none")})

library(cowplot)

main_plot <- plot_grid(plotlist = list_of_plots,
                       nrow=2,ncol=2)
# extract the legend from one of the plots
legend <- get_legend(

  list_of_plots[[1]] +
    guides(color = guide_legend(nrow = 1)) +
    theme(legend.position = "bottom")
)


plot_grid(main_plot, legend, ncol = 1, rel_heights = c(1, .2))

#Shared legends • cowplot

Thanks! Is there any way I could specify the "Good", "Bad", "X" and "Y"?

Yeah, you can add plot titles

This topic was automatically closed 21 days after the last reply. New replies are no longer allowed.

If you have a query related to it or one of the replies, start a new topic and refer back with a link.