################## SHINY APP ##########################################
require(openxlsx)
require(lubridate)
require(DT)
require(shinyjs)
require(shinyjqui)
require(yarrr)
require(colorspace)
require(reshape2)
require(markdown)
require(dplyr)
require(plyr)
require(tidyr)
source("tmdlCalcs.R")
perc.red <- function(x,y){100-x/y*100}
deqPalette <- c("#0080b7","#00afd8","#ADD361")
#dwqPalette <- c("#034963","#0b86a3","#00a1c6")
dwqPalette <- c("#febb12","#0b86a3","#62bc99")
boxcolors = dwqPalette
linecolors = deqPalette
ui <- fluidPage(title="E.coli Data Explorer",
titlePanel(title=div(img(width="8%",height="8%",src="dwq_logo_small.png"), em("Escherichia coli"),"Data Visualization Tool")),
tabsetPanel(id="all_the_things",
tabPanel("Upload Data",
useShinyjs(),
h3("Select your Excel workbook containing ", em("E.coli "), "data"),
p(strong("NOTE: "),"Workbooks must fit the ", em("E.coli"), " template, but you have the option in this app to calculate loadings and seasonal geomeans on the uploaded dataset."),
sidebarPanel(fileInput("workbook","Select Workbook"),
uiOutput("loadcalcs"),
uiOutput("selectsheet"),
uiOutput("dwnloadbutton")),
mainPanel(h4("Data View"),
h5("Toggle between sheets in the workbook using the drop down menu at the bottom of the sidebar."),
DTOutput("datview"), style= "font-size:75%")
),
tabPanel("Time Series",
shinyjs::useShinyjs(),
h3("Bacterial Concentrations Over Time by Site"),
sidebarPanel(radioButtons("plottype", label = "Select Plot Type", choices = c("Point","Line"), selected = "Point", inline = TRUE),
div(id = "date",
uiOutput("tsdatrange")),
checkboxInput("perc_exc", label = strong("Show % exceedance of max criterion by site?"),value = FALSE),
br(),
uiOutput("checkbox"),
br(),
uiOutput("checkbox1")),
mainPanel(plotOutput("Time_Series"),
hr(),
br(),
div(DT::dataTableOutput("Time_Data"), style= "font-size:75%"))),
tabPanel("Upstream-Downstream",
h3("Bacterial Concentrations Upstream to Downstream"),
h5("Use the date range slider to select the period of record over which to view ",em("E.coli"), " concentrations. The red dotted line in the boxplot represents the maximum",em("E.coli"), "concentration criterion, while the orange dotted line represents the geometric mean criterion."),
sidebarPanel(uiOutput("usds_site"),
uiOutput("usds_date"),
checkboxInput("rec_only", label = strong("Rec season data only")),
checkboxInput("vieworddat", label = strong("View data points"))),
mainPanel(plotOutput("UD_Geomeans", height="700px"))),
tabPanel("Monthly",
h3("Bacterial Concentrations/Loadings by Month"),
sidebarPanel(uiOutput("monthsite"),
div(id="date1",uiOutput("mondatrange")),
br(),
uiOutput("mon_unit_type"),
checkboxInput("viewmondat", label = "View data points?")),
mainPanel(plotOutput("Monthly_Geomeans", height="700px"),
hr(),
br(),
div(DT::dataTableOutput("Monthly_Data"), style= "font-size:75%"))),
tabPanel("Rec/Non-Rec",
h3("Bacterial Concentrations/Loadings by Year"),
sidebarPanel(uiOutput("recsite"),
br(),
br(),
uiOutput("rec_unit_type"),
checkboxInput("viewrecdat", label = "View data points?")),
mainPanel(plotOutput("Rec_Geomeans", height="700px"),
hr(),
br(),
div(DT::dataTableOutput("Rec_Data"), style= "font-size:75%"))),
tabPanel("Irrigation/Non-Irrigation",
h3("Bacterial Concentrations/Loadings by Year"),
sidebarPanel(uiOutput("irgsite"),
br(),
br(),
uiOutput("irg_unit_type"),
checkboxInput("viewirgdat", label = "View data points?")),
mainPanel(plotOutput("Irg_Geomeans", height="800px"),
hr(),
br(),
div(DT::dataTableOutput("Irg_Data"), style= "font-size:75%"))),
tabPanel("Load Duration Curves",
h3("Bacterial Loadings Across Flow Regimes"),
p(strong("NOTE: "),em("E.coli "),"loadings are calculated using the ", strong("geometric mean criterion "),"based on the water body's beneficial use classification. Percentages in parentheses indicate the percent of observed loading values exceeding the TMDL at each flow regime."),
sidebarPanel(uiOutput("ldcsite"),
radioButtons("ldc_type", label = "Plot Type", choices = c("Scatterplot", "Boxplot"), selected = "Scatterplot", inline = TRUE),
selectInput("pt_type",
label = "Data Category",
choices=c("Calendar Seasons","Recreation Seasons","Irrigation Seasons")), width = 3),
mainPanel(plotOutput("LDC", width="100%", height="700px"),
hr(),
div(DT::dataTableOutput("LDC_Data", height=20),style="font-size:75%")))#,
# tabPanel("User Guide",
# includeMarkdown("user_guide.Rmd"))
)
)
# Define server logic required to draw a histogram
server <- function(input, output) {
###################################### FILE UPLOAD SECTION ################################
# File Info
workbook <- reactiveValues()
snames <- reactiveValues()
# Obtain file path
observeEvent(input$workbook,{
fileup = input$workbook
workbook$wb_path = fileup$datapath})
# Run tmdl tools widget, which disables once clicked
output$loadcalcs <- renderUI({
req(input$workbook)
radioButtons("loadcalcs", label = "Perform Geomean/Loading Calculations?", selected = character(0), choices=c("Yes","No"), inline=TRUE)
})
observeEvent(input$loadcalcs,{
disable("loadcalcs")
})
# Download button that shows after sheet widget
output$dwnloadbutton <- renderUI({
req(input$selectsheet)
downloadButton("export_loadcalcs","Export workbook")
})
### Reading in the data from the file to the reactive environment ###
observe({
req(input$loadcalcs)
if(input$loadcalcs=="Yes"){
out <- tmdlCalcs(workbook$wb_path, exportfromfunc = FALSE)
}else{
dat = openxlsx::loadWorkbook(workbook$wb_path)
sheets = dat$sheet_names[!dat$sheet_names=="READ ME"]
out <- lapply(sheets, function(x)openxlsx::readWorkbook(workbook$wb_path, sheet = x, detectDates = TRUE))
names(out) = sheets
}
workbook$Ecoli_data = out$Ecoli_data
workbook$Inputs = out$Inputs
if(!is.null(out$Site_order)){
workbook$Site_order = out$Site_order
}
if(!is.null(out$Daily_Geomean_Data)){
out$Daily_Geomean_Data$E.coli_Geomean = round(out$Daily_Geomean_Data$E.coli_Geomean,1)
workbook$Daily_Geomean_Data = out$Daily_Geomean_Data
workbook$Monthly_Data = out$Monthly_Data
workbook$Rec_Season_Data = out$Rec_Season_Data
workbook$Irg_Season_Data = out$Irg_Season_Data
}
if(!is.null(out$Flow_data)){
workbook$Flow_data = out$Flow_data
if(!is.null(out$LDC_Data)){
# rounding
ldc = out$LDC_Data
nums <- unlist(lapply(ldc, is.numeric))
ldc[,nums] = round(ldc[,nums],1)
workbook$LDC_Data = ldc
}
}
snames$sheets = names(workbook)[!names(workbook)=="wb_path"]
})
# Create drop down menu of sheets contained in xlsx file
output$selectsheet <- renderUI({
req(workbook$Inputs)
selectInput("selectsheet", label = "Select sheet to view.", selected = NULL, choices=c(snames$sheets))
})
# Object to be fed to the download handler
wbdwn <- reactiveValues()
# Create workbook where each workbook reactive values object is added to the wbdwn reactive values object for use in download handler.
observe({
req(workbook$Inputs)
wbdownload <- reactiveValuesToList(workbook)
wbdownload$wb_path = NULL
wb <- openxlsx::createWorkbook()
for(i in 1:length(wbdownload)){
addWorksheet(wb, names(wbdownload)[i], gridLines = TRUE)
writeData(wb, sheet = names(wbdownload)[i], wbdownload[[i]], rowNames = FALSE, colNames = TRUE)
}
if(length(wbdownload)>7){
worksheetOrder(wb) = c(5,1,7,3,9,2,4,6,8)
}else{worksheetOrder(wb) = c(4,1,6,7,2,3,5)}
wbdwn$outputworkbook = wb
})
# Download results of loadcalcs
output$export_loadcalcs <- downloadHandler(
filename = paste0(unlist(strsplit(input$workbook$name,".xlsx")),"_",Sys.Date(),".xlsx"),
content = function(file) {
openxlsx::saveWorkbook(wbdwn$outputworkbook, file)
}
)
observe({
req(input$selectsheet)
tableview = workbook[[input$selectsheet]]
# Load data tables on first page
output$datview <- renderDT(tableview,
rownames = FALSE,selection='none',filter="top",
options = list(scrollY = '600px', paging = FALSE, scrollX=TRUE))
})
# Add loading tab if loadings present
observe({
if(!is.null(workbook$LDC_Data)){
showTab(inputId="all_the_things", target = "Load Duration Curves")
}else{
hideTab(inputId="all_the_things", target = "Load Duration Curves")
}
})
# Add upstream downstream tab if order present
observe({
if(!is.null(workbook$Site_order)){
showTab(inputId="all_the_things", target = "Upstream-Downstream")
}else{
hideTab(inputId="all_the_things", target = "Upstream-Downstream")
}
})
# Add unique site names to LDC drop down list (if flow data are available)
output$ldcsite <- renderUI({
req(workbook$LDC_Data)
selectInput("ldcsite",
label = "Site Name",
choices=c(unique(workbook$LDC_Data$ML_Name)))
})
## Save Criteria in own reactive values for use in all plots ##
crits <- reactiveValues()
observe({
req(workbook$Inputs)
inputs <- workbook$Inputs
crits$maxcrit = as.numeric(inputs$Value[inputs$Parameter == "Max Criterion"])
crits$geomcrit = as.numeric(inputs$Value[inputs$Parameter == "Geometric Mean Criterion"])
})
################################# TIME SERIES SECTION ########################################
# Get time series max and min date range based on data upload
output$tsdatrange <- renderUI({
req(workbook$Daily_Geomean_Data)
if(!is.null(workbook$Flow_data)){
time1 = workbook$Daily_Geomean_Data$Date
time2 = workbook$Flow_data$Date
timeseries = unique(c(time1,time2))
}else{
timeseries <- workbook$Daily_Geomean_Data$Date
}
sliderInput("tsdatrange",
label="Date Range",
min=min(timeseries),
max=max(timeseries),
value = c(min(timeseries),max(timeseries)),
dragRange = TRUE, timeFormat="%Y-%m-%d")
})
# Create checkbox menu for e.coli concentrations based on sites present
output$checkbox <- renderUI({
req(workbook$Daily_Geomean_Data)
timeseries <- workbook$Daily_Geomean_Data
choice <- unique(timeseries$ML_Name)
checkboxGroupInput("checkbox","Select E.coli Site(s)", choices = choice, selected = choice[1])
})
# Create checkbox menu for flow based on tabs and sites present
output$checkbox1 <- renderUI({
req(workbook$Flow_data)
flow <- workbook$Flow_data
choice <- unique(flow$ML_Name)
checkboxGroupInput("checkbox1","Select Flow Site(s)", choices = choice, selected = character(0))
})
# Create timeseries data object based on data input, sites, and date ranges selected
timeseriesdat <- reactiveValues()
# Create ecoli dataset and place date range and colors into reactive object
observe({
req(workbook$Daily_Geomean_Data)
# Assign site colors
colrs <- yarrr::piratepal("basel")
sites = unique(workbook$Daily_Geomean_Data$ML_Name)
nsites = length(sites)
ML_Col = as.character(rep(colrs, length.out = nsites))
sitecols = data.frame(ML_Name = sites, ML_Col = rep(colrs, length.out = nsites))
timeseriesdat$sitecols = sitecols
# Sort to ecoli sites and date range
x = workbook$Daily_Geomean_Data
x = x[x$ML_Name %in% input$checkbox,]
if(!is.null(input$tsdatrange)){
timeseriesdat$min = input$tsdatrange[1]
timeseriesdat$max = input$tsdatrange[2]
}
x <- x[x$Date>=timeseriesdat$min&x$Date<=timeseriesdat$max,]
if(dim(x)[1]>0){
timeseriesdat$x = x
}else{timeseriesdat$x = NULL}
})
# Create flow dataset
observe({
req(input$checkbox1)
x1 = workbook$Flow_data
x1 = x1[x1$ML_Name %in% input$checkbox1,]
x1 <- x1[x1$Date>=timeseriesdat$min&x1$Date<=timeseriesdat$max,]
if(dim(x1)[1]>0){
timeseriesdat$x1 = x1
}else{timeseriesdat$x1 = NULL}
})
output$Time_Series <- renderPlot({
req(timeseriesdat$min,timeseriesdat$max)
colrs = timeseriesdat$sitecols
min = timeseriesdat$min
max = timeseriesdat$max
par(mar=c(5.1,4.1,4.1,4.1))
# Base plot
if(!is.null(input$checkbox)|!is.null(input$checkbox1)){
# Create an empty plot
plot(1, type="n", xlab="", ylab="MPN/100 mL", xaxt="n", xlim=c(min, max), ylim=c(0, 2420))
axis.Date(1, at=seq(min, max, by="6 months"), format="%m-%Y", las=2, cex=0.8)
abline(h=crits$maxcrit,col="red", lwd=2)
abline(h=crits$geomcrit, col="orange", lwd=2)
site = vector()
colr = vector()
}
# E.coli plots
if(!is.null(timeseriesdat$x)){
x = timeseriesdat$x
# Get number of sites
uni.sites <- unique(x$ML_Name)
# Start plotting ecoli concentrations
for(i in 1:length(uni.sites)){
concol = as.character(colrs$ML_Col[colrs$ML_Name == uni.sites[i]])
y = x[x$ML_Name==uni.sites[i],]
perc.exc = round(length(y$E.coli_Geomean[y$E.coli_Geomean>as.numeric(crits$maxcrit)])/length(y$E.coli_Geomean)*100, digits=0)
if(input$plottype=="Line"){
lines(y$E.coli_Geomean~y$Date, lwd=1, lty=1, col=concol)
}
points(y$E.coli_Geomean~y$Date, pch=21, cex=2, col="black", bg=concol)
if(input$perc_exc){
site[i] = paste0(as.character(uni.sites[i])," (",perc.exc,"% Exceed)")
}else{site[i] = as.character(uni.sites[i])}
colr[i] = concol
}
l=legend("topleft",c(site,paste0("Max Crit - ",crits$maxcrit," MPN/100 mL"),paste0("Geometric Mean Crit - ",crits$geomcrit," MPN/100 mL")),col=c(rep("black",length(colr)),"red","orange"),lwd=c(rep(NA,length(colr)),2,2),pt.bg=c(colr,NA,NA), pch=c(rep(21,length(colr)),NA,NA), bty="n", pt.cex=c(rep(2,length(colr)),NA,NA),cex=1)
}
# Flow plots
if(!is.null(timeseriesdat$x1)){
x1 = timeseriesdat$x1
uni.sites.1 = unique(x1$ML_Name)
site1 = vector()
colr1 = vector()
par(new = TRUE)
plot(1, type="n", xlab="", ylab="", axes = F, xlim=c(min, max), ylim = c(0,max(x1$Flow)))
axis(side = 4)
mtext(side = 4, line = 2, "Flow (cfs)")
for(i in 1:length(uni.sites.1)){
flowcol = as.character(colrs$ML_Col[colrs$ML_Name == uni.sites.1[i]])
y1 = x1[x1$ML_Name==uni.sites.1[i],]
if(input$plottype=="Line"){
lines(y1$Flow~y1$Date, lwd=1, lty=1, col=flowcol)
}
points(y1$Flow~y1$Date, pch=23, cex=2, col="black", bg=ggplot2::alpha(flowcol, 0.6))
site1[i] = uni.sites.1[i]
colr1[i] = flowcol
}
l=legend("topright",c(site1),col="black",pt.bg=c(ggplot2::alpha(colr1, 0.6)), pch=23, bty="n", pt.cex=2,cex=1)
}
})
####################################### UPSTREAM DOWNSTREAM SECTION ##########################
# Sites to choose from
output$usds_site <- renderUI({
req(workbook$Site_order)
siteord = workbook$Site_order
siteord$ML_Name = reorder(siteord$ML_Name, siteord$Order)
selectizeInput("usdssite", label = "Select Sites", choices = siteord$ML_Name, selected = NULL, multiple = TRUE)
})
# Dates to choose from
output$usds_date <- renderUI({
req(workbook$Daily_Geomean_Data)
us_ds_data <- workbook$Daily_Geomean_Data
sliderInput("usdsdate",
label="Date Range",
min=min(us_ds_data$Date),
max=max(us_ds_data$Date),
value = c(min(us_ds_data$Date),max(us_ds_data$Date)),
dragRange = TRUE, timeFormat="%Y-%m-%d")
})
output$UD_Geomeans <- renderPlot({
req(input$usdssite)
req(input$usdsdate)
par(mar= c(10,4,4,1))
siteord = workbook$Site_order[workbook$Site_order$ML_Name%in%input$usdssite,]
siteord$Order = 1:length(siteord$ML_Name)
geomeans <- workbook$Daily_Geomean_Data[workbook$Daily_Geomean_Data$ML_Name%in%input$usdssite,]
selgeomeans <- geomeans[geomeans$Date>=input$usdsdate[1]&geomeans$Date<=input$usdsdate[2],]
usds_data = merge(selgeomeans, siteord, all.x = TRUE)
usds_data$ML_Name = factor(usds_data$ML_Name, levels = c(as.character(siteord$ML_Name)))
if(input$rec_only){usds_data = subset(usds_data, usds_data$Rec_Season=="Rec Season")}
udn_count = tapply(usds_data$E.coli_Geomean, usds_data$ML_Name, length)
boxplot(usds_data$E.coli_Geomean~usds_data$ML_Name, ylab = "E.coli (MPN/100 mL)", xlab = "",ylim = c(-50, max(usds_data$E.coli_Geomean)),col = boxcolors[2], lty = 1, outline = FALSE, las = 2, cex.axis = 0.8)
abline(h = crits$geomcrit, col = linecolors[3], lwd = 3, lty = 2)
abline(h = crits$maxcrit, col = linecolors[2], lwd = 3, lty = 2)
legend("topright",legend = c("Max Crit","Geom Crit"), lty = c(2,2), lwd = c(3,3), col = c(linecolors[2],linecolors[3]), bty = "n")
#mtext(paste0("n=",udn_count), side = 1, line = 3, at = 1:length(unique(usds_data$ML_Name)), cex= 1)
text(x = 1:length(unique(usds_data$ML_Name)), y = rep(-40, length(unique(usds_data$ML_Name))), paste0("n=",udn_count), cex = 0.8)
# add data points
if(input$vieworddat){
points(usds_data$Order, usds_data$E.coli_Geomean, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
})
###################################### MONTH TAB SECTION #####################################
# Sites to choose from
output$monthsite <- renderUI({
req(workbook$Daily_Geomean_Data)
selectInput("monthsite",
label = "Site Name",
choices=unique(workbook$Daily_Geomean_Data$ML_Name))
})
# Dates to choose from
output$mondatrange <- renderUI({
req(input$monthsite)
req(workbook$Daily_Geomean_Data)
sitedates = workbook$Daily_Geomean_Data[workbook$Daily_Geomean_Data$ML_Name==input$monthsite,]
sliderInput("mondatrange",
label="Date Range",
min=min(sitedates$Date),
max=max(sitedates$Date),
value = c(min(sitedates$Date),max(sitedates$Date)),
dragRange = TRUE, timeFormat="%Y-%m-%d")
})
# Craft drop down menu for concentration and loading
output$mon_unit_type <- renderUI({
req(input$mondatrange)
req(workbook$Daily_Geomean_Data)
monthdata <- workbook$Monthly_Data
monthdata = monthdata[monthdata$ML_Name==input$monthsite&!is.na(monthdata$Observed_Loading),"Observed_Loading"]
if(length(monthdata)>0){
subd=c("Concentration","Loading")
}else{subd=c("Concentration")}
selectInput("mon_unit_type","Select Measurement Type", choices = subd)
})
# Create dataset for use in plots and tables
selectedmonthdata <- reactiveValues()
observe({
req(input$mon_unit_type)
if(input$mon_unit_type=="Concentration"){
dailygeomeans <- workbook$Daily_Geomean_Data
seldailygeomeans <- dailygeomeans[dailygeomeans$ML_Name==input$monthsite&dailygeomeans$Date>=input$mondatrange[1]&dailygeomeans$Date<=input$mondatrange[2],]
seldailygeomeans$month = lubridate::month(seldailygeomeans$Date, label=TRUE)
monthpositions_1 = data.frame("position" = 1:12, "month" = month.abb)
seldailygeomeans = merge(seldailygeomeans,monthpositions_1, all.x = TRUE)
selectedmonthdata$alldata = seldailygeomeans
aggseldg0 <- aggregate(E.coli_Geomean~month+MLID+ML_Name, dat=seldailygeomeans, FUN=function(x){exp(mean(log(x)))})
aggseldg0$E.coli_Geomean = round(aggseldg0$E.coli_Geomean, digits = 1)
aggseldg1 <- aggregate(E.coli_Geomean~month+MLID+ML_Name, dat=seldailygeomeans, FUN=length)
names(aggseldg1)[names(aggseldg1)=="E.coli_Geomean"] <- "Ncount"
aggseldg2 <- aggregate(E.coli_Geomean~month+MLID+ML_Name, dat=seldailygeomeans, FUN=median)
names(aggseldg2)[names(aggseldg2)=="E.coli_Geomean"] <- "Median"
aggseldg2$Median = round(aggseldg2$Median, digits = 1)
aggseldg = merge(aggseldg0, aggseldg1, all = TRUE)
aggseldg = merge(aggseldg, aggseldg2, all = TRUE)
aggseldg$Percent_Reduction <- ifelse(aggseldg$E.coli_Geomean>crits$geomcrit,round(perc.red(crits$geomcrit,aggseldg$E.coli_Geomean), digits=0),0)
aggseldg = merge(aggseldg, monthpositions_1, all.x = TRUE)
selectedmonthdata$aggregdata = aggseldg
table = aggseldg[,!names(aggseldg)%in%c("position","MLID","ML_Name")]
table = table[,c("month","Ncount","E.coli_Geomean","Median","Percent_Reduction")]
table = table[order(table$month),]
output$Monthly_Data <- renderDT(table,
colnames = c("Month","Ncount","Geomean (MPN/100 mL)","Median (MPN/100 mL)","Reduction Needed (%)"),
rownames = FALSE,selection='none',
options = list(scrollY = '700px', paging = FALSE, scrollX=FALSE, dom = "t"))
}
# Need to stop app from crashing when loading data not available from user selection
if(input$mon_unit_type=="Loading"&input$monthsite%in%workbook$LDC_Data$ML_Name){
# Isolate to site and period of interest
mon_loadings = workbook$LDC_Data
mon_loads <- mon_loadings[mon_loadings$ML_Name==input$monthsite&mon_loadings$Date>=input$mondatrange[1]&mon_loadings$Date<=input$mondatrange[2],]
mon_loads$month = lubridate::month(mon_loads$Date, label=TRUE)
# Flatten by loading type
monloads_flat = reshape2::melt(mon_loads, measure.vars = c("TMDL","Observed_Loading"), variable.name = "Load_Type", value.name = "Loading")
selectedmonthdata$alldata = monloads_flat
# Create summary table for app
agg_monloads0 = aggregate(Loading~month+Load_Type, dat = monloads_flat, FUN=function(x){exp(mean(log(x)))})
agg_monloads0$Loading = round(agg_monloads0$Loading, digits = 1)
names(agg_monloads0)[names(agg_monloads0)=="Loading"] <- "Geomean_Loading"
agg_monloads1 = aggregate(Loading~month+Load_Type, dat = monloads_flat, FUN=length)
names(agg_monloads1)[names(agg_monloads1)=="Loading"] <- "Ncount"
agg_monloads2 = aggregate(Loading~month+Load_Type, dat = monloads_flat, FUN=median)
agg_monloads2$Loading = round(agg_monloads2$Loading, digits = 1)
names(agg_monloads2)[names(agg_monloads2)=="Loading"] <- "Median_Loading"
aggseldg = merge(agg_monloads0, agg_monloads1, all = TRUE)
aggseldg = merge(aggseldg, agg_monloads2, all = TRUE)
# Percent Reduction calcs
library(tidyr)
gmean_isolated = aggseldg[,c("month","Load_Type","Geomean_Loading")]
gmean_iso = gmean_isolated %>% spread(Load_Type,Geomean_Loading)
gmean_iso$Percent_Reduction <- ifelse(gmean_iso$Observed_Loading>gmean_iso$TMDL,round(perc.red(gmean_iso$TMDL,gmean_iso$Observed_Loading), digits = 0),0)
gmean_iso = gmean_iso[!is.na(gmean_iso$Observed_Loading),c("month","Percent_Reduction")]
gmean_iso$Load_Type = "Observed_Loading"
aggseldg2 = merge(aggseldg, gmean_iso, all.x = TRUE)
selectedmonthdata$aggregdata = aggseldg2
table = aggseldg2
table = table[order(table$Load_Type, table$month),c("month","Load_Type","Ncount","Geomean_Loading","Median_Loading","Percent_Reduction")]
output$Monthly_Data <- renderDT(table,
colnames = c("Month","Load Type","Ncount","Geomean (GigaMPN/day)","Median (GigaMPN/day)","Reduction Needed (%)"),
rownames = FALSE,selection='none',filter="top",
options = list(scrollY = '700px', paging = FALSE, scrollX=FALSE, dom = "t"))
}
})
output$Monthly_Geomeans <- renderPlot({
req(selectedmonthdata$aggregdata)
if(input$mon_unit_type=="Concentration"){
y = selectedmonthdata$alldata
y = droplevels(y[order(y$month),])
positions = unique(y[,c("month","position")])
posi = positions[order(positions$month),]
boxplot(y$E.coli_Geomean~y$month, at = unique(y$position), ylab = "E.coli (MPN/100 mL)", xlab = "",col = boxcolors[2], lty = 1, outline = FALSE)
abline(h = crits$geomcrit, col = linecolors[3], lwd = 3, lty = 2)
abline(h = crits$maxcrit, col = linecolors[2], lwd = 3, lty = 2)
legend("topright",legend = c("Max Crit","Geom Crit"), lty = c(2,2), lwd = c(3,3), col = c(linecolors[2],linecolors[3]), bty = "n")
ncounts = selectedmonthdata$aggregdata[,c("month","Ncount")]
ncounts = ncounts$Ncount[order(ncounts$month)]
mtext(paste0("n=",ncounts), side = 1, line = 3, at = posi$position, cex=1)
# add data points
if(input$viewmondat){
points(y$position, y$E.coli_Geomean, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
}
if(input$mon_unit_type=="Loading"&input$monthsite%in%workbook$LDC_Data$ML_Name){
monloads_flat = selectedmonthdata$alldata
# Get boxplot labels
monlabs = sort(unique(monloads_flat$month))
monthpositions = c(1:35)
spacing = monthpositions%%3
where = monthpositions[!spacing==0]
monlab_pos = where[c(TRUE, FALSE)]+0.5
repmons = data.frame("month" = rep(month.abb, each = 2), "position" = where, "Load_Type"= rep(c("TMDL","Observed_Loading"),12))
# data frame with all loading data and their positions
pointpos = merge(monloads_flat, repmons, all.x = TRUE)
boxplot(monloads_flat$Loading~monloads_flat$Load_Type+monloads_flat$month, at = where, xaxt = "n", ylab = "Loading (GigaMPN/day)", xlab = "",col = boxcolors[1:2], lty = 1, outline = FALSE)
axis(side = 1, at = monlab_pos,labels = month.abb)
legend("topright",legend = c("TMDL","Observed Loading"), pch = c(22,22), col = "black", pt.bg = c(boxcolors[1],boxcolors[2]), pt.cex = 1.5, bty = "n")
mtext(paste0("n=",selectedmonthdata$aggregdata$Ncount), side = 1, line = 3, at = where, cex= 0.7)
if(input$viewmondat){
points(pointpos$position, pointpos$Loading, pch = 22, cex = 1, col = "black", bg = boxcolors[3])
}
}
})
################################## REC TAB SECTION ##########################################
# Sites to choose from
output$recsite <- renderUI({
req(workbook$Rec_Season_Data)
recsites <- unique(workbook$Rec_Season_Data$ML_Name)
selectInput("recsite",
label = "Site Name",
choices=recsites)
})
# Craft drop down menu for concentration and loading
output$rec_unit_type <- renderUI({
req(workbook$Rec_Season_Data)
recdata <- workbook$Rec_Season_Data
recdata = recdata[recdata$ML_Name==input$recsite&!is.na(recdata$Observed_Loading),"Observed_Loading"]
if(length(recdata)>0){
subd=c("Concentration","Loading")
}else{subd=c("Concentration")}
selectInput("rec_unit_type","Select Measurement Type", choices = subd, selected = subd[1])
})
# Create rec data reactive object
recdataset <- reactiveValues()
observe({
req(input$rec_unit_type)
recdataset$aggregdat = workbook$Rec_Season_Data[workbook$Rec_Season_Data$ML_Name==input$recsite,]
if(input$rec_unit_type=="Concentration"){
concdata = workbook$Daily_Geomean_Data[workbook$Daily_Geomean_Data$ML_Name==input$recsite,]
concdata$Year = lubridate::year(concdata$Date)
concdata$Rec_Season = factor(concdata$Rec_Season, levels = c("Rec Season","Not Rec Season"))
recdataset$data = concdata
# For the table
aggreg = recdataset$aggregdat
concmed = aggregate(E.coli_Geomean~Rec_Season+Year, data = concdata, FUN = median)
names(concmed)[names(concmed)=="E.coli_Geomean"] <- "Median"
aggreg1 = merge(aggreg, concmed, all.x = TRUE)
aggreg1$E.coli_Geomean = round(aggreg1$E.coli_Geomean, digits = 1)
aggreg2 = aggreg1[,c("Year","Rec_Season","Ncount_rec_C","E.coli_Geomean","Median","Percent_Reduction_C")]
names(aggreg2) = c("Year","Season","Ncount","Geomean (MPN/100 mL)", "Median (MPN/100 mL)", "Percent Reduction (%)")
output$Rec_Data <- renderDT(aggreg2,
rownames = FALSE,selection='none',
options = list(scrollY = '700px', paging = FALSE, scrollX=FALSE, dom = "t"))
}
if(input$rec_unit_type=="Loading"&input$recsite%in%workbook$LDC_Data$ML_Name){
loaddat = workbook$LDC_Data[workbook$LDC_Data$ML_Name==input$recsite,]
# Because flow data may be present outside of the time period of ecoli data, ensure loading dataset cut to a date range with both TMDL and observed loading
mindate = min(loaddat$Date[!is.na(loaddat$Observed_Loading)])
maxdate = max(loaddat$Date[!is.na(loaddat$Observed_Loading)])
loaddat = loaddat[loaddat$Date>=mindate&loaddat$Date<=maxdate,]
loaddat$Year = lubridate::year(loaddat$Date)
recdataset$data = loaddat
# For the table
aggreg = recdataset$aggregdat
# Calculate median
oloadmed = aggregate(Observed_Loading~Rec_Season+Year, data = loaddat, FUN = median)
oloadmed$Load_Type = "Observed_Loading"
names(oloadmed)[names(oloadmed)=="Observed_Loading"] <- "Median"
tloadmed = aggregate(TMDL~Rec_Season+Year, data = loaddat, FUN = median)
tloadmed$Load_Type = "TMDL"
names(tloadmed)[names(tloadmed)=="TMDL"] <- "Median"
loadmeds = merge(oloadmed, tloadmed, all = TRUE)
# Flatten aggregated data
aggreg1 = tidyr::gather(aggreg, key = "Load_Type", value = "Geomean_Loading", Observed_Loading, TMDL)
aggreg1 = aggreg1[!is.na(aggreg1$Geomean_Loading),]
aggreg2 = merge(aggreg1, loadmeds, all.x = TRUE)
aggreg2$Percent_Reduction_L[aggreg2$Load_Type=="TMDL"] <- "Not applicable"
aggreg3 = aggreg2[,c("Year","Rec_Season","Ncount_rec_L","Load_Type","Geomean_Loading","Median","Percent_Reduction_L")]
aggreg3$Geomean_Loading = round(aggreg3$Geomean_Loading, digits = 1)
names(aggreg3) = c("Year","Season","Ncount","Load Type","Geomean (GigaMPN/day)", "Median (GigaMPN/day)", "Percent Reduction (%)")
output$Rec_Data <- renderDT(aggreg3,
rownames = FALSE,selection='none',filter="top",
options = list(scrollY = '700px', paging = FALSE, scrollX=FALSE, dom = "t"))
}
})
output$Rec_Geomeans <- renderPlot({
req(input$rec_unit_type)
recdata = recdataset$data
aggdata = recdataset$aggregdat
if(input$rec_unit_type=="Concentration"){
# Get x-axis set up
yearnum = length(unique(recdata$Year))
positions = 1:(yearnum*2+(yearnum-1))
rid = positions%%3
positions = positions[!rid==0]
yearpos = data.frame("Year"=rep(unique(recdata$Year),each = 2), "position" = positions, "Rec_Season" = rep(c("Rec Season","Not Rec Season"),yearnum))
yearlab = data.frame("position" = positions[c(TRUE,FALSE)]+0.5, "Year" = unique(recdata$Year))
recdata1 = merge(recdata,yearpos, all.x = TRUE)
aggdata1 = merge(aggdata, yearpos, all.x = TRUE)
boxplot(recdata1$E.coli_Geomean~recdata1$Rec_Season+recdata1$Year, at = positions, xaxt = "n", xlab = "", ylab = "E.coli (MPN/100 mL)",col = boxcolors[1:2], lty = 1, outline = FALSE)
axis(1, at = yearlab$position, label = yearlab$Year)
abline(h = crits$geomcrit, col = linecolors[3], lwd = 3, lty = 2)
abline(h = crits$maxcrit, col = linecolors[2], lwd = 3, lty = 2)
legend("topleft",legend = c("Rec","Not Rec",paste("Max Crit -",crits$maxcrit),paste("Geom Crit -",crits$geomcrit)), pch = c(22,22,NA,NA), lty = c(NA, NA, 2,2), lwd = c(NA, NA, 3,3), pt.bg = c(boxcolors[1],boxcolors[2],NA,NA), col = c("black","black", linecolors[2],linecolors[3]),bty = "n")
#text(aggdata1$position,rep(-10, length(aggdata1$position)), labels = paste("n =",aggdata1$Ncount_rec_C), cex = 0.7)
mtext(paste("n =",aggdata1$Ncount_rec_C), side = 1, line = 3, at = aggdata1$position, las = 2, cex = 0.9)
# Add data points
if(input$viewrecdat){
points(recdata1$position, recdata1$E.coli_Geomean, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
}
if(input$rec_unit_type=="Loading"&input$recsite%in%workbook$LDC_Data$ML_Name){
recdata2 = recdata[!is.na(recdata$Rec_Season),]
recdata_flat = tidyr::gather(recdata2, key = "Type", value = "Load", c("TMDL","Observed_Loading"))
plotrange = c(min(recdata_flat$Load),max(recdata_flat$Load))
### Rec season
recl = recdata_flat[which(recdata_flat$Rec_Season=="Rec Season"),]
# Get x-axis set up
yearnum1 = length(unique(recl$Year))
positions1 = 1:(yearnum1*2+(yearnum1-1))
rid1 = positions1%%3
positions1 = positions1[!rid1==0]
yearpos1 = data.frame("Year"=rep(unique(recl$Year),each = 2), "position" = positions1, "Type" = rep(c("Observed_Loading","TMDL"),yearnum1))
yearlab1 = data.frame("position" = positions1[c(TRUE,FALSE)]+0.5, "Year" = unique(recl$Year))
recl = merge(recl,yearpos1, all.x = TRUE)
aggdata1 = merge(aggdata, yearlab1, all.x = TRUE)
aggyear1 = unique(aggdata1[which(aggdata1$Rec_Season=="Rec Season"),c("Year","Ncount_rec_L","position")])
aggyear1 = aggyear1[complete.cases(aggyear1),]
### Not rec season
nrecl = recdata_flat[which(recdata_flat$Rec_Season=="Not Rec Season"),]
# Get x-axis set up
yearnum2 = length(unique(nrecl$Year))
positions2 = 1:(yearnum2*2+(yearnum2-1))
rid2 = positions2%%3
positions2 = positions2[!rid2==0]
yearpos2 = data.frame("Year"=rep(unique(nrecl$Year),each = 2), "position" = positions2, "Type" = rep(c("Observed_Loading","TMDL"),yearnum2))
yearlab2 = data.frame("position" = positions2[c(TRUE,FALSE)]+0.5, "Year" = unique(nrecl$Year))
nrecl = merge(nrecl,yearpos2, all.x = TRUE)
aggdata2 = merge(aggdata, yearlab2, all.x = TRUE)
aggyear2 = unique(aggdata2[which(aggdata2$Rec_Season=="Not Rec Season"),c("Year","Ncount_rec_L","position")])
aggyear2 = aggyear2[complete.cases(aggyear2),]
par(mfrow = c(1,2))
boxplot(recl$Load~recl$Type+recl$Year, at = positions1, main = "Rec Season", xaxt = "n", xlab = "", ylab = "Loading (GigaMPN/day)",ylim = c(0,plotrange[2]),col = boxcolors[c(1,3)], lty = 1, outline = FALSE)
axis(1, at = yearlab1$position, label = yearlab1$Year)
legend("topleft",legend = c("Rec Season","Not Rec Season","TMDL"), pch = c(22,22,22), pt.bg = c(boxcolors[1],boxcolors[2],boxcolors[3]), col = c("black","black", "black"),bty = "n")
text(aggyear1$position,rep(-10, length(aggyear1$position)), labels = paste("n =",aggyear1$Ncount_rec_L), cex = 0.8)
if(input$viewrecdat){
points(recl$position, recl$Load, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
boxplot(nrecl$Load~nrecl$Type+nrecl$Year, at = positions2, main = "Not Rec Season", xaxt = "n", xlab = "", ylim = c(0,plotrange[2]),ylab = "",col = boxcolors[c(2,3)], lty = 1, outline = FALSE)
axis(1, at = yearlab2$position, label = yearlab2$Year)
text(aggyear2$position,rep(-10, length(aggyear2$position)), labels = paste("n =",aggyear2$Ncount_rec_L), cex = 0.8)
if(input$viewrecdat){
points(nrecl$position, nrecl$Load, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
}
})
############################### IRRIGATION SEASON TAB #######################################
# Sites to choose from
output$irgsite <- renderUI({
req(workbook$Irg_Season_Data)
irgsites <- unique(workbook$Irg_Season_Data$ML_Name)
selectInput("irgsite",
label = "Site Name",
choices=irgsites)
})
# Craft drop down menu for concentration and loading
output$irg_unit_type <- renderUI({
req(workbook$Irg_Season_Data)
irgdata <- workbook$Irg_Season_Data
irgdata = irgdata[irgdata$ML_Name==input$irgsite&!is.na(irgdata$Observed_Loading),"Observed_Loading"]
if(length(irgdata)>0){
subd=c("Concentration","Loading")
}else{subd=c("Concentration")}
selectInput("irg_unit_type","Select Measurement Type", choices = subd, selected = subd[1])
})
# Create irg data reactive object
irgdataset <- reactiveValues()
observe({
req(input$irg_unit_type)
irgdataset$aggregdat = workbook$Irg_Season_Data[workbook$Irg_Season_Data$ML_Name==input$irgsite,]
if(input$irg_unit_type=="Concentration"){
concdata = workbook$Daily_Geomean_Data[workbook$Daily_Geomean_Data$ML_Name==input$irgsite,]
concdata$Year = lubridate::year(concdata$Date)
concdata$Irg_Season = factor(concdata$Irg_Season, levels = c("Irrigation Season","Not Irrigation Season"))
irgdataset$data = concdata
# For the table
aggreg = irgdataset$aggregdat
concmed = aggregate(E.coli_Geomean~Irg_Season+Year, data = concdata, FUN = median)
names(concmed)[names(concmed)=="E.coli_Geomean"] <- "Median"
aggreg1 = merge(aggreg, concmed, all.x = TRUE)
aggreg1$E.coli_Geomean = round(aggreg1$E.coli_Geomean, digits = 1)
aggreg2 = aggreg1[,c("Year","Irg_Season","Ncount_irg_C","E.coli_Geomean","Median","Percent_Reduction_C")]
names(aggreg2) = c("Year","Season","Ncount","Geomean (MPN/100 mL)", "Median (MPN/100 mL)", "Percent Reduction (%)")
output$Irg_Data <- renderDT(aggreg2,
rownames = FALSE,selection='none',
options = list(scrollY = '700px', paging = FALSE, scrollX=FALSE, dom = "t"))
}
if(input$irg_unit_type=="Loading"&input$irgsite%in%workbook$LDC_Data$ML_Name){
loaddat = workbook$LDC_Data[workbook$LDC_Data$ML_Name==input$irgsite,]
# Because flow data may be present outside of the time period of ecoli data, ensure loading dataset cut to a date range with both TMDL and observed loading
mindate = min(loaddat$Date[!is.na(loaddat$Observed_Loading)])
maxdate = max(loaddat$Date[!is.na(loaddat$Observed_Loading)])
loaddat = loaddat[loaddat$Date>=mindate&loaddat$Date<=maxdate,]
loaddat$Year = lubridate::year(loaddat$Date)
irgdataset$data = loaddat
# For the table
aggreg = irgdataset$aggregdat
# Calculate median
oloadmed = aggregate(Observed_Loading~Irg_Season+Year, data = loaddat, FUN = median)
oloadmed$Load_Type = "Observed_Loading"
names(oloadmed)[names(oloadmed)=="Observed_Loading"] <- "Median"
tloadmed = aggregate(TMDL~Irg_Season+Year, data = loaddat, FUN = median)
tloadmed$Load_Type = "TMDL"
names(tloadmed)[names(tloadmed)=="TMDL"] <- "Median"
loadmeds = merge(oloadmed, tloadmed, all = TRUE)
# Flatten aggregated data
aggreg1 = tidyr::gather(aggreg, key = "Load_Type", value = "Geomean_Loading", Observed_Loading, TMDL)
aggreg1 = aggreg1[!is.na(aggreg1$Geomean_Loading),]
aggreg2 = merge(aggreg1, loadmeds, all.x = TRUE)
aggreg2$Percent_Reduction_L[aggreg2$Load_Type=="TMDL"] <- "Not applicable"
aggreg3 = aggreg2[,c("Year","Irg_Season","Ncount_irg_L","Load_Type","Geomean_Loading","Median","Percent_Reduction_L")]
aggreg3$Geomean_Loading = round(aggreg3$Geomean_Loading, digits = 1)
names(aggreg3) = c("Year","Season","Ncount","Load Type","Geomean (GigaMPN/day)", "Median (GigaMPN/day)", "Percent Reduction (%)")
output$Irg_Data <- renderDT(aggreg3,
rownames = FALSE,selection='none',filter="top",
options = list(scrollY = '700px', paging = FALSE, scrollX=FALSE, dom = "t"))
}
})
output$Irg_Geomeans <- renderPlot({
req(input$irg_unit_type)
irgdata = irgdataset$data
aggdata = irgdataset$aggregdat
if(input$irg_unit_type=="Concentration"){
# Get x-axis set up
yearnum = length(unique(irgdata$Year))
positions = 1:(yearnum*2+(yearnum-1))
rid = positions%%3
positions = positions[!rid==0]
yearpos = data.frame("Year"=rep(unique(irgdata$Year),each = 2), "position" = positions, "Irg_Season" = rep(c("Irrigation Season","Not Irrigation Season"),yearnum))
yearlab = data.frame("position" = positions[c(TRUE,FALSE)]+0.5, "Year" = unique(irgdata$Year))
irgdata1 = merge(irgdata,yearpos, all.x = TRUE)
aggdata1 = merge(aggdata, yearpos, all.x = TRUE)
boxplot(irgdata1$E.coli_Geomean~irgdata1$Irg_Season+irgdata1$Year, at = positions, xaxt = "n", xlab = "", ylab = "E.coli (MPN/100 mL)",col = boxcolors[1:2], lty = 1, outline = FALSE)
axis(1, at = yearlab$position, label = yearlab$Year)
abline(h = crits$geomcrit, col = linecolors[3], lwd = 3, lty = 2)
abline(h = crits$maxcrit, col = linecolors[2], lwd = 3, lty = 2)
legend("topleft",legend = c("Irrigation","Not Irrigation",paste("Max Crit -",crits$maxcrit),paste("Geom Crit -",crits$geomcrit)), pch = c(22,22,NA,NA), lty = c(NA, NA, 2,2), lwd = c(NA, NA, 3,3), pt.bg = c(boxcolors[1],boxcolors[2],NA,NA), col = c("black","black", linecolors[2],linecolors[3]),bty = "n")
#text(aggdata1$position,rep(-10, length(aggdata1$position)), labels = paste("n =",aggdata1$Ncount_irg_C), cex = 0.7)
mtext(paste("n =",aggdata1$Ncount_irg_C), side = 1, line = 3, at = aggdata1$position, las = 2, cex = 0.9)
# Add data points
if(input$viewirgdat){
points(irgdata1$position, irgdata1$E.coli_Geomean, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
}
if(input$irg_unit_type=="Loading"&input$irgsite%in%workbook$LDC_Data$ML_Name){
irgdata2 = irgdata[!is.na(irgdata$Irg_Season),]
irgdata_flat = tidyr::gather(irgdata2, key = "Type", value = "Load", c("TMDL","Observed_Loading"))
plotrange = c(min(irgdata_flat$Load),max(irgdata_flat$Load))
### Rec season
irgl = irgdata_flat[which(irgdata_flat$Irg_Season=="Irrigation Season"),]
# Get x-axis set up
yearnum1 = length(unique(irgl$Year))
positions1 = 1:(yearnum1*2+(yearnum1-1))
rid1 = positions1%%3
positions1 = positions1[!rid1==0]
yearpos1 = data.frame("Year"=rep(unique(irgl$Year),each = 2), "position" = positions1, "Type" = rep(c("Observed_Loading","TMDL"),yearnum1))
yearlab1 = data.frame("position" = positions1[c(TRUE,FALSE)]+0.5, "Year" = unique(irgl$Year))
irgl = merge(irgl,yearpos1, all.x = TRUE)
aggdata1 = merge(aggdata, yearlab1, all.x = TRUE)
aggyear1 = unique(aggdata1[which(aggdata1$Irg_Season=="Irrigation Season"),c("Year","Ncount_irg_L","position")])
aggyear1 = aggyear1[complete.cases(aggyear1),]
### Not irg season
nirgl = irgdata_flat[which(irgdata_flat$Irg_Season=="Not Irrigation Season"),]
# Get x-axis set up
yearnum2 = length(unique(nirgl$Year))
positions2 = 1:(yearnum2*2+(yearnum2-1))
rid2 = positions2%%3
positions2 = positions2[!rid2==0]
yearpos2 = data.frame("Year"=rep(unique(nirgl$Year),each = 2), "position" = positions2, "Type" = rep(c("Observed_Loading","TMDL"),yearnum2))
yearlab2 = data.frame("position" = positions2[c(TRUE,FALSE)]+0.5, "Year" = unique(nirgl$Year))
nirgl = merge(nirgl,yearpos2, all.x = TRUE)
aggdata2 = merge(aggdata, yearlab2, all.x = TRUE)
aggyear2 = unique(aggdata2[which(aggdata2$Irg_Season=="Not Irrigation Season"),c("Year","Ncount_irg_L","position")])
aggyear2 = aggyear2[complete.cases(aggyear2),]
par(mfrow = c(1,2))
boxplot(irgl$Load~irgl$Type+irgl$Year, at = positions1, main = "Irrigation Season", xaxt = "n", xlab = "", ylab = "Loading (GigaMPN/day)",ylim = c(0,plotrange[2]),col = boxcolors[c(1,3)], lty = 1, outline = FALSE)
axis(1, at = yearlab1$position, label = yearlab1$Year)
legend("topleft",legend = c("Irrigation Season","Not Irrigation Season","TMDL"), pch = c(22,22,22), pt.bg = c(boxcolors[1],boxcolors[2],boxcolors[3]), col = c("black","black", "black"),bty = "n")
text(aggyear1$position,rep(-10, length(aggyear1$position)), labels = paste("n =",aggyear1$Ncount_irg_L), cex = 0.8)
if(input$viewirgdat){
points(irgl$position, irgl$Load, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
boxplot(nirgl$Load~nirgl$Type+nirgl$Year, at = positions2, main = "Not Irrigation Season", xaxt = "n", xlab = "", ylim = c(0,plotrange[2]),ylab = "",col = boxcolors[c(2,3)], lty = 1, outline = FALSE)
axis(1, at = yearlab2$position, label = yearlab2$Year)
text(aggyear2$position,rep(-10, length(aggyear2$position)), labels = paste("n =",aggyear2$Ncount_irg_L), cex = 0.8)
if(input$viewirgdat){
points(nirgl$position, nirgl$Load, pch = 22, cex = 1.2, col = "black", bg = boxcolors[3])
}
}
})
########################################### LOADING TAB ######################################
output$LDC <- renderPlot({
req(input$pt_type)
req(input$ldcsite)
ldcdata = workbook$LDC_Data
x = ldcdata[ldcdata$ML_Name==input$ldcsite,]
flow.plot <- x[order(x$Flow_Percentile),]
flow.plot$Regime = "Low"
flow.plot$Regime[flow.plot$Flow_Percentile<=90] = "Dry"
flow.plot$Regime[flow.plot$Flow_Percentile<=60] = "Mid"
flow.plot$Regime[flow.plot$Flow_Percentile<=40] = "Moist"
flow.plot$Regime[flow.plot$Flow_Percentile<=10] = "High"
exc_regime <- function(x){
x = x[!is.na(x$Observed_Loading),]
exceed = round(length(x$Observed_Loading[x$Observed_Loading>x$TMDL])/length(x$Observed_Loading)*100, digits = 0)
}
flow_exc = plyr::ddply(.data = flow.plot, .variables = c("Regime"), .fun = exc_regime)
names(flow_exc)[names(flow_exc)=="V1"] = "Percent Exceedance"
flow_exc$`Percent Exceedance` = paste(flow_exc$`Percent Exceedance`,"%")
# Pull out observed loadings (E.coli data)
ecoli.loads <- x[!is.na(x$E.coli_Geomean),]
plot(1, type="n", xlab="Flow Exceedance Percentile", ylab="E.coli Load (GigaMPN/day)", xlim=c(0, 100), ylim=c(0,max(c(ecoli.loads$Observed_Loading, ecoli.loads$TMDL))), main=paste("Load Duration Curve:",x$ML_Name[1]))
abline(v=10, lty=2)
abline(v=40, lty=2)
abline(v=60, lty=2)
abline(v=90, lty=2)
text(5, max(ecoli.loads$Observed_Loading)-.3*max(ecoli.loads$Observed_Loading),paste0("High \n Flows \n (",flow_exc$`Percent Exceedance`[flow_exc$Regime=="High"],")"))
text(25, max(ecoli.loads$Observed_Loading)-.3*max(ecoli.loads$Observed_Loading), paste0("Moist \n Conditions \n (",flow_exc$`Percent Exceedance`[flow_exc$Regime=="Moist"],")"))
text(50, max(ecoli.loads$Observed_Loading)-.3*max(ecoli.loads$Observed_Loading), paste0("Mid-Range \n Flows \n (",flow_exc$`Percent Exceedance`[flow_exc$Regime=="Mid"],")"))
text(75, max(ecoli.loads$Observed_Loading)-.3*max(ecoli.loads$Observed_Loading), paste0("Dry \n Conditions \n (",flow_exc$`Percent Exceedance`[flow_exc$Regime=="Dry"],")"))
text(95, max(ecoli.loads$Observed_Loading)-.3*max(ecoli.loads$Observed_Loading),paste0("Low \n Flows \n (",flow_exc$`Percent Exceedance`[flow_exc$Regime=="Low"],")"))
lines(flow.plot$TMDL~flow.plot$Flow_Percentile, col="firebrick3", lwd=2)
# Plot types
if(input$ldc_type == "Scatterplot"){
if(input$pt_type=="Calendar Seasons"){
colpal <- colorspace::sequential_hcl(4)
wine <- ecoli.loads[ecoli.loads$CalSeason=="Winter",]
spre <- ecoli.loads[ecoli.loads$CalSeason=="Spring",]
sume <- ecoli.loads[ecoli.loads$CalSeason=="Summer",]
fale <- ecoli.loads[ecoli.loads$CalSeason=="Fall",]
points(wine$Observed_Loading~wine$Flow_Percentile, pch=21, col="black", bg=colpal[4], cex=2)
points(spre$Observed_Loading~spre$Flow_Percentile, pch=21, col="black", bg=colpal[3], cex=2)
points(sume$Observed_Loading~sume$Flow_Percentile, pch=21, col="black", bg=colpal[2], cex=2)
points(fale$Observed_Loading~fale$Flow_Percentile, pch=21, col="black", bg=colpal[1], cex=2)
legend("topright",legend=c("TMDL", "E.coli Loading - Winter", "E.coli Loading - Spring", "E.coli Loading - Summer","E.coli Loading - Fall"), bty="n", col=c("firebrick3","black","black","black","black"), lty=c(1,NA,NA,NA,NA),lwd=c(2,NA,NA,NA,NA),pch=c(NA,21,21,21,21), pt.bg=c(NA,colpal[4],colpal[3],colpal[2],colpal[1]), pt.cex=c(NA,2,2,2,2),cex=1)
}
# Point colors
if(input$pt_type=="Recreation Seasons"){
colpal <- colorspace::rainbow_hcl(2)
rec <- ecoli.loads[ecoli.loads$Rec_Season=="Rec Season",]
nonrec <- ecoli.loads[ecoli.loads$Rec_Season=="Not Rec Season",]
points(rec$Observed_Loading~rec$Flow_Percentile, pch=21, col="black", bg=colpal[1], cex=2)
points(nonrec$Observed_Loading~nonrec$Flow_Percentile, pch=21, col="black", bg=colpal[2], cex=2)
legend("topright",legend=c("TMDL","E.coli Loading - Rec", "E.coli Loading - Non-Rec"), bty="n", col=c("firebrick3","black","black"), lty=c(1,NA,NA),lwd=c(2,NA,NA),pch=c(NA,21,21), pt.bg=c(NA,colpal), pt.cex=c(NA,2,2),cex=1)
}
if(input$pt_type=="Irrigation Seasons"){
colpal <- colorspace::terrain_hcl(2)
irg <- ecoli.loads[ecoli.loads$Irg_Season=="Irrigation Season",]
nonirg <- ecoli.loads[ecoli.loads$Irg_Season=="Not Irrigation Season",]
points(irg$Observed_Loading~irg$Flow_Percentile, pch=21, col="black", bg=colpal[1], cex=2)
points(nonirg$Observed_Loading~nonirg$Flow_Percentile, pch=21, col="black", bg=colpal[2], cex=2)
legend("topright",legend=c("TMDL", "E.coli Loading - Irrigation", "E.coli Loading - No Irrigation"), bty="n", col=c("firebrick3","black","black"), lty=c(1,NA,NA),lwd=c(2,NA,NA),pch=c(NA,21,21), pt.bg=c(NA,colpal), pt.cex=c(NA,2,2),cex=1)
}
}else{
colpal <- colorspace::sequential_hcl(4)
# Add boxplots
ecoli.loads$Flow_Cat = "High"
ecoli.loads$Flow_Cat[ecoli.loads$Flow_Percentile>10&ecoli.loads$Flow_Percentile<=40] = "Moist"
ecoli.loads$Flow_Cat[ecoli.loads$Flow_Percentile>40&ecoli.loads$Flow_Percentile<=60] = "MidRange"
ecoli.loads$Flow_Cat[ecoli.loads$Flow_Percentile>60&ecoli.loads$Flow_Percentile<=90] = "Dry"
ecoli.loads$Flow_Cat[ecoli.loads$Flow_Percentile>90&ecoli.loads$Flow_Percentile<=100] = "Low"
ecoli.loads$Flow_Cat = factor(ecoli.loads$Flow_Cat, levels= c("High","Moist", "MidRange","Dry","Low"))
boxplot(ecoli.loads$Observed_Loading~ecoli.loads$Flow_Cat, col=ggplot2::alpha(boxcolors[2],0.7), at = c(5,25,50,75,95),lty=1, xaxt="n", frame=FALSE, boxwex = 5, add=TRUE)
legend("topright",legend=c("TMDL", "E.coli Loading"), bty="n", col=c("firebrick3","black"), lty=c(1,NA),lwd=c(2,NA),pch=c(NA,22), pt.bg=c(NA,ggplot2::alpha(boxcolors[2],0.7)), pt.cex=c(NA,2),cex=1)
}
})
output$LDC_Data <- renderDT(workbook$LDC_Data,
rownames = FALSE,selection='none',filter="top",
options = list(scrollY = '300px', paging = FALSE, scrollX=TRUE))
}
# Run the application
shinyApp(ui = ui, server = server)
#### UNUSED CODE ####
# out$geom_crit = out$Inputs[out$Inputs$Parameter=="Geometric Mean Criterion","Value"]
# out$max_crit = out$Inputs[out$Inputs$Parameter=="Max Criterion","Value"]
# out$cf = out$Inputs[out$Inputs$Parameter=="Correction Factor","Value"]
# out$mos = out$Inputs[out$Inputs$Parameter=="Margin of Safety","Value"]
# output$Monthly_Geomeans <- renderPlotly({
# req(selectedmonthdata$seldg)
# y = selectedmonthdata$seldg
# y = droplevels(y[order(y$month),])
# monthmed = tapply(y$E.coli_Geomean, y$month, median)
# monthmed_pos = rep(max(monthmed)*-0.05, length(monthmed))
# monthn_count = tapply(y$E.coli_Geomean, y$month, length)
# month_geomean = tapply(y$E.coli_Geomean, y$month, function(x){exp(mean(log(x)))})
# perc_red = ifelse(month_geomean>crits$geomcrit,round(perc.red(crits$geomcrit,month_geomean), digits=0),0)
# # Add criteria
# geom = list(type = 'line', x0 = -1, x1 = length(monthmed_pos), y0 = crits$geomcrit, y1 = crits$geomcrit, line=list(dash='dot', color = "orange", width=2))
# max = list(type = 'line', x0 = -1, x1 = length(monthmed_pos), y0 = crits$maxcrit, y1 = crits$maxcrit, line=list(dash='dot', color = "red", width=2))
#
# # initiate a line shape object
# line <- list(
# type = "line",
# line = list(color = "green"),
# xref = "x",
# yref = "y"
# )
#
# lines <- list()
# for (i in c(0:(length(monthmed_pos)-1))) {
# line[["x0"]] <- i-0.25
# line[["x1"]] <- i + 0.25
# line[c("y0", "y1")] <- month_geomean[i+1]
# lines <- c(lines, list(line))
# }
#
# line[["x0"]] <- -1
# line[["x1"]] <- length(monthmed_pos)
# line[c("y0", "y1")] <- crits$geomcrit
# line$line$color = "orange"
# lines <- c(lines, list(line))
#
# line[["x0"]] <- -1
# line[["x1"]] <- length(monthmed_pos)
# line[c("y0", "y1")] <- crits$maxcrit
# line$line$color = "red"
# lines <- c(lines, list(line))
#
# # add = selectedmonthdata$aggseldg
# # add = droplevels(add[order(add$month),])
# #barcolors = piratepal(palette="up")
# if(input$mon_unit_type=="Concentration"){
# month_c = plot_ly(x =~y$month, y =~y$E.coli_Geomean, type ="box", boxpoints = "outliers")%>%
# layout(xaxis = list(title = ""), yaxis = list(title = "E.coli Concentration (MPN/100 mL)"),font = list(family = "Arial, sans-serif"), shapes = lines)%>%
# add_annotations(x = 0:(length(monthmed_pos)-1), y = monthmed_pos, text = paste("n =",monthn_count), showarrow = FALSE)
# month_c
# # # Straight bar plot - concentrations
# # uplim = max(x$E.coli_Geomean)*1.2
# # mo_conc.p <- x$E.coli_Geomean
# # barp <- barplot(mo_conc.p, main = "Monthly E.coli Concentration Geomeans", ylim=c(0, uplim), names.arg = x$month,ylab="E.coli Concentration (MPN/100 mL)",col=barcolors[1])
# # legend("topright",legend=c("Geomean Standard", "% Reduction Needed"), bty="n", fill=c("white","white"), border=c("white","white"),lty=c(1,NA),lwd=c(2,NA),cex=1)
# # box(bty="l")
# # abline(h=crits$geomcrit, col="black", lwd=2)
# # ncount = paste0("n=",x$Ncount)
# # mtext(ncount, side = 1, line = 0, cex=0.8, at = barp)
# # barperc <- data.frame(cbind(barp,x$E.coli_Geomean, x$Percent_Reduction))
# # barperc <- barperc[barperc$X3>0,]
# # if(dim(barperc)[1]>0){
# # barperc$X4 <- paste(barperc$X3,"%",sep="")
# # text(barperc$X1,barperc$X2+0.1*mean(barperc$X2),labels=barperc$X4,cex=1)
# # }
# # if(input$mon_medplot){
# # # Obtain boxplot stats from loading data
# # y = selectedmonthdata$seldg
# # y = droplevels(y[order(y$month),])
# #
# # # Get axes right to accommodate boxplot overlay (if checkbox checked)
# # uplim1 = quantile(y$E.coli_Geomean,1)
# # uplim1 = max(uplim, uplim1)
# #
# # # Bar plot
# # barp <- barplot(mo_conc.p, main = "Monthly E.coli Concentration Geomeans with Quartile Overlay", ylim=c(0, uplim1), names.arg = x$month, ylab="E.coli Concentration (MPN/100 mL)",col=barcolors[1])
# # abline(h=crits$geomcrit, col="black", lty=2, lwd=2)
# # legend("topright",legend=c("Median", "Geomean Standard","Outliers"), bty="n", pch=c(NA,NA,1),fill=c(NA,NA,"white"),border=c("white","white","white"),lty=c(1,2,NA),lwd=c(3,2,NA),cex=1)
# # box(bty="l")
# # mtext(ncount, side = 1, line = 0, cex = 0.8, at = barp)
# #
# # # x-axis arguments for boxplot based on barplot placement
# #
# # boxplot(y$E.coli_Geomean~y$month,
# # lty=1, xaxt="n", frame=FALSE, col=ggplot2::alpha(barcolors[1],0.1), boxwex = 0.7, at=barp[,1], add=TRUE)
# # }
# }
# if(input$mon_unit_type=="Loading"){
# cols = piratepal(palette="up")
# # Narrow dataset
# monthdatl <- workbook$LDC_Data
# datrange <- monthdatl[monthdatl$ML_Name==input$monthsite&monthdatl$Date>=input$mondatrange[1]&monthdatl$Date<=input$mondatrange[2],c("MLID","ML_Name","Date","TMDL","Observed_Loading")]
# if(dim(datrange)[1]>0){
# datrange <- datrange[!is.na(datrange$Observed_Loading),]
# datstack <- reshape2::melt(data = datrange, id.vars = c("MLID", "ML_Name", "Date"), value.vars=c("TMDL","Observed_Loading"), variable.name = "Meas_Type")
# datstack$month = lubridate::month(datstack$Date, label=TRUE)
# datstack$Meas_Type = factor(datstack$Meas_Type, levels = levels(datstack$Meas_Type)[c(2,1)])
# names(datstack)[names(datstack)=="value"]<-"Loading"
# x <- aggregate(Loading~month+MLID+ML_Name+Meas_Type, dat=datstack, FUN=function(x){exp(mean(log(x)))})
# x_ncount <- aggregate(Loading~month+MLID+ML_Name+Meas_Type, dat=datstack, FUN=length)
# x_ncount <- x_ncount[x_ncount$Meas_Type=="Observed_Loading",]
# names(x_ncount)[names(x_ncount)=="Loading"]<- "Ncount"
# x_ncount = x_ncount[order(x_ncount$month),]
# x = dcast(data=x, month~Meas_Type, value.var="Loading")
# x = x[order(x$month),]
# x$Percent_Reduction = ifelse(x$Observed_Loading>x$TMDL,round(perc.red(x$TMDL,x$Observed_Loading), digits=0),0)
# uplim = max(c(x$Observed_Loading,x$TMDL))*1.2
# mo_load.p <- x[,names(x)%in%c("Observed_Loading","TMDL")]
#
# # Straight bar plots
# barp <- barplot(t(mo_load.p), beside=T, main = "Monthly E.coli Loading Geomeans",names.arg=x$month, ylim=c(0, uplim), ylab="E.coli Loading (GigaMPN/day)",col=c(cols[1],cols[2]))
# legend("topright",legend=c("Observed Loading","TMDL", "% Reduction Needed"), bty="n", fill=c(cols[1],cols[2],"white"), border=c("black","black","white"),cex=1)
# box(bty="l")
# barps <- barp[1,]
# barperc <- data.frame(cbind(barps,x$Observed_Loading, x$Percent_Reduction))
# barperc <- barperc[barperc$V3>0,]
# if(dim(barperc)[1]>0){
# barperc$V3 <- paste(barperc$V3,"%",sep="")
# text(barperc$barps,barperc$V2+0.1*mean(barperc$V2),labels=barperc$V3,cex=1)
# }
#
# # Add ncounts
# ncountpos = colMeans(barp)
# mtext(c(paste0("n=",x_ncount$Ncount)),side = 1,line = 0,at = ncountpos, cex=0.8)
#
# if(input$mon_medplot){
# # Get axes right to accommodate boxplot overlay (if checkbox checked)
# uplim1 = quantile(datstack$Loading,1)
# uplim1 = max(uplim, uplim1)
#
# # Bar plot
# barp <- barplot(t(mo_load.p), beside=T, names.arg = x$month, main = "Monthly E.coli Loading Geomeans with Quartile Overlay", ylim=c(0, uplim1*1.1), ylab="E.coli Loading (GigaMPN/day)",col=c(cols[1],cols[2]))
# legend("topright",legend=c("Observed Loading","TMDL", "Median","Outliers"), bty="n", pch=c(NA,NA,NA,1),fill=c(cols[1],cols[2],NA,"white"),border=c("black","black","white","white"),lty=c(NA,NA,1,NA),lwd=c(NA,NA,3,NA),cex=1)
# box(bty="l")
# mtext(c(paste0("n=",x_ncount$Ncount)),side = 1,line = 0,at = ncountpos, cex=0.8)
# # x-axis arguments for boxplot based on barplot placement
# ax <- c(barp[1,],barp[2,])
# ax_spots = ax[order(ax)]
#
# boxplot(datstack$Loading~datstack$Meas_Type+lubridate::month(datstack$Date),
# lty=1, xaxt="n", frame=FALSE, col=ggplot2::alpha(c(cols[1],cols[2]),0.1), boxwex = 0.7, at=ax_spots, add=TRUE)
# }
# }
# }
# })
# month_c = plot_ly(x =~y$month, y =~y$E.coli_Geomean, type ="box", name = "Monthly Concentrations",boxpoints = "outliers")%>%
# #add_trace(x = month_geomean_df$month, y = month_geomean_df$E.coli_Geomean, name = "Monthly Geomean", line = list(color = "gold"))%>%
# layout(xaxis = list(title = ""), yaxis = list(title = "E.coli Concentration (MPN/100 mL)"),font = list(family = "Arial, sans-serif"), xaxis2 = list(overlaying = "x", showticklabels = FALSE, showline = FALSE))%>%
# add_trace(x = ~c(0,1), y = ~c(crits$maxcrit, crits$maxcrit), type = "scatter", mode = "lines", name = "Max Crit", xaxis = "x2", line = list(color = "green", dash = "dot"))%>%
# add_trace(x = ~c(0,1), y = ~c(crits$geomcrit, crits$geomcrit), type = "scatter", mode = "lines", name = "Geomean Crit", xaxis = "x2", line = list(color = "red", dash = "dot")) #%>%
# #add_annotations(x = 0:(length(monthmed_pos)-1), y = monthmed_pos, text = paste("n =",monthn_count), showarrow = FALSE)%>%
# #add_annotations(x = perc_red_df$xpos, y = perc_red_df$ypos, text = paste0(perc_red_df$perc_red,"%"), showarrow = FALSE, font = list(size = 9))
# month_l = plot_ly(x =~monloads_flat$month, y =~monloads_flat$Loading, color = ~monloads_flat$Load_Type, type ="box", boxpoints = "outliers")%>%
# layout(boxmode = "group", xaxis = list(title = ""), yaxis = list(title = "E.coli Loading (GigaMPN/day)"),font = list(family = "Arial, sans-serif"), xaxis2 = list(overlaying = "x", showticklabels = FALSE, showline = FALSE)) #%>%
# #add_trace(x = ~mloadgeomean$month, y = ~mloadgeomean$Loading, color = ~mloadgeomean$Load_Type, xaxis = "x2", line = list(color = "gold"))
#add_trace(x = month_geomean_df$month, y = month_geomean_df$E.coli_Geomean, name = "Monthly Geomean", line = list(color = "gold"))%>%
#add_annotations(x = 0:(length(monthmed_pos)-1), y = monthmed_pos, text = paste("n =",monthn_count), showarrow = FALSE)%>%
#add_annotations(x = perc_red_df$xpos, y = perc_red_df$ypos, text = paste0(perc_red_df$perc_red,"%"), showarrow = FALSE, font = list(size = 9))
# What data to show in table
# observe({
# req(workbook$Daily_Geomean_Data)
# if(!is.null(timeseriesdat$x1)){
# ecoli_ts = timeseriesdat$x
# flow_ts = timeseriesdat$x1
# timeseriesdat$tabledata = merge(ecoli_ts, flow_ts, all = TRUE)
# }else{
# timeseriesdat$tabledata = timeseriesdat$x
# }
# })
#
# output$Time_Data <- renderDT(timeseriesdat$tabledata,
# rownames = FALSE,selection='none',filter="top",
# options = list(scrollY = '300px', paging = FALSE, scrollX=TRUE))
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.