Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
432 views
in Technique[技术] by (71.8m points)

r - Create a reactive function outside the shiny app

I am trying to decompose the code of my shiny app in order to improve readability and to test some functions using the testthat package.

I would like to have some files (for example server_utils.R) in which I can write "normal" functions that I can test and then make them reactive.

For example I would like to have something like this in server_utils.R:

my_sum <- function(x, y) {
  x + y
}

and something like this in the app:

my_sum_reactive(input$x, input$y)

Do you know if a such behavior is possible?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

Shiny modules is what might help you.

See here: https://shiny.rstudio.com/articles/modules.html

As you can read in the article the desired functionality to pass in input is possible if you wrap the input in a reactive() function. (See the end of the "Writing server functions" section of the article).

You would define the my_sum function as follows: (Note that you have to use the variables a and b as reactives a() and b() and wrap the result in a reactive() function.)

my_sum <- function(input, output, session, a, b) {
  reactive(as.numeric(a()) + as.numeric(b()))
}

And could use it as:

my_sum_reactive <- callModule(my_sum, "id", reactive(input$a), reactive(input$b))

which is then usable as:

my_sum_reactive()

Reproducible example:

library(shiny)

my_sum <- function(input, output, session, a, b) {
  reactive(as.numeric(a()) + as.numeric(b()))
}

ui <- fluidPage({
  fluidRow(
    selectInput("a", "a", 1:3),
    selectInput("b", "b", 1:3),
    textOutput("txt")
  )
})

server <- function(input, output, session) {
  my_sum_reactive <- callModule(my_sum, "id", reactive(input$a), reactive(input$b))
  output$txt <- renderText(paste0("The sum is: ", my_sum_reactive())) 
}
shinyApp(ui, server)

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
...