Overlay Static Images on R Leaflet htmlwidget - html

It it possible to overlay an image to R leaflet maps - or perhaps in the leaflet html - that would stay fixed overtop the map itself?
That is, the image wouldn't be rendered on the map itself, but fixed in the viewport of the browser, so that when you pan or zoom, it would stay the same size in the same position.
For example, I would want to overlay this image, fixed to the top-left of a map rendered with the following R code:
library(htmlwidgets)
library(leaflet)
m <- leaflet() %>%
addTiles() %>%
addMarkers(lng=174.768, lat=-36.852, popup="The birthplace of R")
saveWidget(m, file = "m.html", selfcontained = F)

You can do this with addLogo() from package mapview.
library(htmlwidgets)
library(leaflet)
library(mapview)
img <- "https://www.r-project.org/logo/Rlogo.svg"
m <- leaflet() %>%
addTiles() %>%
addMarkers(lng=174.768, lat=-36.852, popup="The birthplace of R") %>%
addLogo(img, url = "https://www.r-project.org/logo/")
m

In the html, you can add a with a high z-index - which places the inside above the htmlwidget.
For the example above, including the following html above the htmlwidget container overlays the image.
<div style="position:fixed;top:0px;left:0px;z-index:11000;">
<img src="https://www.r-project.org/logo/Rlogo.svg"/>
</div>

I know this is a leaflet question but I wanted to see if it worked with googelway and add_overlay() - and it does:
library(googleway)
map_key <- 'my_map_key'
google_map(key = map_key ) %>%
add_overlay(north = -36.852, east = 174.768, west = 174.668, south = -36.952,
overlay_url = "https://www.r-project.org/logo/Rlogo.svg")

Related

Lag in HTML Outputs within R

