Nothing
validation <- function(D1,D2,valid){
if(class(D2)[1] != "dist"){
#matrix ?
if(!is.matrix(D2)){
if(!is.data.frame(D2)){return("stratigraphic connection data must be a data.frame.")}
#number of col ?
if(valid == 1){
if(length(D2[1,])!=2){
return(
"Stratigraphic connection must have 2 colunms. Change data type parameter or try to inverse contingency table and stratigraphic connection."
)}
}else{
if(length(D2[1,])!=3){
return("Time range data must have 3 colunms. Change data type parameter or try to inverse contingency table and time range data.")}
}
if(valid == 1){
D2 <- adjacency(D2)
}else{
if(!is.numeric(D2[,2]) || !is.numeric(D2[,3])){return("The upper and lower limit must be numeric.")}
D2 <- overlap(D2)
}
}
#diag = 0 ?
if(sum(diag(D2)) != 0){
return("D2: The diagonal must be equal to 0.")
}
#symetric ?
if(!isSymmetric(D2)){
return("D2 is not symmetric.")
}
}
if(class(D1)[1] != "dist") {
#matrix ?
if(min(D1) < 0){
return("First source is a contingency table and can not contain negative value.")
}
if(!is.matrix(D1)){
D1 <- as.matrix(CAdist(D1,nCP="max",graph=FALSE))
}
#diag = 0 ?
if(sum(diag(D1)) != 0){
stop("D1: The diagonal must be equal to 0.")
}
#symetric ?
if(!isSymmetric(D1)){
stop("D1 is not symmetric.")
}
}
if(!dim(D1)[1] == dim(D1)[2]){return("D1 not a square matrix.")}
if(!dim(D2)[1] == dim(D2)[2]){return("D2 not a square matrix.")}
if(!length(D1) == length(D2)){return("Contingency table and the second source have not the same size.")}
#dist (positive matrix) ?
if(min(D1) < 0){return("D1 is not positive.")}
if(min(D2) < 0){return("D2 is not positive.")}
return("")
}
generateClone <- function(D1,D2,i,j){
D1bis <- rbind(D1,clone=D1[i,])
D1bis <- cbind(D1bis,clone=c(D1[i,],0))
D2bis <- rbind(D2,clone=D2[j,])
D2bis <- cbind(D2bis,clone=c(D2[j,],0))
return(list(D1bis,D2bis))
}
temp_cov <- function (df) {
indice <- function(inf1,sup1,inf2,sup2){
if(sup1 < inf1 || inf2 > sup2){
return(99)
}else{
inf1 <- as.numeric(inf1)
sup1 <- as.numeric(sup1)
inf2 <- as.numeric(inf2)
sup2 <- as.numeric(sup2)
total_overlap_inf <- min(inf1,inf2)
total_overlap_sup <- max(sup1,sup2)
total_overlap <- total_overlap_sup - total_overlap_inf
within_overlap_inf <- max(inf1,inf2)
within_overlap_sup <- min(sup1,sup2)
within_overlap <- within_overlap_sup - within_overlap_inf
i <- within_overlap / total_overlap
return(i)
}
}
recouvrement_indice_matrix <- function(df){
df <- as.data.frame(df)
overlap_matrix <- matrix(nrow = length(df[,1]), ncol = length(df[,1]))
for(i in 1:length(df[,1])){
for(j in 1:length(df[,1])){
if(i != j){
ens1 <- df[i,]
ens2 <- df[j,]
ind <- indice(ens1[1,2],ens1[1,3],ens2[1,2],ens2[1,3])
overlap_matrix[i,j] <- overlap_matrix[j,i] <- ind
}
}
}
diag(overlap_matrix) <- 1
return(overlap_matrix)
}
O <- recouvrement_indice_matrix(df[,1:3])
D <- O + 1
D <- 2 - D
D <- D / 2
dimnames(D) <- list(df[,1],df[,1])
return(D)
}
let <- function(alphabet) function(i) {
base10toA <- function(n, A) {
stopifnot(n >= 0L)
N <- length(A)
j <- n %/% N
if (j == 0L) A[n + 1L] else paste0(Recall(j - 1L, A), A[n %% N + 1L])
}
vapply(i-1L, base10toA, character(1L), alphabet)
}
Int2Alpha <- function(int){
first <- trunc(int)
l1 <- let(LETTERS)(first)
second <- arrondi((int - trunc(int))*10,2)
l2 <- c()
for(i in 1:length(second)){
if(second[i] == 0){
l2 <- c(l2,"")
}else{
f <- nchar(second[i])
if(f == 1){
l2 <- c(l2,as.character(second[i]))
}
if(f >= 3){
new <- unlist(strsplit(as.character(second[i]),".",fixed=T))
new <- paste0(new[1],new[2])
l2 <- c(l2,new)
}
}
}
return(paste0(l1,l2))
}
make.chars <- function(length.out, case, n.char = NULL) {
if(is.null(n.char))
n.char <- ceiling(log(length.out, 26))
m <- sapply(n.char:1, function(x) {
rep(rep(1:26, each = 26^(x-1)) , length.out = length.out)
})
m.char <- switch(case,
'lower' = letters[m],
'upper' = LETTERS[m]
)
m.char <- LETTERS[m]
dim(m.char) <- dim(m)
apply(m.char, 1, function(x) paste(x, collapse = ""))
}
get.letters <- function(length.out, case = 'upper'){
max.char <- ceiling(log(length.out, 26))
grp <- rep(1:max.char, 26^(1:max.char))[1:length.out]
unlist(lapply(unique(grp), function(n) make.chars(length(grp[grp == n]), case = case, n.char = n)))
}
Alpha2Int <- function(alpha){
letter <- get.letters(800)
first <- c()
second <- c()
for(i in 1:length(alpha)){
first <- c(first,str_extract(alpha[i], "[aA-zZ]+"))
tmp <- str_extract(alpha[i], "[0-9]+")
if(is.na(tmp)){tmp <- ""}
second <- c(second,tmp)
}
n <- nchar(max(second))
second <- as.numeric(paste0("0.",second))
second[is.na(second)] <- 0
for(i in 1:length(alpha)){
first[i] <- which(letter == first[i])
}
first <- as.numeric(first)
return(first+second)
}
CAdist <- function(df, nCP = NULL, graph = TRUE){
#===============================================================================
# GENERATE DISTANCE MATRIX WITH CORRESPONDENCE ANALYSiS (CA) (Fr: Analyse Factorielle des Correspondances)
#
# Authors : A.COULON
# Last update : 23 october 2018
#
# Arguments:
# df The pottery contingence table
# nCP The number of principal component to keep
# graph Logical for print or not the plot of the CA
#
#===============================================================================
if(!is.table(df)){
if(is.matrix(df)){df <- as.data.frame(df)}
if(!is.data.frame(df)){stop("df is not a data frame.")}
}
if(FALSE %in% (df == trunc(df))){stop("The data frame must contain integers.")}
max <- min( nrow(df)-1,ncol(df)-1)
if(nCP == "max"){nCP <- max}
if(nCP > max){nCP <- max}
df.CA <- CA(df, ncp = nCP, graph=graph)
dist <- dist(df.CA$row$coord)/max(dist(df.CA$row$coord))
return(as.matrix(dist))
}
EPM <- function(x) {
x <- as.matrix(x)
x[is.na(x)] <- 0
ni. <- rep(1,nrow(x))
nj. <- margin.table(x, margin = 2)
n. <- sum(nj.)
TabInde <- (nj.%*%t(ni.)/n.)
TabInde <- t(TabInde)
x <- prop.table(x, margin = 1)
TabEcart <- x - TabInde
TabEcart <- as.data.frame(TabEcart)
return(TabEcart)
}
plot_EPPM <- function(x,show,permute,col_weight) {
if(is.table(x)){
x <- as.data.frame(x)
x <- matrix(x[,3],
ncol=sqrt(length(x[,2])),
dimnames=list(unique(x[,1]),unique(x[,1])))
x <- as.data.frame(x)
}
if(is.matrix(x)){x <- as.data.frame(x)}
if(!is.data.frame(x)){stop("x is not a data frame.")}
for (i in 1:length(x[1,])){
if(!(sum(x[,i]) == round(sum(x[,i])))){stop("The data frame must contains integers.")}
}
.data <- c()
Cluster <- c()
labels <- factor(rownames(x),levels = rev(unique(rownames(x))))
#permute type in x
if(permute){
if(show == "EPPM"){
ecart <- as.data.frame(EPM(x))
ecart[ecart < 0] <- 0
i <- seq(nrow(ecart),1)
barycenter <- colSums(ecart * i) / colSums(ecart)
x <- x[,order(barycenter)]
}else{
i <- seq(nrow(x),1)
barycenter <- colSums(x * i) / colSums(x)
x <- x[,order(barycenter)]
}
}
rowsum <- rowSums(x)
#add Weight to x
x <- cbind(x, Weight = rowSums(x) / sum(x) * rowSums(x))
#data
data <- as.data.frame(x)
data <- mutate(data,ens = labels,rowsum = rowsum)
data <- gather(data,key = "type", value = "frequency",-ens,-rowsum, factor_key = TRUE)
data <- mutate(data,frequency = frequency / rowsum)
#remove col rowsum
data <- data[-2]
data$frequency[is.na(data$frequency)] <- 0
#EPPM
ecart <- as.data.frame(EPM(x[-length(x[1,])]))
save_ecart <- ecart
ecart <- cbind(ecart,Weight=c(0))
ecart[ecart < 0] <- 0
ecart <- mutate(ecart,ens = labels)
ecart <- gather(ecart,key = "type", value = "EPPM", -ens, factor_key = TRUE)
ecart$EPPM[ecart$type == "Weight"] <- 0
# Join data and EPPM
data <- inner_join(data,ecart,by = c("ens", "type"))
data <- mutate(data,frequency = frequency - EPPM)
data <- gather(data,key = "legend", value = "frequency", -ens,
-type, factor_key = TRUE)
#if insert hiatus in df replace NA by 0 (NA are generating by divising by 0 (rowsum of a hiatus is 0))
data[is.na(data)] <- 0
#center (div /2 et copy for one part - and the other +)
data <- rbind(data,data)
data <- mutate(data,frequency = frequency * c(rep(.5, nrow(data)/2), rep(-.5, nrow(data)/2)))
#color for Weight
tmp <- data$frequency[data$type == "Weight"]
levels(data$legend) <- c(levels(data$legend),"1","2","3","4","5","6","7","8","9","10","Weight")
data$legend[data$type == "Weight"] <- "Weight"
breaks <- c("frequency","EPPM","Weight")
#define the color
freq <- c("frequency","frequencies","freq","fq","fr\u00E9quence","fr\u00E9quences","fr\u00E9q")
EPPM <- c("EPPM","ecart","\u00E9cart","ecarts","\u00E9carts")
if(show %in% freq){
color <- c("frequency"="#bebebe","EPPM"="#bebebe","Weight"="#7f7f7f")
#remove EPPM from legend
breaks <- c("frequency","Weight")
default_col <- "#bebebe"
}else{
if(show %in% EPPM){
color <- c("frequency"=NA,"EPPM"="black","Weight"="#7f7f7f")
#remove frequency from legend
breaks <- c("EPPM","Weight")
default_col <- NA
}else{
#default color grey: frequency, black: EPPM, my_palette: weight
color <- c("frequency"="#bebebe","EPPM"="black","Weight"="#7f7f7f")
default_col <- NA
}
}
#ggplot
p <- ggplot(data = data) +
facet_grid( ~type, scales = "free", space = "free_x") +
geom_col(aes(x = ens, y = frequency, fill = legend), width = 1) +
scale_x_discrete(labels = rev(rownames(x))) +
coord_flip() +
scale_fill_manual(values = color,
aesthetics = "fill",
limits = breaks,
na.value = default_col
) +
scale_y_continuous(breaks = c(-.1,.1),labels = c("","20% ")) +
labs(
title = "Seriograph",
subtitle = "EPPM (Ecart Positif au Pourcentage Moyen) Positive Deviation at Average Percentage",
caption = "Warnings: The frequencies are calculated independently for each element (row).
You can see the relative number of observations in the Weight column"
) +
theme_grey(base_size = 15) +
annotate("segment",x = 0, y = -.04, xend = 0, yend = .04, color = "white") +
theme(legend.position = "bottom",
panel.spacing = unit(.2, "lines"),
strip.text.x = element_text(angle = 90),
axis.text.x = element_text(hjust=1,margin = margin(t = -13)),
axis.ticks.length = unit(.5, "cm"),
axis.title.x = element_blank(),
axis.title.y = element_blank(),
axis.ticks.y = element_blank(),
plot.caption = element_text(face = "italic", hjust = 0)
)
plot(p)
}
CA_var_data <- function(res, xax = 1, yax = 2, var_sup = TRUE, var_hide = "None",
var_lab_min_contrib = 0) {
tmp_x <- res$vars %>%
filter(Axis == xax) %>%
select("Level", "Position", "Type", "Class", "Coord", "Contrib", "Cos2", "Count")
tmp_y <- res$vars %>%
filter(Axis == yax) %>%
select("Level", "Position", "Type", "Class", "Coord", "Contrib", "Cos2", "Count")
if (!var_sup) {
tmp_x <- tmp_x %>% filter(Type == 'Active')
tmp_y <- tmp_y %>% filter(Type == 'Active')
}
if (var_hide != "None") {
tmp_x <- tmp_x %>% filter(Position != var_hide)
tmp_y <- tmp_y %>% filter(Position != var_hide)
}
tmp <- tmp_x %>%
left_join(tmp_y, by = c("Level", "Position", "Type", "Class", "Count")) %>%
mutate(Contrib = Contrib.x + Contrib.y,
Cos2 = Cos2.x + Cos2.y,
tooltip = paste(paste0("<strong>", Level, "</strong><br />"),
paste0("<strong>",
gettext("Position", domain = "R-explor"),
":</strong> ", Position, "<br />"),
paste0("<strong>Axis ",xax," :</strong> ", Coord.x, "<br />"),
paste0("<strong>Axis ", yax," :</strong> ", Coord.y, "<br />"),
ifelse(is.na(Cos2), "",
paste0("<strong>",
gettext("Squared cosinus", domain = "R-explor"),
":</strong> ", Cos2, "<br />")),
ifelse(is.na(Contrib), "",
paste0("<strong>",
gettext("Contribution:", domain = "R-explor"),
"</strong> ", Contrib, "<br />")),
ifelse(is.na(Count), "",
paste0("<strong>",
gettext("Count:", domain = "R-explor"),
"</strong> ", Count))),
Lab = ifelse(Contrib >= as.numeric(var_lab_min_contrib) |
(is.na(Contrib) & as.numeric(var_lab_min_contrib) == 0), Level, ""))
data.frame(tmp)
}
elbow_finder <- function(x_values, y_values) {
# Max values to create line
max_x_x <- max(x_values)
max_x_y <- y_values[which.max(x_values)]
max_y_y <- max(y_values)
max_y_x <- x_values[which.max(y_values)]
max_df <- data.frame(x = c(max_y_x, max_x_x), y = c(max_y_y, max_x_y))
# Creating straight line between the max values
fit <- lm(max_df$y ~ max_df$x)
# Distance from point to line
distances <- c()
for(i in 1:length(x_values)) {
distances <- c(distances,
abs( coef(fit)[2] * x_values[i] - y_values[i] + coef(fit)[1] ) / sqrt( coef(fit)[2]^2 + 1^2))
}
return(distances)
}
corCriterion <- function(tree,D1,D2) {
d2 <- cophenetic(tree)
res <- abs(cor(as.dist(D1),d2) - cor(as.dist(D2),d2))
return(res)
}
server <- function(input, output, session) {
#------------------------------------------------------#
# modalDialog wait message
#------------------------------------------------------#
waitModal <- function() {
modalDialog(title="Initialisation", size = c("s"),
div(style="height:25px;"),
h4("Wait . . . ", style="margin-left:100px;"),
hr(style="border-color: #222222;"),
footer = NULL
)
}
#------------------------------------------------------#
# modalDialog sort periods
#------------------------------------------------------#
sortPeriod <- function(failed = FALSE) {
modalDialog(title="Sort clusters:",size=c("m"),
div(style="height:15px;"),
h3("Sort rows",style="text-align:center;"),hr(style="border-color: #222222;"),
h4("Sort each row from the oldest to the newest!"),
helpText("Note: Drag and drop clusters to sort them.
Drag unused row into the trash to remove them from the seriograph.
You can insert 'Hiatus' by picking it up and dropping it off where you want."),
orderInput('seq2',span(icon("sort-amount-up",lib = "font-awesome"),'Sort the cluster'),
items = Int2Alpha(sort(unique(values[["cluster"]]))),
placeholder = 'There must be at least one item', connect = "rm",
item_class = 'success'),
hr(style="border-color: #b2b2b2;"),
column(4,
orderInput('hiatus', span(icon("plus",lib = "font-awesome"),'Add'), items = c("Hiatus"),
connect = 'seq2', as_source = TRUE, item_class = 'warning', width = '70px')
),
column(8,
orderInput('rm', span(icon("trash",lib = "font-awesome"),'Remove from seriograph'),
items = NULL,connect = "seq2", placeholder = 'Drag the items here to delete them',
item_class = 'danger')
),
div(style="height:50px;"),
if (failed)
div(tags$b("You have to select the sequence!", style = "color: red;")),
footer = tagList(
modalButton("Cancel"),
actionButton("tri", "OK")
)
)
}
#------------------------------------------------------#
# modalDialog subdivise
#------------------------------------------------------#
subModal1 <- function(failed = FALSE) {
modalDialog(title="divide a cluster:",size=c("s"),
div(style="height:15px;"),
h3("Subdivide a cluster",style="text-align:center;"),hr(style="border-color: #222222;"),
h4("Select one cluster to divide!"),
selectInput("where","Cluster to divide:",
choices = as.list(sort(Int2Alpha((values[["div"]])))),
selected = 1,
multiple = FALSE),
footer = tagList(
modalButton("Cancel"),
actionButton("sub1", "Next")
)
)
}
#------------------------------------------------------#
# modalDialog subdivise2
#------------------------------------------------------#
subModal2 <- function(failed = FALSE) {#
modalDialog(title="divide a cluster:",size=c("s"),
div(style="height:15px;"),
h3("Subdivide a cluster",style="text-align:center;"),hr(style="border-color: #222222;"),
h4("How many sub-class do you want ?"),
sliderInput("sk",label = "Number:" ,min = 2,
max = length(values[["cluster_ori"]][values[["cluster_ori"]] == Alpha2Int(input$where)])-1,
step = 1, value = 2),
footer = tagList(
modalButton("Cancel"),
actionButton("back", "Back"),
actionButton("sub2", "Finish")
)
)
}
#------------------------------------------------------#
# modalDialog import
#------------------------------------------------------#
import1Modal <- function(failed = FALSE) {
modalDialog(title="Step 1:",size=c("l"),
div(style="height:15px;"),
h3("Step 1",style="text-align:center;"),hr(style="border-color: #222222;"),
h4("Upload file contingency table"),
# Input: Select a file ----
fileInput("fileD1", span(icon("import", lib = "glyphicon"),"Choose CSV File"),
multiple = FALSE,
accept = c("text/csv",
"text/comma-separated-values,text/plain",
".csv")
),
actionButton(inputId = "toggle", span(icon("cogs",lib = "font-awesome"),"Settings")),
fluidRow(shinydashboard::box(id="myBox",
fluidRow(
column(width = 6,
# Input: Checkbox if file has header ----
span(strong("Header")),
checkboxInput("headerD1", "Header (colnames)", TRUE),
checkboxInput("rownamesD1", "rownames", TRUE)
),
column(width = 6,
# Input: Select quotes ----input$dec
radioButtons("quoteD1", "Quote",
choices = c(None = "",
"Double Quote" = '"',
"Single Quote" = "'"),
selected = '"')
)
),
fluidRow(
column(width = 6,
# Input: Select separator ----
radioButtons("sepD1", "Separator",
choices = c(Comma = ",",
Semicolon = ";",
Tab = "\t",
Space = " "),
selected = ";")
),
column(width = 6,
radioButtons("decD1", "Decimal",
choices = c("Dot" = '.', "Comma" = ","),
selected = '.')
)
)
)),
tableOutput("contentsD1"),
if (failed)
div(tags$b("Your data must be match with the example above ! Change parameter or file.",
style = "color: red;")),
footer = tagList(
modalButton("Cancel"),
actionButton("import2", icon("arrow-right",lib = "font-awesome"))
)
)
}
#------------------------------------------------------#
# modalDialog import
#------------------------------------------------------#
import2Modal <- function(failed = FALSE) {
modalDialog(title="Step 2:",size=c("l"),
div(style="height:15px;"),
h3("Step 2",style="text-align:center;"),hr(style="border-color: #222222;"),
h4("Upload file temporal data"),
radioButtons("datatype", "Type",
choices = c("Stratigraphic connection" = 1,
"Time range data" = 2),
selected = 1),
fileInput("fileD2", span(icon("import", lib = "glyphicon"),"Choose CSV File"),
multiple = FALSE,
accept = c("text/csv",
"text/comma-separated-values,text/plain",
".csv")
),
actionButton(inputId = "toggle", span(icon("cogs",lib = "font-awesome"),"Settings")),
fluidRow(shinydashboard::box(id="myBox",
fluidRow(
column(width = 6,
# Input: Checkbox if file has header ----
span(strong("Header")),
checkboxInput("headerD2", "Header (colnames)", TRUE),
checkboxInput("rownamesD2", "rownames", FALSE)
),
column(width = 6,
# Input: Select quotes ----input$dec
radioButtons("quoteD2", "Quote",
choices = c(None = "",
"Double Quote" = '"',
"Single Quote" = "'"),
selected = '"')
)
),
fluidRow(
column(width = 6,
# Input: Select separator ----
radioButtons("sepD2", "Separator",
choices = c(Comma = ",",
Semicolon = ";",
Tab = "\t",
Space = " "),
selected = ";")
),
column(width = 6,
radioButtons("decD2", "Decimal",
choices = c("Dot" = '.',
"Comma" = ","),
selected = '.')
)
)
)),
tableOutput("contentsD2"),
if (failed)
div(tags$b("Your data must be match with the example above ! Change parameter or file.",
style = "color: red;")),
footer = tagList(
modalButton("Cancel"),
actionButton("back1", icon("arrow-left",lib = "font-awesome")),
actionButton("import3", icon("arrow-right",lib = "font-awesome"))
)
)
}
#------------------------------------------------------#
# modalDialog import
#------------------------------------------------------#
import3Modal <- function(failed = FALSE) {
modalDialog(title="Step 3:",size=c("l"),
div(style="height:15px;"),
h3("Step 3",style="text-align:center;"),hr(style="border-color: #222222;"),
h4("Visualisation and confirm"),
tableOutput("contentsD1"),
tableOutput("contentsD2"),
v <- validation(values[["D1"]],values[["D2"]],input$datatype),
if(v == ""){
div(tags$b("Valid data!", style = "color: green;"))
}else{
div(tags$b(paste("Invalid data!",v), style = "color: red;"))
},
if (failed)
div(tags$b("Your data must be match with the example above ! Change parameter or file.",
style = "color: red;")),
footer = tagList(
modalButton("Cancel"),
actionButton("back2", icon("arrow-left",lib = "font-awesome")),
actionButton("Finishimport", "Finish")
)
)
}
#------------------------------------------------------#
# modalDialog select axis
#------------------------------------------------------#
pre_selectaxis <- function() {
modalDialog(title="Select number of axis:",size=c("l"),
div(style="height:15px;"),
h3("Select number of axis:",style="text-align:center;"),hr(style="border-color: #222222;"),
HTML('<p>Our first source of information is a contingency table. We need to construct a distance matrix from this table. We perform a correspondence analysis (CA) on the contingency table and then use the distances of the components (chi-square metric).</p>
<p>It is necessary to choose the number of axes (CA components) to be used to construct the distance matrix.</p>
<p>By examining the eigenvalues, it is possible to determine the number of principal axes to be considered. The eigenvalues correspond to the amount of information retained by each axis.</p>
<p>A heuristic method is often used: one constructs the graph of eigenvalues sorted in descending order and retains the eigenvalues (and associated principal components) preceding the first "elbow".</p>
<p>Another approach is based on maintaining an approximation quality of the original data, measured by the explained inertia rate (e.g. 85%). As many axes as necessary are chosen so that the sum of the corresponding eigenvalues exceeds the target inertia rate.</p>'),
footer = tagList(
actionButton("nextCA", "OK")
)
)
}
selectaxis <- function() {
modalDialog(title="Select number of axes:",size=c("l"),
div(style="height:15px;"),
h3("Select number of axis:",style="text-align:center;"),hr(style="border-color: #222222;"),
plotlyOutput("axisCAplot"),
sliderInput("axisNumber",label = "Number:" ,min = 1,
max = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1),
step = 1, value = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1)),
footer = tagList(
modalButton("Cancel"),
actionButton("aCA", "OK")
)
)
}
selectaxis2 <- function() {
modalDialog(title="Select number of axis:",size=c("l"),
div(style="height:15px;"),
h3("Select number of axis:",style="text-align:center;"),hr(style="border-color: #222222;"),
plotlyOutput("axisCAplot"),
sliderInput("axisNumber",label = "Number:" ,min = 1,
max = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1),
step = 1, value = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1)),
footer = tagList(
actionButton("aCA", "OK")
)
)
}
values <- reactiveValues()
values[["nCP"]] <- "max"
values[["cluster"]] <- c()
values[["ADD"]] <- FALSE
values[["hiatus"]] <- NULL
values[["sortperiodtest"]] <- FALSE
values[["D_alpha"]] <- NULL
values[["valid"]] <- 1
values[["alphaplot"]] <- NULL
values[["dendrogram"]] <- NULL
values[["seriograph"]] <- NULL
values[["CA"]] <- NULL
values[["truecolor"]] <- NULL
values[["order"]] <- NULL
values[["table_serio"]] <- NULL
shinyjs::hide("toggle")
shinyjs::show("nodata")
observeEvent(input$axe1,{
values[["axe1"]] <- input$axe1
})
observeEvent(input$axe2,{
values[["axe2"]] <- input$axe2
})
observeEvent(input$width1,{
values[["width1"]] <- input$width1
})
observeEvent(input$height1,{
values[["height1"]] <- input$height1
})
observeEvent(input$width2,{
values[["width2"]] <- input$width2
})
observeEvent(input$height2,{
values[["height2"]] <- input$height2
})
observeEvent(input$width3,{
values[["width3"]] <- input$width3
})
observeEvent(input$height3,{
values[["height3"]] <- input$height3
})
observeEvent(input$width4,{
values[["width4"]] <- input$width4
})
observeEvent(input$height4,{
values[["height4"]] <- input$height4
})
observeEvent(input$width5,{
values[["width5"]] <- input$width5
})
observeEvent(input$height5,{
values[["height5"]] <- input$height5
})
observeEvent(input$width6,{
values[["width6"]] <- input$width6
})
observeEvent(input$height4,{
values[["height6"]] <- input$height6
})
observeEvent(input$method,{
if(input$method == 1){values[["method"]] <- "ward.D"}
if(input$method == 2){values[["method"]] <- "ward.D2"}
if(input$method == 3){values[["method"]] <- "single"}
if(input$method == 4){values[["method"]] <- "complete"}
if(input$method == 5){values[["method"]] <- "average"}
if(input$method == 6){values[["method"]] <- "mcquitty"}
#if(input$method == 7){values[["method"]] <- "median"}
#if(input$method == 8){values[["method"]] <- "centroid"}
values[["cluster"]] <- values[["cluster_ori"]]
values[["ADD"]] <- FALSE
values[["div"]] <- as.numeric(names(table(values[["cluster_ori"]]))[table(values[["cluster_ori"]])>1])
enable("subdivise")
values[["hiatus"]] <- NULL
values[["sortperiodtest"]] <- FALSE
values[["step"]] <- NULL
values[["which"]] <- NULL
values[["where"]] <- NULL
values[["order"]] <- NULL
values[["firstClustSett"]] <- TRUE
})
#raw stratigraphic data (Network)
values[["data2"]] <- values[["raw"]] <- data.frame(
ens = c("AI09","AI08","AI07","AI06","AI05","AI04","AI03",
"AI02","AI01","AO05","AO04","AO03","AO02","AO01","APQR03","APQR02","APQR01"),
linked_at = c("AI08,AI06","AI07","AI04","AI05","AI01","AI03","AI02","","","AO04","AO03",
"AO02,AO01","","","APQR02","APQR01","")
)
#contingency table
values[["data1"]] <- values[["cont"]] <- data.frame(
Cat10 = c(1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0),
Cat20 = c(4,8,0,0,0,0,0,0,0,6,0,0,0,0,0,0,0),
Cat30 = c(18,24,986,254,55,181,43,140,154,177,66,1,24,15,0,31,37),
Cat40.50 = c(17,121,874,248,88,413,91,212,272,507,187,40,332,174,17,288,224),
Cat60 = c(0,0,1,0,0,4,4,3,0,3,0,0,0,0,0,0,0),
Cat70 = c(3,1,69,54,10,72,7,33,74,36,16,4,40,5,0,17,13),
Cat80 = c(4,0,10,0,12,38,2,11,38,26,25,1,18,4,0,25,7),
Cat100.101 = c(23,4,26,51,31,111,36,47,123,231,106,21,128,77,10,151,114),
Cat102 = c(0,1,2,2,4,4,13,14,6,6,0,0,12,5,1,17,64),
Cat110.111.113 = c(0,0,22,1,17,21,12,20,30,82,15,22,94,78,18,108,8),
Cat120.121 = c(0,0,0,0,0,0,0,0,0,0,66,0,58,9,0,116,184),
Cat122 = c(0,0,0,0,0,0,0,0,0,0,14,0,34,5,0,134,281),
row.names = c("AI01","AI02","AI03","AI04","AO03","AI05","AO01","AI07","AI08",
"AO02","AI06","AO04","APQR01","APQR02","AO05","APQR03","AI09")
)
output$data1 <- renderTable(rownames = TRUE, bordered = TRUE,digits = 0,{
values[["data1"]]
})
output$data2 <- renderTable(bordered = TRUE,{
values[["data2"]]
})
output$data1f <- renderTable(rownames = TRUE, bordered = TRUE,digits = 0,{
data.frame(
Cat10 = c(1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0),
Cat20 = c(4,8,0,0,0,0,0,0,0,6,0,0,0,0,0,0,0),
Cat30 = c(18,24,986,254,55,181,43,140,154,177,66,1,24,15,0,31,37),
Cat40.50 = c(17,121,874,248,88,413,91,212,272,507,187,40,332,174,17,288,224),
Cat60 = c(0,0,1,0,0,4,4,3,0,3,0,0,0,0,0,0,0),
Cat70 = c(3,1,69,54,10,72,7,33,74,36,16,4,40,5,0,17,13),
Cat80 = c(4,0,10,0,12,38,2,11,38,26,25,1,18,4,0,25,7),
Cat100.101 = c(23,4,26,51,31,111,36,47,123,231,106,21,128,77,10,151,114),
Cat102 = c(0,1,2,2,4,4,13,14,6,6,0,0,12,5,1,17,64),
Cat110.111.113 = c(0,0,22,1,17,21,12,20,30,82,15,22,94,78,18,108,8),
Cat120.121 = c(0,0,0,0,0,0,0,0,0,0,66,0,58,9,0,116,184),
Cat122 = c(0,0,0,0,0,0,0,0,0,0,14,0,34,5,0,134,281),
row.names = c("AI01","AI02","AI03","AI04","AO03","AI05","AO01","AI07","AI08",
"AO02","AI06","AO04","APQR01","APQR02","AO05","APQR03","AI09")
)
})
output$data2f <- renderTable(bordered = TRUE,{
data.frame(
ens = c("AI09","AI08","AI07","AI06","AI05","AI04","AI03",
"AI02","AI01","AO05","AO04","AO03","AO02","AO01","APQR03","APQR02","APQR01"),
linked_at = c("AI08,AI06","AI07","AI04","AI05","AI01","AI03","AI02","","","AO04","AO03",
"AO02,AO01","","","APQR02","APQR01","")
)
})
output$data3f <- renderTable(bordered = TRUE,digits=0,{
data.frame(
ens = c("AI09","AI08","AI07","AI06","AI05","AI04","AI03",
"AI02","AI01","AO05","AO04","AO03","AO02","AO01","APQR03","APQR02","APQR01"),
inf = c(400,420,500,590,600,550,400,750,700,750,900,800,700,800,850,1000,1050),
sup = c(500,500,600,800,800,700,600,800,900,850,1100,950,800,900,900,1100,1100)
)
})
output$axisCAplot <- renderPlotly({
cont <- values[["data1"]]
tmp <- CA(cont, graph=FALSE)
x <- paste0(rownames(tmp$eig)," (",arrondi(tmp$eig[,3],1),"%)")
Eigen_value <- tmp$eig[,1]
df2 <- data.frame(x,Eigen_value)
df2 <- within(df2,Principal_Component <- factor(x,levels = x))
plot_ly(df2,
x = ~Principal_Component,
y = ~Eigen_value,
type = "bar"
)
})
output$timerange <- renderPlotly({
data <- values[["data2"]]
data <- data[order(data[,1]),]
res <- timerange(data = data,cluster = values[["cluster"]])
values[["order"]] <- res$order
res$plot
})
output$selectAlpha <- renderPlot({
if(values[["firstClustSett"]]){
showModal(pre_selectaxis())
}else{
showModal(waitModal())
shinyjs::show("toggle")
shinyjs::hide("nodata")
progress1 <- Progress$new(session, min = 0, max = 2)
on.exit(progress1$close())
progress1$set(message = 'Initialisation and calcul of the default alpha ..')
raw <- values[["data2"]]
cont <- values[["data1"]]
if(values[["valid"]] == 1){
D2 <- adjacency(raw)
}else{
D2 <- overlap(raw)
}
D1 <- CAdist(cont,nCP=values[["nCP"]],graph=TRUE)
values[["CA"]] <- recordPlot()
progress1$set(value = 1)
sa <- hclustcompro_select_alpha(D1, D2, method = values[["method"]],resampling=FALSE, ite= 5)
values[["alphaplot"]] <- sa$alpha.plot
print(sa$alpha.plot)
progress1$set(value = 2)
updateSliderInput(session, "alpha", value = sa$alpha)
updateSliderInput(session, "k", value = values[["nb_classes"]],min=2,
max = length(values[["raw"]][,1])-1,step = 1)
removeModal()
}
})
observeEvent(input$aCA,values[["firstClustSett"]] <- FALSE)
output$dendrogramme <- renderPlot({
raw <- values[["data2"]]
cont <- values[["data1"]]
if(values[["valid"]] == 1){
D2 <- adjacency(raw)
}else{
D2 <- overlap(raw)
}
D1 <- CAdist(cont,nCP=values[["nCP"]],graph=FALSE)
alpha <- input$alpha
#create mixing matrix
D1 <- as.dist(D1)
D2 <- as.dist(D2)
D1 <- as.matrix(D1)
D2 <- as.matrix(D2)
#sort labels
D1.Tmp <- D1[sort(labels(D1)[[1]]),sort(labels(D1)[[1]])]
D2.Tmp <- D2[sort(labels(D2)[[1]]),sort(labels(D2)[[1]])]
D1 <- as.dist(D1.Tmp)
D2 <- as.dist(D2.Tmp)
#normalization
if(max(D1) != 0){
D1 <- D1 / max(D1)
}
if(max(D2) != 0){
D2 <- D2 / max(D2)
}
#mixt matrix
dist.mixt <- (alpha) * D1 + (1-alpha) * D2
dist.mixt <- as.dist(dist.mixt)
values[["D_alpha"]] <- dist.mixt
#CAH
tree <- hclust(dist.mixt, method = values[["method"]])
values[["tree"]] <- tree
#wss
D <- as.matrix(dist.mixt)
n <- length(D[,1])
if(length(D[,1]) > 20){n <- 20}
values[["n"]] <- n
wss <- c()
sil <- c()
for ( i in 2:(n-1)){
cutree <- cutree(tree,i)
res <- cluster.stats(D,cutree)
wss <- c(wss,res$within.cluster.ss)
sil <- c(sil,res$avg.silwidth)
}
values[["wss_v"]] <- wss
values[["sil_v"]] <- sil
Within_Sum_of_Square <- rbind(seq(2,(n-1)),wss)
color_wss <- elbow_finder(seq(2,(n-1)),wss)
dataplot <- t(Within_Sum_of_Square)
dataplot <- as.data.frame(dataplot)
colnames(dataplot) <- c("Number_of_groups","Within_Sum_of_Square")
q <- ggplot(dataplot,aes(x=Number_of_groups, y=Within_Sum_of_Square)) +
geom_point(aes(color=color_wss),size=2) + scale_colour_gradientn(colours=c("brown1","chartreuse3")) +
geom_line(linetype = 3) +
scale_x_continuous(breaks = dataplot$Number_of_groups ,
labels = dataplot$Number_of_groups ) +
ylim(0,max(wss)+1) +
labs(title = "Within Sum of Square" , subtitle = "Partition evaluation") +
theme(legend.position="none")
values[["wss"]] <- q
#silhouette
Average_Sil_Width <- rbind(seq(2,(n-1)),sil)
dataplot <- t(Average_Sil_Width)
dataplot <- as.data.frame(dataplot)
dataplot <- na.omit(dataplot)
colnames(dataplot) <- c("Number_of_groups","Average_Sil_Width")
p <- ggplot(dataplot,aes(x=Number_of_groups, y=Average_Sil_Width)) +
geom_point(aes(color=Average_Sil_Width),size=2) +
scale_colour_gradientn(colours=c("brown1","chartreuse3")) +
geom_line(linetype = 3) + ylim(0,1) +
scale_x_continuous(breaks = dataplot$Number_of_groups,
labels = dataplot$Number_of_groups) +
labs(title = "Average Silhouette Width", subtitle = "Partition evaluation") +
theme(legend.position="none")
values[["silhouette"]] <- p
#dendrogram
title <- paste("Cluster Dendrogram with alpha =",alpha)
subtitle <- paste("The mixing matrix is made of ",alpha * 100,"% of D1 and ",(1-alpha) * 100,"% of D2.")
plot(tree,
h=-1, main = title, sub = subtitle, xlab=paste0("dist.mixt, method: \"",values[["method"]],"\""))
if(length(input$k) == 0){
k <- 2
}else{
k <- input$k
}
cluster <- cutree(tree, k = k)
order <- unique(cluster[tree$order])
for(i in 1:length(order)){
if(i != order[i] && i < order[i]){
cluster[cluster == i] <- 0
cluster[cluster == order[i]] <- i
cluster[cluster == 0] <- order[i]
order <- unique(cluster[tree$order])
}
}
if(values[["ADD"]] == FALSE && values[["sortperiodtest"]] == FALSE){
values[["clusterserio"]] <- values[["cluster"]] <- cluster
values[["cluster_ori"]] <- cluster
values[["div"]] <- as.numeric(names(table(values[["cluster_ori"]]))[table(values[["cluster_ori"]])>1])
}
rect.hclust(tree, k = k, border = rainbow_hcl(k, c = 80, l = 60, start = 0, end = 360*(k-1)/k))
col <- rainbow_hcl(length(unique(cluster)), c = 80, l = 60, start = 0,
end = 360*(length(unique(cluster))-1)/(length(unique(cluster))))
for(i in 1:length(unique(cluster))){
x <- mean(which(cluster[tree$order] == sort(unique(cluster))[i]))
mtext(paste0(LETTERS[i]), side = 1, line = .5, at = x, col = col[i], cex=1.5)
}
mtext("Cluster:",side = 1, line = .5, at = 0, col = "#767676", cex=1.2)
mtext("Order:",side = 1, line = 1.5, at = 0, col = "#767676", cex=1.2)
if(values[["sortperiodtest"]]){
}
#if subdivide
if(values[["ADD"]]){
#rectangle
for(i in 1:length(values[["which"]])){
#col <- rainbow_hcl(length(unique(values[["cluster"]])), c = 80, l = 60, start = 0,
# end = 360*(length(unique(values[["cluster"]]))-1)/(length(unique(values[["cluster"]]))))
#index <- which(unique(values[["cluster"]][tree$order]) > values[["where"]][[i]])
rect.hclust(tree,h = tree$height[values[["step"]][[i]]+1],which = values[["which"]][[i]],
border = values[["truecolor"]][values[["where"]][[i]]])#col[index])
}
#cluster white erase
for(i in 1:length(unique(values[["cluster_ori"]]))){
x <- mean(which(values[["cluster_ori"]][tree$order] == sort(unique(values[["cluster_ori"]]))[i]))
mtext(Int2Alpha(sort(unique(values[["cluster_ori"]]))[i]), side = 1, line = .5, at = x, col = "white",
cex=1.5)
}
#cluster col
for(i in 1:length(unique(values[["cluster"]]))){
x <- mean(which(values[["cluster"]][tree$order] == sort(unique(values[["cluster"]]))[i]))
j <- trunc(sort(unique(values[["cluster"]]))[i])
mtext(Int2Alpha(sort(unique(values[["cluster"]]))[i]), side = 1, line = .5, at = x,
col = values[["truecolor"]][j], cex=1.5)
}
for(i in 1:length(unique(values[["clusterserio"]]))){
#if not remove period
if(!nchar(sort(unique(values[["clusterserio"]]))[i]) == 5){
x <- mean(which(values[["clusterserio"]][tree$order] == sort(unique(values[["clusterserio"]]))[i]))
#y <- which(unique(values[["clusterserio"]][tree$order]) == sort(unique(values[["clusterserio"]]))[i])
j <- trunc(sort(unique(values[["cluster"]]))[i])
mtext(paste0(sort(unique(values[["clusterserio"]]))[i]), side = 1, line = 1.5, at = x,
col = "#333333", cex=1.3)
#if remove elt period
}else{
x <- mean(which(values[["clusterserio"]][tree$order] == sort(unique(values[["clusterserio"]]))[i]))
#y <- which(unique(values[["clusterserio"]][tree$order]) == sort(unique(values[["clusterserio"]]))[i])
j <- trunc(sort(unique(values[["cluster"]]))[i])
mtext("Rm", side = 1, line = 1.5, at = x, col = "#333333", cex=1.3)
}
}
#not subdivide
}else{
for(i in 1:length(unique(values[["clusterserio"]]))){
#if not remove period
if(!nchar(sort(unique(values[["clusterserio"]]))[i]) == 5){
x <- mean(which(values[["clusterserio"]][tree$order] == sort(unique(values[["clusterserio"]]))[i]))
#y <- which(unique(values[["clusterserio"]][tree$order]) == sort(unique(values[["clusterserio"]]))[i])
j <- trunc(sort(unique(values[["cluster"]]))[i])
mtext(paste0(sort(unique(values[["clusterserio"]]))[i]), side = 1, line = 1.5, at = x,
col = "#333333", cex=1.3)
#if remove elt period
}else{
x <- mean(which(values[["clusterserio"]][tree$order] == sort(unique(values[["clusterserio"]]))[i]))
#y <- which(unique(values[["clusterserio"]][tree$order]) == sort(unique(values[["clusterserio"]]))[i])
j <- trunc(sort(unique(values[["cluster"]]))[i])
mtext("Rm", side = 1, line = 1.5, at = x, col = "#333333", cex=1.3)
}
}
}
values[["dendrogram"]] <- recordPlot()
})
output$EPPM <- renderPlot({
seq <- values[["clusterserio"]]
hiatus <- values[["hiatus"]]
cont <- values[["data1"]]
cont <- cont[sort(labels(cont)[[1]]),]
cont2 <- mutate(cont, Cluster = factor(seq))
cont2 <- group_by(cont2, Cluster)
cont2 <- summarise_all(cont2, sum)
cont2 <- as.data.frame(cont2)
row.names(cont2) <- as.character(unique(sort(seq)))
cont2 <- cont2[,-1]
remove <- which(nchar(rownames(cont2)) == 5)
#remove <- which(rownames(cont2) >= 900)
if(length(remove) >= 1){
cont2 <- cont2[-remove,]
}
cont2 <- cont2[order(as.numeric(rownames(cont2)),decreasing = T),]
rownames(cont2) <- as.character(paste0("Cluster.",rownames(cont2)))
#hiatus
if(length(hiatus) > 0 && !is.na(hiatus)){
#insert hiatus
label <- "Hiatus"
insert <- values[["hiatus"]]
insert <- sort(length(cont2[,1]) - insert)
for (i in length(insert):1){
if(insert[i] < length(cont2[,1]) && insert[i] >= 1 && insert[i] == trunc(insert[i])){
cont2 <- rbind(cont2[1:insert[i],], label = rep(0,length(cont2[1,])),
cont2[(insert[i]+1):length(cont2[,1]),])
if(length(insert)== 1){
row.names(cont2)[insert[i]+1] <- label
}else{
row.names(cont2)[insert[i]+1] <- paste0(label,".",(length(insert)+1 - i))
}
}else{
warning("Some positions are outside the range. Ex: ",insert[i])
}
}
}
show <- c("both","frequency","EPPM")[as.numeric(input$show)]
values[["table_serio"]] <- cont2
plot_EPPM(cont2, permute=input$permute, col_weight = input$col_weight, show = show)
values[["seriograph"]] <- recordPlot()
})
output$CA <- renderScatterD3({
updateNumericInput(session, "axe1", max = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1))
updateNumericInput(session, "axe2", max = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1))
res <- explor::prepare_results(CA(values[["data1"]], ncp = min( nrow(values[["data1"]])-1,ncol(values[["data1"]])-1)))
xax = values[["axe1"]]
yax = values[["axe2"]]
var_sup = TRUE
var_hide = "None"
var_lab_min_contrib = 0
point_size = 64
col_var = "Position"
symbol_var = NULL
size_var = NULL
size_range = c(10,300)
zoom_callback = NULL
in_explor = FALSE
## Settings changed if not run in explor
html_id <- if(in_explor) "explor_var" else NULL
dom_id_svg_export <- if(in_explor) "explor-var-svg-export" else NULL
dom_id_lasso_toggle <- if(in_explor) "explor-var-lasso-toggle" else NULL
lasso <- if(in_explor) TRUE else FALSE
lasso_callback <- if(in_explor) explor_multi_lasso_callback() else NULL
zoom_callback <- if(in_explor) explor_multi_zoom_callback(type = "var") else NULL
var_data <- CA_var_data(res, xax, yax, var_sup, var_hide, var_lab_min_contrib)
scatterD3::scatterD3(
x = var_data[, "Coord.x"],
y = var_data[, "Coord.y"],
xlab = names(res$axes)[res$axes == xax],
ylab = names(res$axes)[res$axes == yax],
lab = var_data[, "Lab"],
point_size = point_size,
point_opacity = 1,
col_var = if (is.null(col_var)) NULL else var_data[,col_var],
col_lab = col_var,
symbol_var = if (is.null(symbol_var)) NULL else var_data[,symbol_var],
symbol_lab = symbol_var,
size_var = if (is.null(size_var)) NULL else var_data[,size_var],
size_lab = size_var,
size_range = if (is.null(size_var)) c(10,300) else c(30,400) * point_size / 32,
tooltip_text = var_data[, "tooltip"],
type_var = ifelse(var_data[, "Class"] == "Quantitative", "arrow", "point"),
unit_circle = var_sup && "Quantitative" %in% var_data[,"Class"],
key_var = paste(var_data[,"Position"], var_data[,"Level"], sep = "-"),
fixed = TRUE,
html_id = html_id,
dom_id_svg_export = dom_id_svg_export,
dom_id_lasso_toggle = dom_id_lasso_toggle,
lasso = lasso,
lasso_callback = lasso_callback,
zoom_callback = zoom_callback
)
})
output$WSS <- renderPlot({
print(values[["wss"]])
})
output$silhouette <- renderPlot({
print(values[["silhouette"]])
})
observeEvent(input$aCA,{
values[["nCP"]] <- input$axisNumber
removeModal()
})
observeEvent(input$nextCA,{
removeModal()
showModal(selectaxis2())
})
observeEvent(input$sort,{
showModal(sortPeriod())
})
observeEvent(input$tri,{
remove <- input$rm_order
remove <- remove[2][remove[2] != "Hiatus"]
order <- input$seq2_order
if(is.na(order[2])[1] || ( length(order[2]) == 1 && order[2][1] == "Hiatus" )){
removeModal()
}else{
hiatus <- which(order[2] == "Hiatus")
for (i in 1:length(hiatus)){
hiatus[i] <- hiatus[i] - 1 * i
}
values[["hiatus"]] <- hiatus
order <- order[2][order[2] != "Hiatus"]
remove <- remove[!is.na(remove)]
if(length(remove) >= 1){
remove <- Alpha2Int(remove)
}
split <- Alpha2Int(order)
if(length(split)==0){
removeModal()
showModal(sortPeriod(TRUE))
}else{
cluster <- values[["cluster"]]
seq <- cluster
if(length(remove) >= 1){
for(i in 1:length(remove)){
removeseq <- which(seq %in% remove[i])
seq[removeseq] <- seq[removeseq] + as.numeric(paste0("0.00",i))
}
}
c <- 0
d <- 1
pelt <- 0
for (i in 1:length(split)) {
elt <- as.numeric(split[i])
felt <- as.numeric(split[i+1])
if(elt != as.integer(elt)){
if(as.integer(elt) != as.integer(pelt)){
c <- c + 1
d <- 1
}
seq[cluster == elt] <- as.numeric(paste0(c,".",d))
d <- d + 1
}else{
c <- c + 1
seq[cluster == elt] <- c
d <- 1
}
pelt <- elt
}
values[["clusterserio"]] <- seq
values[["sortperiodtest"]] <- TRUE
removeModal()
}
}
})
observeEvent(input$subdivise,{
showModal(subModal1())
})
observeEvent(input$sub1,{
removeModal()
showModal(subModal2())
})
observeEvent(input$sub2,{
removeModal()
ok <- TRUE
cluster <- values[["cluster"]]
tree <- values[["tree"]]
where <- Alpha2Int(input$where)
values[["div"]] <- values[["div"]][values[["div"]] != where]
if(length(values[["div"]]) == 0){
disable("subdivise")
}
sk <- input$sk
step <- length(cluster)-1
while(ok){
clusters <- cutree(tree,h = tree$height[step])
if(length(unique(clusters[cluster == where])) == sk){
ok <- FALSE
}else{
step <- step - 1
}
}
#reorder value
order <- unique(clusters[tree$order])
for(i in 1:length(order)){
if(i != order[i] && i < order[i]){
clusters[clusters == i] <- 0
clusters[clusters == order[i]] <- i
clusters[clusters == 0] <- order[i]
order <- unique(clusters[tree$order])
}
}
nb <- which(values[["cluster_ori"]] == Alpha2Int(input$where))
nb <- clusters[nb]
which <- sort(unique(nb))
#rename value
resume <- table(clusters[cluster == where])
c <- 1
for(i in as.numeric(names(resume))){
clusters[clusters == i] <- c
c <- c+1
}
c <- c-1
clusters <- clusters / 10 ^nchar(c)
for(i in 1:length(cluster)){
ifelse(cluster[i] == where,
cluster[i] <- where + clusters[i],
cluster[i] <- cluster[i])
}
values[["clusterserio"]] <- values[["cluster"]] <- cluster
values[["step"]][[length(values[["step"]])+1]] <- step
values[["which"]][[length(values[["which"]])+1]] <- which
values[["where"]][[length(values[["where"]])+1]] <- Alpha2Int(input$where)
values[["ADD"]] <- TRUE
})
observeEvent(input$alpha,{
values[["cluster"]] <- values[["cluster_ori"]]
values[["ADD"]] <- FALSE
values[["div"]] <- as.numeric(names(table(values[["cluster_ori"]]))[table(values[["cluster_ori"]])>1])
enable("subdivise")
values[["hiatus"]] <- NULL
values[["sortperiodtest"]] <- FALSE
values[["order"]] <- NULL
})
observeEvent(input$k,{
values[["cluster"]] <- values[["cluster_ori"]]
values[["ADD"]] <- FALSE
values[["div"]] <- as.numeric(names(table(values[["cluster_ori"]]))[table(values[["cluster_ori"]])>1])
enable("subdivise")
values[["hiatus"]] <- NULL
values[["sortperiodtest"]] <- FALSE
values[["truecolor"]] <- rainbow_hcl(input$k, c = 80, l = 60, start = 0,
end = 360*(input$k-1)/input$k)
values[["step"]] <- NULL
values[["which"]] <- NULL
values[["where"]] <- NULL
values[["order"]] <- NULL
values[["table_serio"]] <- NULL
})
observeEvent(input$back,{
removeModal()
showModal(subModal1())
})
observeEvent(input$reset,{
values[["cluster"]] <- values[["cluster_ori"]]
values[["ADD"]] <- FALSE
values[["div"]] <- as.numeric(names(table(values[["cluster_ori"]]))[table(values[["cluster_ori"]])>1])
enable("subdivise")
values[["hiatus"]] <- NULL
values[["sortperiodtest"]] <- FALSE
values[["step"]] <- NULL
values[["which"]] <- NULL
values[["where"]] <- NULL
values[["order"]] <- NULL
values[["table_serio"]] <- NULL
})
output$contentsD1 <- renderTable({
# input$file1 will be NULL initially. After the user selects
# and uploads a file, head of that data file by default,
# or all rows if selected, will be shown.
req(input$fileD1)
inFile <- input$fileD1
if(is.null(inFile))
return(NULL)
tryCatch({
if(input$rownamesD1){
df <- read.table(input$fileD1$datapath,
header = input$headerD1,
sep = input$sepD1,
dec = input$decD1,
quote = input$quoteD1,
row.names = 1,
check.names = TRUE,
stringsAsFactors=FALSE)
}else{
df <- read.table(input$fileD1$datapath,
header = input$headerD1,
sep = input$sepD1,
dec = input$decD1,
quote = input$quoteD1,
check.names = TRUE,
stringsAsFactors=FALSE)
}
},
error = function(e) {
# return a safeError if a parsing error occurs
stop(safeError(e))
})
values[["D1"]] <- df
return(head(df))
},rownames=TRUE)
output$contentsD2 <- renderTable({
# input$file1 will be NULL initially. After the user selects
# and uploads a file, head of that data file by default,
# or all rows if selected, will be shown.
req(input$fileD2)
inFile <- input$fileD2
if(is.null(inFile))
return(NULL)
tryCatch({
if(input$rownamesD2){
df <- read.table(input$fileD2$datapath,
header = input$headerD2,
sep = input$sepD2,
dec = input$decD2,
quote = input$quoteD2,
row.names = 1,
check.names = TRUE,
stringsAsFactors=FALSE)
}else{
df <- read.table(input$fileD2$datapath,
header = input$headerD2,
sep = input$sepD2,
dec = input$decD2,
quote = input$quoteD2,
check.names = TRUE,
stringsAsFactors=FALSE)
}
},
error = function(e) {
# return a safeError if a parsing error occurs
stop(safeError(e))
})
if(input$datatype == 2){values[["timerange"]] <- df}
values[["D2"]] <- df
return(head(df))
},rownames=TRUE)
observeEvent(input$data,{
showModal(import1Modal())
shinyjs::hide(id = "myBox")
})
observeEvent(input$back1,{
showModal(import1Modal())
shinyjs::hide(id = "myBox")
})
observeEvent(input$back2,{
showModal(import2Modal())
shinyjs::hide(id = "myBox")
})
observeEvent(input$import2,{
showModal(import2Modal())
shinyjs::hide(id = "myBox")
})
observeEvent(input$import3,{
showModal(import3Modal())
})
observeEvent(input$Finishimport,{
v <- validation(values[["D1"]],values[["D2"]],input$datatype)
if(!v == ""){
removeModal()
showModal(import3Modal(TRUE))
}else{
removeModal()
values[["nCP"]] <- "max"
values[["cluster"]] <- values[["cluster_ori"]]
values[["ADD"]] <- FALSE
values[["div"]] <- as.numeric(names(table(values[["cluster_ori"]]))[table(values[["cluster_ori"]])>1])
enable("subdivise")
values[["data1"]] <- values[["D1"]]
values[["data2"]] <- values[["D2"]]
values[["D1"]] <- NULL
values[["D2"]] <- NULL
values[["PA"]] <- NULL
values[["sortperiodtest"]] <- FALSE
values[["clusterserio"]] <- c(1)
values[["valid"]] <- input$datatype
values[["firstClustSett"]] <- TRUE
updateNumericInput(session, "axe1", value = 1)
updateNumericInput(session, "axe2", value = 2)
}
})
observeEvent(input$data,{
shinyjs::disable("import2")
})
observeEvent(input$import2,{
shinyjs::disable("import3")
})
observeEvent(input$fileD1,{
shinyjs::enable("import2")
})
observeEvent(input$fileD2,{
shinyjs::enable("import3")
})
observeEvent(input$toggle, {
if(input$toggle %% 2 == 0){
shinyjs::hide(id = "myBox")
}else{
shinyjs::show(id = "myBox")
}
})
observeEvent(input$refresh, {
session$reload()
})
observeEvent(input$axesCA, {
showModal(selectaxis())
})
#EXPORT BUTTON
output$alpha.pdf <- downloadHandler(
filename = "alpha.pdf",
content = function(file) {
cairo_pdf(file,width=12)
print(values[["alphaplot"]])
dev.off()
}
)
output$alpha.png <- downloadHandler(
filename = "alpha.png",
content = function(file) {
png(file,
width = values[["width1"]],
height = values[["height1"]]
)
print(values[["alphaplot"]])
dev.off()
}
)
output$dendrogram.pdf <- downloadHandler(
filename = "dendrogram.pdf",
content = function(file) {
cairo_pdf(file,width=12)
print(values[["dendrogram"]])
dev.off()
}
)
output$dendrogram.png <- downloadHandler(
filename = "dendrogram.png",
content = function(file) {
png(file,
width = values[["width2"]],
height = values[["height2"]]
)
print(values[["dendrogram"]])
dev.off()
}
)
output$seriograph.pdf <- downloadHandler(
filename = "seriograph.pdf",
content = function(file) {
cairo_pdf(file,width=12)
print(values[["seriograph"]])
dev.off()
}
)
output$seriograph.png <- downloadHandler(
filename = "seriograph.png",
content = function(file) {
png(file,
width = values[["width3"]],
height = values[["height3"]]
)
print(values[["seriograph"]])
dev.off()
}
)
output$silplot.pdf <- downloadHandler(
filename = "silplot.pdf",
content = function(file) {
cairo_pdf(file,width=12)
print(values[["silplot"]])
dev.off()
}
)
output$silplot.png <- downloadHandler(
filename = "silplot.png",
content = function(file) {
png(file,
width = values[["width4"]],
height = values[["height4"]]
)
print(values[["silplot"]])
dev.off()
}
)
output$wss.pdf <- downloadHandler(
filename = "wss.pdf",
content = function(file) {
cairo_pdf(file,width=7)
print(values[["wss"]])
dev.off()
}
)
output$wss.png <- downloadHandler(
filename = "wss.png",
content = function(file) {
png(file,
width = 500,
height = 500
)
print(values[["wss"]])
dev.off()
}
)
output$silhouette.pdf <- downloadHandler(
filename = "silhouette.pdf",
content = function(file) {
cairo_pdf(file,width=7)
print(values[["silhouette"]])
dev.off()
}
)
output$silhouette.png <- downloadHandler(
filename = "silhouette.png",
content = function(file) {
png(file,
width = 500,
height = 500
)
print(values[["silhouette"]])
dev.off()
}
)
output$table_serio.csv <- downloadHandler(
filename = function() {
paste("table_serio", ".csv", sep = "")
},
content = function(file) {
write.csv2(values[["table_serio"]], file, row.names = TRUE)
}
)
observeEvent(input$seriograph.pdf,{
showNotification("wait for backup in progress",duration=15)
})
output$detail <- renderPlotly({
raw <- values[["data2"]]
cont <- values[["data1"]]
if(values[["valid"]] == 1){
D2 <- adjacency(raw)
}else{
D2 <- temp_cov(raw)
}
D1 <- CAdist(cont,nCP=values[["nCP"]],graph=FALSE)
method <- values[["method"]]
acc = 2
METHODS <- c("ward.D", "single", "complete", "average", "mcquitty",
"median", "centroid", "ward.D2")
if (method == "ward") {
message("The \"ward\" method has been renamed to \"ward.D\"; note new avaible method \"ward.D2\"")
method <- "ward.D"
}
i.meth <- pmatch(method, METHODS)
if (is.na(i.meth))
stop("invalid clustering method", paste("", method))
if (i.meth == -1)
stop("ambiguous clustering method", paste("", method))
method <- METHODS[i.meth]
if(!is.numeric(acc)) {stop("acc must be numeric!")}
if(acc < 1) {
acc <- 1;
message("The minimal value allowed for acc is 1.")
}
if(class(D1)[1] == "hclustcompro_cl"){
if(is.null(D1$D1) || is.null(D1$D2)){
stop("We don't find dissmilarities in hclustcompro_cl object.")
}else{
D2 <- D1$D2
D1 <- D1$D1
}
}else{
if(is.null(D1) || is.null(D2)){
stop("We don't find dissmilarities in D1 and D2 arguments.")
}
#test
if(class(D1)[1] != "dist"){
#matrix ?
if(!is.matrix(D1)){
D1 <- as.matrix(CAdist(cont,nCP=values[["nCP"]],graph=FALSE))
}
#diag = 0 ?
if(sum(diag(D1)) != 0){
stop("D1: in distance matrix the diagonal is equal to 0.")
}
#symetric ?
if(!isSymmetric(D1)){
stop("D1 is not symmetric.")
}
}
if(class(D2)[1] != "dist"){
#matrix ?
if(!is.matrix(D2)){
if(valid){
D2 <- adjacency(raw)
}else{
D2 <- temp_cov(raw)
}
}
#diag = 0 ?
if(sum(diag(D2)) != 0){
stop("D2: in distance matrix the diagonal is equal to 0.")
}
#symetric ?
if(!isSymmetric(D2)){
stop("D2 is not symmetric.")
}
}
if(!length(D1[,1]) == length(D1[1,])){stop("D1 not a square matrix.")}
if(!length(D2[,1]) == length(D2[1,])){stop("D2 not a square matrix.")}
#dist (positive matrix) ?
if(min(D1) < 0){stop("D1 not a matrix dissimilarity (positive).")}
if(min(D2) < 0){stop("D2 not a matrix distance (positive).")}
if(median(D2) != 0 && median(D2) != 1){
if(median(D1) == 0 || median(D1) == 1){
message("We switch the two matrices. Stratigraphic data must be in D1 and ceramic data in D2.")
tmp <- D1
D1 <- D2
D2 <- tmp
}
}
#normalization
if(max(D1) != 0){
D1 <- D1 / max(D1)
}
if(max(D2) != 0){
D2 <- D2 / max(D2)
}
#create mixing matrix
D1 <- as.dist(D1)
D2 <- as.dist(D2)
D1 <- as.matrix(D1)
D2 <- as.matrix(D2)
#sort labels
D1.Tmp <- D1[sort(labels(D1)[[1]]),sort(labels(D1)[[1]])]
D2.Tmp <- D2[sort(labels(D2)[[1]]),sort(labels(D2)[[1]])]
D1 <- as.matrix(D1.Tmp)
D2 <- as.matrix(D2.Tmp)
}
D1save <- as.matrix(D1)
D2save <- as.matrix(D2)
save_lines <- NULL
alpha_seq <- seq(0,1,0.01)
showModal(waitModal())
withProgress(message = 'Resampling process', value = 0, {
nb_elt <- length(D1save[,1])
for(i in 1:nb_elt){
# update progress bar
incProgress(1/nb_elt, detail = paste("Doing part", i))
Sys.sleep(0.1)
df <- NULL
for(j in 1:nb_elt){
if(j != i ){
list <- generateClone(D1save,D2save,i,j)
D1 <- list[[1]]
D2 <- list[[2]]
dist.dend <- c()
for(alpha in alpha_seq){
Mdist <- (alpha)*D1 + (1-alpha)*D2
mixt.dist <- as.dist(Mdist)
tree <- fastcluster::hclust(mixt.dist,method=method)
new <- corCriterion(tree,D1,D2)
dist.dend <- c(dist.dend,new)
}
if(is.null(df)){
df <- data.frame(alpha = alpha_seq, height = dist.dend)
}else{
df <- cbind(df,dist.dend)
}
}
}
mean <- unlist(lapply(as.data.frame(t(df[-1])),mean))
if(is.null(save_lines)){
save_lines <- cbind(df$alpha,mean)
}else{
save_lines <- cbind(save_lines,mean)
}
}
})
colnames(save_lines) <- c("alpha",rownames(D1)[1:nb_elt])
rownames(save_lines) <- c()
removeModal()
p <- plot_ly(width = 760, height = 400)
for (k in 2:length(colnames(save_lines))) {
p <- add_lines(p,x=save_lines[,1],y=save_lines[,k],name=colnames(save_lines)[k])
}
p
})
observe({
if(2 > 1){
output$SilPlot <- renderPlot({
cluster <- values[["cluster"]]
cls <- sort(unique(cluster))
for (i in length(cls):1){
cluster[cluster == cls[i]] <- i
}
Dmatrix <- values[["D_alpha"]]
names <- labels(Dmatrix)
text <- c("")
for (i in 1:length(names)){
text <- paste0(text,i,":",names[i],"\n")
}
sil <- silhouette(cluster,Dmatrix)
col <- rainbow_hcl(length(unique(trunc(values[["cluster"]]))), c = 80, l = 60, start = 0,
end = 360*(length(unique(trunc(values[["cluster"]])))-1)/(length(unique(trunc(values[["cluster"]])))))
col <- col[trunc(sort(values[["cluster"]]))]
par(fig=c(.2,1,0,1), new=TRUE)
plot(sil, col = col)
par(fig=c(0,.2,0,1), new=TRUE)
plot.new()
mtext(text,3,adj=0,padj=1.1)
values[["silplot"]] <- recordPlot()
})
}
})
observeEvent(input$wiki, {
updateTabsetPanel(session, "navbar", selected = "4")
})
observeEvent(input$over, {
updateTabsetPanel(session, "tabsetperso", selected = "Overview")
})
observeEvent(input$clustsett, {
updateTabsetPanel(session, "tabsetperso", selected = "Clustering settings")
})
observeEvent(input$resviz, {
updateTabsetPanel(session, "tabsetperso", selected = "Results visualization")
})
##dendrogramme click
output$click_info <- renderPrint({
if(length(input$k) == 0){
cat("hcluscompro")
}else{
size <- c()
cluster <- values[["cluster"]]
nb <- length(unique(cluster))
tot <- length(cluster)
cat("The selected partition contains",nb,"clusters among",tot,"observations.\ncluster:\t")
for (k in unique(values[["cluster"]])){
size <- c(size,length(cluster[cluster == k]))
cat(k,"\t")
}
cat("\nSize:\t\t")
for(y in 1:nb){
cat(size[y],"\t")
}
}
})
output$formula <- renderUI({
withMathJax(paste0("$$ \\boldsymbol{D}_\\alpha=\\alpha \\boldsymbol{D}_1+(1-\\alpha) \\boldsymbol{D}_2 $$"))
})
}
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.