Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

help creating choropleth map? #169

Closed
ignacio82 opened this issue Aug 24, 2015 · 5 comments
Closed

help creating choropleth map? #169

ignacio82 opened this issue Aug 24, 2015 · 5 comments

Comments

@ignacio82
Copy link

My data looks like this:

states <-
  structure(
    list(
      State = c(
        "CA", "TX", "IL", "FL", "NY", "OH",
        "NJ", "GA", "MI", "PA", "MA", "CO", "AZ", "NC", "VA", "WA", "IN",
        "MD", "MN", "WI", "MO", "TN", "IA", "KY", "LA", "SC", "CT", "AL",
        "KS", "OR", "OK", "AR", "NV", "UT", "NE", "ID", "MS", "DC", "NM",
        "NH", "ME", "AK", "RI", "MT", "HI", "WV", "SD", "ND", "DE", "VT",
        "WY", "PR", "GU", "VI", "MP", "AS", "na", "MH", "FM", "PW"
      ),
      count = c(
        1590533L, 1016328L, 754535L, 742603L, 714205L,
        538719L, 477278L, 452064L, 437162L, 428616L, 420332L, 391084L,
        380853L, 354601L, 342533L, 335505L, 294670L, 286026L, 273427L,
        246172L, 238968L, 236037L, 235030L, 209514L, 199013L, 191707L,
        185521L, 179931L, 163477L, 159862L, 142610L, 136006L, 120111L,
        117338L, 112671L, 106176L, 102564L, 100168L, 97496L, 69881L,
        69508L, 68684L, 65631L, 62109L, 61123L, 57300L, 57254L, 56091L,
        51696L, 33944L, 32136L, 4822L, 598L, 468L, 49L, 19L, 17L,
        11L, 2L, 1L
      )
    ), .Names = c("State", "count"), class = c("tbl_dt",
                                               "tbl", "data.table", "data.frame"), row.names = c(NA,-60L), .internal.selfref = <
      pointer:0x0000000000320788 >
  )

I would like to create a map of the US using count to color each state. I can create a map of the US with this code:

library(leaflet)
library(maps)
mapStates = map("state", fill = TRUE, plot = FALSE)
leaflet(data = mapStates) %>% addTiles() %>%
  addPolygons(fillColor = topo.colors(10, alpha = NULL), stroke = FALSE)

but, I'm not sure how to change that code to tell it to use my data to color the states.

Thanks for the help!

@chris-holcomb
Copy link

The first example @ https://rstudio.github.io/leaflet/shapes.html shows you how to do this.

?leaflet leads to:
"data
a data object (currently supported objects are matrices, data frames, and spatial objects from the sp package of classes SpatialPoints, SpatialPointsDataFrame, Polygon, Polygons, SpatialPolygons, SpatialPolygonsDataFrame, Line, Lines, SpatialLines, and SpatialLinesDataFrame)"

But you are sending class(mapStates) = "map" to leaflet. Maybe there's a way to convert it but I don't see why when you can find anything in maps in a more standard format. FWIW, you probably should just use data.frame instead of structure. In that example, after making sure your states$count lines up with the data used in that example, you would just replace states$AWATER with states$count.

@ignacio82
Copy link
Author

I am able to follow the example and create a map of the US (I only had to change 2013 for 2014)

library(rgdal)
library(leaflet)

# From https://www.census.gov/geo/maps-data/data/cbf/cbf_state.html
states <- readOGR(dsn = "./cb_2014_us_state_20m.shp",
                  layer = "cb_2014_us_state_20m", verbose = FALSE)

neStates <- subset(states, states$STUSPS %in% c(
  "CT","ME","MA","NH","RI","VT","NY","NJ","PA"
))

leaflet(states) %>%
  addPolygons(
    stroke = FALSE, fillOpacity = 0.5, smoothFactor = 0.5,
    color = ~colorQuantile("YlOrRd", states$AWATER)(AWATER)
  ) 

What I am not sure is how to change the data to use my_counts$counts instead of states$AWATER
This is the data frame i want to use:

