R
We present in this section the shiny
package, which allows us to create web application (local to a computer, local into an inside network, or online).
library(shiny)
We see in the previous sessions that it is a diffuclt task to analysis deeply some datasets, when we produce a lot of tables and graphics. A good way to tackle this problem is to create a (simple) application, which allows us to interact with data and methods.
To create a web application with shiny
, you have to create a specific folder with specifics files:
app.R
server.R
and ui.R
I prefer the second choice to separate the user interface side (in ui.R
) and the server side (in server.R
).
Since we want an interactive application, we have to manage both sides of it:
R
produces the outputs, from data and inputsIn the following subsection are presented the contents of the two files. You can copy this to test inside RStudio.
We create a folder, names for instance web-application
, with two files:
library(shiny)
shinyUI(fluidPage(
titlePanel("Web application")
))
library(shiny)
shinyServer(function(input, output) {
})
In RStudio, when a file named ui.R
or server.R
or app.R
is open, you get a button names Run App. If you click on them, you must have a new window with only the main title.
The funtion shinyUI()
define the UI section of an application. In this, we create a fluidPage()
, which can contain many panel, as we see later.
The function shinyServer()
permits us to define a function taking input
and output
parameters defined in ui.R
, to explain how outputs are created from data and inputs.
If you want to run directly the application, write the following code into R
console.
runUrl("http://fxjollois.github.io/stat-prog-R/web-application-1.zip")
We add in the preceding application a plot and a table, without any interaction at this moment. So, we have to define the outputs in ui.R
, with functions names plotOutput()
for any plot, and tableOutput()
for tables. These functions must have a parameter, which is the name of the output.
Now, in server.R
, we define the plot and the table to produce. We use iris
dataset, with functions renderPlot()
for any plot, and renderTable()
for tables.
To enhance the presentation of the application, we use a sidebarLayout
which divides the window into two sections:
sidebarPanel()
: usually all the controls (interactions)mainPanel()
: the outputs generated from choice made by usersAnd in the server.R
, we compute PCA on the data before the definition of the server operation.
library(shiny)
shinyUI(fluidPage(
titlePanel("Web application"),
sidebarLayout(
sidebarPanel(),
mainPanel(
helpText("Mean values of attributes for each species"),
tableOutput("tab"),
helpText("PCA first factorial map for individuals"),
plotOutput("graph")
)
)
))
library(shiny)
library(FactoMineR)
pca = PCA(iris, quali.sup = 5, graph = FALSE)
shinyServer(function(input, output) {
output$tab <- renderTable({
aggregate(. ~ Species, iris, mean)
}, digits = 2)
output$graph <- renderPlot({
par(mar = c(4, 4, 0, 0) + .1)
plot(Dim.2 ~ Dim.1, pca$ind$coord,
col = rainbow(3)[iris$Species], pch = 19)
})
})
If you want to run directly the application, write the following code into R
console.
runUrl("http://fxjollois.github.io/stat-prog-R/web-application-2.zip")
Now, we add interactions in the application, then the user (you or someone else if you publish your app) can interact with data. First, we add two inputs into ui.R
:
selectInput()
function ;radioButtons()
.These two functions take at least three parameters:
server.R
For radioButtons()
, we add the parameter inline=TRUE
to have all the button on one line.
Second, we use theses inputs as object of input
parameter in the server function, to use the user choice in the produced outputs. The value inside these inputs are characters.
library(shiny)
shinyUI(fluidPage(
titlePanel("Web application"),
sidebarLayout(
sidebarPanel(
helpText("Choose the statistic you want to compute"),
selectInput("stat", "Statistic", c("mean", "median", "min", "max")),
helpText("Choose the PCA dimension to plot"),
radioButtons("dimX", "X", choices = 1:4, inline = TRUE),
radioButtons("dimY", "Y", choices = 1:4, inline = TRUE)
),
mainPanel(
# helpText("Mean values of attributes for each species"),
textOutput("text"),
tableOutput("tab"),
helpText("PCA first factorial map for individuals"),
plotOutput("graph")
)
)
))
library(shiny)
library(FactoMineR)
pca = PCA(iris, quali.sup = 5, graph = FALSE)
shinyServer(function(input, output) {
output$text <- renderText({
paste(input$stat, "values of attributes for each species")
})
output$tab <- renderTable({
aggregate(. ~ Species, iris, function(x) {
switch(input$stat,
mean = mean(x),
median = median(x),
min = min(x),
max = max(x))
})
}, digits = 2)
output$graph <- renderPlot({
dimX = as.numeric(input$dimX)
dimY = as.numeric(input$dimY)
m = data.frame(x = pca$ind$coord[,dimX],
y = pca$ind$coord[,dimY])
par(mar = c(4, 4, 0, 0) + .1)
plot(y ~ x, m,
col = rainbow(3)[iris$Species], pch = 19,
xlab = paste("Dimension", dimX),
ylab = paste("Dimension", dimY))
})
})
If you want to run directly the application, write the following code into R
console.
runUrl("http://fxjollois.github.io/stat-prog-R/web-application-3.zip")
At the end, we add in our application three upgrades:
ui.R
: the only choice is 0
at the beginning of the applicationserver.R
: we indicate the new choices (between 1 and the number of dimension in PCA) in a observe()
function, with updateRadioButtons()
dimY
and dimX
inputs, to change dimY
value according to a new value of dimX
server.R
: we modify the selected value in dimY
(with updateRadioButtons()
) to the first value different from dimX
server.R
:
reactive()
returning the subset with the two choosen dimensionsrenderPlot()
We add some controls in the outputs to avoid error during the execution of the application.
library(shiny)
shinyUI(fluidPage(
titlePanel("Web application"),
sidebarLayout(
sidebarPanel(
helpText("Choose the statistic you want to compute"),
selectInput("stat", "Statistic", c("mean", "median", "min", "max")),
helpText("Choose the PCA dimension to plot"),
radioButtons("dimX", "X", choices = 0),
radioButtons("dimY", "Y", choices = 0)
),
mainPanel(
helpText("Mean values of attributes for each species"),
tableOutput("tab"),
helpText("PCA first factorial map for individuals"),
plotOutput("graph")
)
)
))
library(shiny)
library(FactoMineR)
pca = PCA(iris, quali.sup = 5, graph = FALSE)
nDim = ncol(pca$ind$coord)
shinyServer(function(input, output, session) {
observe({
updateRadioButtons(session, "dimX",
choices = 1:nDim,
inline = TRUE,
selected = 1)
updateRadioButtons(session, "dimY",
choices = 1:nDim,
inline = TRUE,
selected = 2)
})
observe({
dimX = input$dimX
if (input$dimY == dimX) {
dimY = which(!(1:nDim == dimX))[1]
updateRadioButtons(session, "dimY",
selected = dimY)
}
})
output$tab <- renderTable({
aggregate(. ~ Species, iris, function(x) {
switch(input$stat,
mean = mean(x),
median = median(x),
min = min(x),
max = max(x))
})
}, digits = 2)
subPCA <- reactive({
if (input$dimX == 0) return(NULL)
dimX = as.numeric(input$dimX)
dimY = as.numeric(input$dimY)
m = data.frame(x = pca$ind$coord[,dimX],
y = pca$ind$coord[,dimY])
})
output$graph <- renderPlot({
m = subPCA()
if (is.null(m)) return(NULL)
par(mar = c(4, 4, 0, 0) + .1)
plot(y ~ x, m,
col = rainbow(3)[iris$Species], pch = 19,
xlab = paste("Dimension", input$dimX),
ylab = paste("Dimension", input$dimY))
})
})
If you want to run directly the application, write the following code into R
console.
runUrl("http://fxjollois.github.io/stat-prog-R/web-application-4.zip")
We can modify the user interface in many different ways with shiny
package. It exists also some other packages allowing us to personnalize applications (shinydashboard
, shinythemes
, …)
Use the shiny
package to create an application able to help us in the clustering process of our data.