[英]How to observe and track a single value from two renderUI elements in shiny
这是一个简单的应用程序,用户可以在其中键入 (numericInput, bpm_numeric) 或滑动 (sliderInput, bpm_slider) 输入值。 这两个 UI 元素都应与任一选择保持同步。 但是,输出只需要跟踪一次。 下面我跟踪它两次,但我只需要用户的一份“选择/输入”副本。 我想我需要使用reactiveValues
,但我不确定该方法。
library(shiny)
ui <- fluidPage(
titlePanel("Reverb & Delay Calculator"),
sidebarLayout(
sidebarPanel(
uiOutput("bpm_numeric"),
uiOutput("bpm_slider")
),
mainPanel(
p("Numeric value is:"),
verbatimTextOutput("numeric_val"),
p("Slider value is:"),
verbatimTextOutput("slider_val")
)
)
)
server <- function(input, output, session) {
output$bpm_numeric = renderUI({
numericInput(
"bpm_numeric",
"BPM Numeric",
value = 60, min = 40, max = 300
)
})
output$bpm_slider = renderUI({
sliderInput(
"bpm_slider",
"BPM Slider",
value = 60, min = 40, max = 300
)
})
# See how I can track "both", but really I only need to track "one" since
# they should stay in-sync with one another. Maybe reactiveValues???
output$numeric_val <- renderText({ input$bpm_numeric })
output$slider_val <- renderText({ input$bpm_slider })
observeEvent(input$bpm_numeric, {
val = input$bpm_numeric
updateSliderInput(session, "bpm_slider", value = val)
})
observeEvent(input$bpm_slider, {
val = input$bpm_slider
updateNumericInput(session, "bpm_numeric", value = val)
})
}
shinyApp(ui = ui, server = server)
注意:虽然我目前正在使用uiOuput()
+ renderUI()
+ update___Input()
,但这不一定是必需的。 如果输入 UI 保持同步,我对其他方法持开放态度,我有一份同步输出的副本。
这是一个想法。 它能够概括了一点,但它仍然依赖于你明知要以这种方式结合起来哪个ID。
对您当前示例的修改:
defbmp <- 60
,有助于确保所有元素都从同一个位置开始。useval
反应之外,将所有对input$bpm_numeric
或_slider
引用替换为useval()
。lastval
反应值。useval <- eventReactive({},{})
块,取决于每个要同步的元素。 最终产品(不包括ui
组件,那里没有变化):
defbpm <- 60 # new
server <- function(input, output, session) {
output$bpm_numeric = renderUI({
numericInput(
"bpm_numeric",
"BPM Numeric",
value = defbpm, min = 40, max = 300 # update
)
})
output$bpm_slider = renderUI({
sliderInput(
"bpm_slider",
"BPM Slider",
value = defbpm, min = 40, max = 300 # update
)
})
output$numeric_val <- renderText({ useval() }) # update
output$slider_val <- renderText({ useval() }) # update
lastval <- shiny::reactiveVal(defbpm) # new
useval <- eventReactive({
input$bpm_numeric
input$bpm_slider
}, {
newval <- setdiff(c(input$bpm_numeric, input$bpm_slider), lastval())
if (length(newval) > 0) {
if (newval != input$bpm_numeric) updateNumericInput(session, "bpm_numeric", value = newval)
if (newval != input$bpm_slider) updateSliderInput(session, "bpm_slider", value = newval)
lastval(newval)
}
lastval()
}) # new
}
改善这一点的方法(我目前不知道):
character
向量;eventReactive
以通过编程方式生成条件表达式,我目前还不是一个足以做到这一点的大师; 和numericInput
或sliderInput
(或其他东西),以便更通用地调用update*
函数。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.