Printing Out Calculated Values - r

I am in the process of learning R and am having some issues. I am trying to add a tab to my app to calculate a few values based on the data I put in. I have a frame of locations and I have some math I did to calculate the values of interest.
I want to take the value called loft and put a string on the panel that says "Loft at Impact is: XXX" with what number is calculated. The data files have several pages in excel I want to shuffle through. Currently it all works except the values I am trying to calculate. It works as expected in a regular R script but I am struggling getting it into R Shiny. I don't think I understand how to manipulate and deal with reactive data and such. Here is my current code:
#Import needed libraries
library(shiny)
library(readxl)
library(plotly)
library(DT)
#start app
runApp(
list(
ui = fluidPage(
#Main Title
titlePanel("Putt Viewer"),
sidebarLayout(
#File input on sidebar
sidebarPanel(
fileInput('file1', ' .xlsx file',
accept = c(".xlsx")
),
#Shot selection
numericInput('shotSelect','Which Shot Would you like to see?', 1, 1)
),
mainPanel(
#Sets up different panels for the main screen
tabsetPanel(
tabPanel("3D View", plotlyOutput("putterPlot2"),
helpText("3D Rendering of data points.")),
tabPanel("Overhead View", plotlyOutput("putterPlot"),
helpText("Overhead view of the toe and heel fiducial markers.")),
tabPanel("View Raw Data", dataTableOutput("contents"),
helpText("Explore the generated data in a table.")),
tabPanel("Face at Launch", textOutput("contents2"))
)
)
),
),
#starts and runs the server functions
server = function(input, output){
data <- reactive({
req(input$file1)
inFile <- input$file1
data <- read_excel(inFile$datapath, input$shotSelect + 1)
})
impactFrame <- data[nrow(shotData)-1,]
launchPoints <- structure(list(X = c(impactFrame$TToe.x_mm,impactFrame$MToe.x_mm, impactFrame$Heel.x_mm, 0),
Y = c(impactFrame$TToe.y_mm,impactFrame$MToe.y_mm, impactFrame$Heel.y_mm, 0),
Z = c(impactFrame$TToe.z_mm,impactFrame$MToe.z_mm, impactFrame$Heel.z_mm, 0)),
.Names = c("X", "Y", "Z"), row.names = c(NA, 3L), class = "data.frame")
ABi = launchPoints[1,2] - launchPoints[1,1] #x2-x1
ABj = launchPoints[2,2] - launchPoints[2,1] #y2-y1
ABk = launchPoints[3,2] - launchPoints[3,1] #z2-z1
ACi = launchPoints[1,3] - launchPoints[1,1] #x3-x1
ACj = launchPoints[2,3] - launchPoints[2,1] #y3-y1
ACk = launchPoints[3,3] - launchPoints[3,1] #z3-z1
AB = c(ABi, ABj, ABk)
AC = c(ACi, ACj, ACk)
normalijk = cross(AB,AC) #face vector
midABi = ABi / 2 + launchPoints[1,1]
midABj = ABj / 2 + launchPoints[2,1]
midABk = ABk / 2 + launchPoints[3,1]
midABCi = launchPoints[3,1] - midABi
midABCj = launchPoints[3,2] - midABj
midABCk = launchPoints[3,3] - midABk
liePlane = c(midABCi, midABCj, midABCk) #lie plane
loft <- reactiveValues(atan(normalijk[3] / sqrt(normalijk[1] ^ 2 + normalijk[2] ^ 2))) #loft
faceAngle = atan(normalijk[2] / sqrt(normalijk[1] ^ 2 + normalijk[2] ^ 2)) # face angle
lie = atan(liePlane[3] / sqrt(liePlane[1] ^ 2 + liePlane[2] ^ 2))
})
output$contents2 <- renderText(loft)
#Tab 3 output of the data
output$contents <- DT::renderDataTable({
#makes sure there is a file and its correct
req(input$file1)
inFile <- input$file1
data = read_excel(inFile$datapath, input$shotSelect + 1)
data
})
output$putterPlot2 <- renderPlotly({
#makes sure there is a file and its correct
req(input$file1)
inFile <- input$file1
data = read_excel(inFile$datapath, input$shotSelect + 1)
plot_ly(data, x = ~TToe.x_mm, y = ~TToe.y_mm, z = ~TToe.z_mm, type="scatter3d", name = "TToe Fiducials", mode="markers", color = ~Timestamp_ms) %>%
add_trace(x = ~MToe.x_mm, y = ~MToe.y_mm, z = ~MToe.z_mm, type="scatter3d", name = "TToe Fiducials", mode="markers", color = ~Timestamp_ms) %>%
add_trace(x = ~Heel.x_mm, y = ~Heel.y_mm + 3, z = ~Heel.z_mm - 25, type="scatter3d", name = "Heel Fiducials", mode="markers", color = ~Timestamp_ms) %>%
layout(title = 'Putter Face Location Data',
scene = list(xaxis = list(title = 'X (mm)', range = c(-200,200), ticktype = "array"),
yaxis = list(title = 'Y (mm)', range = c(-100,100), ticktype = "array"),
zaxis = list(title = 'Z (mm)', range = c(-100,100), ticktype = "array"),
showlegend = FALSE))
})
output$putterPlot <- renderPlotly({
req(input$file1)
inFile <- input$file1
data = read_excel(inFile$datapath, input$shotSelect + 1)
plot_ly(data, x = ~TToe.x_mm, y = ~TToe.y_mm, type="scatter", name = "Toe Data", mode="markers") %>%
add_trace( x = ~MToe.x_mm, y = ~MToe.y_mm, name = 'Toe Regression Fit', mode = 'lines', alpha = 1) %>%
add_trace(x = ~Heel.x_mm, y = ~Heel.y_mm + 3, type="scatter", name = "Heel Data", mode="markers") %>%
add_trace( x = ~Heel.x_mm, y = ~Heel.y_mm, name = 'Heel Regression Fit', mode = 'lines', alpha = 1) %>%
layout(title = 'Top Down View of Toe and Heel',
scene = list(xaxis = list(title = 'X (mm)', range = c(-200,200), ticktype = "array"),
yaxis = list(title = 'Y (mm)', range = c(-100,100), ticktype = "array"),
showlegend = FALSE))
})
}
)
)

