Применение границ карты листовок для фильтрации данных в Shiny - PullRequest
0 голосов
/ 01 мая 2018

Код ниже предназначен для воспроизведения того, что найдено в в этом примере , за исключением добавления дополнительного параметра для "скорости". Тем не менее, моя ссылка на карту с данными не работает - Может кто-нибудь помочь мне обнаружить ошибку ? Исходный код обновляет таблицу на основе границ карты, в то время как в моем коде изменение масштаба карты не влияет на мою таблицу. Я также не могу заставить фильтр «скорости» работать с таблицей и картой, и это именно та функция, которую я ищу. Любые указатели будут оценены.

library(shiny)
library(magrittr)
library(leaflet)
library(DT)

ships <-
  read.csv(
    "https://raw.githubusercontent.com/Appsilon/crossfilter-demo/master/app/ships.csv"
  )

ui <- shinyUI(fluidPage(
  titlePanel(""),
  sidebarLayout(
    sidebarPanel(width = 3,
                 numericInput(
                   "speed", label = h5("Ship's Speed"), value = 100
                 )),
    mainPanel(tabsetPanel(
      type = "tabs",
      tabPanel(
        "Leaflet",
        leafletOutput("leafletmap", width = "350px"),
        dataTableOutput("tbl")
      )
    ))
  )
))

server <- shinyServer(function(input, output) {
  in_bounding_box <- function(data, lat, long, bounds, speed) {
    data %>%
      dplyr::filter(
        lat > bounds$south &
          lat < bounds$north &
          long < bounds$east & long > bounds$west & ship_speed < input$speed
      )
  }

  output$leafletmap <- renderLeaflet({
    leaflet() %>%
      addProviderTiles("Esri.WorldImagery", group = "ESRI World Imagery") %>%
      addCircleMarkers(
        data = ships,
        ~ long ,
        ~ lat,
        popup =  ~ speed,
        radius = 5 ,
        stroke = FALSE,
        fillOpacity = 0.8,
        popupOptions = popupOptions(closeButton = FALSE)
      )
  })

  data_map <- reactive({
    if (is.null(input$map_bounds)) {
      ships
    } else {
      bounds <- input$map_bounds
      in_bounding_box(ships, lat, long, bounds, speed)
    }
  })

  output$tbl <- DT::renderDataTable({
    DT::datatable(
      data_map(),
      extensions = "Scroller",
      style = "bootstrap",
      class = "compact",
      width = "100%",
      options = list(
        deferRender = TRUE,
        scrollY = 300,
        scroller = TRUE,
        dom = 'tp'
      )
    )
  })


})

shinyApp(ui = ui, server = server)

Ответы [ 2 ]

0 голосов
/ 01 мая 2018

Два небольших изменения:

  • В приведенном вами примере input$map_bounds работает, потому что объект вывода листовки называется map. Однако вы переименовали его в leafletmap, поэтому нам следует обратиться к input$leafletmap_bounds.
  • в выражении dplyr мы должны ссылаться на speed, а не ship_speed.

Рабочий код приведен ниже, надеюсь, это поможет!


library(shiny)
library(magrittr)
library(leaflet)
library(DT)

ships <-
  read.csv(
    "https://raw.githubusercontent.com/Appsilon/crossfilter-demo/master/app/ships.csv"
  )

ui <- shinyUI(fluidPage(
  titlePanel(""),
  sidebarLayout(
    sidebarPanel(width = 3,
                 numericInput(
                   "speed", label = h5("Ship's Speed"), value = 100
                 )),
    mainPanel(tabsetPanel(
      type = "tabs",
      tabPanel(
        "Leaflet",
        leafletOutput("leafletmap", width = "350px"),
        dataTableOutput("tbl")
      )
    ))
  )
))

server <- shinyServer(function(input, output) {
  in_bounding_box <- function(data, lat, long, bounds, speed) {
    data %>%
      dplyr::filter(
        lat > bounds$south &
          lat < bounds$north &
          long < bounds$east & long > bounds$west & speed < input$speed
      )
  }

  output$leafletmap <- renderLeaflet({
    leaflet() %>%
      addProviderTiles("Esri.WorldImagery", group = "ESRI World Imagery") %>%
      addCircleMarkers(
        data = ships,
        ~ long ,
        ~ lat,
        popup =  ~ speed,
        radius = 5 ,
        stroke = FALSE,
        fillOpacity = 0.8,
        popupOptions = popupOptions(closeButton = FALSE)
      )
  })

  data_map <- reactive({
    if (is.null(input$leafletmap_bounds)) {
      ships
    } else {
      bounds <- input$leafletmap_bounds
      in_bounding_box(ships, lat, long, bounds, speed)
    }
  })

  output$tbl <- DT::renderDataTable({
    DT::datatable(
      data_map(),
      extensions = "Scroller",
      style = "bootstrap",
      class = "compact",
      width = "100%",
      options = list(
        deferRender = TRUE,
        scrollY = 300,
        scroller = TRUE,
        dom = 'tp'
      )
    )
  })


})

shinyApp(ui = ui, server = server)
0 голосов
/ 01 мая 2018

Карта листовок, которую вы отображаете, называется leafletmap. Поэтому вместо того, чтобы ссылаться на map_bounds, попробуйте изменить его на leafletmap_bounds:

  data_map <- reactive({
    if (is.null(input$leafletmap_bounds)) {
      ships
    } else {
      bounds <- input$leafletmap_bounds
      in_bounding_box(ships, lat, long, bounds, speed)
    }
  })

Также в фильтре измените ship_speed на speed. Надеюсь, сработает.

...