From 797602bd0a45d630c638f71bccdc132baea41168 Mon Sep 17 00:00:00 2001 From: Grant McDermott Date: Wed, 17 Jun 2026 09:27:16 -0700 Subject: [PATCH 1/2] fix #627 --- R/tinytheme.R | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/R/tinytheme.R b/R/tinytheme.R index 556a8230..13426246 100644 --- a/R/tinytheme.R +++ b/R/tinytheme.R @@ -240,6 +240,14 @@ tinytheme = function( settings[[n]] = dots[[n]] } + # `col.default` < 0 gotcha for user-supplied palettes.(#627) + if ("palette.qualitative" %in% names(dots) && + !("col.default" %in% names(dots)) && + is.numeric(settings[["col.default"]]) && + settings[["col.default"]] < 0L) { + settings[["col.default"]] = abs(settings[["col.default"]]) + } + # Compute mgp from spacing primitives when dynmar is active and the user # didn't provide an explicit mgp override. The near edge of margin text # (facing the plot region) aligns with the half-cell boundary (0.5*cex from From 0bc59d90bff1109f8177c95712096a4fb683fe1c Mon Sep 17 00:00:00 2001 From: Grant McDermott Date: Wed, 17 Jun 2026 09:27:21 -0700 Subject: [PATCH 2/2] test --- inst/tinytest/test-tinytheme.R | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/inst/tinytest/test-tinytheme.R b/inst/tinytest/test-tinytheme.R index 7c6491e0..26d87bb7 100644 --- a/inst/tinytest/test-tinytheme.R +++ b/inst/tinytest/test-tinytheme.R @@ -238,3 +238,14 @@ f = function () { theme = list("clean", palette.qualitative = pal, pch = 21)) } expect_snapshot_plot(f, label = "tinytheme_ephemeral_palette_function_qualitative") + + +# User palette override should not be trimmed by a theme's negative +# col.default (e.g. bw's -1), which would silently recycle colours. (#627) +f = function() { + plt( + Sepal.Length ~ Petal.Length | Species, iris, + theme = list("bw", palette.qualitative = c("red", "blue", "green")) + ) +} +expect_silent(f())