Related

R plotly Update Title When Using Transform Filter

I've created a graph that lets you pick which group's data to plot. I'd like to change the title when you pick the group, but I'm not sure how or if its possible. I'm having trouble learning which way to structure lists for certain plotly parameters. Even if I could add custom text to graph would probably work.
#Working Example so Far
library(plotly)
x <- c(1:100)
random_y <- rnorm(100, mean = 0)
random_y_prim <- rnorm(100, mean = 50)
mydata <- data.frame(x, random_y, random_y_prim, group = rep(letters[1:4], 25))
# Make Group List Button
groupList <- unique(mydata$group)
groupLoop <- list()
for (iter in 1:length(groupList)) {
groupLoop[[iter]] <- list(method = "restyle",
args = list("transforms[0].value", groupList[iter]),
label = groupList[iter])
}
# Set up Axis labeling
f <- list(
family = "Verdana",
size = 18,
color = "#7f7f7f"
)
xLab <- list(
title = "x Axis",
titlefont = f
)
yLab <- list(
title = "y Axis",
titlefont = f
)
fig <- plot_ly(mydata, x = ~x, y = ~random_y
, type = 'scatter', mode = 'lines',
transforms = list(
list(
type = 'filter',
target = ~mydata$group,
operation = '=',
value = groupList[1]
)
)
)
fig <- fig %>%
layout(
title = "Updating Practice",
xaxis = xLab,
yaxis = yLab,
updatemenus = list(
list(
type = 'dropdown',xanchor = 'center',
yanchor = "top",
active = 1,
buttons = groupLoop
)
)
)
fig

Plotly working locally but not on Shiny server