my_counts <- data.frame(
  State = c(
    "CA", "TX", "IL", "FL", "NY", "OH",
    "NJ", "GA", "MI", "PA", "MA", "CO", "AZ", "NC", "VA", "WA", "IN",
    "MD", "MN", "WI", "MO", "TN", "IA", "KY", "LA", "SC", "CT", "AL",
    "KS", "OR", "OK", "AR", "NV", "UT", "NE", "ID", "MS", "DC", "NM",
    "NH", "ME", "AK", "RI", "MT", "HI", "WV", "SD", "ND", "DE", "VT",
    "WY", "PR", "GU", "VI", "MP", "AS", "na", "MH", "FM", "PW"
  ),
  count = c(
    1590533L, 1016328L, 754535L, 742603L, 714205L,
    538719L, 477278L, 452064L, 437162L, 428616L, 420332L, 391084L,
    380853L, 354601L, 342533L, 335505L, 294670L, 286026L, 273427L,
    246172L, 238968L, 236037L, 235030L, 209514L, 199013L, 191707L,
    185521L, 179931L, 163477L, 159862L, 142610L, 136006L, 120111L,
    117338L, 112671L, 106176L, 102564L, 100168L, 97496L, 69881L,
    69508L, 68684L, 65631L, 62109L, 61123L, 57300L, 57254L, 56091L,
    51696L, 33944L, 32136L, 4822L, 598L, 468L, 49L, 19L, 17L,
    11L, 2L, 1L
  )
)

Thanks a lot @cholcomb !

@jcheng5
Copy link
Member

jcheng5 commented Aug 25, 2015

Try using sp::merge to combine states with my_counts. http://www.inside-r.org/packages/cran/sp/docs/merge

@mbacou
Copy link

mbacou commented Aug 26, 2015

@ignacio82 this has in fact nothing to do with leaflet, but here is an example of how to work with SpatialPolygonsDataFrame attribute tables.

# Use data.table or dplyr as you prefer
library(data.table)
states <- readOGR("./cb_2014_us_state_500k", "cb_2014_us_state_500k")

# Make a copy of the SPDF attribute table, and then work normally, as with any data.frame/data.table object
states.dt <- data.table(states@data)
# Create an explicit attribute to keep polygons IDs (useful to "re-attach" the table to the polygons later)
states.dt[, rn := row.names(states)]

my_counts <- data.table(
  State = c(
    "CA", "TX", "IL", "FL", "NY", "OH",
    "NJ", "GA", "MI", "PA", "MA", "CO", "AZ", "NC", "VA", "WA", "IN",
    "MD", "MN", "WI", "MO", "TN", "IA", "KY", "LA", "SC", "CT", "AL",
    "KS", "OR", "OK", "AR", "NV", "UT", "NE", "ID", "MS", "DC", "NM",
    "NH", "ME", "AK", "RI", "MT", "HI", "WV", "SD", "ND", "DE", "VT",
    "WY", "PR", "GU", "VI", "MP", "AS", "na", "MH", "FM", "PW"
  ),
  count = c(
    1590533L, 1016328L, 754535L, 742603L, 714205L,
    538719L, 477278L, 452064L, 437162L, 428616L, 420332L, 391084L,
    380853L, 354601L, 342533L, 335505L, 294670L, 286026L, 273427L,
    246172L, 238968L, 236037L, 235030L, 209514L, 199013L, 191707L,
    185521L, 179931L, 163477L, 159862L, 142610L, 136006L, 120111L,
    117338L, 112671L, 106176L, 102564L, 100168L, 97496L, 69881L,
    69508L, 68684L, 65631L, 62109L, 61123L, 57300L, 57254L, 56091L,
    51696L, 33944L, 32136L, 4822L, 598L, 468L, 49L, 19L, 17L,
    11L, 2L, 1L
  )
)

# Index the 2 data.tables on their common keys and join them
setkey(states.dt, STUSPS)
setkey(my_counts, State)
states.dt <- my_counts[states.dt]

# Re-attach the attribute table to the SPDF
setkey(states.dt, rn)
states@data <- data.frame(states.dt[row.names(states)])
# Make sure polygons IDs and data.frame row.names match
states <- spChFIDs(states, states$rn)

# Create map as usual...

@ignacio82
Copy link
Author

Thanks a lot!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants