Derek Corcoran
Derek Corcoran

Reputation: 4102

Vectors of latitude and longitude in geolocation app in shiny

I am building and app, that includes geolocation captures using the geoloc package

This is an example app:

library(shiny)
library(leaflet)
library(geoloc)

ui <- fluidPage(
  h2("Where Am I?"),
  tags$p("Click the button to get your location"),
  geoloc::button_geoloc("myBtn", "Get my Location"),
  tags$br(),
  textOutput("coords"),
  textOutput("col"),
  leafletOutput("lf")
)

server <- function(input, output) {
  output$coords <- renderText(paste(input$myBtn_lat, input$myBtn_lon, sep = ", "))
  
  Lats <- reactiveValues(Lat = NULL)
  
  observeEvent(input$myBtn_lat, {
    Lats$Lat <- append(Lats$Lat, input$myBtn_lat)
  })
  
  
  output$col <- renderText({
    Lats$Lat
  })
  
  output$lf <- renderLeaflet({
    req(input$myBtn_lon)
    req(input$myBtn_lat)
    leaflet() %>%
      addTiles() %>%
      setView(as.numeric(input$myBtn_lon), as.numeric(input$myBtn_lat), zoom = 17) %>%
      addMarkers(as.numeric(input$myBtn_lon), as.numeric(input$myBtn_lat), label = "You're here!")
  })
}

shinyApp(ui, server)

I have two questions for this:

How to get a vector of latitudes and longitudes with the button

I need this because usually, we like to take 4 or 5 times the location and then use the median.

This has been addressed in this question, however, there are some kinks I can't figure out since the button is a custom one, and the inputs are not input$myBtn, but input$myBtn_lat and input$myBtn_lon, I find it hard to compute. This is what I am trying to do with the observe events

How to transform this into shiny modules

This will go to a larger shiny app, so I would love to generate modules for this, but again, the facto that the input in ui is "myBtn", but then in the server I have 2 inputs (MyBtn_lon and MyBtn_lat), make it very hard to figure out

Any help is welcome

Upvotes: 0

Views: 403

Answers (2)

bdedu
bdedu

Reputation: 393

How about the following code with Shiny modules? I tested and it worked.

library(shiny)
library(leaflet)
library(geoloc)

mapUI <- function(id, label = "Location in map"){
  ns <- NS(id)
  
  tagList(
    geoloc::button_geoloc(ns("myBtn"), "Get my Location"),
    tags$br(),
    textOutput(ns("coords")),
    textOutput(ns("col")),
    textOutput(ns("md")), # for median latitude
    leafletOutput(ns("lf"))
  )
}

mapServer <- function(id){
  moduleServer(
    id,
    function(input, output, session){
      output$coords <- renderText(paste(input$myBtn_lat, input$myBtn_lon, sep = ", "))
      
      Lats <- reactiveValues(Lat = NULL)
      
      observeEvent(input$myBtn, {
        Lats$Lat <- c(Lats$Lat, input$myBtn_lat)
      })
      
      
      output$col <- renderText({
        Lats$Lat 
      })
      
      # add median latitude
      output$md <- renderText({
        req(input$myBtn_lat)
        if(length(Lats$Lat) %% 5 == 0){
          paste0("Median latitute is: ", median(Lats$Lat))
        } 
      })
      
      output$lf <- renderLeaflet({
        req(input$myBtn_lon)
        req(input$myBtn_lat)
        leaflet() %>%
          addTiles() %>%
          setView(as.numeric(input$myBtn_lon), as.numeric(input$myBtn_lat), zoom = 17) %>%
          addMarkers(as.numeric(input$myBtn_lon), as.numeric(input$myBtn_lat), label = "You're here!")
      })
    }
  )
}

ui <- fluidPage(
  h2("Where Am I?"),
  tags$p("Click the button to get your location"),
  mapUI("map1")
)

server <- function(input, output, session) {
  mapServer("map1")
  
}

shinyApp(ui, server)

Upvotes: 1

bdedu
bdedu

Reputation: 393

You should click "myBtn", not "myBtn_lat". So try change observeEvent(input$myBtn_lat to observeEvent(input$myBtn. In addition, what is the purpose to take 4 or 5 times the location? The coordinates do not change or change very little every time you click the button.

Upvotes: 1

Related Questions