(v3.1.0.9019) Fix the data labels of labels_sir_count() being placed on the wrong bars with position = "dodge" or "stack"

This commit is contained in:
dr. M.S. (Matthijs) Berends committed 2026-11-09 21:52:40 +01:00
1 parent 77b6cb1713
commit 054066b855
6 files changed
+37 -5

No files matched your search

+1 -1
View File
@@ -1,5 +1,5 @@
Package: AMR
Version: 3.1.0.9018
Version: 3.1.0.9019
Date: 2026-11-09
Title: Antimicrobial Resistance Data Analysis
Description: Functions to simplify and standardise antimicrobial resistance (AMR)
+3 -1
View File
@@ -1,4 +1,4 @@
# AMR 3.1.0.9018
# AMR 3.1.0.9019
This version fixes a critical bug in WISCA that biased all coverage estimates of `wisca()` and `antibiogram(..., wisca = TRUE)` downwards since AMR 3.0.0. Users are strongly advised to re-run their WISCA analyses.
@@ -19,6 +19,8 @@ This version fixes a critical bug in WISCA that biased all coverage estimates of
* Fixed punctuation being italicised along with taxonomic names, e.g., `"(S. aureus)"` now gives `"(*S. aureus*)"` instead of `"(S. *aureus)*"`
* `NA` values now return `NA` instead of `"NA"`
* Taxonomic names are now looked up once per session, making the function considerably faster for long vectors
* `labels_sir_count()` and `ggplot_sir()`
* Fixed the data labels being placed on the wrong bars with `position = "dodge"` or `position = "stack"`. They are now grouped like the bars, using the new `fill` argument of `labels_sir_count()`, which `ggplot_sir()` sets automatically
* `ggplot_pca()`
* Fixed an error when setting `groups` together with `labels`, and setting `groups` without `labels` now colours the points by these groups instead of using them as labels, as documented
* WISCA (`wisca()` and `antibiogram(..., wisca = TRUE)`)
+2 -1
View File
@@ -33,7 +33,7 @@
#' @param data A [data.frame] with column(s) of class [`sir`] (see [as.sir()]).
#' @param position Position adjustment of bars, either `"fill"`, `"stack"` or `"dodge"`.
#' @param x Variable to show on x axis, either `"antibiotic"` (default) or `"interpretation"` or a grouping variable.
#' @param fill Variable to categorise using the plots legend, either `"antibiotic"` (default) or `"interpretation"` or a grouping variable.
#' @param fill Variable to categorise using the plots legend, either `"interpretation"` (default) or `"antibiotic"` or a grouping variable. For [labels_sir_count()], this must be the same as the `fill` of [geom_sir()], so that the labels are placed on the right bars.
#' @param breaks A [numeric] vector of positions.
#' @param limits A [numeric] vector of length two providing limits of the scale, use `NA` to refer to the existing minimum or maximum.
#' @param facet Variable to split plots by, either `"interpretation"` (default) or `"antibiotic"` or a grouping variable.
@@ -261,6 +261,7 @@ ggplot_sir <- function(data,
p <- p + labels_sir_count(
position = position,
x = x,
fill = fill,
translate_ab = translate_ab,
minimum = minimum,
language = language,
+14 -1
View File
@@ -1454,6 +1454,7 @@ labeller_taxonomy <- structure(
#' @export
labels_sir_count <- function(position = NULL,
x = "antibiotic",
fill = "interpretation",
translate_ab = "name",
minimum = 30,
language = get_AMR_locale(),
@@ -1464,6 +1465,7 @@ labels_sir_count <- function(position = NULL,
stop_ifnot_installed("ggplot2")
meet_criteria(position, allow_class = "character", has_length = 1, is_in = c("fill", "stack", "dodge"), allow_NULL = TRUE)
meet_criteria(x, allow_class = "character", has_length = 1)
meet_criteria(fill, allow_class = "character", has_length = 1)
meet_criteria(translate_ab, allow_class = c("character", "logical"), has_length = 1, allow_NA = TRUE)
meet_criteria(minimum, allow_class = c("numeric", "integer"), has_length = 1, is_positive_or_zero = TRUE, is_finite = TRUE)
language <- validate_language(language)
@@ -1474,18 +1476,29 @@ labels_sir_count <- function(position = NULL,
if (is.null(position)) {
position <- "fill"
}
# labels are grouped like the bars of geom_sir(), so that they are placed on the right bar
vjust <- 0.5
if (identical(position, "fill")) {
# centred in the bar segments
position <- ggplot2::position_fill(vjust = 0.5, reverse = TRUE)
} else if (identical(position, "stack")) {
# centred in the bar segments
position <- ggplot2::position_stack(vjust = 0.5)
} else if (identical(position, "dodge")) {
# on top of the bars, with the default width of geom_col()
position <- ggplot2::position_dodge(width = 0.9)
vjust <- -0.5
}
x_name <- x
ggplot2::geom_text(
mapping = utils::modifyList(ggplot2::aes(), list(label = str2lang("lbl"), x = str2lang(x), y = str2lang("value"))),
mapping = utils::modifyList(ggplot2::aes(), list(label = str2lang("lbl"), x = str2lang(x), y = str2lang("value"), group = str2lang(fill))),
position = position,
inherit.aes = FALSE,
size = datalabels.size,
colour = datalabels.colour,
lineheight = 0.75,
vjust = vjust,
data = function(x) {
transformed <- sir_df(
data = x,
+2 -1
View File
@@ -48,6 +48,7 @@ geom_sir(
labels_sir_count(
position = NULL,
x = "antibiotic",
fill = "interpretation",
translate_ab = "name",
minimum = 30,
language = get_AMR_locale(),
@@ -64,7 +65,7 @@ labels_sir_count(
\item{x}{Variable to show on x axis, either \code{"antibiotic"} (default) or \code{"interpretation"} or a grouping variable.}
\item{fill}{Variable to categorise using the plots legend, either \code{"antibiotic"} (default) or \code{"interpretation"} or a grouping variable.}
\item{fill}{Variable to categorise using the plots legend, either \code{"interpretation"} (default) or \code{"antibiotic"} or a grouping variable. For \code{\link[=labels_sir_count]{labels_sir_count()}}, this must be the same as the \code{fill} of \code{\link[=geom_sir]{geom_sir()}}, so that the labels are placed on the right bars.}
\item{facet}{Variable to split plots by, either \code{"interpretation"} (default) or \code{"antibiotic"} or a grouping variable.}
+15
View File
@@ -160,5 +160,20 @@ test_that("test-ggplot_sir.R", {
scale_sir_colours(aesthetics = "fill", Value4 = "S", Value5 = "I", Value6 = "R"))$data),
"data.frame"
)
# datalabels are placed on their own bar, also when dodged or stacked
for (pos in c("fill", "stack", "dodge")) {
built <- ggplot_build(ggplot_sir(example_isolates[, c("AMX", "CIP")], position = pos, guideline = NULL))
bars <- built$data[[1]]
labels <- built$data[[2]]
bars <- bars[order(bars$x, bars$group), , drop = FALSE]
labels <- labels[order(labels$x, labels$group), , drop = FALSE]
expect_equal(labels$x, bars$x)
if (pos == "dodge") {
expect_equal(labels$y, bars$ymax)
} else {
expect_equal(labels$y, (bars$ymin + bars$ymax) / 2)
}
}
}
})