Xaringan: hover position is slightly off when using plotly

Created on 8 Jan 2018  ·  10Comments  ·  Source: yihui/xaringan

Sorry I understand that the support for HTML widgets is experimental and low priority. This may or may not relate to #77 , but thought I'd bring this to your attention anyways... Please feel free to close if this is not of immediate interest.

Basically I wanted to be able to use plotly's hover behavior to display information when doing presentation, but came to realize that the position is a little off. In this below example, especially the (2, 4) dot, the hover text gets displayed when I moused over to somewhere to the left of the actual dot, but not when the mouse is on the dot.

I was using xaringan 0.4 and plotly 4.7.1.

蟹蟹!

````

title: "xaringan + plotly"
subtitle: "Hover is slightly off?"
author: "Yue Jiang"
date: "2018/1/7"
output:
xaringan::moon_reader:
lib_dir: libs
nature:
highlightStyle: github
highlightLines: true

countIncrementalSlides: false

```{r setup, include=FALSE}
options(htmltools.dir.version = FALSE)

# Hover your mouse on these 3 dots and see when the hover text gets displayed

esp the (2, 4) dot
```{r, message=FALSE, fig.width=6, fig.height=4}
library(plotly)
df <- data.frame(x=c(1,2,1), y=c(3,4,5))
plot_ly(data=df, x=~x, y=~y)

Library versions

{r} packageVersion("xaringan") packageVersion("plotly")
````

graphical issues

Most helpful comment

Yeah this has really been bothering me these days... I still haven't been able to track down the exact issue, but have found a workaround: wrapping htmlwidgets inside iframe with widgetframe seems to fix my issue... and also #77. While I continue to look into this, I'm pasting the workaround here.

---
title: "xaringan + plotly"
subtitle: "Hover is slightly off?"
author: "Yue Jiang"
date: "2018/1/25"
output:
  xaringan::moon_reader:
    lib_dir: libs
    nature:
      highlightStyle: github
      highlightLines: true
      countIncrementalSlides: false
---

```{r setup, include=FALSE}
options(htmltools.dir.version = FALSE)
```

# Hover your mouse on these 3 dots and see when the hover text gets displayed

esp the (2, 4) dot
```{r, message=FALSE, fig.width=6, fig.height=4}
library(plotly)
df <- data.frame(x=c(1,2,1), y=c(3,4,5))
plot_ly(data=df, x=~x, y=~y)
```

---
# This is a work around for my issue #98

```{r, message=FALSE}
library(widgetframe)
l <- plot_ly(data=df, x=~x, y=~y)
frameWidget(l, width='60%', height='40%')
```

---
# This also fixes #77

```{r, echo=FALSE}
library(leaflet)
df <- data.frame(
  name = c("Adyghe", "Udi"),
  lat = c(44, 40.9),
  long = c(39.33,47.7236),
  stringsAsFactors = FALSE)

l <- leaflet(df) %>% 
  addTiles() %>%
  addCircleMarkers(~long, ~lat, 
                   popup = ~name,
                   stroke = FALSE,
                   fillOpacity = 1)

frameWidget(l)
```

All 10 comments

You can check if resizing your browser window fixes the issue. If not, I don't have time to investigate this issue, but I do have a conjecture: I think the problem may be solved if we can find a way to hold on HTML widgets (don't initialize them) until the slide is visible. If you are familiar with JavaScript, this will be a good challenge for you to solve.

I'm not the author of the plotly package, and I don't know if plotly widgets are rendered or not when a slide is not visible, but in my DT package, I'll hold on when the DT widget does not have non-zero width/height:

https://github.com/rstudio/DT/blob/f27ce3232e7eff1bc71ec3842449f424ea7177f5/inst/htmlwidgets/datatables.js#L112-L115

and render the widget when the resize event is triggered:

https://github.com/rstudio/DT/blob/f27ce3232e7eff1bc71ec3842449f424ea7177f5/inst/htmlwidgets/datatables.js#L989-L990

In xaringan, I'll manually trigger the resize event when the afterShowSlide event is triggered:

