The goal of riskcalc
is to accelerate building
shiny
-based risk
calculators for https://riskcalc.org/. It enables you to export an
executable application template into a directory containing the
pre-populated R
scripts to run your app using the standard formatting.
You can get a blank template to start from scratch, or provide model
objects to the call to populate inputs/outputs for you. From there, you
can make the necessary tweaks to complete your application.
You can install the development version of riskcalc
from
GitHub with:
# install.packages("devtools")
devtools::install_github("ClevelandClinicQHS/riskcalc")
Here we’ll go through a couple examples. First, load the package.
# Load the package
library(riskcalc)
The risk_calulator
function by default will export a blank application
template to your working directory with a default name. You can
optionally specify the location to place the app, as well as its name.
risk_calculator(
app_directory = "/PATH_TO_FOLDER",
app_name = "BlankRiskCalculator"
)
Execution of the above code will create a new directory in
/PATH_TO_FOLDER/BlankRiskCalculator
with the following contents:
global.R
: Objects to load/execute when the app is launchedui.R
: Default interface to the applicationserver.R
: App server with dormant functionality (though the code templates are present)
In RStudio, we can then open (one of) these files and click Run App
,
as it is a functioning shiny
application. It looks like this:
It provides the default app themes and information panels, as well as
creates the necessary source code link for when the R
code gets pushed
to the website’s GitHub
repository. The
ui.R
and server.R
files have various placeholders for you to go in
and add titles, variable inputs, etc., as needed.
You can also provide a glm
or coxph
object to the risk_calculator
function call to get the scripts for a functioning risk calculator with
all of the inputs and prediction calculation setup for you, along with
other arguments for various formatting preferences. We’ll go through an
example of a creating an application that mimics the appearance and
functionality of the bladder cancer
app:
# Load packages
library(riskcalc)
library(survival)
# Build the model
mod <-
coxph(
formula = Surv(Time, Recurrence) ~ .,
data = bladderCancer
)
mod |>
# Build the risk calculator
risk_calculator(
time = 5, # Produce 5-year survival probabilities
app_directory = "/PATH_TO_FOLDER",
app_name = "bladderCancer",
title = "Predicting 5-Year Recurrence-Free Survival after Radical Cystectomy for Bladder Cancer",
citation =
htmltools::HTML("<p>[1] International Bladder Cancer Nomogram Consortium, Bochner BH, Kattan MW, Vora KC.
<a href = 'http://jco.ascopubs.org/content/24/24/3967.full.pdf'> Postoperative nomogram predicting risk of recurrence after radical cystectomy for bladder cancer</a>
. J Clin Oncol. 2006 Aug 20;24(24):3967-72. Epub 2006 Jul 24. Erratum in: J Clin Oncol. 2007 Apr 10;25(11):1457</p>"),
label = "Percentage of 5-Year Recurrence-Free Survival",
value_header = "Probability",
format = function(x) paste0(round(100 * x), "%"),
labels =
c(
Age = "Age (Years)",
RCTumorPathology = "RC Tumor Pathology",
RCTumorHistology = "RC Tumor Histology",
RCTumorGrade = "RC Tumor Grade",
LymphNodeStatus = "LymphNodeStatus",
DaysBetweenDXRC = "Days Between Dx and RC (Days)"
),
levels =
list(
Gender =
c(
M = "Male",
`F` = "Female"
)
),
placeholders = c(Age = "20-100")
)
This creates a new directory in /PATH_TO_FOLDER/bladderCancer
with the
following contents:
global.R
: Objects to load/execute when the app is launched, including loading thecoxph
model object, the function to generate the prediction, the time point of interest, and the function for formatting the final result in the table.ui.R
: Interface to the application including the title, predictor inputs (with formatted labels), citation information, etc.server.R
: Application server that validates inputs, creates the input data frame from the current selections, and produces the result output table.model.RData
: Thecoxph
object that was passed to the function call, used for generating predictions.
In RStudio, we can then open (one of) these .R
files and click
Run App
, as it is a functioning shiny
application. It looks like
this after the inputs are entered and the “Run Calculator” button is
pressed:
Some notes on select arguments:
app_name
: We use short-hand names for applications in their URL at riskcalc.org (e.g., https://riskcalc.org/bladderCancer/). The source code for applications were added to our QHS GitHub page. Part of that was to add source code links back to GitHub within the apps themselves. So when this argument is used, it will automatically add the source code link to the assumed spot that it would be on GitHub (see bottom-right of screenshot above).citation
: This is where applications typically display the source publication for the risk calculator. It could just be a simple character string, but in this case, HTML code was supplied to add text that contains a hyperlink to the publication.format
: This is a transformation that can be applied to the default result value for preferred display. For acoxph
object, by default, the survival probability (which is what we want) is computed at the specifiedtime
point (in this case, 5-years), but we added some rounding and tacked on a%
symbol. For aglm
object, the default output is the predicted value wheretype = "response"
(see?predict.glm
)placeholders
: Adds restrictions for what values can be entered into the numeric predictor inputs. It adds the background text so the user can see the range, but it also enforces this restriction with theshiny::validate
function.