diff --git a/NEWS.md b/NEWS.md index ac61c395d9..a9ba946739 100644 --- a/NEWS.md +++ b/NEWS.md @@ -42,6 +42,8 @@ * `scale_*_datetime` now has support for timezones. If time data has been encoded with a timezone this will be used, but it can be overridden with the `timezone` argument in the scale constructor. + +* `geom_*(show.legend = FALSE)` now works for `guide_colorbar` * The documentation for theme elements has been improved (#1743). diff --git a/R/guide-colorbar.r b/R/guide-colorbar.r index 01e6e56f6c..4ef941d42b 100644 --- a/R/guide-colorbar.r +++ b/R/guide-colorbar.r @@ -211,7 +211,22 @@ guide_merge.colorbar <- function(guide, new_guide) { # this guide is not geom-based. #' @export -guide_geom.colorbar <- function(guide, ...) { +guide_geom.colorbar <- function(guide, layers, default_mapping) { + # Layers that use this guide + guide_layers <- plyr::llply(layers, function(layer) { + matched <- matched_aes(layer, guide, default_mapping) + + if (length(matched) && ((is.na(layer$show.legend) || layer$show.legend))) { + layer + } else { + # This layer does not use this guide + NULL + } + }) + + # Remove this guide if no layer uses it + if (length(compact(guide_layers)) == 0) guide <- NULL + guide } diff --git a/R/guide-legend.r b/R/guide-legend.r index 182fbd58b4..7f01aaa8ca 100644 --- a/R/guide-legend.r +++ b/R/guide-legend.r @@ -252,11 +252,7 @@ guide_merge.legend <- function(guide, new_guide) { guide_geom.legend <- function(guide, layers, default_mapping) { # arrange common data for vertical and horizontal guide guide$geoms <- plyr::llply(layers, function(layer) { - all <- names(c(layer$mapping, if (layer$inherit.aes) default_mapping, layer$stat$default_aes)) - geom <- c(layer$geom$required_aes, names(layer$geom$default_aes)) - matched <- intersect(intersect(all, geom), names(guide$key)) - matched <- setdiff(matched, names(layer$geom_params)) - matched <- setdiff(matched, names(layer$aes_params)) + matched <- matched_aes(layer, guide, default_mapping) if (length(matched) > 0) { # This layer contributes to the legend diff --git a/R/guides-.r b/R/guides-.r index 8095731a4a..ac072842f7 100644 --- a/R/guides-.r +++ b/R/guides-.r @@ -297,3 +297,12 @@ guide_merge <- function(...) UseMethod("guide_merge") guide_geom <- function(...) UseMethod("guide_geom") guide_gengrob <- function(...) UseMethod("guide_gengrob") + +# Helpers +matched_aes <- function(layer, guide, defaults) { + all <- names(c(layer$mapping, if (layer$inherit.aes) defaults, layer$stat$default_aes)) + geom <- c(layer$geom$required_aes, names(layer$geom$default_aes)) + matched <- intersect(intersect(all, geom), names(guide$key)) + matched <- setdiff(matched, names(layer$geom_params)) + setdiff(matched, names(layer$aes_params)) +} diff --git a/tests/testthat/test-guides.R b/tests/testthat/test-guides.R index 0a1aa6d7e1..ba248999bf 100644 --- a/tests/testthat/test-guides.R +++ b/tests/testthat/test-guides.R @@ -8,3 +8,12 @@ test_that("colourbar trains without labels", { expect_equal(names(out$key), c("colour", ".value")) }) +test_that("Colorbar respects show.legend in layer", { + df <- data.frame(x = 1:3, y = 1) + p <- ggplot(df, aes(x = x, y = y, color = x)) + + geom_point(size = 20, shape = 21, show.legend = FALSE) + expect_false("guide-box" %in% ggplotGrob(p)$layout$name) + p <- ggplot(df, aes(x = x, y = y, color = x)) + + geom_point(size = 20, shape = 21, show.legend = TRUE) + expect_true("guide-box" %in% ggplotGrob(p)$layout$name) +})