I found this post on stackoverflow to make an interactive map in R (second answer): Search button for Leaflet R map?
library(leaflet)
library(inlmisc)
df = read.csv(textConnection(
'Name, Lat, Long
<b>location 1</b>,42.3401, -71.0589
<b>location 2</b>,42.3501, -71.0689'))
map=leaflet(df) %>%
addTiles() %>%
setView(lng=-71.0589,lat=42.3301, zoom=12) %>%
addMarkers(~Long, ~Lat, popup = ~Name, group="marker")
map=inlmisc::AddSearchButton(map, group = "marker", zoom = 15,
textPlaceholder = "Search here")
This code works and produces a map:
But for some reason, when I try to search for one of the locations (e.g. "location 1") - the map seems to take a long time to load and experience a lot of lag. As such, I have waited several minutes and was unable to actually search for one of these cities.
Can someone please help me figure out what I am doing wrong?
Thank you!
The problem occurs when there is no label given for the locations.
library(leaflet)
library(inlmisc)
df <- read.csv(textConnection(
'Name, Lat, Long, Label,
<b>location 1</b>,42.3401, -71.0589, Loc 1
<b>location 2</b>,42.3501, -71.0689, Loc 2'))
map <- leaflet(df) %>%
addTiles() %>%
setView(lng=-71.0589,lat=42.3301, zoom=12) %>%
addMarkers(~Long, ~Lat, popup = ~Name, group="marker", label = ~Label) %>%
inlmisc::AddSearchButton(group = "marker", zoom = 15,
textPlaceholder = "Search here")

Adding "Breaks" in "htmlescape"

I am following this tutorial here (https://rstudio.github.io/leaflet/popups.html):
library(htmltools)
library(leaflet)
df <- read.csv(textConnection(
"Name,Lat,Long
Samurai Noodle,47.597131,-122.327298
Kukai Ramen,47.6154,-122.327157
Tsukushinbo,47.59987,-122.326726"
))
leaflet(df) %>% addTiles() %>%
addMarkers(~Long, ~Lat, popup = ~htmlEscape(Name))
Now, I want to the popups to display the information about the name, the longitude and the latitude (i.e. title + value) - I would like it to say:
Name = Insert Restaurant Name Here
(new line)
Longitude = Insert Longitude Name Here
(new line)
Latitude = Insert Latitude Here
I thought that this could be done as follows:
leaflet(df) %>% addTiles() %>%
addMarkers(~Long, ~Lat, popup = ~htmlEscape(df$Name, df$Lat, df$Long))
But this is giving me the following error:
Error in htmlEscape(df$Name, df$Lat, df$Long) : unused argument (df$Long)
I tried to read about this function (https://www.rdocumentation.org/packages/htmltools/versions/0.5.2/topics/htmlEscape), but there does not seem to be too much information on how to use it. I thought that maybe this might require "combining" all the arguments together:
leaflet(df) %>% addTiles() %>%
addMarkers(~Long, ~Lat, popup = ~htmlEscape(c(df$Name, df$Lat, df$Long)))
But now this only displays the final argument (and that too, without the title).
Is "htmlescape()" able to handle multiple arguments?
Thank you!

How to pass a list of urls contained in a dataframe column into a leaflet map?

I want to make a map using leaflet so that the points in the map have popup notes. Each popup will have a clickable link to redirect to an Internet page. The URLs that will be inserted in such popups are in a column of my data frame, which has thousands of rows. Some toy data:
place <- c("a", "b", "c", "d", "e", "f")
thing <- c("potato","melon","black pepper", "bigfoot","black panther", "orchidaceae")
lat <- c(-17.456, 31.4009, 24.293, -8.956, 8.697, -25.257)
long <- c(-63.658,-111.144,-106.759,-81.029,-83.2052,-52.026)
urls <- c("https://en.wikipedia.org/wiki/Potato",
"https://en.wikipedia.org/wiki/Melon",
"https://en.wikipedia.org/wiki/Black_pepper",
"https://en.wikipedia.org/wiki/Bigfoot",
"https://en.wikipedia.org/wiki/Black_panther",
"https://en.wikipedia.org/wiki/Orchidaceae")
d <- data.frame(place, thing, lat, long, urls)
And this is the code I've been trying to use to plot the map:
library(leaflet)
library(tidyverse)
content <- paste("The", thing,
"occurs near.You can find some information",
"<b><a href=d$urls>here</a></b>")
mymap <- d %>%
leaflet() %>%
addProviderTiles(providers$Esri.WorldImagery, group = "World Imagery") %>%
addProviderTiles(providers$Stamen.TonerLite, group = "Toner Lite") %>%
addLayersControl(baseGroups =
c("Toner Lite", "World Imagery")) %>%
addMarkers(label = thing,
popup = content,
icon = ~ icons(iconUrl = "marker_red.png",
iconWidth = 28, iconHeight = 24))%>%
addMiniMap(
toggleDisplay = TRUE,
tiles = providers$Stamen.TonerLite
) %>%
print()
The problem is that the word "here" in the popup is sort of clickable, but does not redirect me to any internet page. I don't know what to do in this situation where the URLs are contained in a column of my data frame. Besides, I have no experience working with HTML objects. Could anyone help me figure out a way to pass those URLs into the popup notes?
Thanks in advance!
The problem is with href=d$urls in the content, d$urls is assigned as the URL and the actual URL is not referred here. It can be resolved using paste0 function.
The content should be
content <- paste("The", thing,
"occurs near.You can find some information",
paste0("<b>here</b>"))
mymap <- d %>%
leaflet() %>%
addProviderTiles(providers$Esri.WorldImagery, group = "World Imagery") %>%
addProviderTiles(providers$Stamen.TonerLite, group = "Toner Lite") %>%
addLayersControl(baseGroups =
c("Toner Lite", "World Imagery")) %>%
addMarkers(label = thing,
popup = content,
icon = ~ icons(iconUrl = "marker_red.png",
iconWidth = 28, iconHeight = 24))%>%
addMiniMap(
toggleDisplay = TRUE,
tiles = providers$Stamen.TonerLite
) %>%
print()

R: Make interactive maps that can be exported to HTML

I have been working with Leaflet for creating cool interactive maps in R. However, I cannot export the maps, as the background map ends up being grey after export.
library(leaflet)
library(htmlwidgets)
m <- leaflet(data.frame(lat = 55.71654, lng = 12.47484))
m <- addCircles(m, popup = "testpopup")
m <- addTiles(m)
m
saveWidget(m, file="testmap.html", selfcontained = TRUE)
Is there an alternative to Leaflet where you can export your interactive maps as HTML? Or do I have to get into the whole Leaflet/Shiny thing?
As mentioned my #Martin Schmelzer then it all works after updating leaflet through the devtools::install_github('rstudio/leaflet'). Thanks.

How to troubleshoot missing OSM tiles in leaflet html widget?

I need to create a web page that includes an interactive map where users can see popup information about data collected at many locations. Using Rstudio and leaflet on Windows, wanting to use OSM base map tiles.
My leaflet map works fine in Rstudio viewer. However, when the 'knitted' page is viewed in Firefox, no OSM map tiles appear although other components of the map are okay. Similarly OSM tiles missing in saved html widget.
I made a simple example to demonstrate.
```{r}
library(leaflet)
library(htmlwidgets)
rand_lng = function(n = 10) rnorm(n, 145.7, .01)
rand_lat = function(n = 10) rnorm(n, -17, .01)
m = leaflet() %>%
addTiles(group = "OSM (default)") %>%
addProviderTiles("Esri.WorldImagery") %>%
addCircleMarkers(rand_lng(5), rand_lat(5), group = "Points")%>%
addLayersControl(
baseGroups = c("OSM (default)","Esri.WorldImagery"),
overlayGroups = c("Points"),
options = layersControlOptions(collapsed = FALSE)) %>%
setView(lng = 145.7, lat = -17, zoom = 12)
m
saveWidget(m, "leaflet_OSMplusEsri.html")
```
This is the output I get in Rstudio viewer, with OSM tiles selected and displayed correctly. When selected, Esri tiles are correct also.
This is the html file shown in Firefox, where OSM tiles do not display despite being selected.
I've been searching all day without discovering how to troubleshoot this. As a newbie perhaps I'm missing something obvious?
I will be very grateful for advice: how to troubleshoot this problem in simple steps?
Took a long time, but I eventually resolved this. In case it helps anyone else, here is the revised version that works properly.
```{r}
library(leaflet)
library(htmlwidgets)
rand_lng = function(n = 10) rnorm(n, 145.7, .01)
rand_lat = function(n = 10) rnorm(n, -17, .01)
m = leaflet() %>%
addProviderTiles(providers$OpenStreetMap, group = "OSM") %>%
addProviderTiles(providers$Esri.WorldImagery, group = "Esri") %>%
addCircleMarkers(rand_lng(5), rand_lat(5), group = "Points")%>%
addMiniMap() %>%
addLayersControl(
baseGroups = c("OSM","Stamen", "Esri"),
overlayGroups = c("Points"),
options = layersControlOptions(collapsed = FALSE)) %>%
setView(lng = 145.7, lat = -17, zoom = 12)
m
saveWidget(m, "leaflet_OSMplusEsri.html")
```
Cause of the problem was addTiles() with default values. I'm not sure why this did not work, hoping someone might be able to explain.