Search code examples
rshinyr-leafletreactable

Leaflet map inside reactable table R Shiny


I would like to include maps in one of the columns of a reactable table, each map would be occupy a cell inside the table. Something like this:

enter image description here

I've tried this:

library(shiny)
library(reactable)
library(leaflet)

ui <- fluidPage(
  mainPanel(
    reactableOutput("table")  
  )
)

server <- function(input, output, session) {
  df_aus <- data.frame(country = "australia",
                        latitude = -35.31,
                        longitude = 149.13)
  
  df_belg <- data.frame(country = "belgium",
                         latitude = 50.83,
                         longitude = 4.33)
  
  map_aus = leaflet(df_aus) %>%
    addProviderTiles("CartoDB.Positron")%>%
    addMarkers(
      label = ~ country,
      layerId = ~ country
      )
  map_belg = leaflet(df_belg) %>%
    addProviderTiles("CartoDB.Positron")%>%
    addMarkers(
      label = ~ country,
      layerId = ~ country
    )
  
  df <- data.frame(country = c("australia","belgium"),
                   values = c(10, 20),
                   map = c(map_aus,map_belg))
  
  output$table <- renderReactable({
    reactable(df)
  })
}

shinyApp(ui, server)

However this returns an error, even though the two maps work. I'm thinking that I might have to include a renderLeaflet() for the columns, but I'm not sure where.

I also tried adding the renderLeaflet() like this: But it did not work either.

  df <- data.frame(country = c("australia","belgium"),
                   values = c(10, 20),
                   map = c(leafletOutput('map_1'), leafletOutput('map_2'))
                   )
  
  output$map_1 <- renderLeaflet(map_aus)
  output$map_2 <- renderLeaflet(map_belg)

Solution

  • You need to do this:

    library(shiny)
    library(reactable)
    library(leaflet)
    
    ui <- fluidPage(
        mainPanel(
            reactableOutput("table")  
        )
    )
    
    server <- function(input, output, session) {
        df_aus <- data.frame(country = "australia",
                             latitude = -35.31,
                             longitude = 149.13)
        
        df_belg <- data.frame(country = "belgium",
                              latitude = 50.83,
                              longitude = 4.33)
        
        map_aus = leaflet(df_aus, height = "100px") %>%
            addProviderTiles("CartoDB.Positron")%>%
            addMarkers(
                label = ~ country,
                layerId = ~ country
            )
        map_belg = leaflet(df_belg, height = "100px") %>%
            addProviderTiles("CartoDB.Positron")%>%
            addMarkers(
                label = ~ country,
                layerId = ~ country
            )
        maps <- list(map_aus, map_belg)
        df <- data.frame(country = c("australia","belgium"),
                         values = c(10, 20),
                         map = NA)
        
        output$table <- renderReactable({
            reactable(data = df, columns = list(
                map = colDef(cell = function(value, index) {
                    maps[[index]]
                })
            ), )
        })
    }
    
    shinyApp(ui, server)
    

    To define a custom column, you need to use colDef and define a function for this column.

    enter image description here