A lightweight Shiny input wrapper around modist: draggable probability distributions that behave like regular Shiny inputs.
shinymodist keeps the default presentation compact and low-noise, while retaining an opt-in style = "modist" mode close to the upstream experience.
Motivation
modist makes probability distributions directly manipulable. shinymodist turns that interaction into a regular Shiny input, so a distribution can become part of the application’s state rather than just a plot.
Bayesian prior elicitation is a natural example: changing an assumption should feel as direct as moving the distribution itself. Here we use two shinymodist inputs for a Normal model with unknown mean and variance:
\[ y_i \mid \mu, \sigma^2 \sim \mathcal{N}(\mu, \sigma^2) \]
\[ \mu \sim \mathcal{N}(m_0, s_0^2), \qquad \sigma^2 \sim \operatorname{InverseGamma}(\alpha_0, \beta_0) \]
After observing data, Bayes’ rule combines the likelihood and both priors:
\[ p(\mu, \sigma^2 \mid y) \propto p(y \mid \mu, \sigma^2)\, p(\mu)\, p(\sigma^2). \]
Drag either prior below, then reveal more real observations from mtcars$mpg. The two panels show how each marginal posterior moves away from — or stays close to — the prior. The posterior is evaluated on a small deterministic grid, keeping the example dependency-free and easy to inspect.
Install
pak::pak("jbkunst/shinymodist")Basic use
library(shiny)
library(shinymodist)
ui <- bslib::page_sidebar(
title = "Basic shinymodist input",
sidebar = bslib::sidebar(
modist_input(
"dist",
family = "normal",
value = list(mu = 0, sigma = 1)
)
),
bslib::card(
bslib::card_header("Reactive value"),
verbatimTextOutput("value")
)
)
server <- function(input, output, session) {
output$value <- renderPrint(input$dist)
}
shinyApp(ui, server)The input returns the distribution family and its canonical parameters:
list(
family = "normal",
mu = 0,
sigma = 1
)A fixed visible scale can be supplied when comparisons need a common domain:
modist_input(
"scores",
family = "normal",
value = list(mu = 1, sigma = 1),
domain = c(-5, 5)
)Server-side updates use update_modist_input().
Styles and bslib
The default style = "minimal" is intentionally quiet: no grid or toolbar, and its visual accents inherit --bs-primary when used inside a bslib theme.
bslib::page_fluid(
theme = bslib::bs_theme(primary = "#6f42c1"),
modist_input("dist")
)Use style = "modist" to keep the original modist appearance and controls.
The input is responsive by default. A fixed CSS height is available only when the surrounding layout needs it:
modist_input("dist", height = "180px")The default height = NULL keeps the current aspect-ratio behavior.
Live demos
The pkgdown site exports the package examples with Shinylive, so they run entirely in the browser with webR:
The live examples run entirely in the browser with Shinylive and webR.
Distribution families
The wrapper exposes all distribution families bundled by modist:
- Normal, Beta, Gamma and Student t
- Exponential, Half Normal and Log Normal
- Cauchy, Laplace and Logistic
- Weibull, Half Student t and Chi-squared
- Inverse Gamma and Kumaraswamy
All families use the same modist_input() API. See the distribution gallery for a compact fillable grid of every supported family.
WebAssembly and Shinylive
The examples can run entirely in the browser with Shinylive and webR. WebAssembly compatibility is checked in CI and supported in package releases.
Credits
shinymodist wraps the JavaScript distribution widgets from William Dean’s modist, distributed under the MIT License.
The compact Shiny-input philosophy is also inspired by Carson Sievert’s histoslider.