From aa6a88238879d07e927e842cd11d95a5a1bc14e7 Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Tue, 29 May 2018 08:47:42 +0900 Subject: [PATCH 01/10] add tests for labs() --- tests/testthat/test-labels.r | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/tests/testthat/test-labels.r b/tests/testthat/test-labels.r index 62a8e1b286..05e92db062 100644 --- a/tests/testthat/test-labels.r +++ b/tests/testthat/test-labels.r @@ -25,6 +25,17 @@ test_that("setting guide labels works", { expect_identical(labs(colour = "my label")$colour, "my label") # American spelling expect_identical(labs(color = "my label")$colour, "my label") + + # No extra elements exists + expect_equivalent(labs(title = "my title"), list(title = "my title")) # formal argument + expect_equivalent(labs(colour = "my label"), list(colour = "my label")) # dot + expect_equivalent(labs(foo = "bar"), list(foo = "bar")) # non-existent param + + # labs() can take a list as the first argument + expect_identical(labs(list(title = "my title", tag = "A)"))$tag, "A)") + + # NULL is preserved + expect_equivalent(labs(title = NULL), list(title = NULL)) }) From cbfd97f1e530d81ce443e50055c6c1ffd5adc8c7 Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Tue, 29 May 2018 08:48:44 +0900 Subject: [PATCH 02/10] make label params as the formal arguments of labs() --- R/labels.r | 24 +++++++++++++++++++----- man/labs.Rd | 20 +++++++++++++++----- 2 files changed, 34 insertions(+), 10 deletions(-) diff --git a/R/labels.r b/R/labels.r index 77203e1bbc..6d9226c7a2 100644 --- a/R/labels.r +++ b/R/labels.r @@ -29,10 +29,14 @@ update_labels <- function(p, labels) { #' changing other scale options. #' #' @param label The text for the axis, plot title or caption below the plot. -#' @param subtitle the text for the subtitle for the plot which will be +#' @param title The text for the title. +#' @param subtitle The text for the subtitle for the plot which will be #' displayed below the title. Leave `NULL` for no subtitle. -#' @param ... A list of new name-value pairs. The name should either be -#' an aesthetic, or one of "title", "subtitle", "caption", or "tag". +#' @param caption The text for the caption which will be displayed in the +#' bottom-right of the plot by default. +#' @param tag The text for the tag label which will be displayed at the +#' top-left of the plot by default. +#' @param ... A list of new name-value pairs. The name should be an aesthetic. #' @export #' @examples #' p <- ggplot(mtcars, aes(mpg, wt, colour = cyl)) + geom_point() @@ -51,10 +55,20 @@ update_labels <- function(p, labels) { #' # The plot tag appears at the top-left, and is typically used #' # for labelling a subplot with a letter. #' p + labs(title = "title", tag = "A") -labs <- function(...) { +#' +#' # If you want to remove a label, set it to NULL. +#' p + labs(title = "title") + labs(title = NULL) +labs <- function(..., title, subtitle, caption, tag) { args <- list(...) - if (is.list(args[[1]])) args <- args[[1]] + if (length(args) > 0 && is.list(args[[1]])) args <- args[[1]] args <- rename_aes(args) + + # Since NULL should be preserved, we should wrap args with list() + if (!missing(title)) args["title"] <- list(title) + if (!missing(subtitle)) args["subtitle"] <- list(subtitle) + if (!missing(caption)) args["caption"] <- list(caption) + if (!missing(tag)) args["tag"] <- list(tag) + structure(args, class = "labels") } diff --git a/man/labs.Rd b/man/labs.Rd index 87d0ebad38..b78f1d41de 100644 --- a/man/labs.Rd +++ b/man/labs.Rd @@ -7,7 +7,7 @@ \alias{ggtitle} \title{Modify axis, legend, and plot labels} \usage{ -labs(...) +labs(..., title, subtitle, caption, tag) xlab(label) @@ -16,13 +16,20 @@ ylab(label) ggtitle(label, subtitle = NULL) } \arguments{ -\item{...}{A list of new name-value pairs. The name should either be -an aesthetic, or one of "title", "subtitle", "caption", or "tag".} +\item{...}{A list of new name-value pairs. The name should be an aesthetic.} -\item{label}{The text for the axis, plot title or caption below the plot.} +\item{title}{The text for the title.} -\item{subtitle}{the text for the subtitle for the plot which will be +\item{subtitle}{The text for the subtitle for the plot which will be displayed below the title. Leave \code{NULL} for no subtitle.} + +\item{caption}{The text for the caption which will be displayed in the +bottom-right of the plot by default.} + +\item{tag}{The text for the tag label which will be displayed at the +top-left of the plot by default.} + +\item{label}{The text for the axis, plot title or caption below the plot.} } \description{ Good labels are critical for making your plots accessible to a wider @@ -53,4 +60,7 @@ p + labs(caption = "(based on data from ...)") # The plot tag appears at the top-left, and is typically used # for labelling a subplot with a letter. p + labs(title = "title", tag = "A") + +# If you want to remove a label, set it to NULL. +p + labs(title = "title") + labs(title = NULL) } From 83a51edf40774e6ed1200dcd6b3ecb5ac48bf139 Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Thu, 31 May 2018 17:13:57 +0900 Subject: [PATCH 03/10] respect missingness in ggtitle() --- R/labels.r | 7 +++++-- tests/testthat/test-labels.r | 7 +++++++ 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/R/labels.r b/R/labels.r index 6d9226c7a2..552a118d16 100644 --- a/R/labels.r +++ b/R/labels.r @@ -86,6 +86,9 @@ ylab <- function(label) { #' @rdname labs #' @export -ggtitle <- function(label, subtitle = NULL) { - labs(title = label, subtitle = subtitle) +ggtitle <- function(label, subtitle) { + args <- list(title = label) + if (!missing(subtitle)) args["subtitle"] <- list(subtitle) + + labs(args) } diff --git a/tests/testthat/test-labels.r b/tests/testthat/test-labels.r index 05e92db062..34955593e0 100644 --- a/tests/testthat/test-labels.r +++ b/tests/testthat/test-labels.r @@ -36,6 +36,13 @@ test_that("setting guide labels works", { # NULL is preserved expect_equivalent(labs(title = NULL), list(title = NULL)) + + # ggtitle works in the same way as labs() + expect_identical(ggtitle("my title")$title, "my title") + expect_identical(ggtitle("my title", + subtitle = "my subtitle")$subtitle, "my subtitle") + expect_equivalent(ggtitle("my title", subtitle = NULL), + list(title = "my title", subtitle = NULL)) }) From 4a1115f03c86e0d926c53ac20f153325fcd9ad7b Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Thu, 31 May 2018 17:22:10 +0900 Subject: [PATCH 04/10] improve description about labs() --- R/labels.r | 10 ++++++++-- man/labs.Rd | 12 +++++++++--- 2 files changed, 17 insertions(+), 5 deletions(-) diff --git a/R/labels.r b/R/labels.r index 552a118d16..ef381765b7 100644 --- a/R/labels.r +++ b/R/labels.r @@ -28,10 +28,16 @@ update_labels <- function(p, labels) { #' the first argument, the `name`). I recommend doing that if you're #' changing other scale options. #' -#' @param label The text for the axis, plot title or caption below the plot. +#' If a plot already has a title, subtitle, caption, etc., and you want to +#' remove it, you can do so by setting the respective argument to `NULL`. For +#' example, if plot `p` has a subtitle, then `p + labs(subtitle = NULL)` will +#' remove the subtitle from the plot. +#' +#' @param label The title of the respective axis (for `xlab()` or `ylab()`) or +#' of the plot (for `ggtitle()``). #' @param title The text for the title. #' @param subtitle The text for the subtitle for the plot which will be -#' displayed below the title. Leave `NULL` for no subtitle. +#' displayed below the title. #' @param caption The text for the caption which will be displayed in the #' bottom-right of the plot by default. #' @param tag The text for the tag label which will be displayed at the diff --git a/man/labs.Rd b/man/labs.Rd index b78f1d41de..73560c2a03 100644 --- a/man/labs.Rd +++ b/man/labs.Rd @@ -13,7 +13,7 @@ xlab(label) ylab(label) -ggtitle(label, subtitle = NULL) +ggtitle(label, subtitle) } \arguments{ \item{...}{A list of new name-value pairs. The name should be an aesthetic.} @@ -21,7 +21,7 @@ ggtitle(label, subtitle = NULL) \item{title}{The text for the title.} \item{subtitle}{The text for the subtitle for the plot which will be -displayed below the title. Leave \code{NULL} for no subtitle.} +displayed below the title.} \item{caption}{The text for the caption which will be displayed in the bottom-right of the plot by default.} @@ -29,7 +29,8 @@ bottom-right of the plot by default.} \item{tag}{The text for the tag label which will be displayed at the top-left of the plot by default.} -\item{label}{The text for the axis, plot title or caption below the plot.} +\item{label}{The title of the respective axis (for \code{xlab()} or \code{ylab()}) or +of the plot (for `ggtitle()``).} } \description{ Good labels are critical for making your plots accessible to a wider @@ -42,6 +43,11 @@ data source. \code{tag} can be used for adding identification tags. You can also set axis and legend labels in the individual scales (using the first argument, the \code{name}). I recommend doing that if you're changing other scale options. + +If a plot already has a title, subtitle, caption, etc., and you want to +remove it, you can do so by setting the respective argument to \code{NULL}. For +example, if plot \code{p} has a subtitle, then \code{p + labs(subtitle = NULL)} will +remove the subtitle from the plot. } \examples{ p <- ggplot(mtcars, aes(mpg, wt, colour = cyl)) + geom_point() From 0ff44f49ccc2b8e0fb128bd74a02afc4a7506fba Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Fri, 1 Jun 2018 18:29:34 +0900 Subject: [PATCH 05/10] use waive() to represent missingness in labs() --- R/labels.r | 20 +++++++------------- man/labs.Rd | 5 +++-- 2 files changed, 10 insertions(+), 15 deletions(-) diff --git a/R/labels.r b/R/labels.r index ef381765b7..9ff76a5fcd 100644 --- a/R/labels.r +++ b/R/labels.r @@ -64,16 +64,13 @@ update_labels <- function(p, labels) { #' #' # If you want to remove a label, set it to NULL. #' p + labs(title = "title") + labs(title = NULL) -labs <- function(..., title, subtitle, caption, tag) { - args <- list(...) - if (length(args) > 0 && is.list(args[[1]])) args <- args[[1]] +labs <- function(..., title = waiver(), subtitle = waiver(), caption = waiver(), tag = waiver()) { + args <- list(..., title = title, subtitle = subtitle, caption = caption, tag = tag) + if (length(args) > 0 && is.list(args[[1]]) && !is.waive(args[[1]])) args <- args[[1]] args <- rename_aes(args) - # Since NULL should be preserved, we should wrap args with list() - if (!missing(title)) args["title"] <- list(title) - if (!missing(subtitle)) args["subtitle"] <- list(subtitle) - if (!missing(caption)) args["caption"] <- list(caption) - if (!missing(tag)) args["tag"] <- list(tag) + is_waive <- vapply(args, is.waive, logical(1)) + args <- args[!is_waive] structure(args, class = "labels") } @@ -92,9 +89,6 @@ ylab <- function(label) { #' @rdname labs #' @export -ggtitle <- function(label, subtitle) { - args <- list(title = label) - if (!missing(subtitle)) args["subtitle"] <- list(subtitle) - - labs(args) +ggtitle <- function(label, subtitle = waiver()) { + labs(title = label, subtitle = subtitle) } diff --git a/man/labs.Rd b/man/labs.Rd index 73560c2a03..a4fb23eac6 100644 --- a/man/labs.Rd +++ b/man/labs.Rd @@ -7,13 +7,14 @@ \alias{ggtitle} \title{Modify axis, legend, and plot labels} \usage{ -labs(..., title, subtitle, caption, tag) +labs(..., title = waiver(), subtitle = waiver(), caption = waiver(), + tag = waiver()) xlab(label) ylab(label) -ggtitle(label, subtitle) +ggtitle(label, subtitle = waiver()) } \arguments{ \item{...}{A list of new name-value pairs. The name should be an aesthetic.} From cc14ce44fd206e709e8d64f85d706244d29b3a94 Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Fri, 1 Jun 2018 18:34:19 +0900 Subject: [PATCH 06/10] fix a typo --- R/labels.r | 2 +- man/labs.Rd | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/R/labels.r b/R/labels.r index 9ff76a5fcd..b684faa70e 100644 --- a/R/labels.r +++ b/R/labels.r @@ -34,7 +34,7 @@ update_labels <- function(p, labels) { #' remove the subtitle from the plot. #' #' @param label The title of the respective axis (for `xlab()` or `ylab()`) or -#' of the plot (for `ggtitle()``). +#' of the plot (for `ggtitle()`). #' @param title The text for the title. #' @param subtitle The text for the subtitle for the plot which will be #' displayed below the title. diff --git a/man/labs.Rd b/man/labs.Rd index a4fb23eac6..c815e70397 100644 --- a/man/labs.Rd +++ b/man/labs.Rd @@ -31,7 +31,7 @@ bottom-right of the plot by default.} top-left of the plot by default.} \item{label}{The title of the respective axis (for \code{xlab()} or \code{ylab()}) or -of the plot (for `ggtitle()``).} +of the plot (for \code{ggtitle()}).} } \description{ Good labels are critical for making your plots accessible to a wider From 0c2008ffc1d3e0d9168291844c2bebe89a736a4f Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Mon, 9 Jul 2018 19:02:10 +0900 Subject: [PATCH 07/10] apply tidyverse style --- tests/testthat/test-labels.r | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/testthat/test-labels.r b/tests/testthat/test-labels.r index 34955593e0..af2f0920a9 100644 --- a/tests/testthat/test-labels.r +++ b/tests/testthat/test-labels.r @@ -39,10 +39,14 @@ test_that("setting guide labels works", { # ggtitle works in the same way as labs() expect_identical(ggtitle("my title")$title, "my title") - expect_identical(ggtitle("my title", - subtitle = "my subtitle")$subtitle, "my subtitle") - expect_equivalent(ggtitle("my title", subtitle = NULL), - list(title = "my title", subtitle = NULL)) + expect_identical( + ggtitle("my title", subtitle = "my subtitle")$subtitle, + "my subtitle" + ) + expect_equivalent( + ggtitle("my title", subtitle = NULL), + list(title = "my title", subtitle = NULL) + ) }) From 755ed179983497da82b048c4206394ebd9907af7 Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Sun, 15 Jul 2018 11:33:06 +0900 Subject: [PATCH 08/10] Enable !!! in labs() --- R/labels.r | 7 ++++--- tests/testthat/test-labels.r | 5 +++-- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/R/labels.r b/R/labels.r index b684faa70e..7df6e37e35 100644 --- a/R/labels.r +++ b/R/labels.r @@ -65,12 +65,13 @@ update_labels <- function(p, labels) { #' # If you want to remove a label, set it to NULL. #' p + labs(title = "title") + labs(title = NULL) labs <- function(..., title = waiver(), subtitle = waiver(), caption = waiver(), tag = waiver()) { - args <- list(..., title = title, subtitle = subtitle, caption = caption, tag = tag) - if (length(args) > 0 && is.list(args[[1]]) && !is.waive(args[[1]])) args <- args[[1]] - args <- rename_aes(args) + args <- rlang::list2(..., title = title, subtitle = subtitle, caption = caption, tag = tag) is_waive <- vapply(args, is.waive, logical(1)) args <- args[!is_waive] + # remove duplicated arguments + args <- args[!duplicated(names(args))] + args <- rename_aes(args) structure(args, class = "labels") } diff --git a/tests/testthat/test-labels.r b/tests/testthat/test-labels.r index af2f0920a9..a813f36845 100644 --- a/tests/testthat/test-labels.r +++ b/tests/testthat/test-labels.r @@ -31,8 +31,9 @@ test_that("setting guide labels works", { expect_equivalent(labs(colour = "my label"), list(colour = "my label")) # dot expect_equivalent(labs(foo = "bar"), list(foo = "bar")) # non-existent param - # labs() can take a list as the first argument - expect_identical(labs(list(title = "my title", tag = "A)"))$tag, "A)") + # labs() has list-splicing semantics + params <- list(title = "my title", tag = "A)") + expect_identical(labs(!!!params)$tag, "A)") # NULL is preserved expect_equivalent(labs(title = NULL), list(title = NULL)) From ccf014f791d7dd50d114ddf12817bd054a72ef08 Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Wed, 25 Jul 2018 14:20:40 +0900 Subject: [PATCH 09/10] Add a news bullet --- NEWS.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/NEWS.md b/NEWS.md index 85bb67443f..c157a60364 100644 --- a/NEWS.md +++ b/NEWS.md @@ -18,6 +18,9 @@ is now always internally converted to "colour", even when part of a longer aesthetic name (e.g., `point_color`) (@clauswilke, #2649). +* `labs()` now has named arguments `title`, `subtitle`, `caption` and `tag` explicitly. + Also, `labs()` now accepts tidyeval (@yutannihilation, #2669). + # ggplot2 3.0.0 ## Breaking changes From 138474d036bb2ce42697c0239e42a543e0fe19ed Mon Sep 17 00:00:00 2001 From: Hiroaki Yutani Date: Mon, 20 Aug 2018 23:03:31 +0900 Subject: [PATCH 10/10] Add the Oxford comma --- NEWS.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/NEWS.md b/NEWS.md index 71db50d4b6..e19b3613c9 100644 --- a/NEWS.md +++ b/NEWS.md @@ -35,7 +35,7 @@ is now always internally converted to "colour", even when part of a longer aesthetic name (e.g., `point_color`) (@clauswilke, #2649). -* `labs()` now has named arguments `title`, `subtitle`, `caption` and `tag` explicitly. +* `labs()` now has named arguments `title`, `subtitle`, `caption`, and `tag`. Also, `labs()` now accepts tidyeval (@yutannihilation, #2669). # ggplot2 3.0.0