在交互式地块中提取鼠标点击的精确坐标

时间:2018-01-30 16:53:58

标签: r ggplot2 shiny plotly interactive

简而言之:我正在寻找一种方法来获取由ggplot2ggplotly呈现的交互式x / y散点图中一系列鼠标位置(点击次数)的精确坐标

我知道plotly(以及R的其他几个交互式绘图包)可以与Shiny结合使用,其中box或lazzo select可以返回所有数据点的列表。选定的子空间。在我正在分析的大多数数据集中,这个列表将是巨大的,然而,我需要能够以R markdown格式重复进行分析(写一些,大多数小于5-6,点坐标更多可读的)。此外,我必须知道点击的确切位置,以便能够在不同数据集中的相同多边形点内提取点,因此一个数据集中选择内的点列表无用。

网格包中的grid.locator()函数几乎完成了我正在寻找的函数(包含在fx gglocator中的函数),但我希望有一种方法可以在交互式绘图中执行相同操作由plotly(或者其他我不知道的东西?)渲染,因为数据集通常是巨大的(见下图),因此能够以交互方式放大和缩小非常受欢迎迭代分析。

enter image description here

通常情况下,我必须多次重新调整轴的大小以模拟放大和缩小,这样做很多次都会耗费精力。正如你在上面的图中所看到的,图中有很多信息需要探索(图中的内存大约为300MB)。

以下是我在静态情节中使用reprex进行此操作的grid.locatorlibrary(ggplot2) library(grid) p <- ggplot(mtcars, aes(wt, mpg)) + geom_point() locator <- function(p) { # Build ggplot object ggobj <- ggplot_build(p) # Extract coordinates xr <- ggobj$layout$panel_ranges[[1]]$x.range yr <- ggobj$layout$panel_ranges[[1]]$y.range # Variable for selected points selection <- data.frame(x = as.numeric(), y = as.numeric()) colnames(selection) <- c(ggobj$plot$mapping$x, ggobj$plot$mapping$y) # Detect and move to plot area viewport suppressWarnings(print(ggobj$plot)) panels <- unlist(current.vpTree()) %>% grep("panel", ., fixed = TRUE, value = TRUE) p_n <- length(panels) seekViewport(panels, recording=TRUE) pushViewport(viewport(width=1, height=1)) # Select point, plot, store and repeat for (i in 1:10){ tmp <- grid.locator('native') if (is.null(tmp)) break grid.points(tmp$x,tmp$y, pch = 16, gp=gpar(cex=0.5, col="darkred")) selection[i, ] <- as.numeric(tmp) } grid.polygon(x= unit(selection[,1], "native"), y= unit(selection[,2], "native"), gp=gpar(fill=NA)) #return a data frame with the coordinates of the selection return(selection) } locator(p)

plotly_click

并从此处使用point.in.polygon函数根据选择对数据进行子集化。

一个可能的解决方案是将100x100的不可见点添加到绘图中,然后在Shiny应用程序中使用event_data()的{​​{1}}功能,但这根本不是理想的。

提前感谢您的想法或解决方案,我希望我的问题足够明确。

- Kasper

1 个答案:

答案 0 :(得分:0)

我用了ggplot2。除了https://shiny.rstudio.com/articles/plot-interaction.html的资料之外,我还要提及以下内容:

首先,在创建绘图时,请勿在“ renderPlot()”内使用“ print()”,否则坐标将是错误的。例如,如果用户界面中包含以下内容:

plotOutput("myplot", click = "myclick")

服务器中的以下内容将起作用:

output$myplot <- renderPlot({
    p = ggplot(data = mtcars, aes(x=mpg, y=hp)) + geom_point()
    p
})

但是,点击坐标会错误:

output$myplot <- renderPlot({
    p = ggplot(data = mtcars, aes(x=mpg, y=hp)) + geom_point()
    print(p)
})

然后,您可以通过添加到服务器来存储坐标:

mydata = reactiveValues(x_values = c(), y_values = c())

observeEvent(input$myclick, {

    mydata$x_values = c(mydata$x_values, input$myclick$x)
    mydata$y_values = c(mydata$y_values, input$myclick$y)

})

除了X-Y坐标外,当将facep与ggplot2一起使用时,您还可以通过以下方式引用所单击的facet面板

input$myclick$panelvar1