0

I'm trying to replicate the solution from this comment using reactive input values through the shiny app, but I can't seem to get dr4pl to recognize the input values as a column of data. I've tried assigning input as a variable, subsetting it with data[[]], etc.

I've created a CSV that contains the example data in the link.

! curve C1 C1 C1 C1 C1 C1 C1 C1 C1 C2 C2 C2 C2 C2 C2 C2 C2 C2 C3 C3 C3 C3 C3 C3 C3 C3 C3

! POC 1.07129314 0.9112628 0.97914297 0.95904437 0.8850967 0.84338263 0.75843762 0.61319681 0.52635571 0.84563087 1.24435113 1.11757648 0.82383523 0.82763447 0.72585483 0.31953609 0.15056989 0.10057988 0.57384256 0.65984339 0.81439758 0.84572057 0.62797088 0.30800934 0.08957274 0.06360764 0.04451161

! dose 0.078125 0.15625 0.3125 0.625 1.25 2.5 5 10 20 0.078125 0.15625 0.3125 0.625 1.25 2.5 5 10 20 0.078125 0.15625 0.3125 0.625 1.25 2.5 5 10 20

Edit: The previous error was due to me forgetting the get(), leading to the values called being empty.

Current error

    Error in ==: comparison (==) is possible only for atomic and list types

ColID appears to lose the full context of input$z? The class of ColID is the same as the example, so not sure what I'm missing

library(shiny)
library(tidyverse)
library(plotly)
library(dr4pl)
library(data.table)



ui <- fluidPage(# Application title
  sidebarLayout(
    sidebarPanel(
      fileInput('file', "Choose CSV File"),
      uiOutput('X_dropdown'),
      uiOutput('Y_dropdown'),
      uiOutput('Z_dropdown'),
      uiOutput('IC50_Checkbox'),
    ),
    
    mainPanel(plotlyOutput("Plot"),
              plotlyOutput("P_IC50_table"))
  ))

# Define server logic required to draw graph
server <- function(input, output, session) {
  #saves uploaded file as a reactive output, file can be changed
  dta <- reactive({
    req(input$file)
    read.csv(input$file$datapath, header = T)
  })
  
  output$X_dropdown <- renderUI({
    req(dta())
    selectInput('x', "X", names(dta()), selected = "dose")
  })
  output$Y_dropdown <- renderUI({
    req(dta())
    selectInput('y', "Y", names(dta()), selected = "POC")
  })
  output$Z_dropdown <- renderUI({
    req(dta())
    selectInput('z', "Color", names(dta()), selected = "curve")
  })
  output$IC50_Checkbox <- renderUI({
    req(dta())
    checkboxInput("ic50", "Calculate ICXX?", value = F)
  })
  
  
  output$Plot <- renderPlotly({
    req(dta())
    req(input$x)
    
    if (input$ic50 == T) {
      #Assign functions to variables
      
      
      multiIC <- function(data, 
                          colDose, colResp, colID, 
                          inhib.percent, 
                          ...) 
      {
        # Get curve IDs
        
        locID <- unique(data[[colID]])
        
        # Prepare a vector to store IC50s
        locIC <- rep(NA, length(locID))
        
        # Calculate IC50 separately for every curve
        #seq_along takes the length of the sequence
        for (ii in seq_along(locID)) {
          # Subset a single dose response
          locSub <- data[get(colID) == locID[[ii]], ]
          
          # Calculate IC50
          locIC[[ii]] <- dr4pl::IC(
            dr4pl::dr4pl(dose = locSub[[colDose]], 
                         response = locSub[[colResp]],
                         ...), 
            inhib.percent)
        }
        
        return(data.frame(id = locID,
                          x = locIC))
      }
      #changed data
      dfIC50 <- multiIC(data = dta(),
                        colDose = input$x,
                        colResp = input$y,
                        colID = input$z,
                        inhib.percent = 50              
      )
      #browser()
      IC50_table <- data.frame(id = locID, x = locIC)
      
      ggplotly(
        width = 500,
        height = 500,
        ggplot(data = dta(),
               aes(
                 x = .data[[input$x]],
                 y = .data[[input$y]],
                 color = as.factor(.data[[input$z]])
               )) +
          labs(color = "") +
          geom_vline(data = IC50_table, aes(xintercept = x))
      )
      
      output$P_IC50_table <- renderTable({
        #Attempt to add in IC50 curve
        IC50_table
      })
    } else{}
})
}
# Run the application
shinyApp(ui = ui, server = server)
Scott
  • 17
  • 5

1 Answers1

1

Can you print the values dta() and input on app initialization. I suspect they are not quite right. if you manually run the multiIC function with fixed values does it give expected response?

Your multiIC is also missing get() in locSub() and unique() in LocID()

A-A-ron
  • 15
  • 6
  • The values seem to be correct on input. This is part of a larger program where if the box is not checked then all of the inputs are read and graphed correctly. If I add back in the "get" and "unique" the error changes back to ``` Warning: Error in ==: comparison (==) is possible only for atomic and list types ``` – Scott Jun 15 '23 at 16:32