Search code examples
rggplot2gisbinningusmap

usmaps R: Use ggplot2 to set bins and manually color


I am using the usmaps() package in R to create a map of the US. I have data set up like so:

Ces_State_Only:

State 1990
Alabama 0.2
Alaska 0.31
Arizona 0.40

I want to create a chloropleth map. I would like to bin my data into the following: 0-0.2, 0.2-0.25, 0.25-0.3, 0.3-0.33, 0.33-36, >36.

My code is:

plot_usmap(data = Ces_State_only, values = "1990") +   scale_colour_gradientn(colours = "Blues", breaks = c(0,.2, .25, 0.3, 0.33, 0.36, 1),limits = c(0, 100))

This code works, but it does not bin my data.

I also tried binning my data before mapping it:

Ces_State_only$Ninety_bin <- cut(Ces_State_only$`1990`,breaks = c(0,0.2, 0.25, 0.3, 0.33, 0.36,1))
    
plot_usmap(data = Ces_State_only, values = "Ninety_bin") +   scale_fill_brewer(palette="Blues",
        aesthetics = "fill",
        na.value = "grey50")+   theme(legend.position = "right")

However, this creates only three different colors on the US Map (for the following bins: 0-0.2, 0.2-0.25, and 0.25-0.3).

Any suggestions or ideas?

Thank you in advance!


Solution

  • Update As of ggplot2 >= 3.5.0 one also has to add show.legend=TRUE to plot_usmap() to show the legend keys for unused factor levels:

    library(usmap)
    library(ggplot2)
    
    plot_usmap(
      data = Ces_State_only, values = "Ninety_bin",
      show.legend = TRUE
    ) +
      scale_fill_brewer(
        palette = "Blues",
        aesthetics = "fill",
        na.value = "grey50",
        drop = FALSE
      ) +
      theme(legend.position = "right")
    

    Original answer

    The issue is that by default usused factor levels get dropped. You could prevent that by setting drop=FALSE in scale_fill_brewer:

    library(usmap)
    library(ggplot2)
    
    plot_usmap(data = Ces_State_only, values = "Ninety_bin") +
      scale_fill_brewer(
        palette = "Blues",
        aesthetics = "fill",
        na.value = "grey50",
        drop = FALSE
      ) +
      theme(legend.position = "right")
    

    DATA

    Ces_State_only <- data.frame(
      check.names = FALSE,
      state = c("Alabama", "Alaska", "Arizona"),
      `1990` = c(0.2, 0.31, 0.4)
    )
    
    Ces_State_only$Ninety_bin <- cut(
      Ces_State_only$`1990`,
      breaks = c(0, 0.2, 0.25, 0.3, 0.33, 0.36, 1)
    )