I am trying to save a plot to a list like here (where x is a counter):
pl_list[[x]] <- renderPlot({ggplot(dfg, aes(x="", y=mean_rel_abund, fill=taxon)) +
geom_bar(stat="identity", width=1) +
scale_fill_manual(values = v2, labels=paste(gsub('\\*', '', dfg$taxon), str_replace_all(paste(round(dfg$mean_rel_abund, 1),"%"), " ", "")))+
# facet_grid(.~ data2()$disease_stat)+
theme_classic() +
theme(axis.line = element_blank(),
axis.text = element_blank(),
axis.ticks = element_blank())})
and then save the output of it like this:
output$pl_list[[x]] <- pl_list[[x]]
then visualize it in a tab by calling the plotOutput function:
appendTab(inputId = "tabs", tabPanel(title = input$caption, value = tid,
headerPanel('Microbiome'),
mainPanel(
plotOutput(pl_list[[tid]]),
selectInput(inputId = shinyInput("case", rv$counter), label = strong("Case"),
choices = unique(data_list[[tid]]$disease_stat),
selected = "DiarrhealControl")
),
actionButton(shinyInput("remove_btn", rv$counter), "Remove", icon = icon("minus-circle"))
))
But I'm getting an error where it says:
Warning: Error in $: Can't read output 'pl_list'
This is the whole code as someone requested:
library(shiny)
library(shinythemes)
library(tidyr)
library(tidyverse)
library(readxl)
library(ggtext)
library(RColorBrewer)
library(dplyr)
library(bslib)
library(shinydashboard)
library(tools)
tid <<- 0
data_list <<- list()
pl_list <<- list()
ui <- fluidPage(
textOutput("text"),
tabsetPanel(id = "tabs",
tabPanel(
title = "Home",
value = "home",
sidebarLayout(
sidebarPanel(
h3("Generate plots"),
fileInput("probe1", "Metadata .XLSX File", accept = "xlsx", buttonLabel = "Browse"),
fileInput("probe2", "Otu_counts (subsample.shared) .TSV File", accept = "tsv", buttonLabel = "Browse"),
fileInput("probe3", "Taxonomy .TSV File", accept = "tsv", buttonLabel = "Browse"),
textInput("caption", "Name of the plot", "Example: plot1"),
verbatimTextOutput("value"),
actionButton("add", "Add", icon = icon("plus-circle"))
),
mainPanel(
helpText("Description:"),
helpText("The required tables need to have information about:...")
)
)
))
)
server <- function(input, output, session) {
shinyInput <- function(name, id) paste(name, id, sep = "_")
rv <- reactiveValues(counter = 0L)
#go to the new created tab
observeEvent(input$add, {
rv$counter <- rv$counter + 1L
updateTabsetPanel(session, "tabs", shinyInput("new_tab", rv$counter))
}, ignoreInit = TRUE)
#creating tab with plot after uploading the files
observeEvent(input$add, {
tid <<- tid + 1
inputs <- reactiveValues(input1 = input$probe1, input2 = input$probe2, input3 = input$probe3)
# print(inputs)
# print(paste0("This is input1: ", inputs$input1))
#data_list <<- append(data_list,
#data processing
metadata <- read_excel(inputs$input1$datapath, na="NA") %>%
select(sample_id, disease_stat) %>%
drop_na(disease_stat)
otu_counts <- read_tsv(inputs$input2$datapath) %>%
select(Group, starts_with("Otu")) %>%
rename(sample_id = Group) %>%
pivot_longer(-sample_id, names_to="otu", values_to = "count")
taxonomy <- read_tsv(inputs$input3$datapath) %>%
select("OTU", "Taxonomy") %>%
rename_all(tolower) %>%
mutate(taxonomy = str_replace_all(taxonomy, "\\(\\d+\\)", ""),
taxonomy = str_replace(taxonomy, ";$", "")) %>%
separate(taxonomy,
into=c("kingdom", "phylum", "class", "order", "family", "genus"),
sep=";")
otu_rel_abund <- inner_join(metadata, otu_counts, by="sample_id") %>%
inner_join(., taxonomy, by="otu") %>%
group_by(sample_id) %>%
mutate(rel_abund = count / sum(count)) %>%
ungroup() %>%
select(-count) %>%
pivot_longer(c("kingdom", "phylum", "class", "order", "family", "genus", "otu"),
names_to="level",
values_to="taxon") %>%
mutate(disease_stat = factor(disease_stat,
levels=c("NonDiarrhealControl",
"DiarrhealControl",
"Case")))
taxon_rel_abund <- otu_rel_abund %>%
filter(level=="phylum") %>%
group_by(disease_stat, sample_id, taxon) %>%
summarize(rel_abund = sum(rel_abund), .groups="drop") %>%
group_by(disease_stat, taxon) %>%
summarize(mean_rel_abund = 100*mean(rel_abund), .groups="drop") %>%
mutate(taxon = str_replace(taxon,
"(.*)_unclassified", "Unclassified *\\1*"),
taxon = str_replace(taxon,
"^(\\S*)$", "*\\1*"))
taxon_pool <- taxon_rel_abund %>%
group_by(taxon) %>%
summarize(pool = max(mean_rel_abund) < 3,
mean = mean(mean_rel_abund),
.groups="drop")
df <- inner_join(taxon_rel_abund, taxon_pool, by="taxon") %>%
mutate(taxon = if_else(pool, "Other", taxon)) %>%
group_by(disease_stat, taxon) %>%
summarize(mean_rel_abund = sum(mean_rel_abund),
mean = min(mean),
.groups="drop") %>%
mutate(taxon = factor(taxon),
taxon = fct_reorder(taxon, mean, .desc=TRUE),
taxon = fct_shift(taxon, n=1))
#print(c(df))
#print(df$taxon)
dff <<- as.data.frame(df)
data_list[[tid]] <<- dff
#creating plot
pl_list[[tid]] <- ggplot(data_list[[tid]], aes(x="", y=mean_rel_abund, fill=taxon)) +
geom_bar(stat="identity", width=1) +
# facet_grid(.~ data2()$disease_stat)+
theme_classic() +
theme(axis.line = element_blank(),
axis.text = element_blank(),
axis.ticks = element_blank())
#print(paste("Before append:", data_list[[tid]]$disease_stat ))
#output$plot <- render....
#finally creating tab after data processing and plot creation
appendTab(inputId = "tabs", tabPanel(title = input$caption, value = tid,
headerPanel('Microbiome'),
mainPanel(
plotOutput(pl_list[[tid]]),
selectInput(inputId = shinyInput("case", rv$counter), label = strong("Case"),
choices = unique(data_list[[tid]]$disease_stat),
selected = "DiarrhealControl")
),
actionButton(shinyInput("remove_btn", rv$counter), "Remove", icon = icon("minus-circle"))
))
#print(pl_list[[tid]])
#print(paste("After append", data_list[[tid]]$disease_stat))
##########################
#print(inputs)
})
## REACTIVITY TO ARRANGE TAB NAMES:
current.tab <- eventReactive(input$tabs, {
# don't accidentally remove main tab:
if (!identical(input$tabs, "home")) {
input$tabs
} else {
NULL
}
})
#observe event for when a choice from a filter is selected
observe({
if (rv$counter > 0L) {
lapply(seq(rv$counter), function(x) {
observeEvent(input[[paste("case", x, sep = "_")]], {
#filtering data based on the selected choice
dfg <- filter(data_list[[tid]], disease_stat == input[[paste("case", x, sep = "_")]])
#print(paste("this is dfg disease_stat:", dfg$disease_stat))
v2 <- rainbow(length(dfg$taxon))
names(v2) <- unique(dfg$taxon)
#print(length(names(v2)))
#print(paste(dfg$taxon, " ", round(dfg$mean_rel_abund, 1),"%"))
if (length(names(v2)) == 1)
{
# v2["Other"] = "#FFFFFF"
}
else
{
v2["Other"] = "#808080"
}
#print(pl_list[[x]])
#overwriting the first created plot on the tab with the newly created one based on the new data
pl_list[[x]] <<- renderPlot({ggplot(dfg, aes(x="", y=mean_rel_abund, fill=taxon)) +
geom_bar(stat="identity", width=1) +
scale_fill_manual(values = v2, labels=paste(gsub('\\*', '', dfg$taxon), str_replace_all(paste(round(dfg$mean_rel_abund, 1),"%"), " ", "")))+
# facet_grid(.~ data2()$disease_stat)+
theme_classic() +
theme(axis.line = element_blank(),
axis.text = element_blank(),
axis.ticks = element_blank())})
#renderPlot(pl_list[[x]])
#print(pl_list[[x]])
output$pl_list[[x]] <- pl_list[[x]]
})
})
}
})
#removing a tab
observe({
if (rv$counter > 0L) {
lapply(seq(rv$counter), function(x) {
observeEvent(input[[paste("remove_btn", x, sep = "_")]], {
#print(paste0("This is x: ",x))
removeTab(inputId = "tabs", target = current.tab())
#print(paste0("Removing: ", input[[paste("remove_btn", x, sep = "_")]]))
})
})
}
})
output$text <- renderText({paste0("You are viewing tab \"", input$tabs, "\"", " Rv$counter is: ", rv$counter)})
}
shinyApp(ui, server)
And link to the files you will need to upload in the shiny app:
https://drive.google.com/drive/folders/1bcGyE42aD5gicmdZseRGqvfT-Iu9FHLP