Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Setting axes limits based on variable values in ggplot

Tags:

r

ggplot2

I have a dataframe with programs and a country for each person in the program. I need to make a bar plot for each program with counts of participants from each country. I am including sample data and the code below.

In reality I have over 20 programs with hundreds of entries for each country and would like to automate this process to iterate over all of the programs by only changing the name of the program in the code. In the bar plot, I need to have data labels on the outer ends of the horizontal bars, however this prints them beyond the limits of the plot window. To solve this, I would like to adjust the scale of the axis, however instead of adjusting it manually for each program, I would like to set the limit to 10% above the maximum value of the 'Count' variable.

My question is whether it is possible to use variable values from a dataframe to set the limits instead of hardcoding them for each plot (and preferably doing this without saving a separate table for country counts). If this is not something that can be done, does anyone know of efficient alternative methods to automate axes scale adjustments and/or adjusting the plot window to fit the labels?

I could not find an answer to this elsewhere, but if a similar question has already been answered, I would be grateful if someone can point me towards the solution.

sample_data <- data.frame(
                          "person_number" = 1:15, 
                          "country" = c("United States", "Canada", "India", "United States", "United 
                                         States", "United States", "India", "China", "China", "United 
                                         States", "China", "India", "Canada", "United States", "China"), 
                          "program" = c("Program1", "Program2", "Program3", "Program2", "Program3", 
                                        "Program3", "Program3", "Program2", "Program3", "Program1", 
                                        "Program1", "Program3", "Program1", "Program2", "Program1")
                          )
sample_data %>% 
    filter(program == "Program1") %>% 
    group_by(country) %>% 
    summarise(Count = n_distinct(person_number)) %>% 
    ggplot(aes(x = reorder(country, Count), y = Count)) +
      geom_bar(stat = "identity", fill = "salmon3") +
      coord_flip() +
      labs(title = "Country for Program1 Applicants") +
      geom_text(aes(label=Count), size=3, hjust=-0.2) +
      ylim(0, max(Count)+0.1*max(Count))                     # this line does not work
                                                             # error message: object 'Count' not found
like image 464
elmg Avatar asked Apr 25 '26 17:04

elmg


1 Answers

This is exactly what the expand parameter in a scale is meant for. We can set a multiplicative axis expansion.

We can also simplify your code a bit:

sample_data %>% 
  filter(program == "Program1") %>% 
  ggplot(aes(x = forcats::fct_infreq(country))) +
  geom_bar(fill = "salmon3") +
  geom_text(aes(label = stat(count)), stat = 'count', size = 3, hjust = -0.2) +
  labs(title = "Country for Program1 Applicants") +
  scale_y_continuous(expand = expansion(c(0, 0.1))) +
  coord_flip()

I also turned off expansion of the left side of the plot. See ?scale_y_continuous and ?expansion.

enter image description here

like image 167
Axeman Avatar answered Apr 27 '26 05:04

Axeman