[GIS] Why does Leaflet with provider tiles not draw markers as expected

leafletleaflet-rrshiny

I'm working with Leaflet maps in Shiny for R. I'm producing a map with some markers on it. When I use addTiles () for my base map, everything works as expected. However with addProviderTiles (), the markers don't appear on the map. Only after I trigger an action that causes them to be redrawn, they show up as I would expect them.

This doesn't seem to be mentioned in the vignettes, so I'm not sure if it's a bug or I'm missing some parameter options.

I made a reproducible example. If you run it as is, the markers will appear normally. If you comment line 13 and uncomment line 14, the markers won't work initially. I added an observer () that redraws the markers when you click on the map.

library(shiny)
library(sp)
library(leaflet)

ui <- bootstrapPage (
                leafletOutput("map", width="80%", height="800px"))

server <- function(input, output, session) {
  output$map <- renderLeaflet({
      print ("render tiles")
      b <- bbox (breweries91)
      leaflet (breweries91) %>%
      addTiles () %>%
#      addProviderTiles (providers$CartoDB.Positron) %>%
      fitBounds (b[1], b[2], b[3], b[4])
      })

  observe ({
      print ("make markers")
      leafletProxy ("map", data = breweries91) %>%
      addAwesomeMarkers ()
      cl <- input$map_click
      if (!is.null (cl))
          print ("click")
      })
}
shinyApp (ui, server)

Edit software versions:

  • Ubuntu: 16.04.2
  • Mozilla Firefox 52.0.1
  • R: 3.3.3
  • leaflet: 1.1.0
  • shiny: 1.0.0

Best Answer

Using the RStudio IDE, your code worked fine in the Viewer Pane. However, it didn't worked using Firefox 52.0.1 browser.

Commenting the observer() function and adding addAwesomeMarkers () to the renderLeaflet({}) worked fine in Firefox 52.0.1 browser. I think Firefox 52.0.1 browser was right, because if you are using an observer function that mean it will draw the markers after the input$map_click action was done and never before that.

One property of the observer function is:

"An observer is like a reactive expression in that it can read reactive values and call reactive expressions ..." (from Shiny package documentation)

Try the suggested code below from your reproducible example:

library(shiny)
library(sp)
library(leaflet)

ui <- bootstrapPage (leafletOutput("map", width = "80%", height = "800px"))

server <- function(input, output, session) {
  output$map <- renderLeaflet({
    print ("render tiles")
    b <- bbox (breweries91)
    leaflet (breweries91) %>%
      # addTiles () %>%
      addProviderTiles (providers$CartoDB.Positron) %>%
      addAwesomeMarkers () %>%
      fitBounds (b[1], b[2], b[3], b[4])
  })

  # observe ({
  #   print ("make markers")
  #   leafletProxy ("map", data = breweries91) %>%
  #     addAwesomeMarkers ()
  #   cl <- input$map_click
  #   if (!is.null (cl))
  #     print ("click")
  # })
}
shinyApp (ui, server)

Also, if you want to preserve the observe function but not to draw the markers at the begining, you can use it in this way:

observe ({
     print ("observe function called")
  #   leafletProxy ("map", data = breweries91) %>%
  #   addAwesomeMarkers ()
     cl <- input$map_click
     if (!is.null (cl))
       print ("click")
   })