Skip to content

Commit 46b8660

Browse files
committed
Merge branch 'master' into gh-pages
2 parents 396f066 + 16b39fe commit 46b8660

31 files changed

Lines changed: 1724 additions & 139 deletions

.Rbuildignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,3 +18,4 @@ tests/figs/*
1818
^docs$
1919
^_pkgdown\.yml$
2020
^\.github$
21+
^release-prep\.R$

.github/workflows/recheck.yaml

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
on:
2+
workflow_dispatch:
3+
inputs:
4+
which:
5+
type: choice
6+
description: Which dependents to check
7+
options:
8+
- strong
9+
- most
10+
11+
name: Reverse dependency check
12+
13+
jobs:
14+
revdep_check:
15+
name: Reverse check ${{ inputs.which }} dependents
16+
uses: r-devel/recheck/.github/workflows/recheck.yml@v1
17+
with:
18+
which: ${{ inputs.which }}
19+
subdirectory: '' # set if your R package is in a subdir of the git repo
20+
repository: '' # set to recheck an R package from another git repo
21+
ref: '' # set to recheck a custom tag/branch from another repo

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,4 @@ cran-comments.md
1212
revdep/*
1313
CRAN-RELEASE
1414
CRAN-SUBMISSION
15+
release-prep.R

DESCRIPTION

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
Package: bayesplot
22
Type: Package
33
Title: Plotting for Bayesian Models
4-
Version: 1.12.0
5-
Date: 2025-04-09
4+
Version: 1.13.0
5+
Date: 2025-06-18
66
Authors@R: c(person("Jonah", "Gabry", role = c("aut", "cre"), email = "jsg2201@columbia.edu"),
77
person("Tristan", "Mahr", role = "aut"),
88
person("Paul-Christian", "Bürkner", role = "ctb"),

NAMESPACE

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -144,6 +144,7 @@ export(ppc_km_overlay_grouped)
144144
export(ppc_loo_intervals)
145145
export(ppc_loo_pit)
146146
export(ppc_loo_pit_data)
147+
export(ppc_loo_pit_ecdf)
147148
export(ppc_loo_pit_overlay)
148149
export(ppc_loo_pit_qq)
149150
export(ppc_loo_ribbon)

NEWS.md

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,12 @@
1+
# bayesplot 1.13.0
2+
3+
* Add `ppc_loo_pit_ecdf()` by @TeemuSailynoja (#345)
4+
* Add possibility for left-truncation to `ppc_km_overlay()` and `ppc_km_overlay_grouped()` by @Sakuski (#347)
5+
* Give user control over extrapolation in `ppc_km_overlay()` and `ppc_km_overlay_grouped()` by @Sakuski (#353)
6+
* Allow passing `moment_match` via `...` for loo functions by @n-kall (#351)
7+
* Skip some tests when missing Suggests by @MichaelChirico (#344)
8+
* Remove a test that will fail with next ggplot2 release (#356)
9+
110
# bayesplot 1.12.0
211

312
* Expand checking workflows to more platforms by @andrjohns (#324)

R/mcmc-distributions.R

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -472,7 +472,7 @@ mcmc_violin <- function(
472472
}
473473
}
474474

475-
geom_args <- list(size = 0.5, na.rm = TRUE, alpha = alpha)
475+
geom_args <- list(linewidth = 0.5, na.rm = TRUE, alpha = alpha)
476476
if (violin) {
477477
geom_args[["draw_quantiles"]] <- probs
478478
} else {

R/ppc-censoring.R

Lines changed: 77 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -24,11 +24,12 @@
2424
#' @section Plot Descriptions:
2525
#' \describe{
2626
#' \item{`ppc_km_overlay()`}{
27-
#' Empirical CCDF estimates of each dataset (row) in `yrep` are overlaid,
28-
#' with the Kaplan-Meier estimate (Kaplan and Meier, 1958) for `y` itself on
29-
#' top (and in a darker shade). This is a PPC suitable for right-censored
30-
#' `y`. Note that the replicated data from `yrep` is assumed to be
31-
#' uncensored.
27+
#' Empirical CCDF estimates of each dataset (row) in `yrep` are overlaid, with
28+
#' the Kaplan-Meier estimate (Kaplan and Meier, 1958) for `y` itself on top
29+
#' (and in a darker shade). This is a PPC suitable for right-censored `y`.
30+
#' Note that the replicated data from `yrep` is assumed to be uncensored. Left
31+
#' truncation (delayed entry) times for `y` can be specified using
32+
#' `left_truncation_y`.
3233
#' }
3334
#' \item{`ppc_km_overlay_grouped()`}{
3435
#' The same as `ppc_km_overlay()`, but with separate facets by `group`.
@@ -40,23 +41,43 @@
4041
#' @template reference-km
4142
#'
4243
#' @examples
44+
#' \donttest{
4345
#' color_scheme_set("brightblue")
44-
#' y <- example_y_data()
46+
#'
4547
#' # For illustrative purposes, (right-)censor values y > 110:
48+
#' y <- example_y_data()
4649
#' status_y <- as.numeric(y <= 110)
4750
#' y <- pmin(y, 110)
51+
#'
4852
#' # In reality, the replicated data (yrep) would be obtained from a
4953
#' # model which takes the censoring of y properly into account. Here,
5054
#' # for illustrative purposes, we simply use example_yrep_draws():
5155
#' yrep <- example_yrep_draws()
5256
#' dim(yrep)
53-
#' \donttest{
57+
#'
58+
#' # Overlay 25 curves
5459
#' ppc_km_overlay(y, yrep[1:25, ], status_y = status_y)
55-
#' }
60+
#'
61+
#' # With extrapolation_factor = 1 (no extrapolation)
62+
#' ppc_km_overlay(y, yrep[1:25, ], status_y = status_y, extrapolation_factor = 1)
63+
#'
64+
#' # With extrapolation_factor = Inf (show all posterior predictive draws)
65+
#' ppc_km_overlay(y, yrep[1:25, ], status_y = status_y, extrapolation_factor = Inf)
66+
#'
5667
#' # With separate facets by group:
5768
#' group <- example_group_data()
58-
#' \donttest{
5969
#' ppc_km_overlay_grouped(y, yrep[1:25, ], group = group, status_y = status_y)
70+
#'
71+
#' # With left-truncation (delayed entry) times:
72+
#' min_vals <- pmin(y, apply(yrep, 2, min))
73+
#' left_truncation_y <- rep(0, length(y))
74+
#' condition <- y > mean(y) / 2
75+
#' left_truncation_y[condition] <- pmin(
76+
#' runif(sum(condition), min = 0.6, max = 0.99) * y[condition],
77+
#' min_vals[condition] - 0.001
78+
#' )
79+
#' ppc_km_overlay(y, yrep[1:25, ], status_y = status_y,
80+
#' left_truncation_y = left_truncation_y)
6081
#' }
6182
NULL
6283

@@ -65,11 +86,24 @@ NULL
6586
#' @param status_y The status indicator for the observations from `y`. This must
6687
#' be a numeric vector of the same length as `y` with values in \{0, 1\} (0 =
6788
#' right censored, 1 = event).
89+
#' @param left_truncation_y Optional parameter that specifies left-truncation
90+
#' (delayed entry) times for the observations from `y`. This must be a numeric
91+
#' vector of the same length as `y`. If `NULL` (default), no left-truncation
92+
#' is assumed.
93+
#' @param extrapolation_factor A numeric value (>=1) that controls how far the
94+
#' plot is extended beyond the largest observed value in `y`. The default
95+
#' value is 1.2, which corresponds to 20 % extrapolation. Note that all
96+
#' posterior predictive draws may not be shown by default because of the
97+
#' controlled extrapolation. To display all posterior predictive draws, set
98+
#' `extrapolation_factor = Inf`.
99+
#'
68100
ppc_km_overlay <- function(
69101
y,
70102
yrep,
71103
...,
72104
status_y,
105+
left_truncation_y = NULL,
106+
extrapolation_factor = 1.2,
73107
size = 0.25,
74108
alpha = 0.7
75109
) {
@@ -79,8 +113,25 @@ ppc_km_overlay <- function(
79113
suggested_package("survival")
80114
suggested_package("ggfortify")
81115

82-
stopifnot(is.numeric(status_y))
83-
stopifnot(all(status_y %in% c(0, 1)))
116+
if (!is.numeric(status_y) || length(status_y) != length(y) || !all(status_y %in% c(0, 1))) {
117+
stop("`status_y` must be a numeric vector of 0s and 1s the same length as `y`.", call. = FALSE)
118+
}
119+
120+
if (!is.null(left_truncation_y)) {
121+
if (!is.numeric(left_truncation_y) || length(left_truncation_y) != length(y)) {
122+
stop("`left_truncation_y` must be a numeric vector of the same length as `y`.", call. = FALSE)
123+
}
124+
}
125+
126+
if (extrapolation_factor < 1) {
127+
stop("`extrapolation_factor` must be greater than or equal to 1.", call. = FALSE)
128+
}
129+
if (extrapolation_factor == 1.2) {
130+
message(
131+
"Note: `extrapolation_factor` now defaults to 1.2 (20%).\n",
132+
"To display all posterior predictive draws, set `extrapolation_factor = Inf`."
133+
)
134+
}
84135

85136
data <- ppc_data(y, yrep, group = status_y)
86137

@@ -96,7 +147,12 @@ ppc_km_overlay <- function(
96147
as.numeric(as.character(.data$group)),
97148
1))
98149

99-
sf_form <- survival::Surv(value, group) ~ rep_label
150+
if (is.null(left_truncation_y)) {
151+
sf_form <- survival::Surv(time = data$value, event = data$group) ~ rep_label
152+
} else {
153+
sf_form <- survival::Surv(time = left_truncation_y[data$y_id], time2 = data$value, event = data$group) ~ rep_label
154+
}
155+
100156
if (!is.null(add_group)) {
101157
data <- dplyr::inner_join(data,
102158
tibble::tibble(y_id = seq_along(y),
@@ -120,6 +176,10 @@ ppc_km_overlay <- function(
120176
fsf$is_y_size <- ifelse(fsf$is_y_color == "yrep", size, 1)
121177
fsf$is_y_alpha <- ifelse(fsf$is_y_color == "yrep", alpha, 1)
122178

179+
max_time_y <- max(y, na.rm = TRUE)
180+
fsf <- fsf %>%
181+
dplyr::filter(.data$is_y_color != "yrep" | .data$time <= max_time_y * extrapolation_factor)
182+
123183
# Ensure that the observed data gets plotted last by reordering the
124184
# levels of the factor "strata"
125185
fsf$strata <- factor(fsf$strata, levels = rev(levels(fsf$strata)))
@@ -164,6 +224,8 @@ ppc_km_overlay_grouped <- function(
164224
group,
165225
...,
166226
status_y,
227+
left_truncation_y = NULL,
228+
extrapolation_factor = 1.2,
167229
size = 0.25,
168230
alpha = 0.7
169231
) {
@@ -175,8 +237,10 @@ ppc_km_overlay_grouped <- function(
175237
add_group = group,
176238
...,
177239
status_y = status_y,
240+
left_truncation_y = left_truncation_y,
178241
size = size,
179-
alpha = alpha
242+
alpha = alpha,
243+
extrapolation_factor = extrapolation_factor
180244
)
181245

182246
p_overlay +

0 commit comments

Comments
 (0)