mirror of
https://github.com/agdamsbo/FreesearchR.git
synced 2025-09-12 09:59:39 +02:00
big steps
This commit is contained in:
parent
52d1791708
commit
ce2558fe90
19 changed files with 3877 additions and 581 deletions
|
@ -1,6 +1,6 @@
|
||||||
Package: freesearcheR
|
Package: freesearcheR
|
||||||
Title: Browser Based Data Analysis
|
Title: Browser Based Data Analysis
|
||||||
Version: 24.12.1
|
Version: 25.1.1
|
||||||
Authors@R:
|
Authors@R:
|
||||||
person("Andreas Gammelgaard", "Damsbo", , "agdamsbo@clin.au.dk", role = c("aut", "cre"),
|
person("Andreas Gammelgaard", "Damsbo", , "agdamsbo@clin.au.dk", role = c("aut", "cre"),
|
||||||
comment = c(ORCID = "0000-0002-7559-1154"))
|
comment = c(ORCID = "0000-0002-7559-1154"))
|
||||||
|
@ -49,7 +49,10 @@ Imports:
|
||||||
shinyWidgets,
|
shinyWidgets,
|
||||||
classInt,
|
classInt,
|
||||||
htmltools,
|
htmltools,
|
||||||
rlang
|
rlang,
|
||||||
|
data.table,
|
||||||
|
apexcharter,
|
||||||
|
teal.modules.general
|
||||||
Suggests:
|
Suggests:
|
||||||
styler,
|
styler,
|
||||||
devtools,
|
devtools,
|
||||||
|
|
9
NEWS.md
9
NEWS.md
|
@ -1,3 +1,12 @@
|
||||||
|
# freesearcheR 25.1.1
|
||||||
|
|
||||||
|
* UI tweaks.
|
||||||
|
|
||||||
|
* NEW: Option to set class as `hms` using the `{hms}` package.
|
||||||
|
|
||||||
|
* NEW: summary grid with sparklines.
|
||||||
|
|
||||||
|
|
||||||
# freesearcheR 24.12.1
|
# freesearcheR 24.12.1
|
||||||
|
|
||||||
* Initial release for Zenodo.
|
* Initial release for Zenodo.
|
||||||
|
|
237
R/data-summary.R
Normal file
237
R/data-summary.R
Normal file
|
@ -0,0 +1,237 @@
|
||||||
|
data_summary_ui <- function(id) {
|
||||||
|
ns <- NS(id)
|
||||||
|
|
||||||
|
toastui::datagridOutput(outputId = "tbl_summary")
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
data_summary_server <- function(id,
|
||||||
|
data) {
|
||||||
|
shiny::moduleServer(
|
||||||
|
id = id,
|
||||||
|
module = function(input, output, session) {
|
||||||
|
ns <- session$ns
|
||||||
|
|
||||||
|
data_r <- shiny::reactive({
|
||||||
|
if (shiny::is.reactive(data)) {
|
||||||
|
data()
|
||||||
|
} else {
|
||||||
|
data
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
output$tbl_summary <- shiny::reactive({
|
||||||
|
toastui::renderDatagrid(
|
||||||
|
data_r() |>
|
||||||
|
overview_vars() |>
|
||||||
|
create_overview_datagrid() |>
|
||||||
|
add_sparkline(
|
||||||
|
column = "vals"
|
||||||
|
)
|
||||||
|
)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
#' Add sparkline to datagrid
|
||||||
|
#'
|
||||||
|
#' @param grid grid
|
||||||
|
#' @param column clumn to transform
|
||||||
|
#'
|
||||||
|
#' @returns datagrid
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' grid <- mtcars |>
|
||||||
|
#' default_parsing() |>
|
||||||
|
#' overview_vars() |>
|
||||||
|
#' toastui::datagrid() |>
|
||||||
|
#' add_sparkline()
|
||||||
|
#' grid
|
||||||
|
add_sparkline <- function(grid, column = "vals", color.main = "#2a8484", color.sec = "#84EF84") {
|
||||||
|
out <- toastui::grid_sparkline(
|
||||||
|
grid = grid,
|
||||||
|
column = column,
|
||||||
|
renderer = function(data) {
|
||||||
|
data_cl <- class(data)
|
||||||
|
if (identical(data_cl, "factor")) {
|
||||||
|
type <- "column"
|
||||||
|
s <- summary(data)
|
||||||
|
ds <- data.frame(x = names(s), y = s)
|
||||||
|
horizontal <- FALSE
|
||||||
|
} else if (any(c("numeric", "integer") %in% data_cl)) {
|
||||||
|
if (length(unique(data)) == length(data)) {
|
||||||
|
type <- "line"
|
||||||
|
ds <- data.frame(x = NA, y = NA)
|
||||||
|
horizontal <- FALSE
|
||||||
|
} else {
|
||||||
|
type <- "box"
|
||||||
|
ds <- data.frame(x = 1, y = data)
|
||||||
|
horizontal <- TRUE
|
||||||
|
}
|
||||||
|
} else if (any(c("Date", "POSIXct", "POSIXt", "hms", "difftime") %in% data_cl)) {
|
||||||
|
type <- "line"
|
||||||
|
ds <- data.frame(x = seq_along(data), y = data)
|
||||||
|
horizontal <- FALSE
|
||||||
|
} else {
|
||||||
|
type <- "line"
|
||||||
|
ds <- data.frame(x = NA, y = NA)
|
||||||
|
horizontal <- FALSE
|
||||||
|
}
|
||||||
|
apexcharter::apex(
|
||||||
|
ds,
|
||||||
|
apexcharter::aes(x, y),
|
||||||
|
type = type,
|
||||||
|
auto_update = TRUE
|
||||||
|
) |>
|
||||||
|
apexcharter::ax_chart(sparkline = list(enabled = TRUE)) |>
|
||||||
|
apexcharter::ax_plotOptions(
|
||||||
|
boxPlot = apexcharter::boxplot_opts(color.upper = color.sec, color.lower = color.main),
|
||||||
|
bar = apexcharter::bar_opts(horizontal = horizontal)
|
||||||
|
) |>
|
||||||
|
apexcharter::ax_colors(
|
||||||
|
c(color.main, color.sec)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
toastui::grid_columns(
|
||||||
|
grid = out,
|
||||||
|
columns = column,
|
||||||
|
minWidth = 200
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
#' Create a data overview data.frame ready for sparklines
|
||||||
|
#'
|
||||||
|
#' @param data data
|
||||||
|
#'
|
||||||
|
#' @returns data.frame
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' mtcars |> overview_vars()
|
||||||
|
overview_vars <- function(data) {
|
||||||
|
data <- as.data.frame(data)
|
||||||
|
|
||||||
|
dplyr::tibble(
|
||||||
|
class = get_classes(data),
|
||||||
|
name = names(data),
|
||||||
|
n_missing = unname(colSums(is.na(data))),
|
||||||
|
p_complete = 1 - n_missing / nrow(data),
|
||||||
|
n_unique = get_n_unique(data),
|
||||||
|
vals = as.list(data)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
#' Create a data overview datagrid
|
||||||
|
#'
|
||||||
|
#' @param data data
|
||||||
|
#'
|
||||||
|
#' @returns datagrid
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' mtcars |>
|
||||||
|
#' overview_vars() |>
|
||||||
|
#' create_overview_datagrid()
|
||||||
|
create_overview_datagrid <- function(data) {
|
||||||
|
# browser()
|
||||||
|
gridTheme <- getOption("datagrid.theme")
|
||||||
|
if (length(gridTheme) < 1) {
|
||||||
|
datamods:::apply_grid_theme()
|
||||||
|
}
|
||||||
|
on.exit(toastui::reset_grid_theme())
|
||||||
|
|
||||||
|
col.names <- names(data)
|
||||||
|
|
||||||
|
std_names <- c(
|
||||||
|
"Name" = "name",
|
||||||
|
"Class" = "class",
|
||||||
|
"Missing" = "n_missing",
|
||||||
|
"Complete" = "p_complete",
|
||||||
|
"Unique" = "n_unique",
|
||||||
|
"Plot" = "vals"
|
||||||
|
)
|
||||||
|
|
||||||
|
headers <- lapply(col.names, \(.x){
|
||||||
|
if (.x %in% std_names) {
|
||||||
|
names(std_names)[match(.x, std_names)]
|
||||||
|
} else {
|
||||||
|
.x
|
||||||
|
}
|
||||||
|
}) |> unlist()
|
||||||
|
|
||||||
|
grid <- toastui::datagrid(
|
||||||
|
data = data,
|
||||||
|
theme = "default",
|
||||||
|
colwidths = "auto"
|
||||||
|
)
|
||||||
|
|
||||||
|
grid <- toastui::grid_columns(
|
||||||
|
grid = grid,
|
||||||
|
columns = col.names,
|
||||||
|
header = headers,
|
||||||
|
resizable = TRUE,
|
||||||
|
width = 80
|
||||||
|
)
|
||||||
|
|
||||||
|
grid <- add_class_icon(
|
||||||
|
grid = grid,
|
||||||
|
column = "class"
|
||||||
|
)
|
||||||
|
|
||||||
|
# grid <- toastui::grid_format(
|
||||||
|
# grid = grid,
|
||||||
|
# "p_complete",
|
||||||
|
# formatter = toastui::JS("function(obj) {return (obj.value*100).toFixed(0) + '%';}")
|
||||||
|
# )
|
||||||
|
|
||||||
|
return(grid)
|
||||||
|
}
|
||||||
|
|
||||||
|
#' Convert class grid column to icon
|
||||||
|
#'
|
||||||
|
#' @param grid grid
|
||||||
|
#' @param column column
|
||||||
|
#'
|
||||||
|
#' @returns datagrid
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
add_class_icon <- function(grid, column = "class") {
|
||||||
|
out <- toastui::grid_format(
|
||||||
|
grid = grid,
|
||||||
|
column = column,
|
||||||
|
formatter = function(value) {
|
||||||
|
lapply(
|
||||||
|
X = value,
|
||||||
|
FUN = function(x) {
|
||||||
|
if (identical(x, "numeric")) {
|
||||||
|
shiny::icon("chart-line")
|
||||||
|
} else if (identical(x, "factor")) {
|
||||||
|
shiny::icon("chart-column")
|
||||||
|
} else if (identical(x, "integer")) {
|
||||||
|
shiny::icon("arrow-down-1-9")
|
||||||
|
} else if (identical(x, "character")) {
|
||||||
|
shiny::icon("arrow-down-a-z")
|
||||||
|
} else if (any(c("Date", "POSIXct", "POSIXt") %in% x)) {
|
||||||
|
shiny::icon("calendar-days")
|
||||||
|
} else if ("hms" %in% x) {
|
||||||
|
shiny::icon("clock")
|
||||||
|
} else {
|
||||||
|
shiny::icon("table")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
toastui::grid_columns(
|
||||||
|
grid = out,
|
||||||
|
header = NULL,
|
||||||
|
columns = column,
|
||||||
|
width = 60
|
||||||
|
)
|
||||||
|
}
|
|
@ -1,125 +1,125 @@
|
||||||
#' #' Shiny UI module to load a data file
|
#' Shiny UI module to load a data file
|
||||||
#' #'
|
|
||||||
#' #' @param id id
|
|
||||||
#' #'
|
|
||||||
#' #' @return shiny UI
|
|
||||||
#' #' @export
|
|
||||||
#' #'
|
|
||||||
#' m_datafileUI <- function(id) {
|
|
||||||
#' ns <- shiny::NS(id)
|
|
||||||
#' shiny::tagList(
|
|
||||||
#' shiny::fileInput(
|
|
||||||
#' inputId = ns("file"),
|
|
||||||
#' label = "Upload a file",
|
|
||||||
#' multiple = FALSE,
|
|
||||||
#' accept = c(
|
|
||||||
#' ".csv",
|
|
||||||
#' ".xlsx",
|
|
||||||
#' ".xls",
|
|
||||||
#' ".dta",
|
|
||||||
#' ".ods",
|
|
||||||
#' ".rds"
|
|
||||||
#' )
|
|
||||||
#' ),
|
|
||||||
#' shiny::h4("Parameter specifications"),
|
|
||||||
#' shiny::helpText(shiny::em("Select the desired variables and press 'Submit'")),
|
|
||||||
#' shiny::uiOutput(ns("include_vars")),
|
|
||||||
#' DT::DTOutput(ns("data_input")),
|
|
||||||
#' shiny::actionButton(ns("submit"), "Submit")
|
|
||||||
#' )
|
|
||||||
#' }
|
|
||||||
#'
|
#'
|
||||||
#' m_datafileServer <- function(id, output.format = "df") {
|
#' @param id id
|
||||||
#' shiny::moduleServer(id, function(input, output, session, ...) {
|
|
||||||
#' ns <- shiny::NS(id)
|
|
||||||
#' ds <- shiny::reactive({
|
|
||||||
#' REDCapCAST::read_input(input$file$datapath) |> REDCapCAST::parse_data()
|
|
||||||
#' })
|
|
||||||
#'
|
#'
|
||||||
#' output$include_vars <- shiny::renderUI({
|
#' @return shiny UI
|
||||||
#' shiny::req(input$file)
|
#' @export
|
||||||
#' shiny::selectizeInput(
|
|
||||||
#' inputId = ns("include_vars"),
|
|
||||||
#' selected = NULL,
|
|
||||||
#' label = "Covariables to include",
|
|
||||||
#' choices = colnames(ds()),
|
|
||||||
#' multiple = TRUE
|
|
||||||
#' )
|
|
||||||
#' })
|
|
||||||
#'
|
#'
|
||||||
#' base_vars <- shiny::reactive({
|
m_datafileUI <- function(id) {
|
||||||
#' if (is.null(input$include_vars)) {
|
ns <- shiny::NS(id)
|
||||||
#' out <- colnames(ds())
|
shiny::tagList(
|
||||||
#' } else {
|
shiny::fileInput(
|
||||||
#' out <- input$include_vars
|
inputId = ns("file"),
|
||||||
#' }
|
label = "Upload a file",
|
||||||
#' out
|
multiple = FALSE,
|
||||||
#' })
|
accept = c(
|
||||||
#'
|
".csv",
|
||||||
#' output$data_input <-
|
".xlsx",
|
||||||
#' DT::renderDT({
|
".xls",
|
||||||
#' shiny::req(input$file)
|
".dta",
|
||||||
#' ds()[base_vars()]
|
".ods",
|
||||||
#' })
|
".rds"
|
||||||
#'
|
)
|
||||||
#' shiny::eventReactive(input$submit, {
|
),
|
||||||
#' # shiny::req(input$file)
|
shiny::h4("Parameter specifications"),
|
||||||
#'
|
shiny::helpText(shiny::em("Select the desired variables and press 'Submit'")),
|
||||||
#' data <- shiny::isolate({
|
shiny::uiOutput(ns("include_vars")),
|
||||||
#' ds()[base_vars()]
|
DT::DTOutput(ns("data_input")),
|
||||||
#' })
|
shiny::actionButton(ns("submit"), "Submit")
|
||||||
#'
|
)
|
||||||
#' file_export(data,
|
}
|
||||||
#' output.format = output.format,
|
|
||||||
#' tools::file_path_sans_ext(input$file$name)
|
m_datafileServer <- function(id, output.format = "df") {
|
||||||
#' )
|
shiny::moduleServer(id, function(input, output, session, ...) {
|
||||||
#' })
|
ns <- shiny::NS(id)
|
||||||
#' })
|
ds <- shiny::reactive({
|
||||||
#' }
|
REDCapCAST::read_input(input$file$datapath) |> REDCapCAST::parse_data()
|
||||||
#'
|
})
|
||||||
#'
|
|
||||||
#'
|
output$include_vars <- shiny::renderUI({
|
||||||
#'
|
shiny::req(input$file)
|
||||||
#'
|
shiny::selectizeInput(
|
||||||
#' file_app <- function() {
|
inputId = ns("include_vars"),
|
||||||
#' ui <- shiny::fluidPage(
|
selected = NULL,
|
||||||
#' m_datafileUI("data"),
|
label = "Covariables to include",
|
||||||
#' # DT::DTOutput(outputId = "redcap_prev")
|
choices = colnames(ds()),
|
||||||
#' toastui::datagridOutput2(outputId = "redcap_prev")
|
multiple = TRUE
|
||||||
#' )
|
)
|
||||||
#' server <- function(input, output, session) {
|
})
|
||||||
#' m_datafileServer("data", output.format = "list")
|
|
||||||
#' }
|
base_vars <- shiny::reactive({
|
||||||
#' shiny::shinyApp(ui, server)
|
if (is.null(input$include_vars)) {
|
||||||
#' }
|
out <- colnames(ds())
|
||||||
#'
|
} else {
|
||||||
#' file_app()
|
out <- input$include_vars
|
||||||
#'
|
}
|
||||||
#' tdm_data_upload <- teal::teal_data_module(
|
out
|
||||||
#' ui <- function(id) {
|
})
|
||||||
#' shiny::fluidPage(
|
|
||||||
#' m_datafileUI(id)
|
output$data_input <-
|
||||||
#' )
|
DT::renderDT({
|
||||||
#' },
|
shiny::req(input$file)
|
||||||
#' server = function(id) {
|
ds()[base_vars()]
|
||||||
#' m_datafileServer(id, output.format = "teal")
|
})
|
||||||
#' }
|
|
||||||
#' )
|
shiny::eventReactive(input$submit, {
|
||||||
#'
|
# shiny::req(input$file)
|
||||||
#' tdm_data_read <- teal::teal_data_module(
|
|
||||||
#' ui <- function(id) {
|
data <- shiny::isolate({
|
||||||
#' shiny::fluidPage(
|
ds()[base_vars()]
|
||||||
#' m_redcap_readUI(id = "redcap")
|
})
|
||||||
#' )
|
|
||||||
#' },
|
file_export(data,
|
||||||
#' server = function(id) {
|
output.format = output.format,
|
||||||
#' moduleServer(
|
tools::file_path_sans_ext(input$file$name)
|
||||||
#' id,
|
)
|
||||||
#' function(input, output, session) {
|
})
|
||||||
#' ns <- session$ns
|
})
|
||||||
#'
|
}
|
||||||
#' m_redcap_readServer(id = "redcap", output.format = "teal")
|
|
||||||
#' }
|
|
||||||
#' )
|
|
||||||
#' }
|
|
||||||
#' )
|
|
||||||
|
file_app <- function() {
|
||||||
|
ui <- shiny::fluidPage(
|
||||||
|
m_datafileUI("data"),
|
||||||
|
# DT::DTOutput(outputId = "redcap_prev")
|
||||||
|
toastui::datagridOutput2(outputId = "redcap_prev")
|
||||||
|
)
|
||||||
|
server <- function(input, output, session) {
|
||||||
|
m_datafileServer("data", output.format = "list")
|
||||||
|
}
|
||||||
|
shiny::shinyApp(ui, server)
|
||||||
|
}
|
||||||
|
|
||||||
|
file_app()
|
||||||
|
|
||||||
|
tdm_data_upload <- teal::teal_data_module(
|
||||||
|
ui <- function(id) {
|
||||||
|
shiny::fluidPage(
|
||||||
|
m_datafileUI(id)
|
||||||
|
)
|
||||||
|
},
|
||||||
|
server = function(id) {
|
||||||
|
m_datafileServer(id, output.format = "teal")
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
tdm_data_read <- teal::teal_data_module(
|
||||||
|
ui <- function(id) {
|
||||||
|
shiny::fluidPage(
|
||||||
|
m_redcap_readUI(id = "redcap")
|
||||||
|
)
|
||||||
|
},
|
||||||
|
server = function(id) {
|
||||||
|
moduleServer(
|
||||||
|
id,
|
||||||
|
function(input, output, session) {
|
||||||
|
ns <- session$ns
|
||||||
|
|
||||||
|
m_redcap_readServer(id = "redcap", output.format = "teal")
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
38
R/helpers.R
38
R/helpers.R
|
@ -148,7 +148,7 @@ file_export <- function(data, output.format = c("df", "teal", "list"), filename,
|
||||||
teal_data(),
|
teal_data(),
|
||||||
{
|
{
|
||||||
assign(name, value |>
|
assign(name, value |>
|
||||||
dplyr::bind_cols() |>
|
dplyr::bind_cols(.name_repair = "unique_quiet") |>
|
||||||
default_parsing())
|
default_parsing())
|
||||||
},
|
},
|
||||||
value = data,
|
value = data,
|
||||||
|
@ -185,8 +185,42 @@ file_export <- function(data, output.format = c("df", "teal", "list"), filename,
|
||||||
#' default_parsing() |>
|
#' default_parsing() |>
|
||||||
#' str()
|
#' str()
|
||||||
default_parsing <- function(data) {
|
default_parsing <- function(data) {
|
||||||
data |>
|
name_labels <- lapply(data,\(.x) REDCapCAST::get_attr(.x,attr = "label"))
|
||||||
|
|
||||||
|
out <- data |>
|
||||||
REDCapCAST::parse_data() |>
|
REDCapCAST::parse_data() |>
|
||||||
REDCapCAST::as_factor() |>
|
REDCapCAST::as_factor() |>
|
||||||
REDCapCAST::numchar2fct()
|
REDCapCAST::numchar2fct()
|
||||||
|
|
||||||
|
purrr::map2(out,name_labels,\(.x,.l){
|
||||||
|
if (!(is.na(.l) | .l=="")) {
|
||||||
|
REDCapCAST::set_attr(.x, .l, attr = "label")
|
||||||
|
} else {
|
||||||
|
attr(x = .x, which = "label") <- NULL
|
||||||
|
.x
|
||||||
|
}
|
||||||
|
# REDCapCAST::set_attr(data = .x, label = .l,attr = "label", overwrite = FALSE)
|
||||||
|
}) |> dplyr::bind_cols()
|
||||||
|
}
|
||||||
|
|
||||||
|
#' Remove NA labels
|
||||||
|
#'
|
||||||
|
#' @param data data
|
||||||
|
#'
|
||||||
|
#' @returns data.frame
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' ds <- mtcars |> lapply(\(.x) REDCapCAST::set_attr(.x,label=NA,attr = "label"))
|
||||||
|
#' ds |> remove_na_attr() |> str()
|
||||||
|
remove_na_attr <- function(data,attr="label"){
|
||||||
|
out <- data |> lapply(\(.x){
|
||||||
|
ls <- REDCapCAST::get_attr(data = .x,attr = attr)
|
||||||
|
if (is.na(ls) | ls == ""){
|
||||||
|
attr(x = .x, which = attr) <- NULL
|
||||||
|
}
|
||||||
|
.x
|
||||||
|
})
|
||||||
|
|
||||||
|
dplyr::bind_cols(out)
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,8 +10,8 @@
|
||||||
m_redcap_readUI <- function(id, include_title = TRUE) {
|
m_redcap_readUI <- function(id, include_title = TRUE) {
|
||||||
ns <- shiny::NS(id)
|
ns <- shiny::NS(id)
|
||||||
|
|
||||||
server_ui <- shiny::column(
|
server_ui <- shiny::tagList(
|
||||||
width = 6,
|
# width = 6,
|
||||||
shiny::tags$h4("REDCap server information"),
|
shiny::tags$h4("REDCap server information"),
|
||||||
shiny::textInput(
|
shiny::textInput(
|
||||||
inputId = ns("uri"),
|
inputId = ns("uri"),
|
||||||
|
@ -27,8 +27,8 @@ m_redcap_readUI <- function(id, include_title = TRUE) {
|
||||||
|
|
||||||
|
|
||||||
params_ui <-
|
params_ui <-
|
||||||
shiny::column(
|
shiny::tagList(
|
||||||
width = 6,
|
# width = 6,
|
||||||
shiny::tags$h4("Data import parameters"),
|
shiny::tags$h4("Data import parameters"),
|
||||||
shiny::helpText("Options here will show, when API and uri are typed"),
|
shiny::helpText("Options here will show, when API and uri are typed"),
|
||||||
shiny::uiOutput(outputId = ns("fields")),
|
shiny::uiOutput(outputId = ns("fields")),
|
||||||
|
@ -63,9 +63,14 @@ m_redcap_readUI <- function(id, include_title = TRUE) {
|
||||||
|
|
||||||
shiny::fluidPage(
|
shiny::fluidPage(
|
||||||
if (include_title) shiny::tags$h3("Import data from REDCap"),
|
if (include_title) shiny::tags$h3("Import data from REDCap"),
|
||||||
fluidRow(
|
bslib::layout_columns(
|
||||||
server_ui,
|
server_ui,
|
||||||
params_ui),
|
params_ui,
|
||||||
|
col_widths = bslib::breakpoints(
|
||||||
|
sm = c(12, 12),
|
||||||
|
md = c(12, 12)
|
||||||
|
)
|
||||||
|
),
|
||||||
shiny::column(
|
shiny::column(
|
||||||
width = 12,
|
width = 12,
|
||||||
# shiny::actionButton(inputId = ns("import"), label = "Import"),
|
# shiny::actionButton(inputId = ns("import"), label = "Import"),
|
||||||
|
@ -270,7 +275,6 @@ m_redcap_readServer <- function(id, output.format = c("df", "teal", "list")) {
|
||||||
#'
|
#'
|
||||||
#' @rdname redcap_read_shiny_module
|
#' @rdname redcap_read_shiny_module
|
||||||
tdm_redcap_read <- teal::teal_data_module(
|
tdm_redcap_read <- teal::teal_data_module(
|
||||||
|
|
||||||
ui <- function(id) {
|
ui <- function(id) {
|
||||||
shiny::fluidPage(
|
shiny::fluidPage(
|
||||||
m_redcap_readUI(id)
|
m_redcap_readUI(id)
|
||||||
|
@ -305,7 +309,7 @@ redcap_app <- function() {
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
server <- function(input, output, session) {
|
server <- function(input, output, session) {
|
||||||
data_val <- shiny::reactiveValues(data=NULL)
|
data_val <- shiny::reactiveValues(data = NULL)
|
||||||
|
|
||||||
ds <- m_redcap_readServer("data", output.format = "df")
|
ds <- m_redcap_readServer("data", output.format = "df")
|
||||||
# output$redcap_prev <- DT::renderDT(
|
# output$redcap_prev <- DT::renderDT(
|
||||||
|
@ -329,7 +333,8 @@ redcap_app <- function() {
|
||||||
|
|
||||||
filtered_data <- IDEAFilter::IDEAFilter("data_filter",
|
filtered_data <- IDEAFilter::IDEAFilter("data_filter",
|
||||||
data = ds,
|
data = ds,
|
||||||
verbose = FALSE)
|
verbose = FALSE
|
||||||
|
)
|
||||||
|
|
||||||
# filtered_data <- shiny::reactive({
|
# filtered_data <- shiny::reactive({
|
||||||
# IDEAFilter::IDEAFilter("data_filter",
|
# IDEAFilter::IDEAFilter("data_filter",
|
||||||
|
|
|
@ -71,7 +71,7 @@ regression_model <- function(data,
|
||||||
.x
|
.x
|
||||||
}
|
}
|
||||||
}) |>
|
}) |>
|
||||||
dplyr::bind_cols()
|
dplyr::bind_cols(.name_repair = "unique_quiet")
|
||||||
|
|
||||||
if (is.null(fun)) auto.mode <- TRUE
|
if (is.null(fun)) auto.mode <- TRUE
|
||||||
|
|
||||||
|
|
34
R/sparkline_h_minimal.R
Normal file
34
R/sparkline_h_minimal.R
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
# dependencies
|
||||||
|
library(apexcharter)
|
||||||
|
library(toastui)
|
||||||
|
|
||||||
|
spark_data <- mtcars |>
|
||||||
|
(\(.x){
|
||||||
|
dplyr::tibble(
|
||||||
|
name = names(.x),
|
||||||
|
vals = as.list(.x)
|
||||||
|
)
|
||||||
|
})()
|
||||||
|
|
||||||
|
ui <- fluidPage(
|
||||||
|
toastui::datagridOutput("tbl")
|
||||||
|
)
|
||||||
|
|
||||||
|
server <- function(input, output) {
|
||||||
|
output$tbl <- toastui::renderDatagrid(
|
||||||
|
spark_data |>
|
||||||
|
toastui::datagrid() |>
|
||||||
|
toastui::grid_sparkline(
|
||||||
|
column = "vals",
|
||||||
|
renderer = function(data) {
|
||||||
|
apex(data.frame(x = 1, y = data), aes(x, y), type = "box") |>
|
||||||
|
ax_chart(sparkline = list(enabled = TRUE)) |>
|
||||||
|
ax_plotOptions(
|
||||||
|
bar = bar_opts(horizontal=TRUE)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
shinyApp(ui = ui, server = server)
|
707
R/update-variables-ext.R
Normal file
707
R/update-variables-ext.R
Normal file
|
@ -0,0 +1,707 @@
|
||||||
|
library(data.table)
|
||||||
|
library(rlang)
|
||||||
|
|
||||||
|
|
||||||
|
#' Select, rename and convert variables
|
||||||
|
#'
|
||||||
|
#' @param id Module id. See [shiny::moduleServer()].
|
||||||
|
#' @param title Module's title, if `TRUE` use the default title,
|
||||||
|
#' use \code{NULL} for no title or a `shiny.tag` for a custom one.
|
||||||
|
#'
|
||||||
|
#' @return A [shiny::reactive()] function returning the updated data.
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @name update-variables
|
||||||
|
#'
|
||||||
|
#' @example examples/variables.R
|
||||||
|
update_variables_ui <- function(id, title = TRUE) {
|
||||||
|
ns <- NS(id)
|
||||||
|
if (isTRUE(title)) {
|
||||||
|
title <- htmltools::tags$h4(
|
||||||
|
i18n("Update & select variables"),
|
||||||
|
class = "datamods-title"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
htmltools::tags$div(
|
||||||
|
class = "datamods-update",
|
||||||
|
shinyWidgets::html_dependency_pretty(),
|
||||||
|
title,
|
||||||
|
htmltools::tags$div(
|
||||||
|
style = "min-height: 25px;",
|
||||||
|
htmltools::tags$div(
|
||||||
|
shiny::uiOutput(outputId = ns("data_info"), inline = TRUE),
|
||||||
|
shiny::tagAppendAttributes(
|
||||||
|
shinyWidgets::dropMenu(
|
||||||
|
placement = "bottom-end",
|
||||||
|
shiny::actionButton(
|
||||||
|
inputId = ns("settings"),
|
||||||
|
label = phosphoricons::ph("gear"),
|
||||||
|
class = "pull-right float-right"
|
||||||
|
),
|
||||||
|
shinyWidgets::textInputIcon(
|
||||||
|
inputId = ns("format"),
|
||||||
|
label = i18n("Date format:"),
|
||||||
|
value = "%Y-%m-%d",
|
||||||
|
icon = list(phosphoricons::ph("clock"))
|
||||||
|
),
|
||||||
|
shinyWidgets::textInputIcon(
|
||||||
|
inputId = ns("origin"),
|
||||||
|
label = i18n("Date to use as origin to convert date/datetime:"),
|
||||||
|
value = "1970-01-01",
|
||||||
|
icon = list(phosphoricons::ph("calendar"))
|
||||||
|
),
|
||||||
|
shinyWidgets::textInputIcon(
|
||||||
|
inputId = ns("dec"),
|
||||||
|
label = i18n("Decimal separator:"),
|
||||||
|
value = ".",
|
||||||
|
icon = list("0.00")
|
||||||
|
)
|
||||||
|
),
|
||||||
|
style = "display: inline;"
|
||||||
|
)
|
||||||
|
),
|
||||||
|
htmltools::tags$br(),
|
||||||
|
toastui::datagridOutput(outputId = ns("table"))
|
||||||
|
),
|
||||||
|
htmltools::tags$br(),
|
||||||
|
htmltools::tags$div(
|
||||||
|
id = ns("update-placeholder"),
|
||||||
|
shinyWidgets::alert(
|
||||||
|
id = ns("update-result"),
|
||||||
|
status = "info",
|
||||||
|
phosphoricons::ph("info"),
|
||||||
|
datamods::i18n(paste(
|
||||||
|
"Select, rename and convert variables in table above,",
|
||||||
|
"then apply changes by clicking button below."
|
||||||
|
))
|
||||||
|
)
|
||||||
|
),
|
||||||
|
shiny::actionButton(
|
||||||
|
inputId = ns("validate"),
|
||||||
|
label = htmltools::tagList(
|
||||||
|
phosphoricons::ph("arrow-circle-right", title = i18n("Apply changes")),
|
||||||
|
datamods::i18n("Apply changes")
|
||||||
|
),
|
||||||
|
width = "100%"
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
#' @export
|
||||||
|
#'
|
||||||
|
#' @param id Module's ID
|
||||||
|
#' @param data a \code{data.frame} or a \code{reactive} function returning a \code{data.frame}.
|
||||||
|
#' @param height Height for the table.
|
||||||
|
#' @param return_data_on_init Return initial data when module is called.
|
||||||
|
#' @param try_silent logical: should the report of error messages be suppressed?
|
||||||
|
#'
|
||||||
|
#' @rdname update-variables
|
||||||
|
#'
|
||||||
|
update_variables_server <- function(id,
|
||||||
|
data,
|
||||||
|
height = NULL,
|
||||||
|
return_data_on_init = FALSE,
|
||||||
|
try_silent = FALSE) {
|
||||||
|
shiny::moduleServer(
|
||||||
|
id = id,
|
||||||
|
module = function(input, output, session) {
|
||||||
|
ns <- session$ns
|
||||||
|
updated_data <- shiny::reactiveValues(x = NULL)
|
||||||
|
|
||||||
|
data_r <- shiny::reactive({
|
||||||
|
if (shiny::is.reactive(data)) {
|
||||||
|
data()
|
||||||
|
} else {
|
||||||
|
data
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
output$data_info <- shiny::renderUI({
|
||||||
|
shiny::req(data_r())
|
||||||
|
data <- data_r()
|
||||||
|
sprintf(i18n("Data has %s observations and %s variables."), nrow(data), ncol(data))
|
||||||
|
})
|
||||||
|
|
||||||
|
variables_r <- shiny::reactive({
|
||||||
|
shiny::validate(
|
||||||
|
shiny::need(data(), i18n("No data to display."))
|
||||||
|
)
|
||||||
|
data <- data_r()
|
||||||
|
if (isTRUE(return_data_on_init)) {
|
||||||
|
updated_data$x <- data
|
||||||
|
} else {
|
||||||
|
updated_data$x <- NULL
|
||||||
|
}
|
||||||
|
summary_vars(data)
|
||||||
|
})
|
||||||
|
|
||||||
|
output$table <- toastui::renderDatagrid({
|
||||||
|
shiny::req(variables_r())
|
||||||
|
# browser()
|
||||||
|
variables <- variables_r()
|
||||||
|
|
||||||
|
# variables <- variables |>
|
||||||
|
# dplyr::mutate(vals=as.list(dplyr::as_tibble(data_r())))
|
||||||
|
|
||||||
|
# variables <- variables |>
|
||||||
|
# dplyr::mutate(n_id=seq_len(nrow(variables)))
|
||||||
|
|
||||||
|
update_variables_datagrid(
|
||||||
|
variables,
|
||||||
|
height = height,
|
||||||
|
selectionId = ns("row_selected"),
|
||||||
|
buttonId = "validate"
|
||||||
|
)
|
||||||
|
})
|
||||||
|
|
||||||
|
shiny::observeEvent(input$validate,
|
||||||
|
{
|
||||||
|
updated_data$list_rename <- NULL
|
||||||
|
updated_data$list_select <- NULL
|
||||||
|
updated_data$list_mutate <- NULL
|
||||||
|
updated_data$list_relabel <- NULL
|
||||||
|
data <- data_r()
|
||||||
|
new_selections <- input$row_selected
|
||||||
|
if (length(new_selections) < 1) {
|
||||||
|
new_selections <- seq_along(data)
|
||||||
|
}
|
||||||
|
# browser()
|
||||||
|
data_inputs <- data.table::as.data.table(input$table_data)
|
||||||
|
data.table::setorderv(data_inputs, "rowKey")
|
||||||
|
|
||||||
|
old_names <- data_inputs$name
|
||||||
|
new_names <- data_inputs$name_toset
|
||||||
|
new_names[new_names == "New name"] <- NA
|
||||||
|
new_names[is.na(new_names)] <- old_names[is.na(new_names)]
|
||||||
|
new_names[new_names == ""] <- old_names[new_names == ""]
|
||||||
|
|
||||||
|
old_label <- data_inputs$label
|
||||||
|
new_label <- data_inputs$label_toset
|
||||||
|
new_label[new_label == "New label"] <- ""
|
||||||
|
new_label[is.na(new_label)] <- old_label[is.na(new_label)]
|
||||||
|
new_label[new_label == ""] <- old_label[new_label == ""]
|
||||||
|
|
||||||
|
new_classes <- data_inputs$class_toset
|
||||||
|
new_classes[new_classes == "Select"] <- NA
|
||||||
|
|
||||||
|
# browser()
|
||||||
|
data_sv <- variables_r()
|
||||||
|
vars_to_change <- get_vars_to_convert(data_sv, setNames(as.list(new_classes), old_names))
|
||||||
|
|
||||||
|
res_update <- try(
|
||||||
|
{
|
||||||
|
# convert
|
||||||
|
if (nrow(vars_to_change) > 0) {
|
||||||
|
data <- convert_to(
|
||||||
|
data = data,
|
||||||
|
variable = vars_to_change$name,
|
||||||
|
new_class = vars_to_change$class_to_set,
|
||||||
|
origin = input$origin,
|
||||||
|
format = input$format,
|
||||||
|
dec = input$dec
|
||||||
|
)
|
||||||
|
}
|
||||||
|
list_mutate <- attr(data, "code_03_convert")
|
||||||
|
|
||||||
|
# rename
|
||||||
|
list_rename <- setNames(
|
||||||
|
as.list(old_names),
|
||||||
|
unlist(new_names, use.names = FALSE)
|
||||||
|
)
|
||||||
|
list_rename <- list_rename[names(list_rename) != unlist(list_rename, use.names = FALSE)]
|
||||||
|
names(data) <- unlist(new_names, use.names = FALSE)
|
||||||
|
|
||||||
|
# relabel
|
||||||
|
list_relabel <- as.list(new_label)
|
||||||
|
data <- purrr::map2(
|
||||||
|
data, list_relabel,
|
||||||
|
\(.data, .label){
|
||||||
|
if (!(is.na(.label) | .label == "")) {
|
||||||
|
REDCapCAST::set_attr(.data, .label, attr = "label")
|
||||||
|
} else {
|
||||||
|
attr(x = .data, which = "label") <- NULL
|
||||||
|
.data
|
||||||
|
}
|
||||||
|
}
|
||||||
|
) |> dplyr::bind_cols(.name_repair = "unique_quiet")
|
||||||
|
|
||||||
|
# select
|
||||||
|
list_select <- setdiff(names(data), names(data)[new_selections])
|
||||||
|
data <- data[, new_selections, drop = FALSE]
|
||||||
|
},
|
||||||
|
silent = try_silent
|
||||||
|
)
|
||||||
|
|
||||||
|
if (inherits(res_update, "try-error")) {
|
||||||
|
datamods:::insert_error(selector = "update")
|
||||||
|
} else {
|
||||||
|
datamods:::insert_alert(
|
||||||
|
selector = ns("update"),
|
||||||
|
status = "success",
|
||||||
|
tags$b(phosphoricons::ph("check"), datamods::i18n("Data successfully updated!"))
|
||||||
|
)
|
||||||
|
updated_data$x <- data
|
||||||
|
updated_data$list_rename <- list_rename
|
||||||
|
updated_data$list_select <- list_select
|
||||||
|
updated_data$list_mutate <- list_mutate
|
||||||
|
updated_data$list_relabel <- list_relabel
|
||||||
|
}
|
||||||
|
},
|
||||||
|
ignoreNULL = TRUE,
|
||||||
|
ignoreInit = TRUE
|
||||||
|
)
|
||||||
|
|
||||||
|
return(shiny::reactive({
|
||||||
|
data <- updated_data$x
|
||||||
|
code <- list()
|
||||||
|
if (!is.null(data) && shiny::isTruthy(updated_data$list_mutate) && length(updated_data$list_mutate) > 0) {
|
||||||
|
code <- c(code, list(rlang::call2("mutate", !!!updated_data$list_mutate)))
|
||||||
|
}
|
||||||
|
if (!is.null(data) && shiny::isTruthy(updated_data$list_rename) && length(updated_data$list_rename) > 0) {
|
||||||
|
code <- c(code, list(rlang::call2("rename", !!!updated_data$list_rename)))
|
||||||
|
}
|
||||||
|
if (!is.null(data) && shiny::isTruthy(updated_data$list_select) && length(updated_data$list_select) > 0) {
|
||||||
|
code <- c(code, list(rlang::expr(select(-any_of(c(!!!updated_data$list_select))))))
|
||||||
|
}
|
||||||
|
if (!is.null(data) && shiny::isTruthy(updated_data$list_relabel) && length(updated_data$list_relabel) > 0) {
|
||||||
|
code <- c(code, list(rlang::call2("purrr::map2(list_relabel,
|
||||||
|
function(.data,.label){
|
||||||
|
REDCapCAST::set_attr(.data,.label,attr = 'label')
|
||||||
|
}) |> dplyr::bind_cols(.name_repair = 'unique_quiet')")))
|
||||||
|
}
|
||||||
|
if (length(code) > 0) {
|
||||||
|
attr(data, "code") <- Reduce(
|
||||||
|
f = function(x, y) rlang::expr(!!x %>% !!y),
|
||||||
|
x = code
|
||||||
|
)
|
||||||
|
}
|
||||||
|
return(data)
|
||||||
|
}))
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# utils -------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
#' Get variables classes from a \code{data.frame}
|
||||||
|
#'
|
||||||
|
#' @param data a \code{data.frame}
|
||||||
|
#'
|
||||||
|
#' @return a \code{character} vector as same length as number of variables
|
||||||
|
#' @noRd
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#'
|
||||||
|
#' get_classes(mtcars)
|
||||||
|
get_classes <- function(data) {
|
||||||
|
classes <- lapply(
|
||||||
|
X = data,
|
||||||
|
FUN = function(x) {
|
||||||
|
paste(class(x), collapse = ", ")
|
||||||
|
}
|
||||||
|
)
|
||||||
|
unlist(classes, use.names = FALSE)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#' Get count of unique values in variables of \code{data.frame}
|
||||||
|
#'
|
||||||
|
#' @param data a \code{data.frame}
|
||||||
|
#'
|
||||||
|
#' @return a \code{numeric} vector as same length as number of variables
|
||||||
|
#' @noRd
|
||||||
|
#'
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' get_n_unique(mtcars)
|
||||||
|
get_n_unique <- function(data) {
|
||||||
|
u <- lapply(data, FUN = function(x) {
|
||||||
|
if (is.atomic(x)) {
|
||||||
|
data.table::uniqueN(x)
|
||||||
|
} else {
|
||||||
|
NA_integer_
|
||||||
|
}
|
||||||
|
})
|
||||||
|
unlist(u, use.names = FALSE)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#' Add padding 0 to a vector
|
||||||
|
#'
|
||||||
|
#' @param x a \code{vector}
|
||||||
|
#'
|
||||||
|
#' @return a \code{character} vector
|
||||||
|
#' @noRd
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#'
|
||||||
|
#' pad0(1:10)
|
||||||
|
#' pad0(c(1, 15, 150, NA))
|
||||||
|
pad0 <- function(x) {
|
||||||
|
NAs <- which(is.na(x))
|
||||||
|
x <- formatC(x, width = max(nchar(as.character(x)), na.rm = TRUE), flag = "0")
|
||||||
|
x[NAs] <- NA
|
||||||
|
x
|
||||||
|
}
|
||||||
|
|
||||||
|
#' Variables summary
|
||||||
|
#'
|
||||||
|
#' @param data a \code{data.frame}
|
||||||
|
#'
|
||||||
|
#' @return a \code{data.frame}
|
||||||
|
#' @noRd
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#'
|
||||||
|
#' summary_vars(iris)
|
||||||
|
#' summary_vars(mtcars)
|
||||||
|
summary_vars <- function(data) {
|
||||||
|
data <- as.data.frame(data)
|
||||||
|
datsum <- dplyr::tibble(
|
||||||
|
name = names(data),
|
||||||
|
label = lapply(data, \(.x) REDCapCAST::get_attr(.x, "label")) |> unlist(),
|
||||||
|
class = get_classes(data),
|
||||||
|
# n_missing = unname(colSums(is.na(data))),
|
||||||
|
# p_complete = 1 - n_missing / nrow(data),
|
||||||
|
n_unique = get_n_unique(data)
|
||||||
|
)
|
||||||
|
|
||||||
|
datsum
|
||||||
|
}
|
||||||
|
|
||||||
|
add_var_toset <- function(data, var_name, default = "") {
|
||||||
|
datanames <- names(data)
|
||||||
|
datanames <- append(
|
||||||
|
x = datanames,
|
||||||
|
values = paste0(var_name, "_toset"),
|
||||||
|
after = which(datanames == var_name)
|
||||||
|
)
|
||||||
|
data[[paste0(var_name, "_toset")]] <- default
|
||||||
|
data[, datanames]
|
||||||
|
}
|
||||||
|
|
||||||
|
#' @importFrom toastui datagrid grid_columns grid_format grid_style_column
|
||||||
|
#' grid_style_column grid_editor grid_editor_opts grid_selection_row
|
||||||
|
#' @examples
|
||||||
|
#' mtcars |>
|
||||||
|
#' summary_vars() |>
|
||||||
|
#' update_variables_datagrid()
|
||||||
|
#'
|
||||||
|
update_variables_datagrid <- function(data, height = NULL, selectionId = NULL, buttonId = NULL) {
|
||||||
|
# browser()
|
||||||
|
data <- add_var_toset(data, "name", "New name")
|
||||||
|
data <- add_var_toset(data, "class", "Select")
|
||||||
|
data <- add_var_toset(data, "label", "New label")
|
||||||
|
|
||||||
|
gridTheme <- getOption("datagrid.theme")
|
||||||
|
if (length(gridTheme) < 1) {
|
||||||
|
datamods:::apply_grid_theme()
|
||||||
|
}
|
||||||
|
on.exit(toastui::reset_grid_theme())
|
||||||
|
|
||||||
|
col.names <- names(data)
|
||||||
|
|
||||||
|
std_names <- c(
|
||||||
|
"name", "name_toset", "label", "label_toset", "class", "class_toset", "n_missing", "p_complete", "n_unique"
|
||||||
|
) |>
|
||||||
|
setNames(c(
|
||||||
|
"Name", "New name", "Label", "New label", "Class", "New class", "Missing", "Complete", "Unique"
|
||||||
|
))
|
||||||
|
|
||||||
|
headers <- lapply(col.names, \(.x){
|
||||||
|
if (.x %in% std_names) {
|
||||||
|
names(std_names)[match(.x, std_names)]
|
||||||
|
} else {
|
||||||
|
.x
|
||||||
|
}
|
||||||
|
}) |> unlist()
|
||||||
|
|
||||||
|
grid <- toastui::datagrid(
|
||||||
|
data = data,
|
||||||
|
theme = "default",
|
||||||
|
colwidths = NULL
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_columns(
|
||||||
|
grid = grid,
|
||||||
|
columns = col.names,
|
||||||
|
header = headers,
|
||||||
|
minWidth = 100
|
||||||
|
)
|
||||||
|
|
||||||
|
# grid <- toastui::grid_format(
|
||||||
|
# grid = grid,
|
||||||
|
# "p_complete",
|
||||||
|
# formatter = toastui::JS("function(obj) {return (obj.value*100).toFixed(0) + '%';}")
|
||||||
|
# )
|
||||||
|
grid <- toastui::grid_style_column(
|
||||||
|
grid = grid,
|
||||||
|
column = "name_toset",
|
||||||
|
fontStyle = "italic"
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_style_column(
|
||||||
|
grid = grid,
|
||||||
|
column = "label_toset",
|
||||||
|
fontStyle = "italic"
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_style_column(
|
||||||
|
grid = grid,
|
||||||
|
column = "class_toset",
|
||||||
|
fontStyle = "italic"
|
||||||
|
)
|
||||||
|
|
||||||
|
# grid <- toastui::grid_columns(
|
||||||
|
# grid = grid,
|
||||||
|
# columns = "name_toset",
|
||||||
|
# editor = list(type = "text"),
|
||||||
|
# validation = toastui::validateOpts()
|
||||||
|
# )
|
||||||
|
#
|
||||||
|
# grid <- toastui::grid_columns(
|
||||||
|
# grid = grid,
|
||||||
|
# columns = "label_toset",
|
||||||
|
# editor = list(type = "text"),
|
||||||
|
# validation = toastui::validateOpts()
|
||||||
|
# )
|
||||||
|
#
|
||||||
|
# grid <- toastui::grid_columns(
|
||||||
|
# grid = grid,
|
||||||
|
# columns = "class_toset",
|
||||||
|
# editor = list(
|
||||||
|
# type = "radio",
|
||||||
|
# options = list(
|
||||||
|
# instantApply = TRUE,
|
||||||
|
# listItems = lapply(
|
||||||
|
# X = c("Select", "character", "factor", "numeric", "integer", "date", "datetime", "hms"),
|
||||||
|
# FUN = function(x) {
|
||||||
|
# list(text = x, value = x)
|
||||||
|
# }
|
||||||
|
# )
|
||||||
|
# )
|
||||||
|
# ),
|
||||||
|
# validation = toastui::validateOpts()
|
||||||
|
# )
|
||||||
|
|
||||||
|
grid <- toastui::grid_editor(
|
||||||
|
grid = grid,
|
||||||
|
column = "name_toset",
|
||||||
|
type = "text"
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_editor(
|
||||||
|
grid = grid,
|
||||||
|
column = "label_toset",
|
||||||
|
type = "text"
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_editor(
|
||||||
|
grid = grid,
|
||||||
|
column = "class_toset",
|
||||||
|
type = "select",
|
||||||
|
choices = c("Select new class", "character", "factor", "numeric", "integer", "date", "datetime", "hms")
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_editor_opts(
|
||||||
|
grid = grid,
|
||||||
|
editingEvent = "click",
|
||||||
|
actionButtonId = NULL,
|
||||||
|
session = NULL
|
||||||
|
)
|
||||||
|
grid <- toastui::grid_selection_row(
|
||||||
|
grid = grid,
|
||||||
|
inputId = selectionId,
|
||||||
|
type = "checkbox",
|
||||||
|
return = "index"
|
||||||
|
)
|
||||||
|
|
||||||
|
return(grid)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#' Convert a variable to specific new class
|
||||||
|
#'
|
||||||
|
#' @param data A \code{data.frame}
|
||||||
|
#' @param variable Name of the variable to convert
|
||||||
|
#' @param new_class Class to set
|
||||||
|
#' @param ... Other arguments passed on to methods.
|
||||||
|
#'
|
||||||
|
#' @return A \code{data.frame}
|
||||||
|
#' @noRd
|
||||||
|
#'
|
||||||
|
#' @importFrom utils type.convert
|
||||||
|
#' @importFrom rlang sym expr
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' dat <- data.frame(
|
||||||
|
#' v1 = month.name,
|
||||||
|
#' v2 = month.abb,
|
||||||
|
#' v3 = 1:12,
|
||||||
|
#' v4 = as.numeric(Sys.Date() + 0:11),
|
||||||
|
#' v5 = as.character(Sys.Date() + 0:11),
|
||||||
|
#' v6 = as.factor(c("a", "a", "b", "a", "b", "a", "a", "b", "a", "b", "b", "a")),
|
||||||
|
#' v7 = as.character(11:22),
|
||||||
|
#' stringsAsFactors = FALSE
|
||||||
|
#' )
|
||||||
|
#'
|
||||||
|
#' str(dat)
|
||||||
|
#'
|
||||||
|
#' str(convert_to(dat, "v3", "character"))
|
||||||
|
#' str(convert_to(dat, "v6", "character"))
|
||||||
|
#' str(convert_to(dat, "v7", "numeric"))
|
||||||
|
#' str(convert_to(dat, "v4", "date", origin = "1970-01-01"))
|
||||||
|
#' str(convert_to(dat, "v5", "date"))
|
||||||
|
#'
|
||||||
|
#' str(convert_to(dat, c("v1", "v3"), c("factor", "character")))
|
||||||
|
#'
|
||||||
|
#' str(convert_to(dat, c("v1", "v3", "v4"), c("factor", "character", "date"), origin = "1970-01-01"))
|
||||||
|
#'
|
||||||
|
convert_to <- function(data,
|
||||||
|
variable,
|
||||||
|
new_class = c("character", "factor", "numeric", "integer", "date", "datetime", "hms"),
|
||||||
|
...) {
|
||||||
|
new_class <- match.arg(new_class, several.ok = TRUE)
|
||||||
|
stopifnot(length(new_class) == length(variable))
|
||||||
|
args <- list(...)
|
||||||
|
if (length(variable) > 1) {
|
||||||
|
for (i in seq_along(variable)) {
|
||||||
|
data <- convert_to(data, variable[i], new_class[i], ...)
|
||||||
|
}
|
||||||
|
return(data)
|
||||||
|
}
|
||||||
|
if (identical(new_class, "character")) {
|
||||||
|
data[[variable]] <- as.character(x = data[[variable]], ...)
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(as.character(!!sym(variable)))), variable)
|
||||||
|
)
|
||||||
|
} else if (identical(new_class, "factor")) {
|
||||||
|
data[[variable]] <- as.factor(x = data[[variable]])
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(as.factor(!!sym(variable)))), variable)
|
||||||
|
)
|
||||||
|
} else if (identical(new_class, "numeric")) {
|
||||||
|
data[[variable]] <- as.numeric(type.convert(data[[variable]], as.is = TRUE, ...))
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(as.numeric(!!sym(variable)))), variable)
|
||||||
|
)
|
||||||
|
} else if (identical(new_class, "integer")) {
|
||||||
|
data[[variable]] <- as.integer(x = data[[variable]], ...)
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(as.integer(!!sym(variable)))), variable)
|
||||||
|
)
|
||||||
|
} else if (identical(new_class, "date")) {
|
||||||
|
data[[variable]] <- as.Date(x = data[[variable]], ...)
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(as.Date(!!sym(variable), origin = !!args$origin))), variable)
|
||||||
|
)
|
||||||
|
} else if (identical(new_class, "datetime")) {
|
||||||
|
data[[variable]] <- as.POSIXct(x = data[[variable]], ...)
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(as.POSIXct(!!sym(variable)))), variable)
|
||||||
|
)
|
||||||
|
} else if (identical(new_class, "hms")) {
|
||||||
|
data[[variable]] <- hms::as_hms(x = data[[variable]])
|
||||||
|
attr(data, "code_03_convert") <- c(
|
||||||
|
attr(data, "code_03_convert"),
|
||||||
|
setNames(list(expr(hms::as_hms(!!sym(variable)))), variable)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
return(data)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#' Get variable(s) to convert
|
||||||
|
#'
|
||||||
|
#' @param vars Output of [summary_vars()]
|
||||||
|
#' @param classes_input List of inputs containing new classes
|
||||||
|
#'
|
||||||
|
#' @return a `data.table`.
|
||||||
|
#' @noRd
|
||||||
|
#'
|
||||||
|
#' @importFrom data.table data.table as.data.table
|
||||||
|
#'
|
||||||
|
#' @examples
|
||||||
|
#' # 2 variables to convert
|
||||||
|
#' new_classes <- list(
|
||||||
|
#' "Sepal.Length" = "numeric",
|
||||||
|
#' "Sepal.Width" = "numeric",
|
||||||
|
#' "Petal.Length" = "character",
|
||||||
|
#' "Petal.Width" = "numeric",
|
||||||
|
#' "Species" = "character"
|
||||||
|
#' )
|
||||||
|
#' get_vars_to_convert(summary_vars(iris), new_classes)
|
||||||
|
#'
|
||||||
|
#'
|
||||||
|
#' # No changes
|
||||||
|
#' new_classes <- list(
|
||||||
|
#' "Sepal.Length" = "numeric",
|
||||||
|
#' "Sepal.Width" = "numeric",
|
||||||
|
#' "Petal.Length" = "numeric",
|
||||||
|
#' "Petal.Width" = "numeric",
|
||||||
|
#' "Species" = "factor"
|
||||||
|
#' )
|
||||||
|
#' get_vars_to_convert(summary_vars(iris), new_classes)
|
||||||
|
#'
|
||||||
|
#' # Not set = NA or ""
|
||||||
|
#' new_classes <- list(
|
||||||
|
#' "Sepal.Length" = NA,
|
||||||
|
#' "Sepal.Width" = NA,
|
||||||
|
#' "Petal.Length" = NA,
|
||||||
|
#' "Petal.Width" = NA,
|
||||||
|
#' "Species" = NA
|
||||||
|
#' )
|
||||||
|
#' get_vars_to_convert(summary_vars(iris), new_classes)
|
||||||
|
#'
|
||||||
|
#' # Set for one var
|
||||||
|
#' new_classes <- list(
|
||||||
|
#' "Sepal.Length" = "",
|
||||||
|
#' "Sepal.Width" = "",
|
||||||
|
#' "Petal.Length" = "",
|
||||||
|
#' "Petal.Width" = "",
|
||||||
|
#' "Species" = "character"
|
||||||
|
#' )
|
||||||
|
#' get_vars_to_convert(summary_vars(iris), new_classes)
|
||||||
|
#'
|
||||||
|
#' new_classes <- list(
|
||||||
|
#' "mpg" = "character",
|
||||||
|
#' "cyl" = "numeric",
|
||||||
|
#' "disp" = "character",
|
||||||
|
#' "hp" = "numeric",
|
||||||
|
#' "drat" = "character",
|
||||||
|
#' "wt" = "character",
|
||||||
|
#' "qsec" = "numeric",
|
||||||
|
#' "vs" = "character",
|
||||||
|
#' "am" = "numeric",
|
||||||
|
#' "gear" = "character",
|
||||||
|
#' "carb" = "integer"
|
||||||
|
#' )
|
||||||
|
#' get_vars_to_convert(summary_vars(mtcars), new_classes)
|
||||||
|
get_vars_to_convert <- function(vars, classes_input) {
|
||||||
|
vars <- data.table::as.data.table(vars)
|
||||||
|
classes_input <- data.table::data.table(
|
||||||
|
name = names(classes_input),
|
||||||
|
class_to_set = unlist(classes_input, use.names = FALSE),
|
||||||
|
stringsAsFactors = FALSE
|
||||||
|
)
|
||||||
|
classes_input <- classes_input[!is.na(class_to_set) & class_to_set != ""]
|
||||||
|
classes_df <- merge(x = vars, y = classes_input, by = "name")
|
||||||
|
classes_df <- classes_df[!is.na(class_to_set)]
|
||||||
|
classes_df[class != class_to_set]
|
||||||
|
}
|
||||||
|
|
||||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -5,6 +5,6 @@ account: agdamsbo
|
||||||
server: shinyapps.io
|
server: shinyapps.io
|
||||||
hostUrl: https://api.shinyapps.io/v1
|
hostUrl: https://api.shinyapps.io/v1
|
||||||
appId: 13611288
|
appId: 13611288
|
||||||
bundleId: 9546880
|
bundleId: 9641114
|
||||||
url: https://agdamsbo.shinyapps.io/freesearcheR/
|
url: https://agdamsbo.shinyapps.io/freesearcheR/
|
||||||
version: 1
|
version: 1
|
||||||
|
|
|
@ -18,8 +18,10 @@ library(broom.helpers)
|
||||||
library(easystats)
|
library(easystats)
|
||||||
library(patchwork)
|
library(patchwork)
|
||||||
library(DHARMa)
|
library(DHARMa)
|
||||||
library(datamods)
|
library(apexcharter)
|
||||||
library(toastui)
|
library(toastui)
|
||||||
|
library(datamods)
|
||||||
|
library(data.table)
|
||||||
library(IDEAFilter)
|
library(IDEAFilter)
|
||||||
library(shinyWidgets)
|
library(shinyWidgets)
|
||||||
library(DT)
|
library(DT)
|
||||||
|
@ -39,9 +41,9 @@ server <- function(input, output, session) {
|
||||||
## everything else.
|
## everything else.
|
||||||
files.to.keep <- list.files("www/")
|
files.to.keep <- list.files("www/")
|
||||||
|
|
||||||
output$docs_file <- renderUI({
|
output$docs_file <- shiny::renderUI({
|
||||||
# shiny::includeHTML("www/docs.html")
|
# shiny::includeHTML("www/docs.html")
|
||||||
HTML(readLines("www/docs.html"))
|
shiny::HTML(readLines("www/docs.html"))
|
||||||
})
|
})
|
||||||
|
|
||||||
##############################################################################
|
##############################################################################
|
||||||
|
@ -136,17 +138,35 @@ server <- function(input, output, session) {
|
||||||
rv$data_original <- from_env$data()
|
rv$data_original <- from_env$data()
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
||||||
##############################################################################
|
##############################################################################
|
||||||
#########
|
#########
|
||||||
######### Data modification section
|
######### Data modification section
|
||||||
#########
|
#########
|
||||||
##############################################################################
|
##############################################################################
|
||||||
|
|
||||||
######### Modifications
|
|
||||||
|
|
||||||
shiny::observeEvent(rv$data_original, rv$data <- rv$data_original |> default_parsing())
|
shiny::observeEvent(rv$data_original, rv$data <- rv$data_original |> default_parsing())
|
||||||
shiny::observeEvent(input$data_reset, rv$data <- rv$data_original |> default_parsing())
|
shiny::observeEvent(input$data_reset, rv$data <- rv$data_original |> default_parsing())
|
||||||
|
|
||||||
|
######### Overview
|
||||||
|
|
||||||
|
output$tbl_overview <- toastui::renderDatagrid(
|
||||||
|
data_filter() |>
|
||||||
|
overview_vars() |>
|
||||||
|
create_overview_datagrid()|>
|
||||||
|
add_sparkline(
|
||||||
|
column = "vals",
|
||||||
|
color.main = "#2A004E",
|
||||||
|
color.sec = "#C62300"
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
# data_summary_server(id = "data_summary",
|
||||||
|
# data = data_filter())
|
||||||
|
|
||||||
|
######### Modifications
|
||||||
|
|
||||||
|
|
||||||
## Using modified version of the datamods::cut_variable_server function
|
## Using modified version of the datamods::cut_variable_server function
|
||||||
## Further modifications are needed to have cut/bin options based on class of variable
|
## Further modifications are needed to have cut/bin options based on class of variable
|
||||||
## Could be defined server-side
|
## Could be defined server-side
|
||||||
|
@ -187,7 +207,8 @@ server <- function(input, output, session) {
|
||||||
attr(rv$data, "code")
|
attr(rv$data, "code")
|
||||||
})
|
})
|
||||||
|
|
||||||
updated_data <- datamods::update_variables_server(
|
# updated_data <- datamods::update_variables_server(
|
||||||
|
updated_data <- update_variables_server(
|
||||||
id = "vars_update",
|
id = "vars_update",
|
||||||
data = reactive(rv$data),
|
data = reactive(rv$data),
|
||||||
return_data_on_init = FALSE
|
return_data_on_init = FALSE
|
||||||
|
@ -201,7 +222,7 @@ server <- function(input, output, session) {
|
||||||
str(rv$data)
|
str(rv$data)
|
||||||
})
|
})
|
||||||
|
|
||||||
observeEvent(updated_data(), {
|
shiny::observeEvent(updated_data(), {
|
||||||
rv$data <- updated_data()
|
rv$data <- updated_data()
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -308,10 +329,6 @@ server <- function(input, output, session) {
|
||||||
# gt::gt()
|
# gt::gt()
|
||||||
# })
|
# })
|
||||||
|
|
||||||
shiny::observeEvent(input$act_start, {
|
|
||||||
bslib::nav_select(id = "main_panel", selected = "Modifications")
|
|
||||||
})
|
|
||||||
|
|
||||||
shiny::observeEvent(
|
shiny::observeEvent(
|
||||||
{
|
{
|
||||||
input$load
|
input$load
|
||||||
|
@ -326,7 +343,8 @@ server <- function(input, output, session) {
|
||||||
data <- data_filter() |>
|
data <- data_filter() |>
|
||||||
dplyr::mutate(dplyr::across(dplyr::where(is.character), as.factor)) |>
|
dplyr::mutate(dplyr::across(dplyr::where(is.character), as.factor)) |>
|
||||||
REDCapCAST::fct_drop.data.frame() |>
|
REDCapCAST::fct_drop.data.frame() |>
|
||||||
factorize(vars = input$factor_vars)
|
factorize(vars = input$factor_vars) |>
|
||||||
|
remove_na_attr()
|
||||||
|
|
||||||
if (input$strat_var == "none") {
|
if (input$strat_var == "none") {
|
||||||
by.var <- NULL
|
by.var <- NULL
|
||||||
|
@ -479,7 +497,22 @@ server <- function(input, output, session) {
|
||||||
# )
|
# )
|
||||||
# })
|
# })
|
||||||
|
|
||||||
|
##############################################################################
|
||||||
|
#########
|
||||||
|
######### Page navigation
|
||||||
|
#########
|
||||||
|
##############################################################################
|
||||||
|
|
||||||
|
shiny::observeEvent(input$act_start, {
|
||||||
|
bslib::nav_select(id = "main_panel", selected = "Modifications")
|
||||||
|
})
|
||||||
|
|
||||||
|
|
||||||
|
##############################################################################
|
||||||
|
#########
|
||||||
|
######### Reactivity
|
||||||
|
#########
|
||||||
|
##############################################################################
|
||||||
|
|
||||||
output$uploaded <- shiny::reactive({
|
output$uploaded <- shiny::reactive({
|
||||||
if (is.null(rv$ds)) {
|
if (is.null(rv$ds)) {
|
||||||
|
@ -512,6 +545,12 @@ server <- function(input, output, session) {
|
||||||
|
|
||||||
# shiny::outputOptions(output, "has_input", suspendWhenHidden = FALSE)
|
# shiny::outputOptions(output, "has_input", suspendWhenHidden = FALSE)
|
||||||
|
|
||||||
|
##############################################################################
|
||||||
|
#########
|
||||||
|
######### Downloads
|
||||||
|
#########
|
||||||
|
##############################################################################
|
||||||
|
|
||||||
# Could be rendered with other tables or should show progress
|
# Could be rendered with other tables or should show progress
|
||||||
# Investigate quarto render problems
|
# Investigate quarto render problems
|
||||||
# On temp file handling: https://github.com/quarto-dev/quarto-cli/issues/3992
|
# On temp file handling: https://github.com/quarto-dev/quarto-cli/issues/3992
|
||||||
|
@ -533,6 +572,26 @@ server <- function(input, output, session) {
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
|
output$data_modified <- downloadHandler(
|
||||||
|
filename = shiny::reactive({
|
||||||
|
paste0("modified_data.", input$data_type)
|
||||||
|
}),
|
||||||
|
content = function(file, type = input$data_type) {
|
||||||
|
if (type == "rds"){
|
||||||
|
readr::write_rds(rv$list$data,file = file)
|
||||||
|
} else {
|
||||||
|
haven::write_dta(as.data.frame(rv$list$data),path = file)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
##############################################################################
|
||||||
|
#########
|
||||||
|
######### Clearing the session on end
|
||||||
|
#########
|
||||||
|
##############################################################################
|
||||||
|
|
||||||
session$onSessionEnded(function() {
|
session$onSessionEnded(function() {
|
||||||
cat("Session Ended\n")
|
cat("Session Ended\n")
|
||||||
files <- list.files("www/")
|
files <- list.files("www/")
|
||||||
|
|
|
@ -1,6 +1,16 @@
|
||||||
# ns <- NS(id)
|
# ns <- NS(id)
|
||||||
|
|
||||||
ui_elements <- list(
|
ui_elements <- list(
|
||||||
|
##############################################################################
|
||||||
|
#########
|
||||||
|
######### Home panel
|
||||||
|
#########
|
||||||
|
##############################################################################
|
||||||
|
"home" = bslib::nav_panel(
|
||||||
|
title = "freesearcheR",
|
||||||
|
shiny::markdown(readLines("www/intro.md")),
|
||||||
|
icon = shiny::icon("home")
|
||||||
|
),
|
||||||
##############################################################################
|
##############################################################################
|
||||||
#########
|
#########
|
||||||
######### Import panel
|
######### Import panel
|
||||||
|
@ -8,9 +18,7 @@ ui_elements <- list(
|
||||||
##############################################################################
|
##############################################################################
|
||||||
"import" = bslib::nav_panel(
|
"import" = bslib::nav_panel(
|
||||||
title = "Import",
|
title = "Import",
|
||||||
shiny::fluidRow(
|
shiny::tagList(
|
||||||
column(
|
|
||||||
width = 6,
|
|
||||||
shiny::h4("Choose your data source"),
|
shiny::h4("Choose your data source"),
|
||||||
# shiny::conditionalPanel(
|
# shiny::conditionalPanel(
|
||||||
# condition = "output.has_input=='yes'",
|
# condition = "output.has_input=='yes'",
|
||||||
|
@ -22,6 +30,7 @@ ui_elements <- list(
|
||||||
# Input: Select a file ----
|
# Input: Select a file ----
|
||||||
shinyWidgets::radioGroupButtons(
|
shinyWidgets::radioGroupButtons(
|
||||||
inputId = "source",
|
inputId = "source",
|
||||||
|
selected = "env",
|
||||||
# label = "Choice: ",
|
# label = "Choice: ",
|
||||||
choices = c(
|
choices = c(
|
||||||
"File upload" = "file",
|
"File upload" = "file",
|
||||||
|
@ -48,15 +57,6 @@ ui_elements <- list(
|
||||||
shiny::conditionalPanel(
|
shiny::conditionalPanel(
|
||||||
condition = "input.source=='env'",
|
condition = "input.source=='env'",
|
||||||
import_globalenv_ui(id = "env", title = NULL)
|
import_globalenv_ui(id = "env", title = NULL)
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
# )
|
|
||||||
),
|
|
||||||
column(
|
|
||||||
width = 6,
|
|
||||||
shiny::markdown(readLines("www/intro.md"))
|
|
||||||
)
|
|
||||||
),
|
),
|
||||||
shiny::conditionalPanel(
|
shiny::conditionalPanel(
|
||||||
condition = "input.source=='redcap'",
|
condition = "input.source=='redcap'",
|
||||||
|
@ -72,6 +72,7 @@ ui_elements <- list(
|
||||||
shiny::helpText('After importing, hit "Start" or navigate to the desired tab.'),
|
shiny::helpText('After importing, hit "Start" or navigate to the desired tab.'),
|
||||||
shiny::br(),
|
shiny::br(),
|
||||||
shiny::br()
|
shiny::br()
|
||||||
|
)
|
||||||
),
|
),
|
||||||
##############################################################################
|
##############################################################################
|
||||||
#########
|
#########
|
||||||
|
@ -82,44 +83,21 @@ ui_elements <- list(
|
||||||
# bslib::nav_panel_hidden(
|
# bslib::nav_panel_hidden(
|
||||||
bslib::nav_panel(
|
bslib::nav_panel(
|
||||||
# value = "overview",
|
# value = "overview",
|
||||||
title = "Modifications",
|
title = "Data",
|
||||||
bslib::navset_bar(
|
bslib::navset_bar(
|
||||||
fillable = TRUE,
|
fillable = TRUE,
|
||||||
# bslib::nav_panel(
|
|
||||||
# title = "Edit",
|
|
||||||
# datamods::edit_data_ui(id = "edit_data")
|
|
||||||
# ),
|
|
||||||
# bslib::nav_panel(
|
|
||||||
# title = "Overview",
|
|
||||||
# DT::DTOutput(outputId = "table")
|
|
||||||
# ),
|
|
||||||
bslib::nav_panel(
|
bslib::nav_panel(
|
||||||
title = "Rename and select",
|
title = "Summary & filter",
|
||||||
tags$h3("Select, rename and convert variables"),
|
tags$h3("Data summary and filtering"),
|
||||||
fluidRow(
|
fluidRow(
|
||||||
column(
|
shiny::column(
|
||||||
width = 6,
|
width = 9,
|
||||||
# radioButtons(),
|
shiny::tags$p(
|
||||||
shiny::actionButton("data_reset", "Restore original data"),
|
"Below is a short summary table of the provided data.
|
||||||
shiny::tags$br(),
|
On the right hand side you have the option to create filters.
|
||||||
shiny::helpText("Reset to original imported dataset"),
|
At the bottom you'll find a raw overview of the original vs the modified data.")
|
||||||
shiny::tags$br(),
|
|
||||||
datamods::update_variables_ui("vars_update")
|
|
||||||
),
|
|
||||||
column(
|
|
||||||
width = 6,
|
|
||||||
tags$b("Original data:"),
|
|
||||||
# verbatimTextOutput("original"),
|
|
||||||
verbatimTextOutput("original_str"),
|
|
||||||
tags$b("Modified data:"),
|
|
||||||
# verbatimTextOutput("modified"),
|
|
||||||
verbatimTextOutput("modified_str")
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
),
|
),
|
||||||
bslib::nav_panel(
|
|
||||||
title = "Filter and modify",
|
|
||||||
shinyWidgets::html_dependency_winbox(),
|
|
||||||
fluidRow(
|
fluidRow(
|
||||||
# column(
|
# column(
|
||||||
# width = 3,
|
# width = 3,
|
||||||
|
@ -136,23 +114,117 @@ ui_elements <- list(
|
||||||
# verbatimTextOutput(outputId = "filtered_code")
|
# verbatimTextOutput(outputId = "filtered_code")
|
||||||
# ),
|
# ),
|
||||||
shiny::column(
|
shiny::column(
|
||||||
width = 8,
|
width = 9,
|
||||||
toastui::datagridOutput(outputId = "table_mod"),
|
toastui::datagridOutput(outputId = "tbl_overview"),
|
||||||
|
# data_summary_ui(id = "data_summary"),
|
||||||
shiny::tags$b("Reproducible code:"),
|
shiny::tags$b("Reproducible code:"),
|
||||||
shiny::verbatimTextOutput(outputId = "filtered_code")
|
shiny::verbatimTextOutput(outputId = "filtered_code")
|
||||||
),
|
),
|
||||||
shiny::column(
|
shiny::column(
|
||||||
width = 4,
|
width = 3,
|
||||||
shiny::actionButton("modal_cut", "Create factor from a variable"),
|
IDEAFilter::IDEAFilter_ui("data_filter") # ,
|
||||||
|
# shiny::actionButton("save_filter", "Apply the filter")
|
||||||
|
)
|
||||||
|
),
|
||||||
|
fluidRow(
|
||||||
|
column(
|
||||||
|
width = 6,
|
||||||
|
tags$b("Original data:"),
|
||||||
|
# verbatimTextOutput("original"),
|
||||||
|
verbatimTextOutput("original_str")
|
||||||
|
),
|
||||||
|
column(
|
||||||
|
width = 6,
|
||||||
|
tags$b("Modified data:"),
|
||||||
|
# verbatimTextOutput("modified"),
|
||||||
|
verbatimTextOutput("modified_str")
|
||||||
|
)
|
||||||
|
)
|
||||||
|
),
|
||||||
|
# bslib::nav_panel(
|
||||||
|
# title = "Overview",
|
||||||
|
# DT::DTOutput(outputId = "table")
|
||||||
|
# ),
|
||||||
|
bslib::nav_panel(
|
||||||
|
title = "Modify",
|
||||||
|
tags$h3("Subset, rename and convert variables"),
|
||||||
|
fluidRow(
|
||||||
|
shiny::column(
|
||||||
|
width = 9,
|
||||||
|
shiny::tags$p("Below, you can subset the data (by not selecting the variables to exclude on applying changes), rename variables, set new labels (for nicer tables in the analysis report) and change variable classes.
|
||||||
|
Italic text can be edited/changed.
|
||||||
|
On the right, you can create and modify factor/categorical variables as well as resetting the data to the originally imported data.")
|
||||||
|
)
|
||||||
|
),
|
||||||
|
fluidRow(
|
||||||
|
shiny::column(
|
||||||
|
width = 9,
|
||||||
|
update_variables_ui("vars_update")
|
||||||
|
),
|
||||||
|
shiny::column(
|
||||||
|
width = 3,
|
||||||
|
shiny::actionButton("modal_cut", "Create factor variable"),
|
||||||
|
shiny::tags$br(),
|
||||||
|
shiny::helpText("Create factor/categorical variable from an other value."),
|
||||||
shiny::tags$br(),
|
shiny::tags$br(),
|
||||||
shiny::tags$br(),
|
shiny::tags$br(),
|
||||||
shiny::actionButton("modal_update", "Reorder factor levels"),
|
shiny::actionButton("modal_update", "Reorder factor levels"),
|
||||||
shiny::tags$br(),
|
shiny::tags$br(),
|
||||||
|
shiny::helpText("Reorder the levels of factor/categorical variables."),
|
||||||
shiny::tags$br(),
|
shiny::tags$br(),
|
||||||
IDEAFilter::IDEAFilter_ui("data_filter") # ,
|
shiny::tags$br(),
|
||||||
|
shiny::actionButton("data_reset", "Restore original data"),
|
||||||
|
shiny::tags$br(),
|
||||||
|
shiny::helpText("Reset to original imported dataset. Careful! There is no un-doing."),
|
||||||
|
shiny::tags$br() # ,
|
||||||
|
# shiny::tags$br(),
|
||||||
|
# shiny::tags$br(),
|
||||||
|
# IDEAFilter::IDEAFilter_ui("data_filter") # ,
|
||||||
# shiny::actionButton("save_filter", "Apply the filter")
|
# shiny::actionButton("save_filter", "Apply the filter")
|
||||||
)
|
)
|
||||||
|
# datamods::update_variables_ui("vars_update")
|
||||||
)
|
)
|
||||||
|
),
|
||||||
|
bslib::nav_panel(
|
||||||
|
title = "Browser",
|
||||||
|
tags$h3("Browse the provided data"),
|
||||||
|
shiny::tags$p(
|
||||||
|
"Below is a data table with all the modified data provided to browse and understand data."
|
||||||
|
),
|
||||||
|
shinyWidgets::html_dependency_winbox(),
|
||||||
|
# fluidRow(
|
||||||
|
# column(
|
||||||
|
# width = 3,
|
||||||
|
# shiny::uiOutput("filter_vars"),
|
||||||
|
# shiny::conditionalPanel(
|
||||||
|
# condition = "(typeof input.filter_vars !== 'undefined' && input.filter_vars.length > 0)",
|
||||||
|
# datamods::filter_data_ui("filtering", max_height = "500px")
|
||||||
|
# )
|
||||||
|
# ),
|
||||||
|
# column(
|
||||||
|
# width = 9,
|
||||||
|
# DT::DTOutput(outputId = "filtered_table"),
|
||||||
|
# tags$b("Code dplyr:"),
|
||||||
|
# verbatimTextOutput(outputId = "filtered_code")
|
||||||
|
# ),
|
||||||
|
# shiny::column(
|
||||||
|
# width = 8,
|
||||||
|
toastui::datagridOutput(outputId = "table_mod") # ,
|
||||||
|
# shiny::tags$b("Reproducible code:"),
|
||||||
|
# shiny::verbatimTextOutput(outputId = "filtered_code")
|
||||||
|
# ),
|
||||||
|
# shiny::column(
|
||||||
|
# width = 4,
|
||||||
|
# shiny::actionButton("modal_cut", "Create factor from a variable"),
|
||||||
|
# shiny::tags$br(),
|
||||||
|
# shiny::tags$br(),
|
||||||
|
# shiny::actionButton("modal_update", "Reorder factor levels")#,
|
||||||
|
# # shiny::tags$br(),
|
||||||
|
# # shiny::tags$br(),
|
||||||
|
# # IDEAFilter::IDEAFilter_ui("data_filter") # ,
|
||||||
|
# # shiny::actionButton("save_filter", "Apply the filter")
|
||||||
|
# )
|
||||||
|
# )
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@ -181,6 +253,20 @@ ui_elements <- list(
|
||||||
sidebar = bslib::sidebar(
|
sidebar = bslib::sidebar(
|
||||||
shiny::helpText(em("Please specify relevant settings for your data, and press 'Analyse'")),
|
shiny::helpText(em("Please specify relevant settings for your data, and press 'Analyse'")),
|
||||||
shiny::uiOutput("outcome_var"),
|
shiny::uiOutput("outcome_var"),
|
||||||
|
shiny::radioButtons(
|
||||||
|
inputId = "all",
|
||||||
|
label = "Specify covariables",
|
||||||
|
inline = TRUE, selected = 2,
|
||||||
|
choiceNames = c(
|
||||||
|
"Yes",
|
||||||
|
"No"
|
||||||
|
),
|
||||||
|
choiceValues = c(1, 2)
|
||||||
|
),
|
||||||
|
shiny::conditionalPanel(
|
||||||
|
condition = "input.all==1",
|
||||||
|
shiny::uiOutput("include_vars")
|
||||||
|
),
|
||||||
shiny::uiOutput("strat_var"),
|
shiny::uiOutput("strat_var"),
|
||||||
shiny::conditionalPanel(
|
shiny::conditionalPanel(
|
||||||
condition = "input.strat_var!='none'",
|
condition = "input.strat_var!='none'",
|
||||||
|
@ -196,20 +282,6 @@ ui_elements <- list(
|
||||||
),
|
),
|
||||||
shiny::helpText("Option to perform statistical comparisons between strata in baseline table.")
|
shiny::helpText("Option to perform statistical comparisons between strata in baseline table.")
|
||||||
),
|
),
|
||||||
shiny::radioButtons(
|
|
||||||
inputId = "all",
|
|
||||||
label = "Specify covariables",
|
|
||||||
inline = TRUE, selected = 2,
|
|
||||||
choiceNames = c(
|
|
||||||
"Yes",
|
|
||||||
"No"
|
|
||||||
),
|
|
||||||
choiceValues = c(1, 2)
|
|
||||||
),
|
|
||||||
shiny::conditionalPanel(
|
|
||||||
condition = "input.all==1",
|
|
||||||
shiny::uiOutput("include_vars")
|
|
||||||
),
|
|
||||||
shiny::radioButtons(
|
shiny::radioButtons(
|
||||||
inputId = "specify_factors",
|
inputId = "specify_factors",
|
||||||
label = "Specify categorical variables?",
|
label = "Specify categorical variables?",
|
||||||
|
@ -258,13 +330,29 @@ ui_elements <- list(
|
||||||
# Button
|
# Button
|
||||||
shiny::downloadButton(
|
shiny::downloadButton(
|
||||||
outputId = "report",
|
outputId = "report",
|
||||||
label = "Download",
|
label = "Download report",
|
||||||
icon = shiny::icon("download")
|
icon = shiny::icon("download")
|
||||||
),
|
),
|
||||||
shiny::helpText("If choosing to output to MS Word, please note, that when opening the document, two errors will pop-up. Choose to repair and choose not to update references. The issue is being worked on. You can always choose LibreOffice instead.")
|
shiny::helpText("If choosing to output to MS Word, please note, that when opening the document, two errors will pop-up. Choose to repair and choose not to update references. The issue is being worked on. You can always choose LibreOffice instead."),
|
||||||
## https://github.com/quarto-dev/quarto-cli/issues/7151
|
shiny::tags$hr(),
|
||||||
# )
|
shiny::h4("Download data"),
|
||||||
# )
|
shiny::helpText("Choose your favourite output data format to download the modified data."),
|
||||||
|
shiny::selectInput(
|
||||||
|
inputId = "data_type",
|
||||||
|
label = "Data format",
|
||||||
|
selected = NULL,
|
||||||
|
choices = list(
|
||||||
|
"R" = "rds",
|
||||||
|
"stata" = "dta"
|
||||||
|
)
|
||||||
|
),
|
||||||
|
shiny::br(),
|
||||||
|
# Button
|
||||||
|
shiny::downloadButton(
|
||||||
|
outputId = "data_modified",
|
||||||
|
label = "Download data",
|
||||||
|
icon = shiny::icon("download")
|
||||||
|
)
|
||||||
),
|
),
|
||||||
bslib::nav_panel(
|
bslib::nav_panel(
|
||||||
title = "Baseline characteristics",
|
title = "Baseline characteristics",
|
||||||
|
@ -303,28 +391,39 @@ dark <- custom_theme(
|
||||||
# Fonts to consider:
|
# Fonts to consider:
|
||||||
# https://webdesignerdepot.com/17-open-source-fonts-youll-actually-love/
|
# https://webdesignerdepot.com/17-open-source-fonts-youll-actually-love/
|
||||||
|
|
||||||
ui <- bslib::page_fluid(
|
ui <- bslib::page_fixed(
|
||||||
|
shiny::tags$style(
|
||||||
|
type = "text/css",
|
||||||
|
# add the name of the tab you want to use as title in data-value
|
||||||
|
shiny::HTML(
|
||||||
|
".container-fluid > .nav > li >
|
||||||
|
a[data-value='freesearcheR'] {font-size: 28px}"
|
||||||
|
)
|
||||||
|
),
|
||||||
title = "freesearcheR",
|
title = "freesearcheR",
|
||||||
theme = light,
|
theme = light,
|
||||||
shiny::useBusyIndicators(),
|
shiny::useBusyIndicators(),
|
||||||
bslib::page_navbar(title = "freesearcheR",
|
bslib::page_navbar(
|
||||||
|
# title = "freesearcheR",
|
||||||
id = "main_panel",
|
id = "main_panel",
|
||||||
# header = shiny::tags$header(shiny::p("Data is only stored temporarily for analysis and deleted immediately afterwards.")),
|
# header = shiny::tags$header(shiny::p("Data is only stored temporarily for analysis and deleted immediately afterwards.")),
|
||||||
|
ui_elements$home,
|
||||||
ui_elements$import,
|
ui_elements$import,
|
||||||
ui_elements$overview,
|
ui_elements$overview,
|
||||||
ui_elements$analyze,
|
ui_elements$analyze,
|
||||||
ui_elements$docs,
|
ui_elements$docs,
|
||||||
# bslib::nav_spacer(),
|
# bslib::nav_spacer(),
|
||||||
# bslib::nav_item(shinyWidgets::circleButton(inputId = "mode", icon = icon("moon"),status = "primary")),
|
# bslib::nav_item(shinyWidgets::circleButton(inputId = "mode", icon = icon("moon"),status = "primary")),
|
||||||
fillable = TRUE,
|
fillable = FALSE,
|
||||||
footer = shiny::tags$footer(
|
footer = shiny::tags$footer(
|
||||||
style = "background-color: #14131326; padding: 4px; text-align: center; bottom: 0; width: 100%;",
|
style = "background-color: #14131326; padding: 4px; text-align: center; bottom: 0; width: 100%;",
|
||||||
shiny::p(
|
shiny::p(
|
||||||
style = "margin: 1",
|
style = "margin: 1",
|
||||||
"Data is only stored for analyses and deleted immediately afterwards."),
|
"Data is only stored for analyses and deleted immediately afterwards."
|
||||||
|
),
|
||||||
shiny::p(
|
shiny::p(
|
||||||
style = "margin: 1; color: #888;",
|
style = "margin: 1; color: #888;",
|
||||||
"Andreas G Damsbo | AGPLv3 license | ", shiny::tags$a("Source on Github", href = "https://github.com/agdamsbo/freesearcheR/", target="_blank", rel="noopener noreferrer")
|
"Andreas G Damsbo | AGPLv3 license | ", shiny::tags$a("Source on Github", href = "https://github.com/agdamsbo/freesearcheR/", target = "_blank", rel = "noopener noreferrer")
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
|
@ -56,7 +56,7 @@ margin: 0 0.8em 0.2em -1em; vertical-align: middle;
|
||||||
<li><p><label><input type="checkbox">Option to edit variable labels for nicer tables</label></p></li>
|
<li><p><label><input type="checkbox">Option to edit variable labels for nicer tables</label></p></li>
|
||||||
</ul></li>
|
</ul></li>
|
||||||
<li><p><label><input type="checkbox">Plot regression analyses results</label></p></li>
|
<li><p><label><input type="checkbox">Plot regression analyses results</label></p></li>
|
||||||
<li><p><label><input type="checkbox">Export modified data</label></p></li>
|
<li><p><label><input type="checkbox" checked>Export modified data. 2025-01-09</label></p></li>
|
||||||
<li><p><label><input type="checkbox">Include reproducible code for all steps</label></p></li>
|
<li><p><label><input type="checkbox">Include reproducible code for all steps</label></p></li>
|
||||||
<li><p><label><input type="checkbox" checked><del>Modify factor levels</del> Factor level modification is possible through converting factors to numeric > cutting numeric with desired fixed values. 2024-12-12</label></p></li>
|
<li><p><label><input type="checkbox" checked><del>Modify factor levels</del> Factor level modification is possible through converting factors to numeric > cutting numeric with desired fixed values. 2024-12-12</label></p></li>
|
||||||
<li><p><label><input type="checkbox" checked>More options for date/datetime/time grouping/factoring. Included weekday and month-only options. 2024-12-12</label></p></li>
|
<li><p><label><input type="checkbox" checked>More options for date/datetime/time grouping/factoring. Included weekday and month-only options. 2024-12-12</label></p></li>
|
||||||
|
|
|
@ -36,7 +36,7 @@ Contributions are very welcome. If you find anything odd, or you think of featur
|
||||||
|
|
||||||
- [ ] Plot regression analyses results
|
- [ ] Plot regression analyses results
|
||||||
|
|
||||||
- [ ] Export modified data
|
- [x] Export modified data. 2025-01-09
|
||||||
|
|
||||||
- [ ] Include reproducible code for all steps
|
- [ ] Include reproducible code for all steps
|
||||||
|
|
||||||
|
|
432
inst/apps/data_analysis_modules/www/intro.html
Normal file
432
inst/apps/data_analysis_modules/www/intro.html
Normal file
File diff suppressed because one or more lines are too long
|
@ -1,12 +1,12 @@
|
||||||
# Welcome
|
# Welcome
|
||||||
|
|
||||||
This is the ***freesearchR*** web data analysis tool. We intend the ***freesearchR*** to be a powerful and free tool for easy data evaluation and analysis at the hands of the clinician.
|
This is the ***freesearcheR*** web data analysis tool. We intend the ***freesearcheR*** to be a powerful and free tool for easy data evaluation and analysis at the hands of the clinician.
|
||||||
|
|
||||||
By intention, this tool has been designed to be simple to use with a minimum of mandatory options to keep the workflow streamlined, while also including a few options to go even further.
|
By intention, this tool has been designed to be simple to use with a minimum of mandatory options to keep the workflow streamlined, while also including a few options to go even further.
|
||||||
|
|
||||||
There are four simple steps to go through:
|
There are four simple steps to go through (see corresponding tabs in the top):
|
||||||
|
|
||||||
1. Import data (a spreadsheet/file on your machine, direct export from a REDCap server, or a local file provided with a package).
|
1. Import data (a spreadsheet/file on your machine, direct export from a REDCap server, or a local file provided with a package) to get started.
|
||||||
|
|
||||||
2. An *optional* step of data modification (change variable classes and creating categorical variables (factors) from numeric or time data)
|
2. An *optional* step of data modification (change variable classes and creating categorical variables (factors) from numeric or time data)
|
||||||
|
|
||||||
|
@ -18,4 +18,4 @@ There are four simple steps to go through:
|
||||||
|
|
||||||
- Evaluation of model assumptions
|
- Evaluation of model assumptions
|
||||||
|
|
||||||
4. Export the the analyses results as for MS Word or [LibreOffice](https://www.libreoffice.org/).
|
4. Export the the analyses results for MS Word or [LibreOffice](https://www.libreoffice.org/) as well as the data with preserved metadata.
|
||||||
|
|
|
@ -97,9 +97,9 @@ footer <- tags$p(
|
||||||
# redcap_browser_app <- teal_init(data = tdm_data_upload)
|
# redcap_browser_app <- teal_init(data = tdm_data_upload)
|
||||||
|
|
||||||
app <- teal::init(
|
app <- teal::init(
|
||||||
# data=tdm_data_read,
|
data=tdm_data_read,
|
||||||
# data = tdm_data_upload,
|
# data = tdm_data_upload,
|
||||||
data = tdm_redcap_read,
|
# data = tdm_redcap_read,
|
||||||
filter = filters,
|
filter = filters,
|
||||||
modules = modules(
|
modules = modules(
|
||||||
tm_data_table("Data Table"),
|
tm_data_table("Data Table"),
|
||||||
|
|
484
renv.lock
484
renv.lock
|
@ -57,6 +57,27 @@
|
||||||
],
|
],
|
||||||
"Hash": "64ff3427f559ce3f2597a4fe13255cb6"
|
"Hash": "64ff3427f559ce3f2597a4fe13255cb6"
|
||||||
},
|
},
|
||||||
|
"Deriv": {
|
||||||
|
"Package": "Deriv",
|
||||||
|
"Version": "4.1.6",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"methods"
|
||||||
|
],
|
||||||
|
"Hash": "cd52c065c9e687c60c56b51f10f7bcd3"
|
||||||
|
},
|
||||||
|
"Formula": {
|
||||||
|
"Package": "Formula",
|
||||||
|
"Version": "1.2-5",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"stats"
|
||||||
|
],
|
||||||
|
"Hash": "7a29697b75e027767a53fde6c903eca7"
|
||||||
|
},
|
||||||
"IDEAFilter": {
|
"IDEAFilter": {
|
||||||
"Package": "IDEAFilter",
|
"Package": "IDEAFilter",
|
||||||
"Version": "0.2.0",
|
"Version": "0.2.0",
|
||||||
|
@ -117,6 +138,19 @@
|
||||||
],
|
],
|
||||||
"Hash": "5122bb14d8736372411f955e1b16bc8a"
|
"Hash": "5122bb14d8736372411f955e1b16bc8a"
|
||||||
},
|
},
|
||||||
|
"MatrixModels": {
|
||||||
|
"Package": "MatrixModels",
|
||||||
|
"Version": "0.5-3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"Matrix",
|
||||||
|
"R",
|
||||||
|
"methods",
|
||||||
|
"stats"
|
||||||
|
],
|
||||||
|
"Hash": "0776bf7526869e0286b0463cb72fb211"
|
||||||
|
},
|
||||||
"R.cache": {
|
"R.cache": {
|
||||||
"Package": "R.cache",
|
"Package": "R.cache",
|
||||||
"Version": "0.16.0",
|
"Version": "0.16.0",
|
||||||
|
@ -280,6 +314,20 @@
|
||||||
],
|
],
|
||||||
"Hash": "a9e2118c664c2cd694f03de074e8d4b3"
|
"Hash": "a9e2118c664c2cd694f03de074e8d4b3"
|
||||||
},
|
},
|
||||||
|
"SparseM": {
|
||||||
|
"Package": "SparseM",
|
||||||
|
"Version": "1.84-2",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"graphics",
|
||||||
|
"methods",
|
||||||
|
"stats",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "e78499cbcbbca98200254bd171379165"
|
||||||
|
},
|
||||||
"V8": {
|
"V8": {
|
||||||
"Package": "V8",
|
"Package": "V8",
|
||||||
"Version": "6.0.0",
|
"Version": "6.0.0",
|
||||||
|
@ -293,6 +341,18 @@
|
||||||
],
|
],
|
||||||
"Hash": "6603bfcbc7883a5fed41fb13042a3899"
|
"Hash": "6603bfcbc7883a5fed41fb13042a3899"
|
||||||
},
|
},
|
||||||
|
"abind": {
|
||||||
|
"Package": "abind",
|
||||||
|
"Version": "1.4-8",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"methods",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "2288423bb0f20a457800d7fc47f6aa54"
|
||||||
|
},
|
||||||
"ape": {
|
"ape": {
|
||||||
"Package": "ape",
|
"Package": "ape",
|
||||||
"Version": "5.8-1",
|
"Version": "5.8-1",
|
||||||
|
@ -312,6 +372,23 @@
|
||||||
],
|
],
|
||||||
"Hash": "54e5b03e928da23e75dc5bb633648d27"
|
"Hash": "54e5b03e928da23e75dc5bb633648d27"
|
||||||
},
|
},
|
||||||
|
"apexcharter": {
|
||||||
|
"Package": "apexcharter",
|
||||||
|
"Version": "0.4.4",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"ggplot2",
|
||||||
|
"htmltools",
|
||||||
|
"htmlwidgets",
|
||||||
|
"jsonlite",
|
||||||
|
"magrittr",
|
||||||
|
"rlang",
|
||||||
|
"shiny"
|
||||||
|
],
|
||||||
|
"Hash": "4bad120b4c71a078d8637f9cbe1eb1df"
|
||||||
|
},
|
||||||
"askpass": {
|
"askpass": {
|
||||||
"Package": "askpass",
|
"Package": "askpass",
|
||||||
"Version": "1.2.1",
|
"Version": "1.2.1",
|
||||||
|
@ -534,6 +611,41 @@
|
||||||
],
|
],
|
||||||
"Hash": "d7e13f49c19103ece9e58ad2d83a7354"
|
"Hash": "d7e13f49c19103ece9e58ad2d83a7354"
|
||||||
},
|
},
|
||||||
|
"car": {
|
||||||
|
"Package": "car",
|
||||||
|
"Version": "3.1-3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"Formula",
|
||||||
|
"MASS",
|
||||||
|
"R",
|
||||||
|
"abind",
|
||||||
|
"carData",
|
||||||
|
"grDevices",
|
||||||
|
"graphics",
|
||||||
|
"lme4",
|
||||||
|
"mgcv",
|
||||||
|
"nlme",
|
||||||
|
"nnet",
|
||||||
|
"pbkrtest",
|
||||||
|
"quantreg",
|
||||||
|
"scales",
|
||||||
|
"stats",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "82067bf302d1440b730437693a86406a"
|
||||||
|
},
|
||||||
|
"carData": {
|
||||||
|
"Package": "carData",
|
||||||
|
"Version": "3.0-5",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R"
|
||||||
|
],
|
||||||
|
"Hash": "ac6cdb8552c61bd36b0e54d07cf2aab7"
|
||||||
|
},
|
||||||
"cards": {
|
"cards": {
|
||||||
"Package": "cards",
|
"Package": "cards",
|
||||||
"Version": "0.4.0",
|
"Version": "0.4.0",
|
||||||
|
@ -688,6 +800,23 @@
|
||||||
],
|
],
|
||||||
"Hash": "8b6512d8f60685736ee3bafdc292190d"
|
"Hash": "8b6512d8f60685736ee3bafdc292190d"
|
||||||
},
|
},
|
||||||
|
"cowplot": {
|
||||||
|
"Package": "cowplot",
|
||||||
|
"Version": "1.1.3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"ggplot2",
|
||||||
|
"grDevices",
|
||||||
|
"grid",
|
||||||
|
"gtable",
|
||||||
|
"methods",
|
||||||
|
"rlang",
|
||||||
|
"scales"
|
||||||
|
],
|
||||||
|
"Hash": "8ef2084dd7d28847b374e55440e4f8cb"
|
||||||
|
},
|
||||||
"cpp11": {
|
"cpp11": {
|
||||||
"Package": "cpp11",
|
"Package": "cpp11",
|
||||||
"Version": "0.5.1",
|
"Version": "0.5.1",
|
||||||
|
@ -794,6 +923,30 @@
|
||||||
],
|
],
|
||||||
"Hash": "33698c4b3127fc9f506654607fb73676"
|
"Hash": "33698c4b3127fc9f506654607fb73676"
|
||||||
},
|
},
|
||||||
|
"doBy": {
|
||||||
|
"Package": "doBy",
|
||||||
|
"Version": "4.6.24",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"Deriv",
|
||||||
|
"MASS",
|
||||||
|
"Matrix",
|
||||||
|
"R",
|
||||||
|
"boot",
|
||||||
|
"broom",
|
||||||
|
"cowplot",
|
||||||
|
"dplyr",
|
||||||
|
"ggplot2",
|
||||||
|
"methods",
|
||||||
|
"microbenchmark",
|
||||||
|
"modelr",
|
||||||
|
"rlang",
|
||||||
|
"tibble",
|
||||||
|
"tidyr"
|
||||||
|
],
|
||||||
|
"Hash": "8ddf795104defe53c5392a588888ec68"
|
||||||
|
},
|
||||||
"doParallel": {
|
"doParallel": {
|
||||||
"Package": "doParallel",
|
"Package": "doParallel",
|
||||||
"Version": "1.0.17",
|
"Version": "1.0.17",
|
||||||
|
@ -886,6 +1039,34 @@
|
||||||
],
|
],
|
||||||
"Hash": "b289af101f62cb7b46c53d1a45ed5198"
|
"Hash": "b289af101f62cb7b46c53d1a45ed5198"
|
||||||
},
|
},
|
||||||
|
"emmeans": {
|
||||||
|
"Package": "emmeans",
|
||||||
|
"Version": "1.10.6",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"estimability",
|
||||||
|
"graphics",
|
||||||
|
"methods",
|
||||||
|
"mvtnorm",
|
||||||
|
"numDeriv",
|
||||||
|
"stats",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "6b0c6fcbdbefe525d2ee713f95880f90"
|
||||||
|
},
|
||||||
|
"estimability": {
|
||||||
|
"Package": "estimability",
|
||||||
|
"Version": "1.5.1",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"stats"
|
||||||
|
],
|
||||||
|
"Hash": "21ec52af13afbcab1cb317567b639b0a"
|
||||||
|
},
|
||||||
"evaluate": {
|
"evaluate": {
|
||||||
"Package": "evaluate",
|
"Package": "evaluate",
|
||||||
"Version": "1.0.1",
|
"Version": "1.0.1",
|
||||||
|
@ -1141,6 +1322,25 @@
|
||||||
],
|
],
|
||||||
"Hash": "14b3b3b923944afb9542dbef4c68bf4b"
|
"Hash": "14b3b3b923944afb9542dbef4c68bf4b"
|
||||||
},
|
},
|
||||||
|
"ggmosaic": {
|
||||||
|
"Package": "ggmosaic",
|
||||||
|
"Version": "0.3.3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"dplyr",
|
||||||
|
"ggplot2",
|
||||||
|
"ggrepel",
|
||||||
|
"plotly",
|
||||||
|
"productplots",
|
||||||
|
"purrr",
|
||||||
|
"rlang",
|
||||||
|
"scales",
|
||||||
|
"tidyr"
|
||||||
|
],
|
||||||
|
"Hash": "9c716443a2b821aa997c5675386bd34b"
|
||||||
|
},
|
||||||
"ggplot2": {
|
"ggplot2": {
|
||||||
"Package": "ggplot2",
|
"Package": "ggplot2",
|
||||||
"Version": "3.5.1",
|
"Version": "3.5.1",
|
||||||
|
@ -1166,6 +1366,22 @@
|
||||||
],
|
],
|
||||||
"Hash": "44c6a2f8202d5b7e878ea274b1092426"
|
"Hash": "44c6a2f8202d5b7e878ea274b1092426"
|
||||||
},
|
},
|
||||||
|
"ggrepel": {
|
||||||
|
"Package": "ggrepel",
|
||||||
|
"Version": "0.9.6",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"Rcpp",
|
||||||
|
"ggplot2",
|
||||||
|
"grid",
|
||||||
|
"rlang",
|
||||||
|
"scales",
|
||||||
|
"withr"
|
||||||
|
],
|
||||||
|
"Hash": "3d4156850acc1161f2f24bc61c9217c1"
|
||||||
|
},
|
||||||
"glue": {
|
"glue": {
|
||||||
"Package": "glue",
|
"Package": "glue",
|
||||||
"Version": "1.8.0",
|
"Version": "1.8.0",
|
||||||
|
@ -1177,6 +1393,20 @@
|
||||||
],
|
],
|
||||||
"Hash": "5899f1eaa825580172bb56c08266f37c"
|
"Hash": "5899f1eaa825580172bb56c08266f37c"
|
||||||
},
|
},
|
||||||
|
"gridExtra": {
|
||||||
|
"Package": "gridExtra",
|
||||||
|
"Version": "2.3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"grDevices",
|
||||||
|
"graphics",
|
||||||
|
"grid",
|
||||||
|
"gtable",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "7d7f283939f563670a697165b2cf5560"
|
||||||
|
},
|
||||||
"gt": {
|
"gt": {
|
||||||
"Package": "gt",
|
"Package": "gt",
|
||||||
"Version": "0.11.1",
|
"Version": "0.11.1",
|
||||||
|
@ -1652,6 +1882,18 @@
|
||||||
],
|
],
|
||||||
"Hash": "110ee9d83b496279960e162ac97764ce"
|
"Hash": "110ee9d83b496279960e162ac97764ce"
|
||||||
},
|
},
|
||||||
|
"microbenchmark": {
|
||||||
|
"Package": "microbenchmark",
|
||||||
|
"Version": "1.5.0",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"graphics",
|
||||||
|
"stats"
|
||||||
|
],
|
||||||
|
"Hash": "f9d226d88d4087d817d4e616626ce8e5"
|
||||||
|
},
|
||||||
"mime": {
|
"mime": {
|
||||||
"Package": "mime",
|
"Package": "mime",
|
||||||
"Version": "0.12",
|
"Version": "0.12",
|
||||||
|
@ -1703,6 +1945,24 @@
|
||||||
],
|
],
|
||||||
"Hash": "f519814037d08eee1343c2e7b5992cc4"
|
"Hash": "f519814037d08eee1343c2e7b5992cc4"
|
||||||
},
|
},
|
||||||
|
"modelr": {
|
||||||
|
"Package": "modelr",
|
||||||
|
"Version": "0.1.11",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"broom",
|
||||||
|
"magrittr",
|
||||||
|
"purrr",
|
||||||
|
"rlang",
|
||||||
|
"tibble",
|
||||||
|
"tidyr",
|
||||||
|
"tidyselect",
|
||||||
|
"vctrs"
|
||||||
|
],
|
||||||
|
"Hash": "4f50122dc256b1b6996a4703fecea821"
|
||||||
|
},
|
||||||
"munsell": {
|
"munsell": {
|
||||||
"Package": "munsell",
|
"Package": "munsell",
|
||||||
"Version": "0.5.1",
|
"Version": "0.5.1",
|
||||||
|
@ -1714,6 +1974,17 @@
|
||||||
],
|
],
|
||||||
"Hash": "4fd8900853b746af55b81fda99da7695"
|
"Hash": "4fd8900853b746af55b81fda99da7695"
|
||||||
},
|
},
|
||||||
|
"mvtnorm": {
|
||||||
|
"Package": "mvtnorm",
|
||||||
|
"Version": "1.3-2",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"stats"
|
||||||
|
],
|
||||||
|
"Hash": "9e8405eacb262c0a939e121650247f4b"
|
||||||
|
},
|
||||||
"nlme": {
|
"nlme": {
|
||||||
"Package": "nlme",
|
"Package": "nlme",
|
||||||
"Version": "3.1-166",
|
"Version": "3.1-166",
|
||||||
|
@ -1735,6 +2006,28 @@
|
||||||
"Repository": "CRAN",
|
"Repository": "CRAN",
|
||||||
"Hash": "27550641889a3abf3aec4d91186311ec"
|
"Hash": "27550641889a3abf3aec4d91186311ec"
|
||||||
},
|
},
|
||||||
|
"nnet": {
|
||||||
|
"Package": "nnet",
|
||||||
|
"Version": "7.3-19",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"stats",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "2c797b46eea7fb58ede195bc0b1f1138"
|
||||||
|
},
|
||||||
|
"numDeriv": {
|
||||||
|
"Package": "numDeriv",
|
||||||
|
"Version": "2016.8-1.1",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "RSPM",
|
||||||
|
"Requirements": [
|
||||||
|
"R"
|
||||||
|
],
|
||||||
|
"Hash": "df58958f293b166e4ab885ebcad90e02"
|
||||||
|
},
|
||||||
"officer": {
|
"officer": {
|
||||||
"Package": "officer",
|
"Package": "officer",
|
||||||
"Version": "0.6.7",
|
"Version": "0.6.7",
|
||||||
|
@ -1838,6 +2131,24 @@
|
||||||
],
|
],
|
||||||
"Hash": "e23fb9ecb1258207bcb763d78d513439"
|
"Hash": "e23fb9ecb1258207bcb763d78d513439"
|
||||||
},
|
},
|
||||||
|
"pbkrtest": {
|
||||||
|
"Package": "pbkrtest",
|
||||||
|
"Version": "0.5.3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"MASS",
|
||||||
|
"Matrix",
|
||||||
|
"R",
|
||||||
|
"broom",
|
||||||
|
"doBy",
|
||||||
|
"dplyr",
|
||||||
|
"lme4",
|
||||||
|
"methods",
|
||||||
|
"numDeriv"
|
||||||
|
],
|
||||||
|
"Hash": "938e6bbc4ac57534f8b43224506a8966"
|
||||||
|
},
|
||||||
"pbmcapply": {
|
"pbmcapply": {
|
||||||
"Package": "pbmcapply",
|
"Package": "pbmcapply",
|
||||||
"Version": "1.5.1",
|
"Version": "1.5.1",
|
||||||
|
@ -1981,6 +2292,17 @@
|
||||||
],
|
],
|
||||||
"Hash": "0c90a7d71988856bad2a2a45dd871bb9"
|
"Hash": "0c90a7d71988856bad2a2a45dd871bb9"
|
||||||
},
|
},
|
||||||
|
"productplots": {
|
||||||
|
"Package": "productplots",
|
||||||
|
"Version": "0.1.1",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"ggplot2",
|
||||||
|
"plyr"
|
||||||
|
],
|
||||||
|
"Hash": "75630cc31052ba299a52bb1adbf59fae"
|
||||||
|
},
|
||||||
"progress": {
|
"progress": {
|
||||||
"Package": "progress",
|
"Package": "progress",
|
||||||
"Version": "1.2.3",
|
"Version": "1.2.3",
|
||||||
|
@ -2094,6 +2416,24 @@
|
||||||
],
|
],
|
||||||
"Hash": "a22b3777f51fd005a7cd4c2bccc385ae"
|
"Hash": "a22b3777f51fd005a7cd4c2bccc385ae"
|
||||||
},
|
},
|
||||||
|
"quantreg": {
|
||||||
|
"Package": "quantreg",
|
||||||
|
"Version": "5.99.1",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"MASS",
|
||||||
|
"Matrix",
|
||||||
|
"MatrixModels",
|
||||||
|
"R",
|
||||||
|
"SparseM",
|
||||||
|
"graphics",
|
||||||
|
"methods",
|
||||||
|
"stats",
|
||||||
|
"survival"
|
||||||
|
],
|
||||||
|
"Hash": "c48844cd7961de506a1b4d22b2e082c7"
|
||||||
|
},
|
||||||
"quarto": {
|
"quarto": {
|
||||||
"Package": "quarto",
|
"Package": "quarto",
|
||||||
"Version": "1.4.4",
|
"Version": "1.4.4",
|
||||||
|
@ -2484,6 +2824,22 @@
|
||||||
],
|
],
|
||||||
"Hash": "836c3464fb0f2ea865ed4c35dcdc1eda"
|
"Hash": "836c3464fb0f2ea865ed4c35dcdc1eda"
|
||||||
},
|
},
|
||||||
|
"shinyTree": {
|
||||||
|
"Package": "shinyTree",
|
||||||
|
"Version": "0.3.1",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"htmlwidgets",
|
||||||
|
"jsonlite",
|
||||||
|
"methods",
|
||||||
|
"promises",
|
||||||
|
"shiny",
|
||||||
|
"stringr"
|
||||||
|
],
|
||||||
|
"Hash": "0493a0d70f834cb251fe4523eb17b82c"
|
||||||
|
},
|
||||||
"shinyWidgets": {
|
"shinyWidgets": {
|
||||||
"Package": "shinyWidgets",
|
"Package": "shinyWidgets",
|
||||||
"Version": "0.8.7",
|
"Version": "0.8.7",
|
||||||
|
@ -2542,6 +2898,19 @@
|
||||||
],
|
],
|
||||||
"Hash": "802e4786b353a4bb27116957558548d5"
|
"Hash": "802e4786b353a4bb27116957558548d5"
|
||||||
},
|
},
|
||||||
|
"shinyvalidate": {
|
||||||
|
"Package": "shinyvalidate",
|
||||||
|
"Version": "0.1.3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"glue",
|
||||||
|
"htmltools",
|
||||||
|
"rlang",
|
||||||
|
"shiny"
|
||||||
|
],
|
||||||
|
"Hash": "fe6e75a1c1722b2d23cb4d4dbe1006df"
|
||||||
|
},
|
||||||
"sodium": {
|
"sodium": {
|
||||||
"Package": "sodium",
|
"Package": "sodium",
|
||||||
"Version": "1.4.0",
|
"Version": "1.4.0",
|
||||||
|
@ -2619,6 +2988,22 @@
|
||||||
],
|
],
|
||||||
"Hash": "93a2b1beac2437bdcc4724f8bf867e2c"
|
"Hash": "93a2b1beac2437bdcc4724f8bf867e2c"
|
||||||
},
|
},
|
||||||
|
"survival": {
|
||||||
|
"Package": "survival",
|
||||||
|
"Version": "3.8-3",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"Matrix",
|
||||||
|
"R",
|
||||||
|
"graphics",
|
||||||
|
"methods",
|
||||||
|
"splines",
|
||||||
|
"stats",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "fe42836742a4f065b3f3f5de81fccab9"
|
||||||
|
},
|
||||||
"sys": {
|
"sys": {
|
||||||
"Package": "sys",
|
"Package": "sys",
|
||||||
"Version": "3.4.3",
|
"Version": "3.4.3",
|
||||||
|
@ -2714,6 +3099,44 @@
|
||||||
],
|
],
|
||||||
"Hash": "b5d3366368999eb2262c2a646a1f0c87"
|
"Hash": "b5d3366368999eb2262c2a646a1f0c87"
|
||||||
},
|
},
|
||||||
|
"teal.modules.general": {
|
||||||
|
"Package": "teal.modules.general",
|
||||||
|
"Version": "0.3.0",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"DT",
|
||||||
|
"R",
|
||||||
|
"checkmate",
|
||||||
|
"dplyr",
|
||||||
|
"forcats",
|
||||||
|
"ggmosaic",
|
||||||
|
"ggplot2",
|
||||||
|
"grid",
|
||||||
|
"logger",
|
||||||
|
"scales",
|
||||||
|
"shiny",
|
||||||
|
"shinyTree",
|
||||||
|
"shinyWidgets",
|
||||||
|
"shinyjs",
|
||||||
|
"shinyvalidate",
|
||||||
|
"stats",
|
||||||
|
"stringr",
|
||||||
|
"teal",
|
||||||
|
"teal.code",
|
||||||
|
"teal.data",
|
||||||
|
"teal.logger",
|
||||||
|
"teal.reporter",
|
||||||
|
"teal.transform",
|
||||||
|
"teal.widgets",
|
||||||
|
"tern",
|
||||||
|
"tibble",
|
||||||
|
"tidyr",
|
||||||
|
"tools",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "f54d7bc27cd048cec3a842f980c74e9b"
|
||||||
|
},
|
||||||
"teal.reporter": {
|
"teal.reporter": {
|
||||||
"Package": "teal.reporter",
|
"Package": "teal.reporter",
|
||||||
"Version": "0.3.1",
|
"Version": "0.3.1",
|
||||||
|
@ -2766,6 +3189,31 @@
|
||||||
],
|
],
|
||||||
"Hash": "a29de94bc89bad9a12a914c17e8269f1"
|
"Hash": "a29de94bc89bad9a12a914c17e8269f1"
|
||||||
},
|
},
|
||||||
|
"teal.transform": {
|
||||||
|
"Package": "teal.transform",
|
||||||
|
"Version": "0.5.0",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"R",
|
||||||
|
"checkmate",
|
||||||
|
"dplyr",
|
||||||
|
"lifecycle",
|
||||||
|
"logger",
|
||||||
|
"methods",
|
||||||
|
"rlang",
|
||||||
|
"shiny",
|
||||||
|
"shinyjs",
|
||||||
|
"shinyvalidate",
|
||||||
|
"stats",
|
||||||
|
"teal.data",
|
||||||
|
"teal.logger",
|
||||||
|
"teal.widgets",
|
||||||
|
"tidyr",
|
||||||
|
"tidyselect"
|
||||||
|
],
|
||||||
|
"Hash": "988a30f3f0f20b2633b41103a8eb4e56"
|
||||||
|
},
|
||||||
"teal.widgets": {
|
"teal.widgets": {
|
||||||
"Package": "teal.widgets",
|
"Package": "teal.widgets",
|
||||||
"Version": "0.4.2",
|
"Version": "0.4.2",
|
||||||
|
@ -2789,6 +3237,42 @@
|
||||||
],
|
],
|
||||||
"Hash": "46a99bbdcd97f8f25070ad23c3b23ad9"
|
"Hash": "46a99bbdcd97f8f25070ad23c3b23ad9"
|
||||||
},
|
},
|
||||||
|
"tern": {
|
||||||
|
"Package": "tern",
|
||||||
|
"Version": "0.9.6",
|
||||||
|
"Source": "Repository",
|
||||||
|
"Repository": "CRAN",
|
||||||
|
"Requirements": [
|
||||||
|
"MASS",
|
||||||
|
"R",
|
||||||
|
"Rdpack",
|
||||||
|
"broom",
|
||||||
|
"car",
|
||||||
|
"checkmate",
|
||||||
|
"cowplot",
|
||||||
|
"dplyr",
|
||||||
|
"emmeans",
|
||||||
|
"forcats",
|
||||||
|
"formatters",
|
||||||
|
"ggplot2",
|
||||||
|
"grid",
|
||||||
|
"gridExtra",
|
||||||
|
"gtable",
|
||||||
|
"labeling",
|
||||||
|
"lifecycle",
|
||||||
|
"magrittr",
|
||||||
|
"methods",
|
||||||
|
"rlang",
|
||||||
|
"rtables",
|
||||||
|
"scales",
|
||||||
|
"stats",
|
||||||
|
"survival",
|
||||||
|
"tibble",
|
||||||
|
"tidyr",
|
||||||
|
"utils"
|
||||||
|
],
|
||||||
|
"Hash": "35fe86bc358b15525217e775f5318d33"
|
||||||
|
},
|
||||||
"textshaping": {
|
"textshaping": {
|
||||||
"Package": "textshaping",
|
"Package": "textshaping",
|
||||||
"Version": "0.4.1",
|
"Version": "0.4.1",
|
||||||
|
|
Loading…
Add table
Reference in a new issue