I am building a shiny app. In the drop down menu I have the categories of a factor variable. I think the problem is in the server but I dont know how to fix it.
Also, I would like that to add a vertical in the histograms at 15 when the colour chosen is yellow, and a vertical line at 20 when the colour chose in the histogram is Red. Can you please help me with my code?
Thanks
library(shiny)
# Creating a fake data frame
categories <- c("A", "B", "c")
values <- c(12, 15, 20)
data <- merge(categories, values)
# Define UI for application
ui <- shinyUI(fluidPage(
# Title panel
titlePanel(title = h1("Title", align = "center")),
sidebarLayout(
# Sidebar panel
sidebarPanel(
# Options
selectInput(inputId = "xcol", label = "Select", choices = levels(data$x)),
br(),
#Colours histogram
radioButtons(inputId = "colour", label = strong("Select the colour of
histogram"), choices = c("Yellow", "Red"), selected = "Yellow"),
br(),
#Bins for histogram
sliderInput(inputId = "bins", label = "Select the number of Bins for the
histogram", min=5, max = 25, value = 15),
br(),
#Density curve
checkboxInput(inputId = "density", label = strong("Show Density Curve"),
value = FALSE),
# Display this only if the density is shown
conditionalPanel(condition = "input.density ==true",
sliderInput(inputId = "bw_adjust",
label = "Bandwidth adjustment:",
min = 0.2, max = 3, value = 1, step = 0.2))
),
# Main Panel
mainPanel(
#plot histogram
plotOutput("plot"),
# Output: Verbatim text for data summary
verbatimTextOutput("summary"))
)))
# Define server logic
server <- shinyServer(function(input, output) {
output$plot <-renderPlot({
hist(data[input$xcol, data$x], breaks = seq(0, max(data[input$xcol,
data$x]), l= input$bins+1), col = "lightblue",
probability = TRUE, xlab = "Values", main = "")
abline(v = mean(data[input$xcol, data$x]), col = "red", lty = 2)
title(main = levels(data$x[input$xcol]))
if (input$density) {
dens <- density(data[input$xcol, data$x], adjust = input$bw_adjust)
lines(dens, col = "blue", lwd = 1)
}
# Generate the summary
output$summary <- renderPrint({
xcol <- xcolInput()
summary(xcol)
})
})
})
# Run the application
shinyApp(ui = ui, server = server)
It looks like you were subsetting data incorrectly. I created a reactive expression for the data subset: data2(), and used that to make the plot outputs. I also added the vertical lines you mention with an if(){...}else{...} statement.
library(shiny)
# Creating a fake data frame
categories <- c("A", "B", "c")
values <- c(12, 15, 20)
data <- merge(categories, values)
# Define UI for application
ui <- shinyUI(fluidPage(
# Title panel
titlePanel(title = h1("Title", align = "center")),
sidebarLayout(
# Sidebar panel
sidebarPanel(
# Options
selectInput(inputId = "xcol", label = "Select", choices = levels(data$x)),
br(),
#Colours histogram
radioButtons(inputId = "colour", label = strong("Select the colour of
histogram"), choices = c("Yellow", "Red"), selected = "Yellow"),
br(),
#Bins for histogram
sliderInput(inputId = "bins", label = "Select the number of Bins for the
histogram", min=5, max = 25, value = 15),
br(),
#Density curve
checkboxInput(inputId = "density", label = strong("Show Density Curve"),
value = FALSE),
# Display this only if the density is shown
conditionalPanel(condition = "input.density ==true",
sliderInput(inputId = "bw_adjust",
label = "Bandwidth adjustment:",
min = 0.2, max = 3, value = 1, step = 0.2))
),
# Main Panel
mainPanel(
#plot histogram
plotOutput("plot"),
# Output: Verbatim text for data summary
verbatimTextOutput("summary"))
)))
# Define server logic
server <- shinyServer(function(input, output) {
data2 <- reactive({data[as.character(data$x)==input$xcol, "y"]})
output$plot <-renderPlot({
hist(data2(), breaks = seq(0, max(c(1, data2()), na.rm=TRUE), l= input$bins+1), col = input$colour,
probability = TRUE, xlab = "Values", main = "")
abline(v = mean(data2()), col = "red", lty = 2)
title(main = input$xcol)
if (input$density) {
dens <- density(data2(), adjust = input$bw_adjust)
lines(dens, col = "blue", lwd = 1)
}
if(input$colour=="Red"){
abline(v=20)}else{abline(v=15)}
# Generate the summary
output$summary <- renderPrint({
#xcol <- xcolInput()
summary(data2())
})
})
})
# Run the application
shinyApp(ui = ui, server = server)
Related
I try to display interactive plots by using R shiny. I can successfully make the GUI and published, but the plots in tabPanel shows nothing, just like the picture shows below. There is the data I used (have been downloaded into my laptop).
I think problem may caused by the way how I preprocessing my data in server.R, but whatever I tried, it still display nothing. No Error shows when I run the app.
enter image description here
My code in ui.R:
library(shiny)
shinyUI(fluidPage(
titlePanel("Data Viz Lab"),
sidebarLayout(
sidebarPanel(
## Add X-Variable select element
selectInput(inputId = "var_x",
label = h5("X-Variable"),
choices = c("Structure.Cost", "Land.Value", "Home.Value", "Home.Price.index"),
selected = "Land.Value"),
## Add Fill Color select element
selectInput(inputId = "color",
label = h5("Fill Color"),
choices = c("brown", "yellow", "green", "blue", "red"),
selected = "brown"),
## Add log-scale check box
checkboxInput(inputId = "log",
label = "log-sclae for X-variable in Scatterplot?",
value = FALSE),
## Add Y-Variable select element
selectInput(inputId = "var_y",
label = h5("Y-Variable"),
choices = c("Structure.Cost", "Land.Value", "Home.Value", "Home.Price.index"),
selected = "Structure.Cost"),
## Add Circle-Size side bar
sliderInput(inputId = "size",
label = h5("Circle-Size"),
min = 1,
max = 10,
value = 3),
## Add Outlier color select element
selectInput(inputId = "color_out",
label = h5("Outlier Color"),
choices = c("white", "yellow", "green", "blue", "red"),
selected = "white")
),
mainPanel(
tabsetPanel( # Establish tabset panel
tabPanel(
# Tab1
title = "Histogram",
value = plotOutput(outputId = "hist") # Add an figure in tab1
),
tabPanel(
# Tab2
title = "Scatterplot",
value = plotOutput(outputId = "scatter") # Add an figure in tab2
)
)
)
)
))
My code in server.R:
library(shiny)
library(ggplot2)
library(sp)
library(dplyr)
# setwd()
landdata = read.csv("landdata.csv")
options(scipen = 999)
shinyServer(function(input, output) {
## Plotting Histogram
output$hist = renderPlot({
# Plotting
if (input$log == FALSE){
ggplot(landdata, aes_string(x = input$var_x)) +
geom_histogram(color = input$color)
}else{
ggplot(landdata, aes_string(x = input$var_x)) +
geom_histogram(color = input$color) +
scale_x_log10(input$var_x)
}
})
## Plotting Scatter plot
output$scatter = renderPlot({
# Data pre-processing
p = ggplot(data = landdata, aes_string(x = input$var_x, y = input$var_y)) +
geom_point() +
stat_ellipse(type = "norm", level = 0.95, color = "black")
build = ggplot_build(p)$data
pts = build[[1]]
elli = build[[2]]
Outlier = point.in.polygon(pts$x, pts$y, elli$x, elli$y)
landdata = cbind(landdata, Outlier)
landdata$Outlier = ifelse(landdata$Outlier == 0, yes = "Y", no = "N") %>% factor(level = c("Y", "N"))
# Plotting
if (input$log == FALSE){
ggplot(landdata, aes_string(x = input$var_x, y = input$var_y)) +
geom_point(aes(color = Outlier), size = input$size) +
scale_color_manual(values = c(input$color, input$color_out))
}else{
ggplot(landdata, aes_string(x = input$var_x, y = input$var_y)) +
geom_point(aes(color = Outlier), size = input$size) +
scale_color_manual(values = c(input$color, input$color_out)) +
scale_x_log10(input$var_x)
}
})
})
The mistake lies in the tabPanel setup. value is not the correct argument for the plot. value is "the value that should be sent when tabsetPanel reports that this tab is selected" (taken from the manual). That means, value has the role of an id (like id argument of tabsetPanel or outputId of plotOutput).
Remove value = to make it work (the code snippet below gave me an output on my system).
tabsetPanel( # Establish tabset panel
tabPanel(
# Tab1
title = "Histogram",
plotOutput(outputId = "hist") # Add an figure in tab1
),
tabPanel(
# Tab2
title = "Scatterplot",
plotOutput(outputId = "scatter") # Add an figure in tab2
)
)
I have a Venn plot in the sidebarPanel and need to remove the background (white) of the plot and add as the same as sidebarPanel
any suggestions?
code is as like this
library(shiny)
ui <- fluidPage(
titlePanel("Old Faithful Geyser Data"),
sidebarLayout(
sidebarPanel(
sliderInput("bins",
"Number of bins:",
min = 1,
max = 50,
value = 30),imageOutput("Vennout")),mainPanel(
plotOutput("distPlot"))))
server <- function(input, output) {
set1 <- paste(rep("word_" , 200) , sample(c(1:1000) , 200 , replace=F) , sep="")
set2 <- paste(rep("word_" , 200) , sample(c(1:1000) , 200 , replace=F) , sep="")
output$Vennout <- renderPlot({
vennplot <-({venn.diagram(
x = list("one" = set1,
"two" = set2),
filename = NULL,
fill = c("orange", "blue"),
alpha = c(0.5,0.5),
label.col = "black",
cat.col = c("cornflowerblue", "pink"),
cat.default.pos = "text",
scaled = FALSE
)}) grid.newpage()
grid.draw(vennplot)})}
shinyApp(ui = ui, server = server)
Set the colours of the lines and fills to match with shiny grey - #F5F5F5:
grid.newpage()
grid.draw(rectGrob(gp = gpar(col = "#F5F5F5", fill = "#F5F5F5")))
grid.draw(vennplot)
Let's consider my very basic application :
Created by code :
Server
library(shiny) # Load shiny package
start <- as.Date("2013-01-01")
end <- as.Date("2016-10-01")
#Apple stock
getSymbols("AAPL", src = "yahoo", from = start, to = end)
apple <- AAPL$AAPL.Close
#Gold
getSymbols('GOLD', src = 'yahoo', from = start, to = end)
gold <- GOLD$GOLD.Close
#S&P500
getSymbols('^GSPC', src = 'yahoo', from = start, to = end)
sp <- as.numeric(`GSPC`[,4])
#Microsoft
getSymbols('MSFT', src = 'yahoo', from = start, to = end)
msft <- MSFT$MSFT.Close
stock.frame <- data.frame(apple, gold, msft, sp)
colnames(stock.frame) <- c('apple', 'gold', 'msft', 'sp')
shinyServer(
function(input, output) {
output$myhist <- renderPlot({
colm <- as.numeric(input$var)
hist(stock.frame[, colm], col = input$colour, xlim = c(min(stock.frame[, colm]), max(stock.frame[, colm])), main = "Histogram of stock dataset", breaks = seq(min(stock.frame[, colm]), max(stock.frame[, colm]), l = input$bin + 1), xlab = names(stock.frame[colm]))
})
}
)
UI
library(shiny) # load the shiny package
# Define UI for application
shinyUI(fluidPage(
# Header or title Panel
titlePanel(h4('Demostration of the renderPlot() - A Histogram with stock dataset', align = "center")),
# Sidebar panel
sidebarPanel(
selectInput("var", label = "1. Select the quantitative Variable",
choices = c("Apple" = 1, "Gold" = 2, "S&P" = 3, "BTC"=4),
selected = 3),
sliderInput("bin", "2. Select the number of histogram BINs by using the slider below", min=5, max=50, value=15),
radioButtons("colour", label = "3. Select the color of histogram",
choices = c("Green", "Red",
"Yellow"), selected = "Green")
),
# Main Panel
mainPanel(
textOutput("text1"),
textOutput("text2"),
textOutput("text3"),
plotOutput("myhist")
)
)
)
I want to have another sidebarPanel (analogous to '1. Select the quantitative Variable') in which I can specify if I want 'Histogram' or 'nothing'. If histogram was choosed then I should have same thing as above. When "nothing' was choosed I should see blank page. Do you know how it can be performed ?
EDIT
I added radiobutton as #r2evans suggested. It now look's in the way following :
shinyUI(fluidPage(
radioButtons("rb", "Plot type:", choiceNames = c("Histogram", "Nothing")),
# Header or title Panel
titlePanel(h4('Demostration of the renderPlot() - A Histogram with stock dataset', align = "center")),
# Sidebar panel
sidebarPanel(
selectInput("var", label = "1. Select the quantitative Variable",
choices = c("Apple" = 1, "Gold" = 2, "S&P" = 3, "BTC"=4),
selected = 3),
sliderInput("bin", "2. Select the number of histogram BINs by using the slider below", min=5, max=50, value=15),
radioButtons("colour", label = "3. Select the color of histogram",
choices = c("Green", "Red",
"Yellow"), selected = "Green")
),
# Main Panel
mainPanel(
textOutput("text1"),
textOutput("text2"),
textOutput("text3"),
plotOutput("myhist")
)
)
)
However after running 'Run App' i see error :
Error in normalizeChoicesArgs: Please specify a non-empty vector for `choices` (or, alternatively, for both `choiceNames` AND `choiceValues`).
81: stop
80: normalizeChoicesArgs
79: radioButtons
Have I done something wrong ?
Perhaps you are looking for a solution like this
library(shiny)
library(quantmod)
start <- as.Date("2013-01-01")
end <- as.Date("2016-10-01")
#Apple stock
getSymbols("AAPL", src = "yahoo", from = start, to = end)
apple <- AAPL$AAPL.Close
#Gold
getSymbols('GOLD', src = 'yahoo', from = start, to = end)
gold <- GOLD$GOLD.Close
#S&P500
getSymbols('^GSPC', src = 'yahoo', from = start, to = end)
sp <- as.numeric(`GSPC`[,4])
#Microsoft
getSymbols('MSFT', src = 'yahoo', from = start, to = end)
msft <- MSFT$MSFT.Close
stock.frame <- data.frame(apple, gold, msft, sp)
colnames(stock.frame) <- c('apple', 'gold', 'msft', 'sp')
cmat <- cor(stock.frame)
### plot_ly(z = cmat, type = "heatmap")
### Define UI for application
ui <- fluidPage(
# Header or title Panel
titlePanel(h4('Demostration of the renderPlot() - A Histogram with stock dataset', align = "center")),
# Sidebar panel
sidebarPanel(
selectInput("var", label = "1. Select the quantitative Variable",
choices = c("Apple" = 1, "Gold" = 2, "S&P" = 3, "BTC"=4),
selected = 3),
sliderInput("bin", "2. Select the number of histogram BINs by using the slider below", min=5, max=50, value=15),
radioButtons("graphtype", label = "Select Type of Graph",
choices = c("Heatmap", "Histogram", "DataTable"), selected = "Heatmap"),
conditionalPanel(
condition = "input.graphtype == 'Histogram' ",
radioButtons("colour", label = "3. Select the color of histogram",
choices = c("Green", "Red", "Yellow"), selected = "Green")
)
),
# Main Panel
mainPanel(
textOutput("text1"),
textOutput("text2"),
textOutput("text3"),
conditionalPanel(
condition = "input.graphtype == 'Heatmap' ", plotlyOutput("heatmap", width = "100%", height="600px")
),
conditionalPanel(
condition = "input.graphtype == 'Histogram' ", plotOutput("myhist")
),
conditionalPanel(
condition = "input.graphtype == 'DataTable' ", DTOutput("tb1")
)
)
)
server <- function(input, output) {
output$myhist <- renderPlot({
colm <- as.numeric(input$var)
hist(stock.frame[, colm], col = input$colour, xlim = c(min(stock.frame[, colm]), max(stock.frame[, colm])), main = "Histogram of stock dataset", breaks = seq(min(stock.frame[, colm]), max(stock.frame[, colm]), l = input$bin + 1), xlab = names(stock.frame[colm]))
})
output$heatmap <- renderPlotly({plot_ly(x = colnames(stock.frame), y = colnames(stock.frame), z = cmat, type = "heatmap") %>%
layout(
xaxis = list(title=colnames(stock.frame)),
yaxis = list(title="ts")
)
})
output$tb1 <- renderDT(stock.frame)
}
# Run the application
shinyApp(ui = ui, server = server)
I'm new to R and shiny. I have a problem that I could not solve.
I have a histogram where I want to make the classes separately selectable.
The classes are all in one column. To make them separately selectable, I did not succeed.
How do I get it to work?
Thanks a lot
## app.R ##
set.seed(24)
df <- data.frame(Class = sample(LETTERS[1:5], 30, replace = TRUE),
Amount = sample(5:20, 30, replace = TRUE),
stringsAsFactors= FALSE, check.names = FALSE)
server <- function(input, output) {
output$distPlot <- renderPlot({
hist(rnorm(input$obs), col = 'darkgray', border = 'white')
})
output$sum = renderPrint({
summary(df)
})
output$str = renderPrint({
str(df)
})
output$data = renderTable({
colm = as.numeric(input$var)
df[colm]
head(df)
})
output$myhist <- renderPlot({
colm = as.numeric(input$var)
hist(df$Amount, col =input$colour, xlim = c(0, max(df$Amount)), main = "Histogram", breaks = seq(0, max(df$Amount),l=input$bin+1),
xlab = names(df$Amount)
)}
)
}
ui <- fluidPage(
sidebarLayout(
sidebarPanel(
selectInput("var", label = "1. Select Class",
choices = c("A" = 1, "B" = 2, "C" = 3, "D"= 4, "E" = 5),
selected = 2),
sliderInput("bin", "2. Select the number of histogram BINs by using the slider below", min=5, max=25, value=15),
radioButtons("colour", label = "3. Select the color of histogram",
choices = c("Green", "Red",
"Blue"), selected = "Green")
),
mainPanel(
tabsetPanel(type="tab",
tabPanel("Plot", plotOutput("myhist")),
tabPanel("Summary", verbatimTextOutput("sum")),
tabPanel("Structure", verbatimTextOutput("str")),
tabPanel("Data", tableOutput("data"))
)
)
)
)
shinyApp(ui = ui, server = server)
I appreciate your help.
You have a few options:
Allow the selectInput to have multiple selections, by adding multiple = TRUE:
selectInput("var", label = "1. Select Class", choices = c("A" = 1, "B" = 2, "C" = 3, "D"= 4, "E" = 5), multiple = TRUE)
Use a checkbox group:
checkboxGroupInput('var', label = "1. Select Class", choices = c("A" = 1, "B" = 2, "C" = 3, "D"= 4, "E" = 5))
I recommend the 2nd option, using a checkbox group, as I believe they are easy for users to understand.
EDIT
As requested here is the full code, with the checkbox group linked to the chart:
## app.R ##
library(shiny)
set.seed(24)
df <- data.frame(Class = sample(LETTERS[1:5], 30, replace = TRUE),
Amount = sample(5:20, 30, replace = TRUE),
stringsAsFactors= FALSE, check.names = FALSE)
server <- function(input, output) {
output$distPlot <- renderPlot({
hist(rnorm(input$obs), col = 'darkgray', border = 'white')
})
output$sum = renderPrint({
summary(df)
})
output$str = renderPrint({
str(df)
})
output$data = renderTable({
colm = as.numeric(input$var)
df[colm]
head(df)
})
output$myhist <- renderPlot({
df_plot <- df[df$Class %in% input$var, ]
hist(df_plot$Amount, col = input$colour, xlim = c(0, max(df_plot$Amount)), main = "Histogram", breaks = seq(0, max(df_plot$Amount),l=input$bin+1),
xlab = names(df_plot$Amount)
)}
)
}
ui <- fluidPage(
sidebarLayout(
sidebarPanel(
checkboxGroupInput('var', label = "1. Select Class", choices = c("A", "B", "C", "D", "E"), selected = "B"),
sliderInput("bin", "2. Select the number of histogram BINs by using the slider below", min=5, max=25, value=15),
radioButtons("colour", label = "3. Select the color of histogram",
choices = c("Green", "Red",
"Blue"), selected = "Green")
),
mainPanel(
tabsetPanel(type="tab",
tabPanel("Plot", plotOutput("myhist")),
tabPanel("Summary", verbatimTextOutput("sum")),
tabPanel("Structure", verbatimTextOutput("str")),
tabPanel("Data", tableOutput("data"))
)
)
)
)
shinyApp(ui = ui, server = server)
I have this shiny code and the plot is not showing for some reason. Can you please extend me a hand?
Is a basic shiny plot to render in the Main Panel. Checked loads of times and still not plotting.
library(shiny)
library(plotly)
library(ggplot2)
ui <- fluidPage(
(titlePanel("APP & MEP | Size (m2) ~ Hours", windowTitle = "app")),
sidebarLayout(
sidebarPanel(
checkboxGroupInput(inputId = "checkgroup",
label = "Select Deparments",
choices = c("All", "ELE", "HVAC", "MAN", "PH", "LV"),
selected = "All", inline = F),
radioButtons(inputId = "radio",
label = "ADD Stat_Smooth?",
choices = c("YES","NO"),
inline = T),
sliderInput(inputId = "slider",
label = "SPAN Setting",
min = 0.2, max = 2, value = 1,
ticks = T)
),
mainPanel(plotOutput(outputId = "plot33"))
)
)
server <- function(input, output){
output$plot33 <- renderPlotly({
gg <- ggplot(sizedf, aes(SIZE, Hours)) + geom_point(aes(color = Department)) + ggtitle("Size(m2) vs Hours per department")
p <- ggplotly(gg)
p
})
}
shinyApp(ui = ui, server = server)
I have seen this same mistake a few time already.
plotlyOutput() should be used, not plotOutput()