You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Shiny新手求助:实现下拉选择响应式表格并保存功能

Hey there! Let's fix up your Shiny app step by step. I see a couple of key issues in your code that are causing the dropdown to misbehave, plus some tweaks needed to save your reactive tables correctly.

Key Problems in Your Original Code

  • The selectInput choices are set incorrectly: (df1(),df2()) won't work because df1 and df2 are reactive expressions. You need to pass human-readable names as choices, not call the reactives directly here.
  • When saving, data <- input$data only grabs the selected dropdown string (not the actual table data). You need to map that string to the corresponding reactive dataframe.
  • The DT::dataTableOutput("responses") is in your UI but has no matching server output—adding a preview of the selected table will make the app more user-friendly.
  • The hardcoded "path" in volumes won't work for file selection; we need to use accessible directories like the user's home folder.

Fixed & Improved Code

# Set libraries
library(shiny)
library(shinyFiles)
library(DT)

shinyApp(
  ui = fluidPage(
    # Preview the selected table for users to verify
    DT::dataTableOutput("selected_table", width = 600),
    tags$hr(),
    # Dropdown with friendly table names mapped to reactive IDs
    selectInput(
      "table_choice", 
      "Select Table to Save:", 
      choices = c("Customer Table 1" = "df1", "Customer Table 2" = "df2")
    ),
    tags$hr(),
    shinySaveButton(
      "save", 
      "Save Selected Table", 
      "Choose where to save your CSV...", 
      filetype = "csv"
    )
  ),
  server = function(input, output, session) {
    # Reactive dataframe 1
    df1 <- reactive({
      data.frame("id" = 1:2, "Age" = c(21,15), "Name" = c("John","Dora"))
    })
    
    # Reactive dataframe 2
    df2 <- reactive({
      data.frame("id" = 2:4, "Age" = c(521,715), "Name" = c("Hellen","Jane"))
    })
    
    # Render preview of the selected table
    output$selected_table <- DT::renderDataTable({
      # Map dropdown selection to the correct reactive table
      switch(input$table_choice,
             "df1" = df1(),
             "df2" = df2())
    })
    
    # Handle save button click
    observeEvent(input$save, {
      # Set up accessible directories for file saving
      volumes <- c(Home = fs::path_home(), "Current Working Dir" = getwd())
      shinyFileSave(input, "save", roots = volumes, session = session)
      
      # Parse the selected save path
      fileinfo <- parseSavePath(volumes, input$save)
      
      # Only proceed if a valid path was chosen
      if (nrow(fileinfo) > 0) {
        # Fetch the actual reactive table data
        selected_data <- switch(input$table_choice,
                                "df1" = df1(),
                                "df2" = df2())
        
        # Save the data to CSV (without extra row numbers)
        write.csv(selected_data, as.character(fileinfo$datapath), row.names = FALSE)
        # Let the user know the save succeeded
        showNotification("Table saved successfully!", type = "message")
      }
    })
  }
)

What Changed & Why

  1. Dropdown Fix:
    We use a named vector for choices so users see friendly labels (like "Customer Table 1") while the app uses the internal reactive IDs ("df1") to map to the actual data. This makes scaling to more tables later easy.

  2. Table Preview:
    The selected_table output lets users see exactly which table they're about to save, reducing mistakes.

  3. Proper Data Access:
    In the save handler, we use switch() to pull the actual reactive dataframe (by calling df1() or df2()) instead of just the dropdown string.

  4. Better File Saving:

    • We use cross-platform accessible directories (home folder + current working dir) instead of a hardcoded path.
    • Added a success notification to confirm the save worked.
    • Disabled row number saving in write.csv() for cleaner output.
  5. Scalability:
    If you add more reactive tables later, just update the choices in selectInput and add another case to the switch() statements—no major rewrites needed.

内容的提问来源于stack exchange,提问作者LivingstoneM

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.14 08:12:39