https://github.com/yihui/xaringan/blob/master/inst/rmarkdown/templates/xaringan/resources/js/show-widgets.js

This works (actually I have never verified it by myself) because the HTML widgets framework triggers the resize handler of the widget when the resize event on the window is triggered:

https://github.com/ramnathv/htmlwidgets/blob/18687ee29485ca4852044bde61499e7418bae44b/inst/www/htmlwidgets.js#L567-L582

I guess the same idea can be used to fix #62 (do not render math expressions until the slide is visible).

Thanks Yihui! Resizing the browser definitely affects the issue, sometimes make it better sometimes worse. And it also seems to be browser dependent, i.e. chrome, safari and firefox has this issue to different degrees. Thanks for pointing out a direction - I'm actually not familiar with javascript, but will be happy to take a stab at this, slowly...

It is a complicated issue, and I guess it will be a long way for you to go :)

Yeah this has really been bothering me these days... I still haven't been able to track down the exact issue, but have found a workaround: wrapping htmlwidgets inside iframe with widgetframe seems to fix my issue... and also #77. While I continue to look into this, I'm pasting the workaround here.

---
title: "xaringan + plotly"
subtitle: "Hover is slightly off?"
author: "Yue Jiang"
date: "2018/1/25"
output:
  xaringan::moon_reader:
    lib_dir: libs
    nature:
      highlightStyle: github
      highlightLines: true
      countIncrementalSlides: false
---

```{r setup, include=FALSE}
options(htmltools.dir.version = FALSE)
```

# Hover your mouse on these 3 dots and see when the hover text gets displayed

esp the (2, 4) dot
```{r, message=FALSE, fig.width=6, fig.height=4}
library(plotly)
df <- data.frame(x=c(1,2,1), y=c(3,4,5))
plot_ly(data=df, x=~x, y=~y)
```

---
# This is a work around for my issue #98

```{r, message=FALSE}
library(widgetframe)
l <- plot_ly(data=df, x=~x, y=~y)
frameWidget(l, width='60%', height='40%')
```

---
# This also fixes #77

```{r, echo=FALSE}
library(leaflet)
df <- data.frame(
  name = c("Adyghe", "Udi"),
  lat = c(44, 40.9),
  long = c(39.33,47.7236),
  stringsAsFactors = FALSE)

l <- leaflet(df) %>% 
  addTiles() %>%
  addCircleMarkers(~long, ~lat, 
                   popup = ~name,
                   stroke = FALSE,
                   fillOpacity = 1)

frameWidget(l)
```

@Yue-Jiang thank you for posting the work around. Fixes the off positioning of the leaflet popups.

It also fixes another issue I had. When adding long character vectors to the leaflet popup, the Xaringan new slide command (---) would be ignored after the leaflet map. Essentially, I was unable to add any new slides after the slide with the leaflet map with the popup inserted but your iframe idea saved the day.

As I said in https://github.com/yihui/xaringan/issues/77#issuecomment-468836308, this issue may have been fixed in the current dev version of xaringan. Please test it! Thank you!

Thanks for the note! Hmmm I don't think it works for me yet... I tested with the same example I posted on top of this thread and still find the hovering position being slightly off. I'm using xaringan 0.8.16 and plotly 4.8.0.

Okay. I realized this issue was kind of random. Sometimes it works and sometimes it doesn't. Even when it works, it stops working after I resize the window a little bit. Below is a screencast:

untitled

I have ran out of ideas. I'm not sure if @cpsievert has an idea on top of his head.

At the moment, I am also using frameWidget() to include any plotly plots in {xaringan} slides. This seems to be the best solution for now.

I found this post by Di useful for this!

Was this page helpful?
0 / 5 - 0 ratings

Related issues

burgerga picture burgerga  ·  3Comments

rsangole picture rsangole  ·  3Comments

pat-s picture pat-s  ·  4Comments

royfrancis picture royfrancis  ·  4Comments

tcgriffith picture tcgriffith  ·  4Comments