From 4ddb5394715f80900d2f9f8f4d6d02045fda8765 Mon Sep 17 00:00:00 2001 From: mtennekes Date: Thu, 4 Apr 2024 22:37:37 +0200 Subject: [PATCH] facet_flip working, xtab margins working, working on wrap panel margins --- R/process_meta.R | 17 +++++++++++++++++ R/step1_helper_facets.R | 18 ++++++++++++++++++ R/step2_data.R | 21 ++++++++++++++++++--- R/step4_plot.R | 32 ++++++++++++++++++++++++++++++++ R/tm_facets.R | 4 ++-- R/tmapGridInit.R | 14 +++++++++----- R/tmap_options.R | 1 + 7 files changed, 97 insertions(+), 10 deletions(-) diff --git a/R/process_meta.R b/R/process_meta.R index 932a5944..979a066e 100644 --- a/R/process_meta.R +++ b/R/process_meta.R @@ -179,6 +179,23 @@ process_meta = function(o, d, cdt, aux) { ifelse("right" %in% panel.xtab.pos, panel.label.height * lineW, 0)) } else c(0, 0, 0, 0) + panel.margin = get_option_class(panel.margin, panel.type) + + panel.xtab.margin = if (panel.type == "xtab") { + c(ifelse("bottom" %in% panel.xtab.pos, panel.margin * lineH, 0), + ifelse("left" %in% panel.xtab.pos, panel.margin * lineW, 0), + ifelse("top" %in% panel.xtab.pos, panel.margin * lineH, 0), + ifelse("right" %in% panel.xtab.pos, panel.margin * lineW, 0)) + } else c(0, 0, 0, 0) + + panel.wrap.margin = if (panel.type == "wrap") { + c(ifelse(panel.wrap.pos == "bottom", panel.margin * lineH, 0), + ifelse(panel.wrap.pos == "left", panel.margin * lineW, 0), + ifelse(panel.wrap.pos == "top", panel.margin * lineH, 0), + ifelse(panel.wrap.pos == "right", panel.margin * lineW, 0)) + } else c(0, 0, 0, 0) + + panel.wrap.size = if (panel.type == "wrap") { c(ifelse(panel.wrap.pos == "bottom", panel.label.height * lineH, 0), ifelse(panel.wrap.pos == "left", panel.label.height * lineW, 0), diff --git a/R/step1_helper_facets.R b/R/step1_helper_facets.R index bfa8c814..6d7b88f2 100644 --- a/R/step1_helper_facets.R +++ b/R/step1_helper_facets.R @@ -43,6 +43,9 @@ get_split_stars_dim = function(lst) { } } +is_rev = function(x) !is.null(x) && substr(x, 1, 1) == "-" +remove_min = function(x) substr(x, 2, nchar(x)) + # ## estimate number of facets step1_rearrange_facets = function(tmo, o) { #o = tmap_options_mode() @@ -208,6 +211,12 @@ step1_rearrange_facets = function(tmo, o) { if (is.na(type)) type = if (nrd <= 1L) "wrapstack" else "grid" if (type %in% c("wrapstack", "wrap", "stack", "page")) { + rev1 = is_rev(by) + rev2 = FALSE + rev3 = FALSE + + if (rev1) by = remove_min(by) + by1 = by by2 = NULL by3 = NULL @@ -258,6 +267,15 @@ step1_rearrange_facets = function(tmo, o) { by2 = columns by3 = pages + rev1 = is_rev(by1) + rev2 = is_rev(by2) + rev3 = is_rev(by3) + + if (rev1) by1 = remove_min(by1) + if (rev2) by2 = remove_min(by2) + if (rev3) by3 = remove_min(by3) + + if (nrd > 3L) { if (nrsd > 3L) stop("The shape object has more than 3 dimensions, so even tm_facets_grid cannot be used.", call. = FALSE) nrvd = 0L diff --git a/R/step2_data.R b/R/step2_data.R index 7aa7e49e..9b2af815 100644 --- a/R/step2_data.R +++ b/R/step2_data.R @@ -21,7 +21,12 @@ step2_data = function(tm) { grps = lapply(tmo, function(tmg) { tmf = tmg$tmf dt = tmg$tms$dt + + if ("by1__" %in% names(dt) && o$rev1) dt[, by1__ := (o$fn[1]+1L)-by1__] + if ("by2__" %in% names(dt) && o$rev2) dt[, by2__ := (o$fn[2]+1L)-by2__] + if ("by3__" %in% names(dt) && o$rev3) dt[, by3__ := (o$fn[3]+1L)-by3__] + if (o$facet.flip && !o$type %in% c("wrapstack", "wrap", "stack")) { if ("by2__" %in% names(dt)) { dt[, by2b__:= by2__] @@ -34,7 +39,7 @@ step2_data = function(tm) { dt[, by1__ := by2b__] dt[, by2b__ := NULL] } - + tmf = within(tmf, { b = ifelse(b == 1L, 2L, ifelse(b == 2L, 1L, b)) v = ifelse(v == 1L, 2L, ifelse(v == 2L, 1L, v)) @@ -42,8 +47,8 @@ step2_data = function(tm) { var__ = ifelse(var__ == "by1__", "by2__", ifelse(var__ == "by2__", "by1__", var__)) gn = gn[c(2,1,3)] gl = gl[c(2,1,3)] - fl = fl[c(2,1,3)] - fn = fn[c(2,1,3)] + #fl = fl[c(2,1,3)] + #fn = fn[c(2,1,3)] }) } @@ -158,5 +163,15 @@ step2_data = function(tm) { # attr(grps, "nrows") = tmo[[1]]$tmf$nrows # attr(grps, "ncols") = tmo[[1]]$tmf$ncols + o = within(o, { + if (rev1) fl[[1]][] = rev(fl[[1]][]) + if (rev2) fl[[2]][] = rev(fl[[2]][]) + if (rev3) fl[[3]][] = rev(fl[[3]][]) + if (facet.flip && !type %in% c("wrapstack", "wrap", "stack")) { + fl[] = fl[c(2,1,3)] + fn = fn[c(2,1,3)] + } + }) + list(tmo = grps, aux = aux, cmp = cmp, o = o) } diff --git a/R/step4_plot.R b/R/step4_plot.R index 6ce0d8c2..2ab8b2af 100644 --- a/R/step4_plot.R +++ b/R/step4_plot.R @@ -469,6 +469,7 @@ step4_plot = function(tm, vp, return.asp, show, knit, args) { o$ng = length(tmx) # determine row and col ids + if (o$panel.type == "xtab") { d[, row := as.integer((i - 1) %% o$nrows + 1)] d[, col := as.integer((((i - 1) %/% o$nrows + 1) - 1) %% o$ncols + 1)] @@ -484,6 +485,37 @@ step4_plot = function(tm, vp, return.asp, show, knit, args) { } d[, page := as.integer(i - 1) %/% (o$nrows * o$ncols) + 1] + + + ### facet.flip and reverse + # if (o$facet.flip) { + # labcols= o$panel.labels[[1]] + # labrows = o$panel.labels[[2]] + # nr = o$nrows + # o$nrows = o$ncols + # o$ncols = nr + # } else { + # labrows = o$panel.labels[[1]] + # labcols = o$panel.labels[[2]] + # } + # + + + # # reverse if specified (with '-' in front of row/col/page variable name in tm_facets) + # if (o$rev1) { + # labs1 = o$panel.labels[[1]] + # d[, by1:=(1L+length(labs1)) - by1] + # o$panel.labels[[1]] = structure(rev(labs1), showNA = attr(labs1, "showNA")) + # } + # if (o$rev2) { + # labs2 = o$panel.labels[[2]] + # d[, by2:=(1L+length(labs2)) - by2] + # o$panel.labels[[2]] = rev(labs2) + # } + # if (o$rev3) { + # d[, by3:=(1L+max(by3)) - by3] + # } + # } diff --git a/R/tm_facets.R b/R/tm_facets.R index 4aef1078..9c0a1f0d 100644 --- a/R/tm_facets.R +++ b/R/tm_facets.R @@ -202,6 +202,6 @@ tm_facets_vstack = function(by = "VARS__", #' @export #' @rdname tm_facets #' @name tm_facet_flip -tm_facets_flip = function() { - tm_options(facet.flip = TRUE) +tm_facets_flip = function(...) { + do.call(tm_facets, list(...)) + tm_options(facet.flip = TRUE) } diff --git a/R/tmapGridInit.R b/R/tmapGridInit.R index a01cf4bd..05a0b24c 100644 --- a/R/tmapGridInit.R +++ b/R/tmapGridInit.R @@ -8,14 +8,16 @@ tmapGridInit = function(o, return.asp = FALSE, vp) { xylab.margins.top = xylab.margins[3], panel.xtab.top = panel.xtab.size[3], + panel.xtab.margin.top = panel.xtab.margin[3], grid.buffers.top = grid.buffers[3], grid.margins.top = grid.margins[3], {if (o$nrows > 1) rep(c(panel.wrap.size[3], 0, panel.wrap.size[1], between.marginH), o$nrows -1) else NULL}, panel.wrap.size[3], 0, panel.wrap.size[1], - grid.margins.top = grid.margins[1], - grid.buffers.top = grid.buffers[1], + grid.margins.bottom = grid.margins[1], + grid.buffers.bottom = grid.buffers[1], + panel.xtab.margin.bottom = panel.xtab.margin[1], panel.xtab.bottom = panel.xtab.size[1], xylab.margins.bottom = xylab.margins[1], @@ -37,14 +39,16 @@ tmapGridInit = function(o, return.asp = FALSE, vp) { xylab.margins.left = xylab.margins[2], panel.xtab.left = panel.xtab.size[2], + panel.xtab.margin.left = panel.xtab.margin[2], grid.buffers.left = grid.buffers[2], grid.margins.left = grid.margins[2], - {if (o$ncols > 1) rep(c(panel.wrap.size[2], 0, panel.wrap.size[4], between.marginW), o$ncols -1) else NULL}, + {if (o$ncols > 1) rep(c(panel.wrap.size[2], 0, panel.wrap.size[4], between.marginW), o$ncols -1) else NULL}, panel.wrap.size[2], 0, panel.wrap.size[4], grid.margins.left = grid.margins[4], grid.buffers.left = grid.buffers[4], + panel.xtab.margin.right = panel.xtab.margin[4], panel.xtab.right = panel.xtab.size[4], xylab.margins.right = xylab.margins[4], @@ -61,8 +65,8 @@ tmapGridInit = function(o, return.asp = FALSE, vp) { nr = length(rows) nc = length(cols) - cols_facet_ids = 1:o$ncols * 4 + 6 - rows_facet_ids = 1:o$nrows * 4 + 6 + cols_facet_ids = 1:o$ncols * 4 + 7 + rows_facet_ids = 1:o$nrows * 4 + 7 #if (o$panel.type == "xtab") { cols_panel_col_ids = cols_facet_ids diff --git a/R/tmap_options.R b/R/tmap_options.R index 9d5d3fc4..45c80b2f 100644 --- a/R/tmap_options.R +++ b/R/tmap_options.R @@ -217,6 +217,7 @@ meta.margins = NA, meta.auto.margins = c(0.4, 0.4, 0.4, 0.4), between.margin = 0.5, + panel.margin = c(xtab = 0.4, wrap = 0), component.offset = c(inside = 0.75, INSIDE = 0, outside = 0, OUTSIDE = 0), component.stack.margin = 0, grid.mark.height = 2,