R闪亮地图搜索输入框 [英] R Shiny map search input box

查看:111
本文介绍了R闪亮地图搜索输入框的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Google地图中,搜索输入框会在用户输入时自动完成地址.在R Shiny中是否可以通过访问自动完成值来实现此目的,以便与映射包一起使用?

In google maps, the search input box auto completes addresses as a user types. Is there a way to do this in R Shiny with access to the autocomplete value in order to use with a mapping package?

此处有一种javascript方法.我尝试在下面的代码中的R Shiny中使用此方法. SymbolixAU指出使用google_map( search_box = TRUE )是一个简单的解决方案.不幸的是,它在我的代码中不起作用,也因为我希望搜索框与地图分开.

There is a javascript method here. I've tried to use this method in R Shiny in the code below. SymbolixAU pointed out using google_map( search_box = TRUE ) which is a simple solution. Unfortunately it doesn't work in my code and also because I would like the search box to be separate from the map.

以下尝试在页面上按此顺序输入了文本输入my_address,输出文本copy_of_address和googleway地图my_map.

The attempt below has a text input my_address, text output copy_of_address and a googleway map my_map in this order on the page.

预期的行为是用户将文本输入到文本输入my_address中,使其自动完成并带有地址(此方法有效),该地址将被复制到文本输出copy_of_address中(这仅显示键入的内容,而不是自动完成的版本),最后,地图将以该地址为中心.

The intended behaviour is for a user to enter text into text input my_address, have it autocomplete with an address (this works), the address will be copied into text output copy_of_address (this only shows what was typed, not the autocompleted version) and finally the map is to be centred on this address.

看到输入框具有自动完成地址,但是地址和地图的副本仅使用用户输入的文本.

See that the input box has the autocomplete address, however the copy of the address and map is using only the user input text.

在下面的代码中,将MyKey替换为您的google api键(有时可以使用空字符串).

In the code below, replace MyKey with your google api key (sometimes an empty string works).

library(shiny)
library(googleway)

key <- "MyKey"
set_key(key = key)
google_keys()

ui <- shiny::basicPage(

  div(
    textInput(inputId = "my_address", label = "")    
    ,textOutput(outputId = "copy_of_address")
    ,HTML(paste0("
          <script>
            function initAutocomplete() {
            new google.maps.places.Autocomplete(
            (document.getElementById('my_address')),
            {types: ['geocode']}
            );
            }
            </script>
            <script src='https://maps.googleapis.com/maps/api/js?key=", key,"&libraries=places&callback=initAutocomplete'
            async defer></script>
    "))
    ,google_mapOutput(outputId = "my_map")
  )

)

server <- function(input, output) {

  my_address <- reactive({
    input$my_address
  })

  output$copy_of_address <- renderText({
    my_address()
  })

  output$my_map <- renderGoogle_map({
    my_address <- my_address()
    validate(
      need(my_address, "Address not available")
    )

    df <- google_geocode(address = my_address)
    my_coords <- geocode_coordinates(df)
    my_coords <- c(my_coords$lat[1], my_coords$lng[1])

    google_map(
      location = my_coords,
      zoom = 12,
      map_type_control = FALSE,
      zoom_control = FALSE,
      street_view_control = FALSE
    )
  })

}

shinyApp(ui, server)

推荐答案

这对我来说并不容易,但我认为我有一个合理的解决方案.最终归结为仔细地从Google 非常复制和粘贴示例,阅读了有关将Javascript中的消息发送给Shiny的信息,将这些想法整合在一起,并很幸运地尝试了200次...

This wasn't easy for me to figure out, but I think I have a reasonable solution. It ultimately came down to copying and pasting the example from Google very carefully, reading about sending messages from Javascript to Shiny, putting the ideas together, and getting lucky on the 200th attempt...

在适当的时候给予信用:

To Give Credit Where It's Due:

Google的链接: https://developers.google.com/maps/documentation/javascript/examples/places-autocomplete

Google's link: https://developers.google.com/maps/documentation/javascript/examples/places-autocomplete

RStudio的链接: https://shiny.rstudio.com/articles/js -send-message.html

RStudio's Link: https://shiny.rstudio.com/articles/js-send-message.html

我的潜在解决方案:

library(shiny)
library(googleway)

key <- "MyKey"
set_key(key = key)
#google_keys()

ui <- shiny::basicPage(

  div(
    textInput(inputId = "my_address", label = "Type An Address")    
    ,textOutput(outputId = "full_address")
    ,HTML(paste0(" <script> 
                function initAutocomplete() {

                 var autocomplete =   new google.maps.places.Autocomplete(document.getElementById('my_address'),{types: ['geocode']});
                 autocomplete.setFields(['address_components', 'formatted_address',  'geometry', 'icon', 'name']);
                 autocomplete.addListener('place_changed', function() {
                 var place = autocomplete.getPlace();
                 if (!place.geometry) {
                 return;
                 }

                 var addressPretty = place.formatted_address;
                 var address = '';
                 if (place.address_components) {
                 address = [
                 (place.address_components[0] && place.address_components[0].short_name || ''),
                 (place.address_components[1] && place.address_components[1].short_name || ''),
                 (place.address_components[2] && place.address_components[2].short_name || ''),
                 (place.address_components[3] && place.address_components[3].short_name || ''),
                 (place.address_components[4] && place.address_components[4].short_name || ''),
                 (place.address_components[5] && place.address_components[5].short_name || ''),
                 (place.address_components[6] && place.address_components[6].short_name || ''),
                 (place.address_components[7] && place.address_components[7].short_name || '')
                 ].join(' ');
                 }
                 var address_number =''
                 address_number = [(place.address_components[0] && place.address_components[0].short_name || '')]
                 var coords = place.geometry.location;
                 //console.log(address);
                 Shiny.onInputChange('jsValue', address);
                 Shiny.onInputChange('jsValueAddressNumber', address_number);
                 Shiny.onInputChange('jsValuePretty', addressPretty);
                 Shiny.onInputChange('jsValueCoords', coords);});}
                 </script> 
                 <script src='https://maps.googleapis.com/maps/api/js?key=", key,"&libraries=places&callback=initAutocomplete' async defer></script>"))
    ,google_mapOutput(outputId = "my_map")
    )

    )

server <- function(input, output) {

  my_address <- reactive({
    if(!is.null(input$jsValueAddressNumber)){
      if(length(grep(pattern = input$jsValueAddressNumber, x = input$jsValuePretty ))==0){
        final_address<- c(input$jsValueAddressNumber, input$jsValuePretty)
      } else{
        final_address<- input$jsValuePretty
      }
      final_address
    }
  })


  output$full_address <- renderText({
    if(!is.null(my_address())){
      my_address()
    }
  })

  output$my_map <- renderGoogle_map({
    my_address <- my_address()
    shiny::validate(
      need(my_address, "Address not available")
    )

    not_a_df <- google_geocode(address = my_address)
    my_coords <- geocode_coordinates(not_a_df)
    my_coords <- c(my_coords$lat[1], my_coords$lng[1])

    google_map(
      location = my_coords,
      zoom = 12,
      map_type_control = FALSE,
      zoom_control = FALSE,
      street_view_control = FALSE
    )
  })

}

shinyApp(ui, server)

我希望这会有所帮助.干杯! --nate

I hope this helps. Cheers! --nate

这篇关于R闪亮地图搜索输入框的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