Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 5 additions & 2 deletions R/facet.R
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ draw_facet_window = function(
sub,
cap,
type,
type_axes_hints = NULL,
xlab,
x, xmax, xmin,
ylab,
Expand Down Expand Up @@ -188,7 +189,8 @@ draw_facet_window = function(
}
}

if (type == "spineplot") omar[4] = 2.1 # FIXME catch for spineplot RHS axis labs
# reserve RHS margin for types with a secondary axis (e.g. spineplot)
if (isTRUE(type_axes_hints[["rhs_axis"]])) omar[4] = 2.1

# FIXME: Is this causing issues for lhs legends with facet_grid?
# catch for missing rhs legend
Expand Down Expand Up @@ -227,7 +229,8 @@ draw_facet_window = function(
# Tick-label *width/height* (whtsbp) is added further below.
side.sub = get_tpar("side.sub", tpar_list = tpars, default = 3)
omar = dynmar_computed
if (type == "spineplot") omar[4] = 2.1 # FIXME catch for spineplot RHS axis labs
# reserve RHS margin for types with a secondary axis (e.g. spineplot)
if (isTRUE(type_axes_hints[["rhs_axis"]])) omar[4] = 2.1
if (par("las") %in% 1:2) {
# extra whitespace bump on the y axis
## overrides for ridge and some types that use integer spacing with (named) axis labels ## FXIME
Expand Down
14 changes: 11 additions & 3 deletions R/legend.R
Original file line number Diff line number Diff line change
Expand Up @@ -82,8 +82,9 @@ legend_outer_margins = function(legend_env, apply = TRUE) {

# Step 1: Prepare margins before measuring
if (legend_env$outer_side) {
# Extra bump for spineplot if outer_right legend (to accommodate secondary y-axis)
if (identical(legend_env$type, "spineplot")) {
# Extra bump for types with a secondary (RHS) axis when an outer legend is
# present, to accommodate that axis (e.g. spineplot).
if (isTRUE(legend_env$type_axes_hints[["rhs_axis"]])) {
lmar[1] = lmar[1] + 1.1
}

Expand Down Expand Up @@ -600,7 +601,7 @@ build_legend_args = function(
}

# Special pt.bg handling for types that need color-based fills
if (identical(type, "spineplot")) {
if (isTRUE(legend_env[["type_axes_hints"]][["legend_fill_from_col"]])) {
legend_args[["pt.bg"]] = legend_args[["pt.bg"]] %||% legend_args[["col"]]
} else if (identical(type, "ridge") && isFALSE(gradient)) {
legend_args[["pt.bg"]] = legend_args[["pt.bg"]] %||% sapply(legend_args[["col"]], function(ccol) seq_palette(ccol, n = 2)[2])
Expand Down Expand Up @@ -739,6 +740,7 @@ build_legend_env = function(

# Visual aesthetics
type,
type_axes_hints = NULL,
pch,
lty,
lwd,
Expand All @@ -761,6 +763,7 @@ build_legend_env = function(
# Initialize metadata
legend_env$gradient = gradient
legend_env$type = type
legend_env$type_axes_hints = type_axes_hints
legend_env$has_sub = has_sub
legend_env$has_cap = has_cap
legend_env$cap_text = cap_text
Expand Down Expand Up @@ -821,6 +824,9 @@ build_legend_env = function(
#' @param labeller Character or function for formatting the labels (`lgnd_labs`).
#' Passed down to [`tinylabel`].
#' @param type Plotting type(s), passed down from [tinyplot].
#' @param type_axes_hints Optional named list of axes/legend behaviour flags that
#' a plot type declares for itself (e.g. `rhs_axis` for a secondary right-hand
#' axis). Passed down from [tinyplot]; defaults to `NULL`.
#' @param pch Plotting character(s), passed down from [tinyplot].
#' @param lty Plotting linetype(s), passed down from [tinyplot].
#' @param lwd Plotting line width(s), passed down from [tinyplot].
Expand Down Expand Up @@ -925,6 +931,7 @@ draw_legend = function(
lgnd_labs = NULL,
labeller = NULL,
type = NULL,
type_axes_hints = NULL,
pch = NULL,
lty = NULL,
lwd = NULL,
Expand Down Expand Up @@ -976,6 +983,7 @@ draw_legend = function(

# Visual aesthetics
type = type,
type_axes_hints = type_axes_hints,
pch = pch,
lty = lty,
lwd = lwd,
Expand Down
3 changes: 3 additions & 0 deletions R/legend_multi.R
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ prepare_legend_multi = function(settings) {
"by_dep",
"lgnd_labs",
"type",
"type_axes_hints",
"pch",
"lty",
"lwd",
Expand All @@ -45,6 +46,7 @@ prepare_legend_multi = function(settings) {
by_dep = by_dep,
lgnd_labs = lgnd_labs,
type = type,
type_axes_hints = type_axes_hints,
pch = pch,
lty = lty,
lwd = lwd,
Expand All @@ -64,6 +66,7 @@ prepare_legend_multi = function(settings) {
),
lgnd_labs = names(bubble_cex),
type = type,
type_axes_hints = type_axes_hints,
pch = pch,
lty = lty,
lwd = lwd,
Expand Down
9 changes: 5 additions & 4 deletions R/lim.R
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@ lim_args = function(settings) {
settings,
environment(),
c(
"xaxb", "xlabs", "xlim", "null_xlim",
"xaxb", "xlabs", "xlim", "null_xlim",
"yaxb", "ylabs", "ylim", "null_ylim",
"datapoints", "type"
"datapoints", "type", "type_axes_hints"
)
)

Expand Down Expand Up @@ -37,8 +37,9 @@ lim_args = function(settings) {
xlim = xlim + c(-0.5, 0.5)
}

if (null_xlim && !is.null(xaxb) && type != "spineplot") xlim = range(c(xlim, xaxb))
if (null_ylim && !is.null(yaxb) && type != "spineplot") ylim = range(c(ylim, yaxb))
prop_lim = isTRUE(type_axes_hints[["proportional_lim"]])
if (null_xlim && !is.null(xaxb) && !prop_lim) xlim = range(c(xlim, xaxb))
if (null_ylim && !is.null(yaxb) && !prop_lim) ylim = range(c(ylim, yaxb))

# update settings
env2env(
Expand Down
12 changes: 9 additions & 3 deletions R/tinyplot.R
Original file line number Diff line number Diff line change
Expand Up @@ -869,7 +869,8 @@ tinyplot.default = function(
group_offsets = NULL,
offsets_axis = NULL,
sub = sub,
type_info = list() # pass type-specific info from type_data to type_draw
type_info = list(), # pass type-specific info from type_data to type_draw
type_axes_hints = NULL # axes/legend behaviour a type declares for itself
)

settings = new.env()
Expand Down Expand Up @@ -1063,7 +1064,7 @@ tinyplot.default = function(
# draw their own in the same place (e.g. spineplot category + numeric labels
# via spine_axis()). Their tick-row margin must still be reserved, else the
# self-drawn labels clip when xlab/ylab = NA makes label_extent = 0 (#635).
.self_axis = identical(type, "spineplot")
.self_axis = isTRUE(type_axes_hints[["self_axes"]])

.dyn = c(
dynmar_side(1, xlab, main = main, sub = sub,
Expand Down Expand Up @@ -1157,6 +1158,7 @@ tinyplot.default = function(
by_dep = by_dep,
lgnd_labs = lgnd_labs,
type = type,
type_axes_hints = type_axes_hints,
pch = pch,
lty = lty,
lwd = lwd,
Expand Down Expand Up @@ -1330,6 +1332,7 @@ tinyplot.default = function(
sub = sub,
cap = cap,
type = type,
type_axes_hints = type_axes_hints,
xlab = xlab,
x = x, xmax = xmax, xmin = xmin,
ylab = ylab,
Expand Down Expand Up @@ -1361,6 +1364,7 @@ tinyplot.default = function(
sub = sub,
cap = cap,
type = type,
type_axes_hints = type_axes_hints,
xlab = xlab,
x = datapoints$x, xmax = datapoints$xmax, xmin = datapoints$xmin,
ylab = ylab,
Expand Down Expand Up @@ -1463,7 +1467,9 @@ tinyplot.default = function(

# empty plot flag
empty_plot = FALSE
if (isTRUE(empty) || isTRUE(type == "n") || ((length(ix) == 0) && !(type %in% c("histogram", "hist", "rect", "segments", "spineplot")))) {
draws_empty = type %in% c("histogram", "hist", "rect", "segments") ||
isTRUE(type_axes_hints[["draw_empty_facet"]])
if (isTRUE(empty) || isTRUE(type == "n") || ((length(ix) == 0) && !draws_empty)) {
empty_plot = TRUE
}

Expand Down
17 changes: 15 additions & 2 deletions R/type_spineplot.R
Original file line number Diff line number Diff line change
Expand Up @@ -283,11 +283,24 @@ data_spineplot = function(off = NULL, breaks = NULL, xlevels = xlevels, ylevels
settings$legend_args[["pt.lwd"]] = settings$legend_args[["pt.lwd"]] %||% 0
settings$legend_args[["y.intersp"]] = settings$legend_args[["y.intersp"]] %||% 1.25
settings$legend_args[["seg.len"]] = settings$legend_args[["seg.len"]] %||% 1.25


# Declare this type's axes/legend behaviour so the main pipeline can read
# semantic flags instead of hardcoding `type == "spineplot"` checks.
# A spineplot suppresses the standard axes (xaxt/yaxt = "n") because it
# draws its own (category + numeric labels, plus a secondary RHS axis)
# via spine_axis(), and uses proportional [0, 1] limits.
type_axes_hints = list(
self_axes = TRUE, # draws own tick-row axes despite xaxt/yaxt = "n"
rhs_axis = TRUE, # secondary right-hand axis (reserve margin)
proportional_lim = TRUE, # [0, 1] limits; don't expand to axis breaks
legend_fill_from_col = TRUE, # legend swatch pt.bg defaults from col
draw_empty_facet = TRUE # can draw with zero per-group rows
)

env2env(environment(), settings, c(
"x", "y", "ymin", "ymax", "xmin", "xmax", "col", "bg", "datapoints",
"by", "facet", "axes", "frame.plot", "xaxt", "yaxt", "xaxs", "yaxs",
"ylabs", "type_info", "facet.args"
"ylabs", "type_info", "facet.args", "type_axes_hints"
))

}
Expand Down
1 change: 1 addition & 0 deletions man/build_legend_env.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

5 changes: 5 additions & 0 deletions man/draw_legend.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions man/facet.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.