Making a vector reactive - r

I apologise in advance for not having a minimal reproducible example. I tried to make one but didn't manage to reproduce the error.
So I have 2 scripts (ui.R and server.R) in the same folder. At the very start of the server script I want to make a vector a which will fill itself with inputs from 2 selectInputs in the ui-script.
#ui
shinyUI(fluidPage(
fluidRow(
column(selectInput(inputId = "input1",
label = "This is input 1",
choices = c("bad","neutral","good"))
column(selectInput(inputId = "input2",
label = "This is input 2",
choices = c("bad","neutral","good"))
#server
shinyServer(function(input, output) {
a <- c(input$input1, input$input2)
})
b <- b[a]
The user interface part is not the problem, the server part is. When I run the app I get this error:
Error in .getReactiveEnvironment()$currentContext() :
Operation not allowed without an active reactive context. (You tried to do something that can only be done from inside a reactive expression or observer.)
So I realize I have to make this vector a somehow reactive but I fail to see how. I tried using the function reactive:
#server
shinyServer(function(input, output) {
a <- reactive({
c(input$input1, input$input2)
})
})
But off course then I get this error because a is no longer a vector but a function.
invalid subscript type 'closure'

Related

Use reactive input into R code calculations for Shiny

I have a shiny application reading an input from ui and I am unable to follow up with the data from the input in my code. As below:
ui <- fluidPage(
...
selectInput("ISvModels", "Choose:",
choices = c(1000,5000)),
)
server <- function(input, output) {
vModels <- reactive({input$ISvModels})
qtModels <- length(vModels)
qtModels
vtModels <- paste0("M",1:qtModels," n = ",vModels," scenarios")
vtModels
}
And I get:
Warning: Error in as.vector: cannot coerce type 'closure' to vector of type 'character'
I tried all sort of things from observe to renders but nothing works. Seems I'm missing some concepts here, hope you can help. Thanks!
Your server needs an output, some way for what you've calculated to be shown to the user. We can use a textOutput to achieve this.
Below is a minimal example, showing a dropdown box linked to a textbox.
library(shiny)
ui <- fluidPage(
#Dropdown
selectInput("ISvModels", "Choose:", choices = c(1000,5000)),
#Textbox
textOutput("mytext")
)
server <- function(input, output, session) {
#Prepare Textbox Content
output$mytext <- renderText({
qtModels <- length(input$ISvModels)
vtModels <- paste0("M", 1:qtModels, " n = ", input$ISvModels," scenarios")
return(vtModels)
})
}
shinyApp(ui, server)

R Shiny - value of input as a variable

I want to use value selected in input (below) in loop.
ui <- fluidPage(
#User dropbox
selectInput("state", "Choose state", choices=ListaKampani$Nazwa)
#Print table to UI
,tableOutput("table1")
ID_kamp <- reactive({input$state})
for (i in ID_kamp) {print(i)}
How I can use value from input as a variable in code?
In next attempt i tried this code:
library(shiny)
ui <- fluidPage(
selectInput("wyb", "Wybierz", c(1,2,3))
)
server <- function(input, output, session) {
wybor <- reactive(input$wyb)
for (a in 1:wybor()) {print(a)}
}
shinyApp(ui, server)
But i have error:
Error in .getReactiveEnvironment()$currentContext() :
Operation not allowed without an active reactive context. (You tried to do something that can only be done from inside a reactive expression or observer.).
How I can make variable for loop make reactive? Reactive() function is not enough ?

use pre assigned variable inside R shiny function as a parameter

I am creating a survey using R shiny and have the following function at the beginning of my Shiny App:
install.packages("devtools")
spotifydata<-spotifycharts::chart_top200_weekly()
s<-spotifydata$artist
h<-head(s,20)
I want to know if there is anywhere to display the output of variable "h"??
I had the idea of using "selectInput" in the following manner to display each result in a drop down menu fashion.
selectInput("artists","pick 3 artists out of the top 10",
c("h[1]","h[2]","h[3]","h[4]","h[5]","h[6]",
"h[7]","h[8]","h[9]","h[10]"),multiple = TRUE)
I know this produces an error But I want to know if there is a way to emulate this
In the selectInput the variables should be written without quotes like this:
selectInput("artists","pick 3 artists out of the top 10",
c(h[1],h[2],h[3],h[4],h[5],h[6],
h[7],h[8],h[9],h[10]),multiple = TRUE)
Following is an app showing the working of the same:
library(shiny)
spotifydata<-spotifycharts::chart_top200_weekly()
s<-spotifydata$artist
h<-head(s,20)
ui <- fluidPage(
selectInput("artists","pick 3 artists out of the top 10",
c(h[1],h[2],h[3],h[4],h[5],h[6],
h[7],h[8],h[9],h[10]),multiple = TRUE)
)
server <- function(input, output)
{}
shinyApp(ui, server)
The output is as follows:
Please note that with this approach the variable h is shared between different user sessions.
If you don't want the variable h to be shared between different user sessions you can use the following approach, where we get h value within the server function and update the choices of select input using the function updateSelectInput
ui <- fluidPage(
selectInput("artists","pick 3 artists out of the top 10",
choices = c(), multiple = TRUE)
)
server <- function(input, output, session)
{
observe({
spotifydata<-spotifycharts::chart_top200_weekly()
s<-spotifydata$artist
h<-head(s,20)
updateSelectInput(session, inputId = "artists", choices = c(h[1],h[2],h[3],h[4],h[5],h[6],
h[7],h[8],h[9],h[10]))
})
}
shinyApp(ui, server)

"Error in formatNoSci(value) : argument "value" is missing, with no default" in Shiny

I have a very simple Shiny.
For some reason I get the errors
Error in formatNoSci(value) : argument "value" is missing, with no default
and
Error in force(ui) : object 'ui' not found.
I've googled these errors and can't find anything.
I can deduce that the ui isn't getting built for some reason, but I don't know why and I have no clue what formatNoSci does.
DF_custs <- data.frame(ID=c(1,2,3,3), val=c(10, 20, 100, 200))
## app.R ##
server <- function(input, output) {
get_cust <- reactive({
cust <- DF_custs[which(DF_custs$ID == input$num), ]
return(cust$val)})
output$result <- renderText({
ans <- get_cust()
paste("You chose: ", ans)})
}
ui <- fluidPage(
numericInput(inputId="num", label="Pick an ID: "),
fluidRow(
column(1,
fluidRow(
wellPanel(
mainPanel(textOutput("result"))))))
)
shinyApp(ui = ui, server = server)
Any advice would be greatly appreciated.
As per #Matt's comment, this is a problem with the initial state of the numericInput in ui being set to NULL, which triggers the reactive function in server. Some solutions would be to
Error handling in server to check that the input is not NULL before trying to retrieve cust, or
Initialising the ID to a default value which exists, or
Converting numericInput to a button style input where the reactive function is not calculated until the user presses "submit".
See also this question: Shiny renderUI selectInput returned NULL

R shiny error: Cannot coerce type 'closure' to vector of type 'double'

I would like to take in a vector of numbers as input and then simply plot the histogram. Here is my R code:
ui.R:
library(shiny)
shinyUI(pageWithSidebar(
headerPanel("Hello Shiny!"),
sidebarPanel(selectInput("Vector", "Select Numbers", c(1,2,3,4), selected = NULL, multiple = TRUE)),
mainPanel( plotOutput("plotVector"))
))
Server.R:
library(shiny)
shinyServer(function(input, output) {
v<- function()
{
v <- rnorm(input$Vector)#take vector as input
}
output$plotVector <- renderPlot({ hist(as.numeric(v))})
})
code to run the app:
library(shiny)
runApp("C:/Users/me/Desktop/R Projects/testShiny")
When I run this I am getting the error "Cannot coerce type 'closure' to vector of type 'double'"
Can you help? Thank you.
On the server side, you define v as a function:
v<- function()
{
v <- rnorm(input$Vector)#take vector as input
}
and then you try to use it as the argument to as.numeric(...):
output$plotVector <- renderPlot({ hist(as.numeric(v))})
so R is trying to convert something of class: function to double.
Edit: to answer OP's followup question. With the following for ui.R and server.R:
On the server side, shinyUI(...) takes two objects which are passed automatically: input and output. The properties of input ("columns" in R terminology) are defined in ui.R by creating various GUI objects. So you create a select object with a call to selectInput(...). The object's id is "Vector". This is referenced on the server side as: input$Vector. Note that what you are calling Vector is actually a single number: whatever the user selects in the select box. Plotting the histogram of a single number is meaningless, so I changed the code to make input$Vector the mean of a normal distribution. You also had the problem that input$Vector was initialized to NULL in your code, which threw an error. So I changed that to initialize to 0.
The statement:
output$mainplot <- ...
on the server side populates an object output$main_plot in ui.R, which is defined by the statement:
... plotOutput("main_plot")...
Rolling it all up, the following:
ui.R:
library(shiny)
shinyUI(pageWithSidebar(
headerPanel("Hello Shiny!"),
sidebarPanel(selectInput("Vector", "Select Mean of Distribution", c(0,1,2,3,4), selected = 0, multiple = TRUE)),
mainPanel( plotOutput("main_plot"))
))
server.R:
library(shiny)
shinyServer(function(input, output) {
v<- function() {
return(rnorm(100,mean=as.numeric(input$Vector)))
}
output$main_plot <-
renderPlot(
hist(v(), breaks=10, xlab="",
main="Histogram of 100 Samples\n taken from: N[mean, sd=1]"))
})
Generates this:
It looks like doing this works!
library(shiny)
shinyServer(function(input, output) {
v<- function()
{
v <- rnorm(input$Vector)#take vector as input
}
output$plotVector <- renderPlot({
data <- v()
hist(data)
})
})

Resources