rr-leafletchoropleth

How to create a choropleth on a leaflet map?


Problem

I have loaded in the shapefile of the UK, no issues. Lets call this FILE1. I also have a data frame file with 2 columns: Longitude, Latitude. lets call this FILE2. I am trying to plot the coordinates of FILE2 onto the shapefile map of FILE1 and create a choropleth map

I am also receiving the following error:

Error in polygonData.default(data) : Don't know how to get path data from object of class tbl_df

CODE

I have taken the code from this question: Choropleth maps in R using leaflet package and adapted it to suit my data

#Plot the Leaflet map----
mymap <- leaflet() %>% 
  addProviderTiles("OpenStreetMap.Mapnik") %>%
  addPolygons(data = coords, #This is data frame of U.K long and lat
              fillColor = ~palette(file$TotalByPostcode), 
              fillOpacity = 0.6,       
              color = "darkgrey",      
              weight = 1.5,            
              popup = popup1)%>%
  addLegend(position = 'topleft', 
            colors = c('#fee0d2',
                       '#fcbba1',
                       '#fc9272',
                       '#fb6a4a',
                       '#ef3b2c',
                       '#cb181d',
                       '#a50f15',
                       '#67000d'), 
            labels = c('0',"","","","","","",'100'), 
            opacity = 0.6,      
            title = "Totals") 

print(map)

Here is my data frame:

Data Frame


Solution

  • I do not have your data in my hand. But I guess that you misunderstood one thing about the leaflet package. If you type ?leaflet in your R Console, you would see the following information in the help page.

    a data object. Currently supported objects are matrices, data frames, spatial objects from the sp package (SpatialPoints, SpatialPointsDataFrame, Polygon, Polygons, SpatialPolygons, SpatialPolygonsDataFrame, Line, Lines, SpatialLines, and SpatialLinesDataFrame), and spatial data frames from the sf package.

    This tells you what kind of data objects leaflet can take. Keeping this point in your mind, and let's check the following two cases.

    CASE1: SpatialPolygonsDataFrame

    In this case, I downloaded a SpatialPolygonsDataFrame using the raster package, which is called UK in my code. I also create a dummy data frame called mydf. In addPolygons(), I am using a spatial object. A map nicely came out.

    library(raster)
    library(leaflet)
    library(tidyverse)
    
    # Get UK polygon data
    UK <- getData("GADM", country = "GB", level = 2)
    
    ### Create dummy data
    set.seed(111)
    mydf <- data.frame(place = unique(UK$NAME_2),
                       value = sample.int(n = 1000000, size = n_distinct(UK$NAME_2), replace = TRUE))
    
    ### Create five colors for fill
    mypal <- colorQuantile(palette = "RdYlBu", domain = mydf$value, n = 5, reverse = TRUE)
    
    leaflet() %>% 
    addProviderTiles("OpenStreetMap.Mapnik") %>%
    setView(lat = 55, lng = -3, zoom = 6) %>%
    addPolygons(data = UK,
                stroke = FALSE, smoothFactor = 0.2, fillOpacity = 0.3,
                fillColor = ~mypal(mydf$value),
                popup = paste("Region: ", UK$NAME_2, "<br>",
                              "Value: ", mydf$value, "<br>")) %>%
    addLegend(position = "bottomright", pal = mypal, values = mydf$value,
              title = "UK value",
              opacity = 1)
    

    enter image description here

    CASE2: tbl_df

    Now let's see what happens with a regular data frame. I am not sure what kind of data you exactly have. But, one thing for sure is that it has tbl_df in class. I wanted to make sure that an object has tbl_df in class. So I did the following. I converted the polygon data (i.e., UK) to a data frame. Let's check the class.

    x <- as_data_frame(fortify(UK))
    class(x)
    #[1] "tbl_df"     "tbl"        "data.frame"
    

    Before we move on, I want to mention again that you cannot draw a polygon with a normal data frame including one with tbl_df in class. This is what I said at the beginning of this post. Hence, the following code, which I just changed UK to x, returned an error message.

    leaflet() %>% 
    addProviderTiles("OpenStreetMap.Mapnik") %>%
    setView(lat = 55, lng = -3, zoom = 6) %>%
    addPolygons(data = x,
                stroke = FALSE, smoothFactor = 0.2, fillOpacity = 0.3,
                fillColor = ~mypal(mydf$value)) %>%
    addLegend(position = "bottomright", pal = mypal, values = mydf$value,
              title = "UK value",
              opacity = 1)  
    

    Error in polygonData.default(data) : Don't know how to get path data from object of class tbl_df

    I hope this demonstration clears up your mind. The lesson to take is: Use a spatial class object from the sp or sf package. In your case, you would perhaps want to use FILE1 in addPolygons(). Make sure that it is a spatial object. If you have a right file, you will see polygons on top of the tile map.