I am trying to create a line graph with two y-axises. The x-axis is the date and both of the y-axises are continuous data. I have working code to do this. It works perfectly, however when I push that to my shiny server (on Ubuntu) I get an error saying that 'x' must be a list. Not sure why this works locally but not on my shiny server.
server.R
dataset <- reactive({
infile <- input$datafile
if (is.null(infile)) {
return(NULL)
}
else {read_excel(infile$datapath)}
})
output$plot_data <- renderPlotly({
# Bring in the data
data <- subset(dataset(), select = c(input$date, input$var1, input$var2))
date <- data[[input$date]]
y_var1 <- data[[input$var1]]
y_var2 <- data[[input$var2]]
y1 <- list(tickfont = list(color = "blue"),
side = "left",
title = input$var1
)
y2 <- list(tickfont = list(color = "green"),
overlaying = "y",
side = "right",
title = input$var2
)
plot <- plot_ly() %>%
add_lines(x = date,
y = y_var1,
name = input$var1,
line = list(color = "blue")) %>%
add_lines(x = date,
y = y_var2,
name = input$var2,
yaxis = "y2",
line = list(color = "green")) %>%
layout(title = "Data Over Time",
yaxis = y1,
yaxis2 = y2
)
plot
ui.R
plotlyOutput('plot_data', height = 500)
Here is some sample data that has a date column and two continuous columns.
Date Impressions Sessions
01/01/2019 34124114 11234323
01/02/2019 43523523 12341244
01/03/2019 56547634 11124324
01/04/2019 65756844 12341234
01/05/2019 32454355 11412432
01/06/2019 23543664 12342412
01/07/2019 23534262 12341244
01/08/2019 12341324 12341234
01/09/2019 34645623 23412341
01/10/2019 64364363 12342123
01/11/2019 24114124 13412342
01/12/2019 23411242 13423442
01/13/2019 24124124 11234242
01/14/2019 42141132 12342144

Shiny Plotly output that changes depending on conditions

I'm trying to make a shiny app for some user-friendly data analysis of some data I have, and I'd like to change the outputted Plotly plot depending on which file i'm looking at. Basically, I'd like to have one plot outputted at a time, where I can cycle through several plots (that don't change place in my shiny app) depending on which folder and criteria i'm using. Currently I'm struggeling with this, and I don't know exactly what to do from here. I've attached a few images to clarify what I mean and what I want.
This photo shows my UI and how I want my figures to be displayed. I'd like all figures to show in that same location, depending on the selected file.
When I switch to 'Datalogger', a new plot is generated, and it is outputted below the first one. I'd like it to be placed on top of it, in the exact same location.
Any help you can offer would be very welcome.
Best,
T.
Script:
# Load packages
library(shiny)
library(shinythemes)
library(dplyr)
library(readr)
library(lubridate)
library(plotly)
#picarro
time = as.character(seq(as.POSIXct("2018-06-01 12:00:00"), as.POSIXct("2018-06-01 12:10:00"), by=seconds() )); ch4.corr = runif(length(time), 1980, 2000);
data = data.frame(time, ch4.corr); data$time = as.POSIXct(time);
#datalogger
time = as.character(seq(as.POSIXct("2018-06-01 12:00:00"), as.POSIXct("2018-06-01 12:10:00"), by=seconds() )); PressureOut = runif(length(time), 1010, 1020);
dlog = data.frame(time, PressureOut); dlog$time = as.POSIXct(time);
#dronelog
time = as.character(seq(as.POSIXct("2018-06-01 12:00:00"), as.POSIXct("2018-06-01 12:10:00"), by=seconds() ));
ulog = data.frame(time); ulog$time = as.POSIXct(time);
#------------------------------------------------------------------------------
ui <- fluidPage(
titlePanel("Active AirCore analysis"),
hr(),
fluidRow(
column(3,
radioButtons("fileInput", "File",
choices = c("Picarro", "Datalogger", "Dronelog"),
selected = "Picarro"),
hr(),
conditionalPanel(
condition = "input.fileInput == 'Picarro'",
sliderInput("timeInputPicarro", "Time", as.POSIXct(data$time[1]), as.POSIXct(data$time[length(data$time)]), c(as.POSIXct(data$time[1])+minutes(1), as.POSIXct(data$time[length(data$time)])-minutes(1)), timeFormat = "%H:%M:%S", ticks = T, step = seconds(1), pre = "")),
conditionalPanel(
condition = "input.fileInput == 'Datalogger'",
sliderInput("timeInputDatalogger", "Time", as.POSIXct(dlog$time[1]), as.POSIXct(dlog$time[length(dlog$time)]), c(as.POSIXct(dlog$time[1]), as.POSIXct(dlog$time[length(dlog$time)])), timeFormat = "%H:%M:%S", ticks = T, step = seconds(1), pre = "")),
conditionalPanel(
condition = "input.fileInput == 'Dronelog'",
sliderInput("timeInputDronelog", "Time", as.POSIXct(ulog$time[1]), as.POSIXct(ulog$time[length(ulog$time)]), c(as.POSIXct(ulog$time[1])+minutes(1), as.POSIXct(ulog$time[length(ulog$time)])-minutes(1)), timeFormat = "%H:%M:%S", ticks = T, step = seconds(1), pre = "")),
hr(),
conditionalPanel(
condition = "input.fileInput == 'Picarro'",
radioButtons("picarroPlotInput", "Plot type",
choices = c("Time-series", "Process"),
selected = "Time-series")),
conditionalPanel(
condition = "input.fileInput == 'Datalogger'",
radioButtons("dataloggerPlotInput", "Plot type",
choices = c("Time-series", "Altitude"),
selected = "Time-series")),
hr(),
checkboxGroupInput(inputId='sidebarOptions',
label=('Options'),
choices=c('Blabla', 'Store data', 'BlablaBla')),
hr()),
br(),
mainPanel(
plotlyOutput("dataplot"),
hr(),
plotlyOutput("dlogplot")
)
)
)
server <- function(input, output, session) {
datasetInputPic <- reactive({ data = data; })
datasetInputPicSamp <- reactive({ dat = data[(data$time>=input$timeInputPicarro[1]) & (data$time<=input$timeInputPicarro[2]),]; })
datasetInputDatalogger <- reactive({ dlog = dlog })
datasetInputDronelog <- reactive({ ulog = ulog })
output$dataplot <- renderPlotly({
if( (input$fileInput == 'Picarro' ) & (input$picarroPlotInput == 'Time-series')){
data = datasetInputPic();
data$time = as.POSIXct(data$time);
dat = datasetInputPicSamp();
dat$time = as.POSIXct(dat$time);
sec.col = "red";
f = list(size = 8);
x <- list(title = " ")
y <- list(title = "CH<sub>4</sub> [ppb]")
p2 = plot_ly() %>%
add_trace(data = data,
x = ~time,
y = ~ch4.corr,
type = 'scatter',
mode = "markers",
marker = list(size = 3, color = 'black')) %>%
add_trace(data = dat,
x = ~time,
y = ~ch4.corr,
type = 'scatter',
mode = "markers",
marker = list(size = 3, color = sec.col)) %>%
layout(xaxis = x, yaxis = y, title = '', showlegend = F, titlefont = f);
s1 = subplot(p2, margin = 0.06,nrows=1,titleY = TRUE) %>%
layout(showlegend = F, margin = list(l=50, r=0, b=50, t=10), titlefont = f);
s1
}
})
output$dlogplot <- renderPlotly({
if( (input$fileInput == 'Datalogger' ) & (input$dataloggerPlotInput == 'Time-series')){
data = datasetInputDatalogger();
data$time = as.POSIXct(data$time);
x <- list(title = " ")
y <- list(title = "Outside pressure [mbar]")
p1 = plot_ly() %>%
add_trace(data = data,
y = ~PressureOut,
x = ~time,
type = 'scatter',
mode = "markers",
marker = list(size = 3, color = 'black'));
s1 = subplot(p1, margin = 0.07, nrows=2, titleY = TRUE, titleX = FALSE)
layout(s1, showlegend = F, margin = list(l=100, r=100, b=0, t=100), title = "Datalogger data")
s1
}
})
outputOptions(output, c("dataplot", "dlogplot"), suspendWhenHidden = TRUE)
}
runApp(list(ui = ui, server = server))
Your issue is that in your ui you have written:
mainPanel(
plotlyOutput("dataplot"),
hr(),
plotlyOutput("dlogplot")
)
Using this structure, the "dlogplot" will always display below the "dataplot" because you essentially gave it its own position in the main panel that is below the "dataplot". One solution, if you want the plots to be displayed in the same exact spot when clicking the various buttons, is to give only one plotlyOutput. Next you would put conditional if, else if and else in renderPlotly. For example:
output$dataplot <- renderPlotly({
if( (input$fileInput == 'Picarro' ) & (input$picarroPlotInput == 'Time-series')){
data = datasetInputPic();
data$time = as.POSIXct(data$time);
dat = datasetInputPicSamp();
dat$time = as.POSIXct(dat$time);
sec.col = "red";
f = list(size = 8);
x <- list(title = " ")
y <- list(title = "CH<sub>4</sub> [ppb]")
p2 = plot_ly() %>%
add_trace(data = data,
x = ~time,
y = ~ch4.corr,
type = 'scatter',
mode = "markers",
marker = list(size = 3, color = 'black')) %>%
add_trace(data = dat,
x = ~time,
y = ~ch4.corr,
type = 'scatter',
mode = "markers",
marker = list(size = 3, color = sec.col)) %>%
layout(xaxis = x, yaxis = y, title = '', showlegend = F, titlefont = f);
s1 = subplot(p2, margin = 0.06,nrows=1,titleY = TRUE) %>%
layout(showlegend = F, margin = list(l=50, r=0, b=50, t=10), titlefont = f);
s1
}
else if( (input$fileInput == 'Datalogger' ) & (input$dataloggerPlotInput == 'Time-series')){
data = datasetInputDatalogger();
data$time = as.POSIXct(data$time);
x <- list(title = " ")
y <- list(title = "Outside pressure [mbar]")
p1 = plot_ly() %>%
add_trace(data = data,
y = ~PressureOut,
x = ~time,
type = 'scatter',
mode = "markers",
marker = list(size = 3, color = 'black'));
s1 = subplot(p1, margin = 0.07, nrows=2, titleY = TRUE, titleX = FALSE)
layout(s1, showlegend = F, margin = list(l=100, r=100, b=0, t=100), title = "Datalogger data")
s1
}
})
This code will put the "dlogplot" and the "dataplot" in the same position in your main panel. (You would also need to get rid of output$dlogplot <- renderPlotly({...}) so that it isn't also trying to make that plot.)
Try this out and see if it works for your purposes.

Render blank plot using plot_geo() in ShinyApp R

I am doing my final project for data visualization.
I would like to render a map with markers on it using Plotly in ShinyApp. The function I am using is plot_geo(). However, the plot works perfectly in the normal R environment, but it fails to render in ShinyApp, only displaying the blank plot. And also no error message is reported.
I have been stuck here for long. Can anyone help? Thanks!
My code (ShinyApp)
library(shiny)
library(plotly)
library(RColorBrewer)
library(ggplot2)
# Define UI for application
ui <- fluidPage(
# Application title
titlePanel("Times University Ranking"),
# Sidebar with a slider input for number of bins
sidebarLayout(
sidebarPanel(
selectInput("year",
"Select a year",
c(2011:2016))
),
# Show a plot of the generated distribution
mainPanel(
plotOutput("map")
)
)
)
# Define server logic required to draw a histogram
server <- function(input, output) {
times <- data.frame(read.csv("./times.csv", header = TRUE))
d <- reactive({
a <- subset(times, year == input$year)
return (a)
})
g <- list(
scope = 'world',
projection = list(type = 'Mercator'),
showframe = FALSE,
showland = TRUE,
showsubunits = TRUE,
landcolor = toRGB("gray95"),
subunitcolor = toRGB("gray85"),
countrycolor = toRGB("gray65"),
countrywidth = 0.5,
subunitwidth = 0.5
)
output$map <- renderPlotly({
p <- plot_geo(data = d(), lat = ~lat, lon = ~lon,
color = ~as.numeric(rescale),
mode = 'markers', colors = "Spectral") %>%
add_markers(text = ~paste(paste("Rank:", world_rank),
university_name, country,
year, sep = "<br />"),
hoverinfo = "text") %>%
colorbar(title = "World Rank") %>%
layout(title = paste(input$year, "Times University Ranking on the Map"),
geo = g)
})
}
# Run the application
shinyApp(ui = ui, server = server)
Normal R code
library(plotly)
library(RColorBrewer)
input <- read.csv("times.csv", header = TRUE)
df <- data.frame(subset(input, year == 2015))
df <- df[sort.int(df$No, decreasing = TRUE), ]
# geo styling
g <- list(
scope = 'world',
projection = list(type = 'Mercator'),
showframe = FALSE,
showland = TRUE,
showsubunits = TRUE,
landcolor = toRGB("gray95"),
subunitcolor = toRGB("gray85"),
countrycolor = toRGB("gray65"),
countrywidth = 0.5,
subunitwidth = 0.5
)
p <- plot_geo(data = df, lat = ~lat,
lon = ~lon, color = ~as.numeric(rescale), mode = 'markers',
colors = "Spectral") %>%
add_markers(
text = ~paste(paste("Rank:", world_rank), university_name,
country, year, sep = "<br />"),
hoverinfo = "text") %>%
colorbar(title = "World Rank") %>%
layout(title = '2016 Times University Rankings on the map', geo = g)

Toggle fill on hover using plotly with Shiny in R

I would like to create a plotly plot where the fill under each line is toggled upon mouseover/hover. The closest that I've come is using a combination of plotly and Shiny in the code below. Basically, I use the function event_data("plotly_hover") with a call to add_trace, which generates the fill for the line. However, when the mouse is moved away from the line, or unhovered, I get an error message: Error: incorrect length (0), expecting: 2366. In addition, the hoverinfo text no longer appears, or only briefly before the fill appears.
I'm not sure what the program is looking for when unhovering, so am not sure why I'm getting this error. Or perhaps there is different and simpler way to toggle the fill for plotly graphs?
ui.R
shinyUI(fluidPage(
titlePanel("Snow Weather Stations"),
mainPanel(
plotlyOutput("testplot", height = "500px")
)
)
)
server.R
library(shiny)
library(plotly)
library(dplyr)
library(tidyr)
csvf <- read.csv(file = "http://bcrfc.env.gov.bc.ca/data/asp/realtime/data/SW.csv",
check.names = FALSE, stringsAsFactors = FALSE)
swe <- csvf %>%
gather(STATION, SWE, -1) %>%
separate(`DATE (UTC)`, c('DATE', 'TIME'), sep = " ") %>%
filter(TIME == "15:00:00") %>%
select(-TIME) %>%
filter(substr(STATION,1,2) == "1A")
swe$DATE <- as.Date(swe$DATE)
swe$HOVERTEXT <- paste(swe$STATION, paste0(swe$SWE, " mm"), sep = "<br>")
xmin <- as.numeric(as.Date("2015-10-01")) * 24 * 60 * 60 * 1000
xmax <- as.numeric(as.Date("2016-09-30")) * 24 * 60 * 60 * 1000
shinyServer(function(input, output) {
output$testplot <- renderPlotly({
plot_ly(swe, x = DATE, y = SWE, group = STATION,
line = list(color = '#CCCCCC'),
text = HOVERTEXT, hoverinfo = "text+x",
hoveron = "points",
key = STATION) %>%
layout(showlegend = FALSE,
hovermode = 'closest',
xaxis = list(title = "",
showgrid = FALSE, showline = TRUE,
mirror = "ticks", ticks = "inside", tickformat = "%b",
hoverformat = "%b %-d",
range = c(xmin, xmax)),
yaxis = list(title = "Snow Water Equivalent (mm)",
showgrid = FALSE, showline = TRUE,
mirror = "ticks", ticks = "inside",
rangemode = "tozero")) %>%
config(displayModeBar = FALSE)
d <- event_data("plotly_hover")
if (is.null(d)) {
stn <- "1A01P Yellowhead Lake"
} else {
stn <- d$key[1]
}
add_trace(filter(swe, STATION == stn), x = DATE, y = SWE,
line = list(color = "404040"), fill = "tozeroy")
})
})

Resources