diff --git a/NAMESPACE b/NAMESPACE index eea1693d..f0b94d09 100644 --- a/NAMESPACE +++ b/NAMESPACE @@ -43,6 +43,7 @@ export(type_vline) importFrom(grDevices,adjustcolor) importFrom(grDevices,as.raster) importFrom(grDevices,axisTicks) +importFrom(grDevices,cairo_pdf) importFrom(grDevices,col2rgb) importFrom(grDevices,colorRampPalette) importFrom(grDevices,convertColor) diff --git a/NEWS.md b/NEWS.md index 810d1be8..b32e27b9 100644 --- a/NEWS.md +++ b/NEWS.md @@ -4,11 +4,18 @@ _If you are viewing this file on CRAN, please check the [latest NEWS](https://grantmcdermott.com/tinyplot/NEWS.html) on our website where the formatting is also better._ -## Development +## 0.3.0.99 (dev version) -Bugs: +New features: + +- `tinyplot(..., file = "*.pdf")` will now default to using `cairo_pdf()` if + cairo graphics are supported on the user's machine. This should help to ensure + better fidelity of (non-standard) fonts in PDFs. (#311 @grantcdermott) + +Bugs fixes: -* The `cex` argument should be respected when using `type="bg"`. Thanks to @rjknell for report #307. +- The `cex` argument should be respected when using `type="bg"`. Thanks to + @rjknell for report #307 and @vincentarelbundock for the fix. ## 0.3.0 diff --git a/R/setup_device.R b/R/setup_device.R index f93ee78e..e3837748 100644 --- a/R/setup_device.R +++ b/R/setup_device.R @@ -14,11 +14,16 @@ setup_device = function(file, width, height) { # close interactive device if not already open if (isTRUE(fkdev)) dev.off() exttype = file_ext(filepath) - if (exttype == "jpg") exttype = "jpeg" + if (exttype == "pdf" && .tpar[["cairo"]]) { + exttype = "cairo" + } else if (exttype == "jpg") { + exttype = "jpeg" + } switch(exttype, png = png(filepath, width = filewidth, height = fileheight, units = "in", res = fileres), jpeg = jpeg(filepath, width = filewidth, height = fileheight, units = "in", res = fileres), pdf = pdf(filepath, width = filewidth, height = fileheight), + cairo = cairo_pdf(filepath, width = filewidth, height = fileheight), svg = svg(filepath, width = filewidth, height = fileheight), stop("\nUnsupported file extension. Only '.png', '.jpg', '.pdf', or '.svg' are allowed.\n") ) diff --git a/R/tinyplot.R b/R/tinyplot.R index bc8ea94b..ece4eeab 100644 --- a/R/tinyplot.R +++ b/R/tinyplot.R @@ -330,7 +330,7 @@ #' out existing `plot` calls for `tinyplot` (or its shorthand alias `plt`), #' without causing unexpected changes to the output. #' -#' @importFrom grDevices axisTicks adjustcolor colorRampPalette extendrange palette palette.colors palette.pals hcl.colors hcl.pals xy.coords png jpeg pdf svg dev.off dev.new dev.list +#' @importFrom grDevices axisTicks adjustcolor cairo_pdf colorRampPalette extendrange palette palette.colors palette.pals hcl.colors hcl.pals xy.coords png jpeg pdf svg dev.off dev.new dev.list #' @importFrom graphics abline arrows axis Axis box boxplot grconvertX grconvertY hist lines mtext par plot.default plot.new plot.window points polygon polypath segments rect text title #' @importFrom utils modifyList head tail #' @importFrom stats na.omit diff --git a/R/tpar.R b/R/tpar.R index 59a42c8c..d1e662df 100644 --- a/R/tpar.R +++ b/R/tpar.R @@ -51,6 +51,7 @@ #' #' * `adj.xlab`: Numeric value between 0 and 1 controlling the alignment of the x-axis label. #' * `adj.ylab`: Numeric value between 0 and 1 controlling the alignment of the y-axis label. +#' * `cairo`: Logical indicating whether \code{\link[grDevices]{cairo_pdf}} should be used when writing plots to PDF. If `FALSE`, then \code{\link[grDevices]{pdf}} will be used instead, with implications for embedding (non-standard) fonts. Only used if `tinyplot(..., file = ".pdf")` is called. Defaults to the value of `capabilities("cairo")`. #' * `dynmar`: Logical indicating whether `tinyplot` should attempt dynamic adjustment of margins to reduce whitespace and/or account for spacing of text elements (e.g., long horizontal y-axis labels). Note that this parameter is tightly coupled to internal `tinythemes()` logic and should _not_ be adjusted manually unless you really know what you are doing or don't mind risking unintended consequences to your plot. #' * `facet.bg`: Character or integer specifying the facet background colour. If an integer, will correspond to the user's default colour palette (see `palette`). Passed to `rect`. Defaults to `NULL` (none). #' * `facet.border`: Character or integer specifying the facet border colour. If an integer, will correspond to the user's default colour palette (see `palette`). Passed to `rect`. Defaults to `NA` (none). @@ -66,8 +67,8 @@ #' * `grid.lwd`: Non-negative numeric giving the line width of the panel grid lines. Defaults to `1`. #' * `grid`: Logical indicating whether a background panel grid should be added to plots automatically. Defaults to `NULL`, which is equivalent to `FALSE`. #' * `lmar`: A numeric vector of form `c(inner, outer)` that gives the margin padding, in terms of lines, around the automatic `tinyplot` legend. Defaults to `c(1.0, 0.1)`. The inner margin is the gap between the legend and the plot region, and the outer margin is the gap between the legend and the edge of the graphics device. -#' * `palette.qualitative`: Palette for qualitative colors. See the `palette` argumetn in `?tinyplot`. -#' * `palette.sequential`: Palette for sequential colors. See the `palette` argumetn in `?tinyplot`. +#' * `palette.qualitative`: Palette for qualitative colors. See the `palette` argument in `?tinyplot`. +#' * `palette.sequential`: Palette for sequential colors. See the `palette` argument in `?tinyplot`. #' * `ribbon.alpha`: Numeric factor in the range `[0,1]` for modifying the opacity alpha of "ribbon" and "area" type plots. Default value is `0.2`. #' #' @importFrom graphics par @@ -219,6 +220,7 @@ known_tpar = c( "cex.ylab", "col.xaxs", "col.yaxs", + "cairo", "dynmar", "facet.bg", "facet.border", @@ -263,6 +265,7 @@ assert_tpar = function(.tpar) { assert_numeric(.tpar[["adj.sub"]], len = 1, lower = 0, upper = 1, null.ok = TRUE, name = "adj.sub") assert_numeric(.tpar[["adj.xlab"]], len = 1, lower = 0, upper = 1, null.ok = TRUE, name = "adj.xlab") assert_numeric(.tpar[["adj.ylab"]], len = 1, lower = 0, upper = 1, null.ok = TRUE, name = "adj.ylab") + assert_flag(.tpar[["cairo"]], name = "cairo") assert_flag(.tpar[["dynmar"]], null.ok = FALSE, name = "dynmar") assert_numeric(.tpar[["lmar"]], len = 2, null.ok = TRUE, name = "lmar") assert_numeric(.tpar[["ribbon.alpha"]], len = 1, lower = 0, upper = 1, null.ok = TRUE, name = "ribbon.alpha") @@ -315,6 +318,9 @@ init_tpar = function(rm_hook = FALSE) { } } + .tpar$cairo = if (is.null(getOption("tinyplot_cairo"))) capabilities("cairo") else as.logical(getOption("tinyplot_cairo")) + + .tpar$dynmar = if (is.null(getOption("tinyplot_dynmar"))) FALSE else as.logical(getOption("tinyplot_dynmar")) # Figure output options if written to file diff --git a/man/tpar.Rd b/man/tpar.Rd index 2a937275..c1fc5914 100644 --- a/man/tpar.Rd +++ b/man/tpar.Rd @@ -62,6 +62,7 @@ you should rather use \code{par()} instead. \itemize{ \item \code{adj.xlab}: Numeric value between 0 and 1 controlling the alignment of the x-axis label. \item \code{adj.ylab}: Numeric value between 0 and 1 controlling the alignment of the y-axis label. +\item \code{cairo}: Logical indicating whether \code{\link[grDevices]{cairo_pdf}} should be used when writing plots to PDF. If \code{FALSE}, then \code{\link[grDevices]{pdf}} will be used instead, with implications for embedding (non-standard) fonts. Only used if \code{tinyplot(..., file = ".pdf")} is called. Defaults to the value of \code{capabilities("cairo")}. \item \code{dynmar}: Logical indicating whether \code{tinyplot} should attempt dynamic adjustment of margins to reduce whitespace and/or account for spacing of text elements (e.g., long horizontal y-axis labels). Note that this parameter is tightly coupled to internal \code{tinythemes()} logic and should \emph{not} be adjusted manually unless you really know what you are doing or don't mind risking unintended consequences to your plot. \item \code{facet.bg}: Character or integer specifying the facet background colour. If an integer, will correspond to the user's default colour palette (see \code{palette}). Passed to \code{rect}. Defaults to \code{NULL} (none). \item \code{facet.border}: Character or integer specifying the facet border colour. If an integer, will correspond to the user's default colour palette (see \code{palette}). Passed to \code{rect}. Defaults to \code{NA} (none). @@ -77,8 +78,8 @@ you should rather use \code{par()} instead. \item \code{grid.lwd}: Non-negative numeric giving the line width of the panel grid lines. Defaults to \code{1}. \item \code{grid}: Logical indicating whether a background panel grid should be added to plots automatically. Defaults to \code{NULL}, which is equivalent to \code{FALSE}. \item \code{lmar}: A numeric vector of form \code{c(inner, outer)} that gives the margin padding, in terms of lines, around the automatic \code{tinyplot} legend. Defaults to \code{c(1.0, 0.1)}. The inner margin is the gap between the legend and the plot region, and the outer margin is the gap between the legend and the edge of the graphics device. -\item \code{palette.qualitative}: Palette for qualitative colors. See the \code{palette} argumetn in \code{?tinyplot}. -\item \code{palette.sequential}: Palette for sequential colors. See the \code{palette} argumetn in \code{?tinyplot}. +\item \code{palette.qualitative}: Palette for qualitative colors. See the \code{palette} argument in \code{?tinyplot}. +\item \code{palette.sequential}: Palette for sequential colors. See the \code{palette} argument in \code{?tinyplot}. \item \code{ribbon.alpha}: Numeric factor in the range \verb{[0,1]} for modifying the opacity alpha of "ribbon" and "area" type plots. Default value is \code{0.2}. } } diff --git a/tinyplot.Rproj b/tinyplot.Rproj index 468aa2fa..dead6016 100644 --- a/tinyplot.Rproj +++ b/tinyplot.Rproj @@ -1,5 +1,4 @@ Version: 1.0 -ProjectId: a8b39023-e69c-4ca8-9eaf-0d4d82596b61 RestoreWorkspace: Default SaveWorkspace: Default