sneeze_shiny
sneeze_shiny

Reputation: 328

How to include multiple layers within the same dataframe using tmap in R?

I am working with some public datasets, which can be accessed here inside the 'stack_question' folder).

I am trying to create a map of all the supermarkets within the state of Kansas using the tmap library in R. Using ggplot, I generated a map using the following code:

library(pacman)
p_load(sf, tidyverse, tmap)

#Read in data
super <- readRDS('supermarket_pt.RDS')
ct<-st_read("US_tract_2010.shp")
food <- read_csv('FoodAtlas.csv')

#Reproject so datasets are projeted in the same way
super <- st_transform(super, st_crs(ct))

#Change data structure to 'numeric'
ct$GEOID10 <- as.numeric(ct$GEOID10)
food$CensusTract <- as.numeric(food$CensusTract)

#Selct for relevant columns to combine the dataset
food <- food %>% 
  select(CensusTract:County)

#Left join ct and modified food dataset
sup <- left_join(ct, food, by = c('GEOID10' = 'CensusTract'))

#Filter dataset to desired state
ks <- sup %>% 
  filter(State == "Kansas")

#Find the supermarkets in Kansas
super_ks <- super[ks, op = st_within]

#Plot the data
ggplot() +
  geom_sf(data = ks) +
  geom_sf(data = super_ks, color = 'steelblue', shape = 18, size = 2)

The following image is output, which is correct:

enter image description here

I need to make the same image with tmap. The problem is that I am getting an error when I run the following code:

#Set tmap mode
tmap_mode('plot')

#Spatially join data
super_state <- st_join(ks, super_ks, join = st_contains, left = TRUE)
na.omit(super_state)

#Generate KS map
qtm(super_state)+
  tm_bubbles('name', col = 'steelblue')

The error:

Error: size argument of tm_symbols/tm_dots is not a numeric variable

When I try this code, I get an image that produces what I don't want:

tm_shape(super_state) +
  tm_polygons('name')

enter image description here

How can I make my tmap map look like the first one?

Upvotes: 1

Views: 1097

Answers (1)

dieghernan
dieghernan

Reputation: 3402

I tried to replicate the map, but the file FoodAtlas.csv is missing. I think this should work (just using the same data that you used for ggplot2 ):


# Same with tmap, you don't need to  create new spatial objects
tm_shape(ks) +
  tm_polygons() +
  tm_shape(super_ks) +
  tm_dots("steelblue", shape = 18, size = 2)

You are getting the second map because you are using name on col parameter. tmap works a bit different than ggplot2:

  • If you use tm_polygons(col="<variable>") you get a choropleth map. The equivalent in ggplot is geom_sf(aes(fill=<variable>)).
  • If you use tm_polygons(col="red" ) or the name of a color in general you get the shape with each polygon filled with that color (equivalent to geom_sf(fill="<a color>").

So basically, on ggplot2 you need to specifically declare the type of layer (using aes or not, depending on your map) but in tmap this is done depending of the type of variable. See here a full reprex:

library(pacman)
p_load(sf, tidyverse, tmap, giscoR)


# Mock your data
ks <- gisco_get_nuts(country = "Belgium", nuts_level = 3)
super_ks <- gisco_get_healthcare(country = "Belgium")

super_ks <- st_transform(super_ks, st_crs(ks))


# Test1: Simple map, plot just the layers
ggplot() +
  geom_sf(data = ks) +
  geom_sf(data = super_ks, color = 'steelblue', shape = 18, size = 2)

enter image description here

# Same with tmap
tm_shape(ks) +
  tm_polygons() +
  tm_shape(super_ks) +
  tm_dots("steelblue", shape = 18, size=.5)

enter image description here


# Test 2: Using aes/col: Thematic map

ggplot() +
  geom_sf(data=ks, aes(fill=NUTS_ID)) +
  geom_sf(data = super_ks, color = 'steelblue', shape = 18, size = 2)

enter image description here


# Same with tmap
tm_shape(ks) +
  tm_polygons("NUTS_ID") +
  tm_shape(super_ks) +
  tm_dots("steelblue", shape = 18, size=.5)

enter image description here

Upvotes: 1

Related Questions