【问题标题】:How do you calculate data taken from textInput boxes in Shiny?您如何计算从 Shiny 中的 textInput 框中获取的数据?
【发布时间】:2016-07-11 01:02:42
【问题描述】:

用户界面代码:

===

library(shiny)

  shinyUI(

    # Use a fluid Bootstrap layout
    fluidPage(    


      # Generate a row with a sidebar
      sidebarLayout(      


        # Define the sidebar with one input
        sidebarPanel(
          sliderInput("capacity", "Current Capacity:", 
                      min=0, max=100, value=10),
          c(list(
            textInput("service", "Service Component Name", ""),
            actionButton("addbtn", "Add Component"))),
            #lapply(seq(10), function(i) uiOutput(paste0("ui", i)))

            br(),
            br(), 
            br(),
            br(),
            br(),
          actionButton("calcbtn", "Calculate Projection")




        ),



        # Create a spot for the barplot
        mainPanel(
          textInput("inputWork","Volume", width="200px"),
          textInput("inputGrowth","Growth Rate", width="100px"),
          lapply(seq(10), function(i) uiOutput(paste0("ui", i)))
          #tags$p("Web"),
          #verbatimTextOutput("input_type_text")

        )

      )
    )
  )

服务器代码:

   server <- function(input, output) 
{
  observeEvent(input$addbtn, {
    n <- isolate(input$addbtn)
    if (n == 0) return()

    # create n-th pair of text input and output
    output[[paste0("ui", n)]] <- renderUI(
      list(textInput(paste0("textin", n), isolate(input$service)),
           textOutput(paste0("textout", n))))

    # display something in the output
    output[[paste0("textout", n)]] <- renderText({
      work<-as.numeric(input$inputWork)
      growth<-as.numeric(input$inputGrowth)
      print(growth)


     #paste("projection", (100+growth)*as.numeric(input[[paste0("textin", n)]]))
    })
  })
  observeEvent(input$calcbtn, {
    n <- isolate(input$calcbtn)
    if (n == 0) return()

    output[[paste0("textout", n)]] <- renderText({
      work<-as.numeric(input$inputWork)
      growth<-as.numeric(input$inputGrowth)
      project<-growth+as.numeric(input$service)

      print(growth)
      print(project)

      paste("projection", ((1+growth/100)*as.numeric(input[[paste0("textin", n)]])))
    })
  })
}

这就是我想要做的。此代码将有一个初始文本框和提交按钮。用户在第一个输入文本中放置一个文本,单击提交按钮,在主面板中生成一个新文本。用户可以多次执行此操作以在主面板中创建多个文本输入框。

我在主面板顶部还有一个静态的另一个 inputText 框,标记为 Workload。

所以,这就是我想要做的:

  1. 用户将在工作负载 textIntut 中插入数据(它需要数字)。
  2. 用户将数据插入到其他动态生成的文本输入框中(都必须是数字)。
  3. 我将从工作负载和所有其他文本框获取值,进行一些计算和预测,并在每个动态生成的文本输入框旁边显示数据,如果我可以在生成的文本框旁边插入文本框以显示我的输出,那就太好了.

例如,我的工作负载中有数据,我生成了 Web_server、App_server 文本输入框。我将从工作负载中获取数据并除以 web_server 中的数据,并将其显示在 web_server 文本输入框旁边(在文本框中显示数据),对 app_server 文本输入框执行相同操作。

任何想法我可以如何在闪亮的情况下做到这一点?这就是我想要完成的图像。鉴于来自用户的工作负载增长率和来自用户输入部分的其他输入,我将不得不计算并填充相应的文本框。

【问题讨论】:

  • 假设calcbtn 是在 UI 中的某处定义的,那么单击它时的预期行为是什么?这会更新所有动态创建的 textOutput,还是只更新其中一个?
  • 您的代码会出现这种行为。它会一一更新textOutput。另外,我从代码中猜想,即使您更改textInput 并再次单击calcbtntextOutput 也不会再更新。现在,单击calcbtn 时,您的预期行为是什么?
  • 提问时,不要分别复制粘贴ui.Rserver.R。人们必须使用它们创建一个文件夹,并创建两个文件只是为了尝试您的代码。相反,准备一组代码,人们可以简单地将其复制到他或她的编辑器中并运行它。
  • 不幸的是,没有。收到答案后,您似乎正在更新您的问题。你不应该那样做,因为如果你改变问题,这个帖子对以后看到这个的其他人来说毫无用处。如果您的原始问题得到解决,请接受并在必要时创建一个新线程。
  • 另外,在提问的时候,尽量做一个最小的可复现的例子。您当前的问题听起来像是在要求人们识别代码中的错误。相反,只需描述你想做什么,以及你是如何陷入困境的。然后人们可以为您提供更多帮助。

