在 R Shiny 中绘图后如何保留曲线?
How to retain the curves after plotting in R Shiny?
我正在构建一个闪亮的应用程序,用户可以在其中向绘图添加不同的曲线,但我无法使绘图保留已添加的曲线。我怎样才能做到这一点?
在下面简化的可重现代码中,总共有 8 种曲线可能性,基于 3 个单选按钮选择,每个单选按钮有 2 个选项。我想将它们保留为单选按钮而不使用复选框,因为在我正在处理的真实应用程序中,将有大约 300 种组合,这些组合太混乱而无法与复选框一起使用。请看下面的代码:
library(shiny)
library(plotly)
library(dplyr)
data111 <-data.frame("x"=1:10, "y"=c(99,98,97,96,95,94,93,92,91,90))
data112 <-data.frame("x"=5:14, "y"=c(79,78,77,76,75,74,73,72,71,70))
data121 <-data.frame("x"=9:18, "y"=c(59,58,57,56,55,54,53,52,51,50))
data122 <-data.frame("x"=3:12, "y"=c(49,48,47,46,45,44,43,42,41,40))
data211 <-data.frame("x"=7:16, "y"=c(29,28,27,26,25,24,23,22,21,20))
data212 <-data.frame("x"=11:20, "y"=c(19,18,17,16,15,14,13,12,11,10))
data221 <-data.frame("x"=2:11, "y"=c(95,94,93,92,91,90,89,88,87,86))
data222 <-data.frame("x"=1:10, "y"=c(45,44,43,42,41,40,39,38,37,36))
ui <- fluidPage(
titlePanel("Curve selection"),
sidebarLayout(
sidebarPanel(
radioButtons(inputId = "option",
label="Choose the option",
choices=c("option1"=1,
"option2"=2),
selected = 1),
radioButtons(inputId = "type",
label="Choose the type",
choices=c("type1"=1,
"type2"=2),
selected = 1),
radioButtons(inputId = "group",
label="Choose the group",
choices=c("group1"=1,
"group2"=2),
selected = 1),
actionButton("add","Add curve to the plot")
),
mainPanel(
plotlyOutput("plot")
)
)
)
server <- function(input, output) {
data <- eventReactive(input$add,{
get(paste0("data",input$option,input$type, input$group))
})
output$plot <- renderPlotly({
data <- data()
p <-plot_ly(type = "scatter", mode="lines")
p<-add_data(p, data) %>% add_trace(p, x= ~x, y = ~y)
p
})
}
shinyApp(ui = ui, server = server)
我希望用户可以在单选按钮选择中选择选项、类型和组,然后添加曲线。之后,重新选择选项、类型和组,并将新曲线添加到图中已有的曲线中。用户应该能够多次执行此操作。您知道如何实现吗?
谢谢!
您将不得不使用一个 reactiveValues
对象,您可以在其中保存已添加的轨迹。
然后你可以使用 add_trace
和 for 循环,例如:
我将您的 eventReactive
更改为 observeEvent
,它将新数据附加到 reactiveValues
列表。
为了防止两次绘制同一个对象,我创建了一个 reactiveValues usedData
对象,它将保存绘图图例名称。如果名称已经在手边,则不会添加任何内容。
server <- function(input, output) {
d <- reactiveValues(a=NULL, name=NULL)
usedData <- reactiveValues(d = NULL)
data <- observeEvent(input$add,{
src = paste0("data",input$option,input$type, input$group)
var <- get(src)
if (src %in% usedData$d) {
print("Data is already plotted")
req(F)
}
if (is.null(d$a)) {
d$a <- list(var)
d$name = list(src)
usedData$d <- src
} else {
d$a <- append(d$a, list(var))
d$name = append(d$name, list(src))
usedData$d <- append(usedData$d, src)
}
})
output$plot <- renderPlotly({
req(d$a)
data <- d$a
names = d$name
p <- plot_ly(data = data[[1]], type = "scatter", mode="lines")
if (length(data) == 1) {
p <- add_trace(p, x= ~x, y = ~y, name = names)
} else {
for (i in 1:length(data)) {
d <- data[[i]]
p <- add_trace(p, data = d, x= ~x, y = ~y, type = "scatter", mode="lines", name = names[[i]])
}
}
p
})
}
我正在构建一个闪亮的应用程序,用户可以在其中向绘图添加不同的曲线,但我无法使绘图保留已添加的曲线。我怎样才能做到这一点?
在下面简化的可重现代码中,总共有 8 种曲线可能性,基于 3 个单选按钮选择,每个单选按钮有 2 个选项。我想将它们保留为单选按钮而不使用复选框,因为在我正在处理的真实应用程序中,将有大约 300 种组合,这些组合太混乱而无法与复选框一起使用。请看下面的代码:
library(shiny)
library(plotly)
library(dplyr)
data111 <-data.frame("x"=1:10, "y"=c(99,98,97,96,95,94,93,92,91,90))
data112 <-data.frame("x"=5:14, "y"=c(79,78,77,76,75,74,73,72,71,70))
data121 <-data.frame("x"=9:18, "y"=c(59,58,57,56,55,54,53,52,51,50))
data122 <-data.frame("x"=3:12, "y"=c(49,48,47,46,45,44,43,42,41,40))
data211 <-data.frame("x"=7:16, "y"=c(29,28,27,26,25,24,23,22,21,20))
data212 <-data.frame("x"=11:20, "y"=c(19,18,17,16,15,14,13,12,11,10))
data221 <-data.frame("x"=2:11, "y"=c(95,94,93,92,91,90,89,88,87,86))
data222 <-data.frame("x"=1:10, "y"=c(45,44,43,42,41,40,39,38,37,36))
ui <- fluidPage(
titlePanel("Curve selection"),
sidebarLayout(
sidebarPanel(
radioButtons(inputId = "option",
label="Choose the option",
choices=c("option1"=1,
"option2"=2),
selected = 1),
radioButtons(inputId = "type",
label="Choose the type",
choices=c("type1"=1,
"type2"=2),
selected = 1),
radioButtons(inputId = "group",
label="Choose the group",
choices=c("group1"=1,
"group2"=2),
selected = 1),
actionButton("add","Add curve to the plot")
),
mainPanel(
plotlyOutput("plot")
)
)
)
server <- function(input, output) {
data <- eventReactive(input$add,{
get(paste0("data",input$option,input$type, input$group))
})
output$plot <- renderPlotly({
data <- data()
p <-plot_ly(type = "scatter", mode="lines")
p<-add_data(p, data) %>% add_trace(p, x= ~x, y = ~y)
p
})
}
shinyApp(ui = ui, server = server)
我希望用户可以在单选按钮选择中选择选项、类型和组,然后添加曲线。之后,重新选择选项、类型和组,并将新曲线添加到图中已有的曲线中。用户应该能够多次执行此操作。您知道如何实现吗?
谢谢!
您将不得不使用一个 reactiveValues
对象,您可以在其中保存已添加的轨迹。
然后你可以使用 add_trace
和 for 循环,例如:
我将您的 eventReactive
更改为 observeEvent
,它将新数据附加到 reactiveValues
列表。
为了防止两次绘制同一个对象,我创建了一个 reactiveValues usedData
对象,它将保存绘图图例名称。如果名称已经在手边,则不会添加任何内容。
server <- function(input, output) {
d <- reactiveValues(a=NULL, name=NULL)
usedData <- reactiveValues(d = NULL)
data <- observeEvent(input$add,{
src = paste0("data",input$option,input$type, input$group)
var <- get(src)
if (src %in% usedData$d) {
print("Data is already plotted")
req(F)
}
if (is.null(d$a)) {
d$a <- list(var)
d$name = list(src)
usedData$d <- src
} else {
d$a <- append(d$a, list(var))
d$name = append(d$name, list(src))
usedData$d <- append(usedData$d, src)
}
})
output$plot <- renderPlotly({
req(d$a)
data <- d$a
names = d$name
p <- plot_ly(data = data[[1]], type = "scatter", mode="lines")
if (length(data) == 1) {
p <- add_trace(p, x= ~x, y = ~y, name = names)
} else {
for (i in 1:length(data)) {
d <- data[[i]]
p <- add_trace(p, data = d, x= ~x, y = ~y, type = "scatter", mode="lines", name = names[[i]])
}
}
p
})
}