Search code examples
rshinycrosstab

Cross tab to complement stacked bar plot in Shiny app


I am having trouble creating a shiny app that creates a dynamic cross tab where one of the variables can be changed.

That is, I would like to create an app that creates a cross tab that shows the percentage of students that passed against each characteristic, as well as displaying this in a bar plot.

The bar plot is no problem. I cannot figure out how to vary the input into the cross tab.

The output$my_table section in the server object is where the problem is.

Any assistance would be greatly appreciated

library(shiny)
library(ggplot2)

students <- data.frame(Passed = c("Y","Y","Y","Y","Y","Y","N","N"), Gender = rep(c("Male","Female"), each = 4), 
                       Subject = rep(c("Maths","Science"), times = 4),Campus =c(rep(c("Victoria"), times = 7), "NSW"))


ui <- fluidPage(
  titlePanel("Percentage Passed by Characteristic"),
  sidebarLayout(sidebarPanel(
    selectInput(
      "Characteristic",
      "Student characteristic",
      choices = colnames(students)[!colnames(students) %in% c("Passed")],
      selected = colnames(students)[2]
    )
  ),
  mainPanel(
    tabPanel("Plot",
             fluidRow(
               plotOutput("barplot"),
               verbatimTextOutput("summary"))
    ),
    tabPanel("Summary",  
             tableOutput("my_table"))
  )
  ))


server <- function(input, output) {
    output$barplot <- renderPlot({
      var <- input$Characteristic
      gg <-
        ggplot(students, aes_string(x = var, fill= "Passed"))
      gg <- gg + geom_bar(position = "Stack")
      gg
    })
    output$my_table <- renderTable({
      var <- input$Characteristic
      prop.table(table(students$Passed, students$var),1)
    })
}



# Create Shiny object
shinyApp(ui = ui, server = server)

Solution

  • The problem is that students$var refers to a column literally named "var", whereas you want the column named by the value of var: students[[var]].

    This is addressed the question "access data frame column using variable", and answered in the last sentence of the winning answer. access data frame column using variable

    I diagnosed the problem by running your code in an interactive R session, setting var to Gender, then running the prop.table(... line, which gives the error:

    Error in table(students$Passed, students$var) :
      all arguments must have the same length
    

    The next problem you'll face is formatting the resulting prop.table, but that deserves another question.