标签: r shiny


【解决方案1】:

以下代码实现:

  1. 单击按钮时添加文本输入(和输出)(最多 10 个)。
  2. 每个文本输出都使用输入信息显示一些消息。

注意:

  • 文本输出显示在输入下方而不是旁边。这更多是关于设计问题。我对 HTML 或 CSS 不是很熟悉,抱歉。
  • 这根本不进行计算。您的任务是添加更多组件并根据需要更改renderText 的内容。
  • 我使用textOutput 来显示计算结果,但您的意图可能是使用textInput。通常,您应该使用textOutput 来显示某些内容,尽管可以将输入对象用作输出对象。
  • 我使用了textInput,但如果输入应始终为数字,您可以改用numericInput,正如其中一位cmets 所建议的那样。

玩得开心。

library(shiny)

ui <- c(list(
  textInput("service", "Service Component Name", ""),
  actionButton("addbtn", "add")),
  lapply(seq(10), function(i) uiOutput(paste0("ui", i)))
)


server <- function(input, output) 
{
  observeEvent(input$addbtn, {
    n <- input$addbtn
    if (n == 0) return()
    if (n > 10) return()

    # create n-th pair of text input and output
    output[[paste0("ui", n)]] <- renderUI(
      list(textInput(paste0("textin", n), isolate(input$service)),
           textOutput(paste0("textout", n))))

    # display something in the output
    output[[paste0("textout", n)]] <- renderText({
      paste("you wrote", input[[paste0("textin", n)]])
    })
  })
}

runApp(list(ui = ui, server = server))

【讨论】:

  • 对不起,我忘了提。输出需要由命令按钮生成。一旦所有输入到位,用户需要能够按下提交按钮,输出框将被填充。你能修改这个吗,我从那里拿来。再次感谢!!!
  • 还有一个按钮可以清除所有字段而不刷新页面?
  • Here 是一种清除所有字段的方法
  • 你也可以这样做。添加一个按钮并重写renderText 部分。这是你的任务!提示:isolateobserveEvent
  • @user1471980 您可以使用reset() 包中的reset() 函数来清除输入。
【解决方案2】:

实现您的愿望的一些技巧是:

  • renderText 正在检查其组件中的更改,并在修改组件的值时执行。这就是为什么对于 input$textin1,在文本输入中输入内容后会立即进行更新。
  • isolate 阻止组件触发执行。使用isolate(input$textin1),修改文本输入不会更新textOutput
  • 对于触发renderText 执行的按钮,您只需在renderText 中添加按钮即可。在内部,当单击按钮时,其值会增加。因此,它是函数正在检查的组件的值修订,执行发生。
  • 最后,您需要对所有textin1textin2、...进行此操作

以下代码实现了这一点。检查与上一个答案的区别。

library(shiny)

ui <- c(list(
  textInput("service", "Service Component Name", ""),
  actionButton("addbtn", "add"), 
  actionButton("calcbtn", "calc")),
  lapply(seq(10), function(i) uiOutput(paste0("ui", i)))
)


server <- function(input, output) 
{
  observeEvent(input$addbtn, {
    n <- input$addbtn
    if (n == 0) return()
    if (n > 10) return()

    # create n-th pair of text input and output
    output[[paste0("ui", n)]] <- renderUI(
      list(textInput(paste0("textin", n), isolate(input$service)),
           textOutput(paste0("textout", n))))

    # display something in the output
    output[[paste0("textout", n)]] <- renderText({
      input$calcbtn
      paste("you wrote", isolate(input[[paste0("textin", n)]]))
    })
  })
}

runApp(list(ui = ui, server = server))

【讨论】:

    猜你喜欢
    • 2021-06-21
    • 2018-09-18
    • 1970-01-01
    • 2020-05-22
    • 2011-12-26
    • 2021-04-17
    • 2022-08-12
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多