线宽与x和y值相关(而不是像素大小) - htmlwidgets plotly R

时间:2017-03-05 19:19:46

标签: r plotly htmlwidgets onrender

我的目标是使用htmlwidgets包中的onRender()函数创建一个绘图,用户可以在其中单击一个点并绘制一条灰线。我试图将灰线的粗细设置为变量。

我有一个暂定的MWE工作,如下所示。但是,我目前有一个问题。基本上,线条的宽度根据图像和/或浏览器的大小而改变。这会产生问题,因为某些点会从灰线内部或外部发生变化,具体取决于线宽的变化(由于图像或浏览器调整大小)。但是,无论点是灰线内部还是外部都有一个含义,我需要保持一致。

因此,我试图将线条的粗细指定为相对于x和y轴值的值(而不是屏幕上可以改变大小的像素值)。我希望这会创建一致的灰线宽度,即使用户调整图像或浏览器大小,也不会相对于点更改。这可以在onRender()函数中完成吗?

library(plotly)
library(broom)
library(htmlwidgets)

dat <- mtcars
dat$mpg <- dat$mpg * 10
maxVal = max(abs(dat))
maxRange = c(-1*maxVal, maxVal)

# Specify line width
ciVal = 100

p <- ggplot(data = dat, aes(x=disp,y=mpg)) + geom_point(size=0.5) + coord_cartesian(xlim = c(maxRange[1], maxRange[2]), ylim = c(maxRange[1], maxRange[2]))

ggplotly(p) %>%
  onRender("
           function(el, x, data) {
            el.on('plotly_click', function(e) {

              var trace1 = {
                 x: [0, 600],
                 y: [0, 600],
                 mode: 'lines',
                 line: {
                   color: 'gray',
                   width: 2*data.ciVal
                 },
                 opacity: 0.5
              }

              Plotly.addTraces(el.id, trace1);
           })
          }
          ", data = list(dat=dat, ciVal=ciVal))

注意:此问题是对我提出的上一个问题(Changing line thickness and opacity in scatterplot on onRender() htmlWidgets in R)的补充调整。

1 个答案:

答案 0 :(得分:1)

不是让一条线具有不同的宽度,而是可以有两条线来标记边框并填充其间的空间(fill: 'tonexty')。因此,该线将始终根据您的轴范围和缩放进行调整。

Normal zoom Zoom in

library(plotly)
library(htmlwidgets)

dat <- mtcars
dat$mpg <- dat$mpg * 10
maxVal = max(abs(dat))
maxRange = c(-1*maxVal, maxVal)

p <- ggplot(data = dat, aes(x=disp,y=mpg)) + geom_point(size=0.5) + coord_cartesian(xlim = c(maxRange[1], maxRange[2]), ylim = c(maxRange[1], maxRange[2]))

ggplotly(p) %>%
  onRender("
           function(el, x, data) {
           el.on('plotly_click', function(e) {

           var trace1 = {
             x: [0, 500],
             y: [450, 50],
             mode: 'lines',
             line: {
               color: 'gray',
               width: 2
             },
             opacity: 0.5
           }
           var trace2 = {
             x: [0, 500],
             y: [250, -150],
             mode: 'lines',
             fill: 'tonexty',
             line: {
               color: 'gray',
               width: 2
             },
             opacity: 0.5
           }
           Plotly.addTraces(el.id, trace1);
           Plotly.addTraces(el.id, trace2);

           })
           }
           ", data = list(dat=dat, ciVal=ciVal))