mirror of
https://github.com/rstudio/shiny.git
synced 2026-01-12 00:19:06 -05:00
Compare commits
24 Commits
cache-even
...
create-sco
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
98d4b5e487 | ||
|
|
32913f9d95 | ||
|
|
cbabf9a2a3 | ||
|
|
03e92c3336 | ||
|
|
997c39fdc0 | ||
|
|
bba2d1ee18 | ||
|
|
a60301810f | ||
|
|
6b261f76b1 | ||
|
|
3db5f21d90 | ||
|
|
121bfcb984 | ||
|
|
265de66946 | ||
|
|
79c5c9f95e | ||
|
|
3354a47e8a | ||
|
|
a1e1416d7a | ||
|
|
24b7a9907f | ||
|
|
0bb53e8ca5 | ||
|
|
ec12caaeba | ||
|
|
5bbf2aa57a | ||
|
|
84ad9997da | ||
|
|
9f6ce87443 | ||
|
|
1ff6c382bf | ||
|
|
c366c10ae1 | ||
|
|
950df1e25c | ||
|
|
909bfa8c14 |
@@ -1,7 +1,7 @@
|
||||
Package: shiny
|
||||
Type: Package
|
||||
Title: Web Application Framework for R
|
||||
Version: 1.1.0.9000
|
||||
Version: 1.1.0.9001
|
||||
Authors@R: c(
|
||||
person("Winston", "Chang", role = c("aut", "cre"), email = "winston@rstudio.com"),
|
||||
person("Joe", "Cheng", role = "aut", email = "joe@rstudio.com"),
|
||||
|
||||
10
NEWS.md
10
NEWS.md
@@ -1,14 +1,18 @@
|
||||
shiny 1.1.0.9000
|
||||
shiny 1.1.0.9001
|
||||
===========
|
||||
|
||||
## Full changelog
|
||||
|
||||
### Minor new features and improvements
|
||||
|
||||
* Added `renderCachedPlot()`, which stores plots in a cache so that they can be served up almost instantly. ([#1997](https://github.com/rstudio/shiny/pull/1997))
|
||||
|
||||
* Support for selecting variables of a data frame with the output values to be used within tidy evaluation. Added functions: `varSelectInput`, `varSelectizeInput`, `updateVarSelectInput`, `updateVarSelectizeInput`. ([#2091](https://github.com/rstudio/shiny/pull/2091))
|
||||
|
||||
* Addressed [#2042](https://github.com/rstudio/shiny/issues/2042): dates outside of `min`/`max` date range are now a lighter shade of grey to highlight the allowed range. ([#2087](https://github.com/rstudio/shiny/pull/2087))
|
||||
|
||||
* Added support for plot interaction when the plot is scaled. ([#2125](https://github.com/rstudio/shiny/pull/2125))
|
||||
|
||||
* Fixed [#1933](https://github.com/rstudio/shiny/issues/1933): extended server-side selectize to lists and optgroups. ([#2102](https://github.com/rstudio/shiny/pull/2102))
|
||||
|
||||
* Fixed [#1935](https://github.com/rstudio/shiny/issues/1935): correctly returns plot coordinates when using outer margins. ([#2108](https://github.com/rstudio/shiny/pull/2108))
|
||||
@@ -17,6 +21,10 @@ shiny 1.1.0.9000
|
||||
|
||||
* Added namespace support when freezing reactiveValue keys. [#2080](https://github.com/rstudio/shiny/pull/2080)
|
||||
|
||||
* Fixed [#2138](https://github.com/rstudio/shiny/issues/2138): Inputs that are part of a `renderUI` were no longer restoring correctly from bookmarked state. [#2139](https://github.com/rstudio/shiny/pull/2139)
|
||||
|
||||
* Fixed [#2093](https://github.com/rstudio/shiny/issues/2093): Make sure bookmark scope directory does not exist before trying to create it. [#2168](https://github.com/rstudio/shiny/pull/2168)
|
||||
|
||||
### Documentation Updates
|
||||
|
||||
* Addressed [#1864](https://github.com/rstudio/shiny/issues/1864) by changing `optgroup` documentation to use `list` instead of `c`. ([#2084](https://github.com/rstudio/shiny/pull/2084))
|
||||
|
||||
@@ -448,7 +448,13 @@ withRestoreContext <- function(ctx, expr) {
|
||||
|
||||
# Is there a current restore context?
|
||||
hasCurrentRestoreContext <- function() {
|
||||
restoreCtxStack$size() > 0
|
||||
if (restoreCtxStack$size() > 0)
|
||||
return(TRUE)
|
||||
domain <- getDefaultReactiveDomain()
|
||||
if (!is.null(domain) && !is.null(domain$restoreContext))
|
||||
return(TRUE)
|
||||
|
||||
return(FALSE)
|
||||
}
|
||||
|
||||
# Call to access the current restore context. First look on the restore
|
||||
|
||||
@@ -249,14 +249,20 @@ nearPoints <- function(df, coordinfo, xvar = NULL, yvar = NULL,
|
||||
x <- asNumber(df[[xvar]])
|
||||
y <- asNumber(df[[yvar]])
|
||||
|
||||
# Get the pixel coordinates of the point
|
||||
coordPx <- scaleCoords(coordinfo$x, coordinfo$y, coordinfo)
|
||||
# Get the coordinates of the point (in img pixel coordinates)
|
||||
point_img <- scaleCoords(coordinfo$x, coordinfo$y, coordinfo)
|
||||
|
||||
# Get pixel coordinates of data points
|
||||
dataPx <- scaleCoords(x, y, coordinfo)
|
||||
# Get coordinates of data points (in img pixel coordinates)
|
||||
data_img <- scaleCoords(x, y, coordinfo)
|
||||
|
||||
# Distances of data points to coordPx
|
||||
dists <- sqrt((dataPx$x - coordPx$x) ^ 2 + (dataPx$y - coordPx$y) ^ 2)
|
||||
# Get x/y distances (in css coordinates)
|
||||
dist_css <- list(
|
||||
x = (data_img$x - point_img$x) / coordinfo$pixelratio$x,
|
||||
y = (data_img$y - point_img$y) / coordinfo$pixelratio$y
|
||||
)
|
||||
|
||||
# Distances of data points to the target point, in css pixels.
|
||||
dists <- sqrt(dist_css$x^2 + dist_css$y^2)
|
||||
|
||||
if (addDist)
|
||||
df$dist_ <- dists
|
||||
@@ -298,50 +304,56 @@ nearPoints <- function(df, coordinfo, xvar = NULL, yvar = NULL,
|
||||
# The coordinfo data structure will look something like the examples below.
|
||||
# For base graphics, `mapping` is empty, and there are no panelvars:
|
||||
# List of 7
|
||||
# $ x : num 4.37
|
||||
# $ y : num 12
|
||||
# $ mapping: Named list()
|
||||
# $ domain :List of 4
|
||||
# $ x : num 4.37
|
||||
# $ y : num 12
|
||||
# $ pixelratio:List of 2
|
||||
# ..$ x: num 2
|
||||
# ..$ y: num 2
|
||||
# $ mapping : Named list()
|
||||
# $ domain :List of 4
|
||||
# ..$ left : num 1.36
|
||||
# ..$ right : num 5.58
|
||||
# ..$ bottom: num 9.46
|
||||
# ..$ top : num 34.8
|
||||
# $ range :List of 4
|
||||
# $ range :List of 4
|
||||
# ..$ left : num 58
|
||||
# ..$ right : num 429
|
||||
# ..$ bottom: num 226
|
||||
# ..$ top : num 58
|
||||
# $ log :List of 2
|
||||
# $ log :List of 2
|
||||
# ..$ x: NULL
|
||||
# ..$ y: NULL
|
||||
# $ .nonce : num 0.343
|
||||
# $ .nonce : num 0.343
|
||||
#
|
||||
# For ggplot2, the mapping vars usually will be included, and if faceting is
|
||||
# used, they will be listed as panelvars:
|
||||
# List of 9
|
||||
# $ x : num 3.78
|
||||
# $ y : num 17.1
|
||||
# $ panelvar1: int 6
|
||||
# $ panelvar2: int 0
|
||||
# $ mapping :List of 4
|
||||
# $ x : num 3.78
|
||||
# $ y : num 17.1
|
||||
# $ pixelratio:List of 2
|
||||
# ..$ x: num 2
|
||||
# ..$ y: num 2
|
||||
# $ panelvar1 : int 6
|
||||
# $ panelvar2 : int 0
|
||||
# $ mapping :List of 4
|
||||
# ..$ x : chr "wt"
|
||||
# ..$ y : chr "mpg"
|
||||
# ..$ panelvar1: chr "cyl"
|
||||
# ..$ panelvar2: chr "am"
|
||||
# $ domain :List of 4
|
||||
# $ domain :List of 4
|
||||
# ..$ left : num 1.32
|
||||
# ..$ right : num 5.62
|
||||
# ..$ bottom: num 9.22
|
||||
# ..$ top : num 35.1
|
||||
# $ range :List of 4
|
||||
# $ range :List of 4
|
||||
# ..$ left : num 172
|
||||
# ..$ right : num 300
|
||||
# ..$ bottom: num 144
|
||||
# ..$ top : num 28.5
|
||||
# $ log :List of 2
|
||||
# $ log :List of 2
|
||||
# ..$ x: NULL
|
||||
# ..$ y: NULL
|
||||
# $ .nonce : num 0.603
|
||||
# $ .nonce : num 0.603
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -2028,55 +2028,13 @@ observeEvent <- function(eventExpr, handlerExpr,
|
||||
invisible(o)
|
||||
}
|
||||
|
||||
#' @section \code{eventReactive} caching:
|
||||
#'
|
||||
#' Like regular \code{\link{reactive}} expressions, the most recent value of a
|
||||
#' \code{eventReactive} is always cached. (Observers are not cached because
|
||||
#' they are used for their side-effects, not their values.) If a
|
||||
#' \code{reactive} or \code{eventReactive} named \code{r} is called with
|
||||
#' \code{r()} and then called again (without being invalidated in between),
|
||||
#' then the second call will simply return the most recent value.
|
||||
#'
|
||||
#' An \code{eventReactive} allows for caching of previous values, by using the
|
||||
#' \code{cache} parameter. When this additional caching is used, a key-value
|
||||
#' store is used, where the result of the \code{eventExpr} is used as the key.
|
||||
#' More specifically, the result from the \code{eventExpr} is combined with
|
||||
#' the \code{eventReactive}'s \code{label} (which defaults to a string
|
||||
#' representation of the \code{expr} code), and they are serialized and hashed
|
||||
#' to generate the key.
|
||||
#'
|
||||
#' When an additional cache is used, it allow for sharing cached values with
|
||||
#' other sessions. If you use \code{cache="session"}, then a separate cache
|
||||
#' will be used for each user session. If you use \code{cache="app"}, then the
|
||||
#' cache for the \code{eventReactive} will be shared across multiple client
|
||||
#' sessions accessing the same Shiny application -- because the \code{label}
|
||||
#' will (by default) be the same when the \code{expr} code is the same, an
|
||||
#' \code{eventReactive} in one session can share values with the corresponding
|
||||
#' \code{eventReactive} in another session. Whenever they have the same result
|
||||
#' for \code{eventExpr}, the value can be drawn from the cache instead of
|
||||
#' being recomputed.
|
||||
#'
|
||||
#' Other types of caching are possible, by passing a cache object with
|
||||
#' \code{$get()} and \code{$set()} methods. It is possible to cache the values
|
||||
#' to disk, or in an external database, and have the cache persist across
|
||||
#' application restarts. See \code{\link{renderCachedPlot}} for more
|
||||
#' information about caching with Shiny.
|
||||
#'
|
||||
#'
|
||||
#' @param cache Extra caching to use for \code{eventReactive}. Note that the
|
||||
#' most recent value is always cached, but this option allows you to cache
|
||||
#' previous values based on the value of \code{eventExpr}. If \code{NULL} (the
|
||||
#' default), do not use extra caching. Other possible values are \code{"app"}
|
||||
#' for an application-level cache, \code{"session"} for a session-level cache,
|
||||
#' or a cache object with \code{$get()} and \code{$set()} methods. See
|
||||
#' \code{\link{renderCachedPlot}} for more information about using caching.
|
||||
#' @rdname observeEvent
|
||||
#' @export
|
||||
eventReactive <- function(eventExpr, valueExpr,
|
||||
event.env = parent.frame(), event.quoted = FALSE,
|
||||
value.env = parent.frame(), value.quoted = FALSE,
|
||||
label = NULL, domain = getDefaultReactiveDomain(),
|
||||
ignoreNULL = TRUE, ignoreInit = FALSE, cache = NULL) {
|
||||
ignoreNULL = TRUE, ignoreInit = FALSE) {
|
||||
|
||||
eventFunc <- exprToFunction(eventExpr, event.env, event.quoted)
|
||||
if (is.null(label))
|
||||
@@ -2088,37 +2046,6 @@ eventReactive <- function(eventExpr, valueExpr,
|
||||
|
||||
initialized <- FALSE
|
||||
|
||||
ensureCacheSetup <- function() {
|
||||
# For our purposes, cache objects must support these methods.
|
||||
isCacheObject <- function(x) {
|
||||
# Use tryCatch in case the object does not support `$`.
|
||||
tryCatch(
|
||||
is.function(x$get) && is.function(x$set),
|
||||
error = function(e) FALSE
|
||||
)
|
||||
}
|
||||
|
||||
if (is.null(cache)) {
|
||||
# No cache
|
||||
return()
|
||||
|
||||
} else if (isCacheObject(cache)) {
|
||||
# If `cache` is already a cache object, do nothing
|
||||
return()
|
||||
|
||||
} else if (identical(cache, "app")) {
|
||||
cache <<- getShinyOption("cache")
|
||||
|
||||
} else if (identical(cache, "session")) {
|
||||
cache <<- session$getCache()
|
||||
|
||||
} else {
|
||||
stop('`cache` must either be NULL, "app", "session", or a cache object with methods, `$get`, and `$set`.')
|
||||
}
|
||||
}
|
||||
ensureCacheSetup()
|
||||
|
||||
|
||||
invisible(reactive({
|
||||
hybrid_chain(
|
||||
eventFunc(),
|
||||
@@ -2130,20 +2057,7 @@ eventReactive <- function(eventExpr, valueExpr,
|
||||
|
||||
req(!ignoreNULL || !isNullEvent(value))
|
||||
|
||||
if (is.null(cache)) {
|
||||
return( isolate(handlerFunc()) )
|
||||
|
||||
} else {
|
||||
key <- digest::digest(list(value, label), "sha256")
|
||||
cached_value <- cache$get(key)
|
||||
if (!is.key_missing(cached_value)) {
|
||||
return(cached_value)
|
||||
}
|
||||
|
||||
result <- isolate(handlerFunc())
|
||||
cache$set(key, result)
|
||||
return(result)
|
||||
}
|
||||
isolate(handlerFunc())
|
||||
}
|
||||
)
|
||||
}, label = label, domain = domain, ..stacktraceon = FALSE))
|
||||
|
||||
@@ -129,6 +129,12 @@
|
||||
#' create a \code{\link{memoryCache}} or \code{\link{diskCache}}, and pass it
|
||||
#' as the \code{cache} argument of \code{renderCachedPlot}.
|
||||
#'
|
||||
#' @section Interactive plots:
|
||||
#'
|
||||
#' \code{renderCachedPlot} can be used to create interactive plots. See
|
||||
#' \code{\link{plotOutput}} for more information and examples.
|
||||
#'
|
||||
#'
|
||||
#' @inheritParams renderPlot
|
||||
#' @param cacheKeyExpr An expression that returns a cache key. This key should
|
||||
#' be a unique identifier for a plot: the assumption is that if the cache key
|
||||
@@ -430,7 +436,7 @@ renderCachedPlot <- function(expr,
|
||||
height <- fitDims$height
|
||||
pixelratio <- session$clientData$pixelratio %OR% 1
|
||||
|
||||
key <- digest::digest(list(outputName, userCacheKeyResult, width, height, res, pixelratio), "sha256")
|
||||
key <- digest::digest(list(outputName, userCacheKeyResult, width, height, res, pixelratio), "xxhash64")
|
||||
|
||||
plotObj <- cache$get(key)
|
||||
|
||||
|
||||
251
R/render-plot.R
251
R/render-plot.R
@@ -162,7 +162,7 @@ resizeSavedPlot <- function(name, session, result, width, height, pixelratio, re
|
||||
coordmap <- NULL
|
||||
outfile <- plotPNG(function() {
|
||||
grDevices::replayPlot(result$recordedPlot)
|
||||
coordmap <<- getCoordmap(result$plotResult, width, height, pixelratio, res)
|
||||
coordmap <<- getCoordmap(result$plotResult, width*pixelratio, height*pixelratio, res*pixelratio)
|
||||
}, width = width*pixelratio, height = height*pixelratio, res = res*pixelratio, ...)
|
||||
on.exit(unlink(outfile), add = TRUE)
|
||||
|
||||
@@ -231,7 +231,7 @@ drawPlot <- function(name, session, func, width, height, pixelratio, res, ...) {
|
||||
list(
|
||||
plotResult = value,
|
||||
recordedPlot = grDevices::recordPlot(),
|
||||
coordmap = getCoordmap(value, width, height, pixelratio, res),
|
||||
coordmap = getCoordmap(value, width*pixelratio, height*pixelratio, res*pixelratio),
|
||||
pixelratio = pixelratio,
|
||||
res = res
|
||||
)
|
||||
@@ -284,22 +284,26 @@ custom_print.ggplot <- function(x) {
|
||||
# below. For base graphics:
|
||||
# plot(mtcars$wt, mtcars$mpg)
|
||||
# str(getPrevPlotCoordmap(400, 300))
|
||||
# List of 1
|
||||
# $ :List of 4
|
||||
# ..$ domain :List of 4
|
||||
# .. ..$ left : num 1.36
|
||||
# .. ..$ right : num 5.58
|
||||
# .. ..$ bottom: num 9.46
|
||||
# .. ..$ top : num 34.8
|
||||
# ..$ range :List of 4
|
||||
# .. ..$ left : num 50.4
|
||||
# .. ..$ right : num 373
|
||||
# .. ..$ bottom: num 199
|
||||
# .. ..$ top : num 79.6
|
||||
# ..$ log :List of 2
|
||||
# .. ..$ x: NULL
|
||||
# .. ..$ y: NULL
|
||||
# ..$ mapping: Named list()
|
||||
# List of 2
|
||||
# $ panels:List of 1
|
||||
# ..$ :List of 4
|
||||
# .. ..$ domain :List of 4
|
||||
# .. .. ..$ left : num 1.36
|
||||
# .. .. ..$ right : num 5.58
|
||||
# .. .. ..$ bottom: num 9.46
|
||||
# .. .. ..$ top : num 34.8
|
||||
# .. ..$ range :List of 4
|
||||
# .. .. ..$ left : num 65.6
|
||||
# .. .. ..$ right : num 366
|
||||
# .. .. ..$ bottom: num 238
|
||||
# .. .. ..$ top : num 48.2
|
||||
# .. ..$ log :List of 2
|
||||
# .. .. ..$ x: NULL
|
||||
# .. .. ..$ y: NULL
|
||||
# .. ..$ mapping: Named list()
|
||||
# $ dims :List of 2
|
||||
# ..$ width : num 400
|
||||
# ..$ height: num 300
|
||||
#
|
||||
# For ggplot2, first you need to define the print.ggplot function from inside
|
||||
# renderPlot, then use it to print the plot:
|
||||
@@ -318,29 +322,33 @@ custom_print.ggplot <- function(x) {
|
||||
# }
|
||||
#
|
||||
# p <- print(ggplot(mtcars, aes(wt, mpg)) + geom_point())
|
||||
# str(getGgplotCoordmap(p, 1, 72))
|
||||
# List of 1
|
||||
# $ :List of 10
|
||||
# ..$ panel : int 1
|
||||
# ..$ row : int 1
|
||||
# ..$ col : int 1
|
||||
# ..$ panel_vars: Named list()
|
||||
# ..$ log :List of 2
|
||||
# .. ..$ x: NULL
|
||||
# .. ..$ y: NULL
|
||||
# ..$ domain :List of 4
|
||||
# .. ..$ left : num 1.32
|
||||
# .. ..$ right : num 5.62
|
||||
# .. ..$ bottom: num 9.22
|
||||
# .. ..$ top : num 35.1
|
||||
# ..$ mapping :List of 2
|
||||
# .. ..$ x: chr "wt"
|
||||
# .. ..$ y: chr "mpg"
|
||||
# ..$ range :List of 4
|
||||
# .. ..$ left : num 40.8
|
||||
# .. ..$ right : num 446
|
||||
# .. ..$ bottom: num 263
|
||||
# .. ..$ top : num 14.4
|
||||
# str(getGgplotCoordmap(p, 400, 300, 72))
|
||||
# List of 2
|
||||
# $ panels:List of 1
|
||||
# ..$ :List of 8
|
||||
# .. ..$ panel : num 1
|
||||
# .. ..$ row : num 1
|
||||
# .. ..$ col : num 1
|
||||
# .. ..$ panel_vars: Named list()
|
||||
# .. ..$ log :List of 2
|
||||
# .. .. ..$ x: NULL
|
||||
# .. .. ..$ y: NULL
|
||||
# .. ..$ domain :List of 4
|
||||
# .. .. ..$ left : num 1.32
|
||||
# .. .. ..$ right : num 5.62
|
||||
# .. .. ..$ bottom: num 9.22
|
||||
# .. .. ..$ top : num 35.1
|
||||
# .. ..$ mapping :List of 2
|
||||
# .. .. ..$ x: chr "wt"
|
||||
# .. .. ..$ y: chr "mpg"
|
||||
# .. ..$ range :List of 4
|
||||
# .. .. ..$ left : num 33.3
|
||||
# .. .. ..$ right : num 355
|
||||
# .. .. ..$ bottom: num 328
|
||||
# .. .. ..$ top : num 5.48
|
||||
# $ dims :List of 2
|
||||
# ..$ width : num 400
|
||||
# ..$ height: num 300
|
||||
#
|
||||
# With a faceted ggplot2 plot, the outer list contains two objects, each of
|
||||
# which represents one panel. In this example, there is one panelvar, but there
|
||||
@@ -348,59 +356,63 @@ custom_print.ggplot <- function(x) {
|
||||
# mtc <- mtcars
|
||||
# mtc$am <- factor(mtc$am)
|
||||
# p <- print(ggplot(mtc, aes(wt, mpg)) + geom_point() + facet_wrap(~ am))
|
||||
# str(getGgplotCoordmap(p, 1, 72))
|
||||
# str(getGgplotCoordmap(p, 400, 300, 72))
|
||||
# List of 2
|
||||
# $ :List of 10
|
||||
# ..$ panel : int 1
|
||||
# ..$ row : int 1
|
||||
# ..$ col : int 1
|
||||
# ..$ panel_vars:List of 1
|
||||
# .. ..$ panelvar1: Factor w/ 2 levels "0","1": 1
|
||||
# ..$ log :List of 2
|
||||
# .. ..$ x: NULL
|
||||
# .. ..$ y: NULL
|
||||
# ..$ domain :List of 4
|
||||
# .. ..$ left : num 1.32
|
||||
# .. ..$ right : num 5.62
|
||||
# .. ..$ bottom: num 9.22
|
||||
# .. ..$ top : num 35.1
|
||||
# ..$ mapping :List of 3
|
||||
# .. ..$ x : chr "wt"
|
||||
# .. ..$ y : chr "mpg"
|
||||
# .. ..$ panelvar1: chr "am"
|
||||
# ..$ range :List of 4
|
||||
# .. ..$ left : num 45.6
|
||||
# .. ..$ right : num 317
|
||||
# .. ..$ bottom: num 251
|
||||
# .. ..$ top : num 35.7
|
||||
# $ :List of 10
|
||||
# ..$ panel : int 2
|
||||
# ..$ row : int 1
|
||||
# ..$ col : int 2
|
||||
# ..$ panel_vars:List of 1
|
||||
# .. ..$ panelvar1: Factor w/ 2 levels "0","1": 2
|
||||
# ..$ log :List of 2
|
||||
# .. ..$ x: NULL
|
||||
# .. ..$ y: NULL
|
||||
# ..$ domain :List of 4
|
||||
# .. ..$ left : num 1.32
|
||||
# .. ..$ right : num 5.62
|
||||
# .. ..$ bottom: num 9.22
|
||||
# .. ..$ top : num 35.1
|
||||
# ..$ mapping :List of 3
|
||||
# .. ..$ x : chr "wt"
|
||||
# .. ..$ y : chr "mpg"
|
||||
# .. ..$ panelvar1: chr "am"
|
||||
# ..$ range :List of 4
|
||||
# .. ..$ left : num 322
|
||||
# .. ..$ right : num 594
|
||||
# .. ..$ bottom: num 251
|
||||
# .. ..$ top : num 35.7
|
||||
# $ panels:List of 2
|
||||
# ..$ :List of 8
|
||||
# .. ..$ panel : num 1
|
||||
# .. ..$ row : int 1
|
||||
# .. ..$ col : int 1
|
||||
# .. ..$ panel_vars:List of 1
|
||||
# .. .. ..$ panelvar1: Factor w/ 2 levels "0","1": 1
|
||||
# .. ..$ log :List of 2
|
||||
# .. .. ..$ x: NULL
|
||||
# .. .. ..$ y: NULL
|
||||
# .. ..$ domain :List of 4
|
||||
# .. .. ..$ left : num 1.32
|
||||
# .. .. ..$ right : num 5.62
|
||||
# .. .. ..$ bottom: num 9.22
|
||||
# .. .. ..$ top : num 35.1
|
||||
# .. ..$ mapping :List of 3
|
||||
# .. .. ..$ x : chr "wt"
|
||||
# .. .. ..$ y : chr "mpg"
|
||||
# .. .. ..$ panelvar1: chr "am"
|
||||
# .. ..$ range :List of 4
|
||||
# .. .. ..$ left : num 33.3
|
||||
# .. .. ..$ right : num 191
|
||||
# .. .. ..$ bottom: num 328
|
||||
# .. .. ..$ top : num 23.1
|
||||
# ..$ :List of 8
|
||||
# .. ..$ panel : num 2
|
||||
# .. ..$ row : int 1
|
||||
# .. ..$ col : int 2
|
||||
# .. ..$ panel_vars:List of 1
|
||||
# .. .. ..$ panelvar1: Factor w/ 2 levels "0","1": 2
|
||||
# .. ..$ log :List of 2
|
||||
# .. .. ..$ x: NULL
|
||||
# .. .. ..$ y: NULL
|
||||
# .. ..$ domain :List of 4
|
||||
# .. .. ..$ left : num 1.32
|
||||
# .. .. ..$ right : num 5.62
|
||||
# .. .. ..$ bottom: num 9.22
|
||||
# .. .. ..$ top : num 35.1
|
||||
# .. ..$ mapping :List of 3
|
||||
# .. .. ..$ x : chr "wt"
|
||||
# .. .. ..$ y : chr "mpg"
|
||||
# .. .. ..$ panelvar1: chr "am"
|
||||
# .. ..$ range :List of 4
|
||||
# .. .. ..$ left : num 197
|
||||
# .. .. ..$ right : num 355
|
||||
# .. .. ..$ bottom: num 328
|
||||
# .. .. ..$ top : num 23.1
|
||||
# $ dims :List of 2
|
||||
# ..$ width : num 400
|
||||
# ..$ height: num 300
|
||||
|
||||
|
||||
getCoordmap <- function(x, width, height, pixelratio, res) {
|
||||
getCoordmap <- function(x, width, height, res) {
|
||||
if (inherits(x, "ggplot_build_gtable")) {
|
||||
getGgplotCoordmap(x, pixelratio, res)
|
||||
getGgplotCoordmap(x, width, height, res)
|
||||
} else {
|
||||
getPrevPlotCoordmap(width, height)
|
||||
}
|
||||
@@ -420,7 +432,7 @@ getPrevPlotCoordmap <- function(width, height) {
|
||||
}
|
||||
|
||||
# Wrapped in double list because other types of plots can have multiple panels.
|
||||
list(list(
|
||||
panel_info <- list(list(
|
||||
# Bounds of the plot area, in data space
|
||||
domain = list(
|
||||
left = usrCoords[1],
|
||||
@@ -444,27 +456,43 @@ getPrevPlotCoordmap <- function(width, height) {
|
||||
# (not an array) in JSON.
|
||||
mapping = list(x = NULL)[0]
|
||||
))
|
||||
|
||||
list(
|
||||
panels = panel_info,
|
||||
dims = list(
|
||||
width = width,
|
||||
height =height
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
# Given a ggplot_build_gtable object, return a coordmap for it.
|
||||
getGgplotCoordmap <- function(p, pixelratio, res) {
|
||||
getGgplotCoordmap <- function(p, width, height, res) {
|
||||
if (!inherits(p, "ggplot_build_gtable"))
|
||||
return(NULL)
|
||||
|
||||
tryCatch({
|
||||
# Get info from built ggplot object
|
||||
info <- find_panel_info(p$build)
|
||||
panel_info <- find_panel_info(p$build)
|
||||
|
||||
# Get ranges from gtable - it's possible for this to return more elements than
|
||||
# info, because it calculates positions even for panels that aren't present.
|
||||
# This can happen with facet_wrap.
|
||||
ranges <- find_panel_ranges(p$gtable, pixelratio, res)
|
||||
ranges <- find_panel_ranges(p$gtable, res)
|
||||
|
||||
for (i in seq_along(info)) {
|
||||
info[[i]]$range <- ranges[[i]]
|
||||
for (i in seq_along(panel_info)) {
|
||||
panel_info[[i]]$range <- ranges[[i]]
|
||||
}
|
||||
|
||||
return(info)
|
||||
return(
|
||||
list(
|
||||
panels = panel_info,
|
||||
dims = list(
|
||||
width = width,
|
||||
height = height
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
}, error = function(e) {
|
||||
# If there was an error extracting info from the ggplot object, just return
|
||||
@@ -491,13 +519,11 @@ find_panel_info <- function(b) {
|
||||
# This is for ggplot2>2.2.1, after an API was introduced for extracting
|
||||
# information about the plot object.
|
||||
find_panel_info_api <- function(b) {
|
||||
# Workaround for check NOTE, until ggplot2 >2.2.1 is released
|
||||
colon_colon <- `::`
|
||||
# Given a built ggplot object, return x and y domains (data space coords) for
|
||||
# each panel.
|
||||
layout <- colon_colon("ggplot2", "summarise_layout")(b)
|
||||
coord <- colon_colon("ggplot2", "summarise_coord")(b)
|
||||
layers <- colon_colon("ggplot2", "summarise_layers")(b)
|
||||
layout <- ggplot2::summarise_layout(b)
|
||||
coord <- ggplot2::summarise_coord(b)
|
||||
layers <- ggplot2::summarise_layers(b)
|
||||
|
||||
# Given x and y scale objects and a coord object, return a list that has
|
||||
# the bases of log transformations for x and y, or NULL if it's not a
|
||||
@@ -827,7 +853,7 @@ find_panel_info_non_api <- function(b, ggplot_format) {
|
||||
|
||||
|
||||
# Given a gtable object, return the x and y ranges (in pixel dimensions)
|
||||
find_panel_ranges <- function(g, pixelratio, res) {
|
||||
find_panel_ranges <- function(g, res) {
|
||||
# Given a vector of unit objects, return logical vector indicating which ones
|
||||
# are "null" units. These units use the remaining available width/height --
|
||||
# that is, the space not occupied by elements that have an absolute size.
|
||||
@@ -957,26 +983,15 @@ find_panel_ranges <- function(g, pixelratio, res) {
|
||||
layout <- layout[order(layout$t, layout$l), ]
|
||||
layout$panel <- seq_len(nrow(layout))
|
||||
|
||||
# When using a HiDPI client on a Linux server, the pixel
|
||||
# dimensions are doubled, so we have to divide the dimensions by
|
||||
# `pixelratio`. When a HiDPI client is used on a Mac server (with
|
||||
# the quartz device), the pixel dimensions _aren't_ doubled, even though
|
||||
# the image has double size. In the latter case we don't have to scale the
|
||||
# numbers down.
|
||||
pix_ratio <- 1
|
||||
if (!grepl("^quartz", names(grDevices::dev.cur()))) {
|
||||
pix_ratio <- pixelratio
|
||||
}
|
||||
|
||||
# Return list of lists, where each inner list has left, right, top, bottom
|
||||
# values for a panel
|
||||
lapply(seq_len(nrow(layout)), function(i) {
|
||||
p <- layout[i, , drop = FALSE]
|
||||
list(
|
||||
left = x_pos[p$l - 1] / pix_ratio,
|
||||
right = x_pos[p$r] / pix_ratio,
|
||||
bottom = y_pos[p$b] / pix_ratio,
|
||||
top = y_pos[p$t - 1] / pix_ratio
|
||||
left = x_pos[p$l - 1],
|
||||
right = x_pos[p$r],
|
||||
bottom = y_pos[p$b],
|
||||
top = y_pos[p$t - 1]
|
||||
)
|
||||
})
|
||||
}
|
||||
|
||||
@@ -916,9 +916,11 @@ ShinySession <- R6Class(
|
||||
# Create subdir for this scope
|
||||
if (!is.null(state$dir)) {
|
||||
scopeState$dir <- file.path(state$dir, namespace)
|
||||
res <- dir.create(scopeState$dir)
|
||||
if (res == FALSE) {
|
||||
stop("Error creating subdirectory for scope ", namespace)
|
||||
if (!dirExists(scopeState$dir)) {
|
||||
res <- dir.create(scopeState$dir)
|
||||
if (res == FALSE) {
|
||||
stop("Error creating subdirectory for scope ", namespace)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because one or more lines are too long
8
inst/www/shared/shiny.min.js
vendored
8
inst/www/shared/shiny.min.js
vendored
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -16,7 +16,7 @@ eventReactive(eventExpr, valueExpr, event.env = parent.frame(),
|
||||
event.quoted = FALSE, value.env = parent.frame(),
|
||||
value.quoted = FALSE, label = NULL,
|
||||
domain = getDefaultReactiveDomain(), ignoreNULL = TRUE,
|
||||
ignoreInit = FALSE, cache = NULL)
|
||||
ignoreInit = FALSE)
|
||||
}
|
||||
\arguments{
|
||||
\item{eventExpr}{A (quoted or unquoted) expression that represents the event;
|
||||
@@ -84,14 +84,6 @@ this is the calling environment.}
|
||||
\item{value.quoted}{Is the \code{valueExpr} expression quoted? By default,
|
||||
this is \code{FALSE}. This is useful when you want to use an expression
|
||||
that is stored in a variable; to do so, it must be quoted with \code{quote()}.}
|
||||
|
||||
\item{cache}{Extra caching to use for \code{eventReactive}. Note that the
|
||||
most recent value is always cached, but this option allows you to cache
|
||||
previous values based on the value of \code{eventExpr}. If \code{NULL} (the
|
||||
default), do not use extra caching. Other possible values are \code{"app"}
|
||||
for an application-level cache, \code{"session"} for a session-level cache,
|
||||
or a cache object with \code{$get()} and \code{$set()} methods. See
|
||||
\code{\link{renderCachedPlot}} for more information about using caching.}
|
||||
}
|
||||
\value{
|
||||
\code{observeEvent} returns an observer reference class object (see
|
||||
@@ -192,42 +184,6 @@ these:
|
||||
}
|
||||
}
|
||||
|
||||
\section{\code{eventReactive} caching}{
|
||||
|
||||
|
||||
Like regular \code{\link{reactive}} expressions, the most recent value of a
|
||||
\code{eventReactive} is always cached. (Observers are not cached because
|
||||
they are used for their side-effects, not their values.) If a
|
||||
\code{reactive} or \code{eventReactive} named \code{r} is called with
|
||||
\code{r()} and then called again (without being invalidated in between),
|
||||
then the second call will simply return the most recent value.
|
||||
|
||||
An \code{eventReactive} allows for caching of previous values, by using the
|
||||
\code{cache} parameter. When this additional caching is used, a key-value
|
||||
store is used, where the result of the \code{eventExpr} is used as the key.
|
||||
More specifically, the result from the \code{eventExpr} is combined with
|
||||
the \code{eventReactive}'s \code{label} (which defaults to a string
|
||||
representation of the \code{expr} code), and they are serialized and hashed
|
||||
to generate the key.
|
||||
|
||||
When an additional cache is used, it allow for sharing cached values with
|
||||
other sessions. If you use \code{cache="session"}, then a separate cache
|
||||
will be used for each user session. If you use \code{cache="app"}, then the
|
||||
cache for the \code{eventReactive} will be shared across multiple client
|
||||
sessions accessing the same Shiny application -- because the \code{label}
|
||||
will (by default) be the same when the \code{expr} code is the same, an
|
||||
\code{eventReactive} in one session can share values with the corresponding
|
||||
\code{eventReactive} in another session. Whenever they have the same result
|
||||
for \code{eventExpr}, the value can be drawn from the cache instead of
|
||||
being recomputed.
|
||||
|
||||
Other types of caching are possible, by passing a cache object with
|
||||
\code{$get()} and \code{$set()} methods. It is possible to cache the values
|
||||
to disk, or in an external database, and have the cache persist across
|
||||
application restarts. See \code{\link{renderCachedPlot}} for more
|
||||
information about caching with Shiny.
|
||||
}
|
||||
|
||||
\examples{
|
||||
## Only run this example in interactive R sessions
|
||||
if (interactive()) {
|
||||
|
||||
@@ -169,6 +169,13 @@ will not have cache key collisions.
|
||||
as the \code{cache} argument of \code{renderCachedPlot}.
|
||||
}
|
||||
|
||||
\section{Interactive plots}{
|
||||
|
||||
|
||||
\code{renderCachedPlot} can be used to create interactive plots. See
|
||||
\code{\link{plotOutput}} for more information and examples.
|
||||
}
|
||||
|
||||
\examples{
|
||||
## Only run examples in interactive R sessions
|
||||
if (interactive()) {
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -249,11 +249,17 @@ function mapValues(obj, f) {
|
||||
const newObj = {};
|
||||
for (let key in obj) {
|
||||
if (obj.hasOwnProperty(key))
|
||||
newObj[key] = f(obj[key]);
|
||||
newObj[key] = f(obj[key], key, obj);
|
||||
}
|
||||
return newObj;
|
||||
}
|
||||
|
||||
// This is does the same as Number.isNaN, but that function unfortunately does
|
||||
// not exist in any version of IE.
|
||||
function isnan(x) {
|
||||
return typeof(x) === 'number' && isNaN(x);
|
||||
}
|
||||
|
||||
// Binary equality function used by the equal function.
|
||||
function _equal(x, y) {
|
||||
if ($.type(x) === "object" && $.type(y) === "object") {
|
||||
|
||||
@@ -21,50 +21,52 @@ test_that("ggplot coordmap", {
|
||||
scale_x_continuous(expand = c(0, 0)) +
|
||||
scale_y_continuous(expand = c(0, 0))
|
||||
png(tmpfile, width = 500, height = 500)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 500, 72)
|
||||
dev.off()
|
||||
|
||||
expect_equal(m$dims, list(width = 500, height = 500))
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(m[[1]]$mapping, list(x = "xvar", y = "yvar"))
|
||||
expect_equal(m$panels[[1]]$mapping, list(x = "xvar", y = "yvar"))
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=0, right=5, bottom=10, top=20))
|
||||
)
|
||||
# Check for no log bases
|
||||
expect_equal(
|
||||
sortList(m[[1]]$log),
|
||||
sortList(m$panels[[1]]$log),
|
||||
sortList(list(x=NULL, y=NULL))
|
||||
)
|
||||
# panel_vars should be an empty named list
|
||||
expect_identical(m[[1]]$panel_vars, list(a=1)[0])
|
||||
expect_identical(m$panels[[1]]$panel_vars, list(a=1)[0])
|
||||
# Sanity check for ranges. Checking exact range values isn't feasible due to
|
||||
# variations in graphics devices, and possible changes to positioning in
|
||||
# ggplot2.
|
||||
expect_true(m[[1]]$range$left > 20 && m[[1]]$range$left < 70)
|
||||
expect_true(m[[1]]$range$right > 480 && m[[1]]$range$right < 499)
|
||||
expect_true(m[[1]]$range$bottom > 450 && m[[1]]$range$bottom < 490)
|
||||
expect_true(m[[1]]$range$top > 1 && m[[1]]$range$top < 20)
|
||||
expect_true(m$panels[[1]]$range$left > 20 && m$panels[[1]]$range$left < 70)
|
||||
expect_true(m$panels[[1]]$range$right > 480 && m$panels[[1]]$range$right < 499)
|
||||
expect_true(m$panels[[1]]$range$bottom > 450 && m$panels[[1]]$range$bottom < 490)
|
||||
expect_true(m$panels[[1]]$range$top > 1 && m$panels[[1]]$range$top < 20)
|
||||
|
||||
|
||||
# Scatterplot where aes() is declared in geom
|
||||
p <- ggplot(dat, aes(xvar)) + geom_point(aes(y=yvar))
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 500, 72)
|
||||
dev.off()
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(sortList(m[[1]]$mapping), list(x = "xvar", y = "yvar"))
|
||||
expect_equal(sortList(m$panels[[1]]$mapping), list(x = "xvar", y = "yvar"))
|
||||
|
||||
|
||||
# Plot with an expression in aes, and a computed variable (histogram)
|
||||
p <- ggplot(dat, aes(xvar/2)) + geom_histogram(binwidth=1)
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 500, 72)
|
||||
dev.off()
|
||||
|
||||
# Check mapping vars - no value for y
|
||||
expect_equal(sortList(m[[1]]$mapping), list(x = "xvar/2", y = NULL))
|
||||
expect_equal(sortList(m$panels[[1]]$mapping), list(x = "xvar/2", y = NULL))
|
||||
})
|
||||
|
||||
|
||||
@@ -81,38 +83,38 @@ test_that("ggplot coordmap with facet_wrap", {
|
||||
scale_y_continuous(expand = c(0, 0)) +
|
||||
facet_wrap(~ g, ncol = 2)
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Should have 3 panels
|
||||
expect_equal(length(m), 3)
|
||||
expect_equal(m[[1]]$panel, 1)
|
||||
expect_equal(m[[1]]$row, 1)
|
||||
expect_equal(m[[1]]$col, 1)
|
||||
expect_equal(m[[2]]$panel, 2)
|
||||
expect_equal(m[[2]]$row, 1)
|
||||
expect_equal(m[[2]]$col, 2)
|
||||
expect_equal(m[[3]]$panel, 3)
|
||||
expect_equal(m[[3]]$row, 2)
|
||||
expect_equal(m[[3]]$col, 1)
|
||||
expect_equal(length(m$panels), 3)
|
||||
expect_equal(m$panels[[1]]$panel, 1)
|
||||
expect_equal(m$panels[[1]]$row, 1)
|
||||
expect_equal(m$panels[[1]]$col, 1)
|
||||
expect_equal(m$panels[[2]]$panel, 2)
|
||||
expect_equal(m$panels[[2]]$row, 1)
|
||||
expect_equal(m$panels[[2]]$col, 2)
|
||||
expect_equal(m$panels[[3]]$panel, 3)
|
||||
expect_equal(m$panels[[3]]$row, 2)
|
||||
expect_equal(m$panels[[3]]$col, 1)
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(m[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "g"))
|
||||
expect_equal(m[[1]]$mapping, m[[2]]$mapping)
|
||||
expect_equal(m[[2]]$mapping, m[[3]]$mapping)
|
||||
expect_equal(m$panels[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "g"))
|
||||
expect_equal(m$panels[[1]]$mapping, m$panels[[2]]$mapping)
|
||||
expect_equal(m$panels[[2]]$mapping, m$panels[[3]]$mapping)
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=0, right=10, bottom=10, top=30))
|
||||
)
|
||||
expect_equal(sortList(m[[1]]$domain), sortList(m[[2]]$domain))
|
||||
expect_equal(sortList(m[[2]]$domain), sortList(m[[3]]$domain))
|
||||
expect_equal(sortList(m$panels[[1]]$domain), sortList(m$panels[[2]]$domain))
|
||||
expect_equal(sortList(m$panels[[2]]$domain), sortList(m$panels[[3]]$domain))
|
||||
|
||||
# Check panel vars
|
||||
factor_vals <- dat$g
|
||||
expect_equal(m[[1]]$panel_vars, list(panelvar1 = factor_vals[1]))
|
||||
expect_equal(m[[2]]$panel_vars, list(panelvar1 = factor_vals[2]))
|
||||
expect_equal(m[[3]]$panel_vars, list(panelvar1 = factor_vals[3]))
|
||||
expect_equal(m$panels[[1]]$panel_vars, list(panelvar1 = factor_vals[1]))
|
||||
expect_equal(m$panels[[2]]$panel_vars, list(panelvar1 = factor_vals[2]))
|
||||
expect_equal(m$panels[[3]]$panel_vars, list(panelvar1 = factor_vals[3]))
|
||||
})
|
||||
|
||||
|
||||
@@ -130,75 +132,75 @@ test_that("ggplot coordmap with facet_grid", {
|
||||
# facet_grid horizontal
|
||||
p1 <- p + facet_grid(. ~ g)
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p1), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p1), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Should have 3 panels
|
||||
expect_equal(length(m), 3)
|
||||
expect_equal(m[[1]]$panel, 1)
|
||||
expect_equal(m[[1]]$row, 1)
|
||||
expect_equal(m[[1]]$col, 1)
|
||||
expect_equal(m[[2]]$panel, 2)
|
||||
expect_equal(m[[2]]$row, 1)
|
||||
expect_equal(m[[2]]$col, 2)
|
||||
expect_equal(m[[3]]$panel, 3)
|
||||
expect_equal(m[[3]]$row, 1)
|
||||
expect_equal(m[[3]]$col, 3)
|
||||
expect_equal(length(m$panels), 3)
|
||||
expect_equal(m$panels[[1]]$panel, 1)
|
||||
expect_equal(m$panels[[1]]$row, 1)
|
||||
expect_equal(m$panels[[1]]$col, 1)
|
||||
expect_equal(m$panels[[2]]$panel, 2)
|
||||
expect_equal(m$panels[[2]]$row, 1)
|
||||
expect_equal(m$panels[[2]]$col, 2)
|
||||
expect_equal(m$panels[[3]]$panel, 3)
|
||||
expect_equal(m$panels[[3]]$row, 1)
|
||||
expect_equal(m$panels[[3]]$col, 3)
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(m[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "g"))
|
||||
expect_equal(m[[1]]$mapping, m[[2]]$mapping)
|
||||
expect_equal(m[[2]]$mapping, m[[3]]$mapping)
|
||||
expect_equal(m$panels[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "g"))
|
||||
expect_equal(m$panels[[1]]$mapping, m$panels[[2]]$mapping)
|
||||
expect_equal(m$panels[[2]]$mapping, m$panels[[3]]$mapping)
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=0, right=10, bottom=10, top=30))
|
||||
)
|
||||
expect_equal(sortList(m[[1]]$domain), sortList(m[[2]]$domain))
|
||||
expect_equal(sortList(m[[2]]$domain), sortList(m[[3]]$domain))
|
||||
expect_equal(sortList(m$panels[[1]]$domain), sortList(m$panels[[2]]$domain))
|
||||
expect_equal(sortList(m$panels[[2]]$domain), sortList(m$panels[[3]]$domain))
|
||||
|
||||
# Check panel vars
|
||||
factor_vals <- dat$g
|
||||
expect_equal(m[[1]]$panel_vars, list(panelvar1 = factor_vals[1]))
|
||||
expect_equal(m[[2]]$panel_vars, list(panelvar1 = factor_vals[2]))
|
||||
expect_equal(m[[3]]$panel_vars, list(panelvar1 = factor_vals[3]))
|
||||
expect_equal(m$panels[[1]]$panel_vars, list(panelvar1 = factor_vals[1]))
|
||||
expect_equal(m$panels[[2]]$panel_vars, list(panelvar1 = factor_vals[2]))
|
||||
expect_equal(m$panels[[3]]$panel_vars, list(panelvar1 = factor_vals[3]))
|
||||
|
||||
|
||||
# facet_grid vertical
|
||||
p1 <- p + facet_grid(g ~ .)
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p1), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p1), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Should have 3 panels
|
||||
expect_equal(length(m), 3)
|
||||
expect_equal(m[[1]]$panel, 1)
|
||||
expect_equal(m[[1]]$row, 1)
|
||||
expect_equal(m[[1]]$col, 1)
|
||||
expect_equal(m[[2]]$panel, 2)
|
||||
expect_equal(m[[2]]$row, 2)
|
||||
expect_equal(m[[2]]$col, 1)
|
||||
expect_equal(m[[3]]$panel, 3)
|
||||
expect_equal(m[[3]]$row, 3)
|
||||
expect_equal(m[[3]]$col, 1)
|
||||
expect_equal(length(m$panels), 3)
|
||||
expect_equal(m$panels[[1]]$panel, 1)
|
||||
expect_equal(m$panels[[1]]$row, 1)
|
||||
expect_equal(m$panels[[1]]$col, 1)
|
||||
expect_equal(m$panels[[2]]$panel, 2)
|
||||
expect_equal(m$panels[[2]]$row, 2)
|
||||
expect_equal(m$panels[[2]]$col, 1)
|
||||
expect_equal(m$panels[[3]]$panel, 3)
|
||||
expect_equal(m$panels[[3]]$row, 3)
|
||||
expect_equal(m$panels[[3]]$col, 1)
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(m[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "g"))
|
||||
expect_equal(m[[1]]$mapping, m[[2]]$mapping)
|
||||
expect_equal(m[[2]]$mapping, m[[3]]$mapping)
|
||||
expect_equal(m$panels[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "g"))
|
||||
expect_equal(m$panels[[1]]$mapping, m$panels[[2]]$mapping)
|
||||
expect_equal(m$panels[[2]]$mapping, m$panels[[3]]$mapping)
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=0, right=10, bottom=10, top=30))
|
||||
)
|
||||
expect_equal(sortList(m[[1]]$domain), sortList(m[[2]]$domain))
|
||||
expect_equal(sortList(m[[2]]$domain), sortList(m[[3]]$domain))
|
||||
expect_equal(sortList(m$panels[[1]]$domain), sortList(m$panels[[2]]$domain))
|
||||
expect_equal(sortList(m$panels[[2]]$domain), sortList(m$panels[[3]]$domain))
|
||||
|
||||
# Check panel vars
|
||||
factor_vals <- dat$g
|
||||
expect_equal(m[[1]]$panel_vars, list(panelvar1 = factor_vals[1]))
|
||||
expect_equal(m[[2]]$panel_vars, list(panelvar1 = factor_vals[2]))
|
||||
expect_equal(m[[3]]$panel_vars, list(panelvar1 = factor_vals[3]))
|
||||
expect_equal(m$panels[[1]]$panel_vars, list(panelvar1 = factor_vals[1]))
|
||||
expect_equal(m$panels[[2]]$panel_vars, list(panelvar1 = factor_vals[2]))
|
||||
expect_equal(m$panels[[3]]$panel_vars, list(panelvar1 = factor_vals[3]))
|
||||
})
|
||||
|
||||
|
||||
@@ -215,43 +217,43 @@ test_that("ggplot coordmap with 2D facet_grid", {
|
||||
|
||||
p1 <- p + facet_grid(g ~ h)
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p1), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p1), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Should have 4 panels
|
||||
expect_equal(length(m), 4)
|
||||
expect_equal(m[[1]]$panel, 1)
|
||||
expect_equal(m[[1]]$row, 1)
|
||||
expect_equal(m[[1]]$col, 1)
|
||||
expect_equal(m[[2]]$panel, 2)
|
||||
expect_equal(m[[2]]$row, 1)
|
||||
expect_equal(m[[2]]$col, 2)
|
||||
expect_equal(m[[3]]$panel, 3)
|
||||
expect_equal(m[[3]]$row, 2)
|
||||
expect_equal(m[[3]]$col, 1)
|
||||
expect_equal(m[[4]]$panel, 4)
|
||||
expect_equal(m[[4]]$row, 2)
|
||||
expect_equal(m[[4]]$col, 2)
|
||||
expect_equal(length(m$panels), 4)
|
||||
expect_equal(m$panels[[1]]$panel, 1)
|
||||
expect_equal(m$panels[[1]]$row, 1)
|
||||
expect_equal(m$panels[[1]]$col, 1)
|
||||
expect_equal(m$panels[[2]]$panel, 2)
|
||||
expect_equal(m$panels[[2]]$row, 1)
|
||||
expect_equal(m$panels[[2]]$col, 2)
|
||||
expect_equal(m$panels[[3]]$panel, 3)
|
||||
expect_equal(m$panels[[3]]$row, 2)
|
||||
expect_equal(m$panels[[3]]$col, 1)
|
||||
expect_equal(m$panels[[4]]$panel, 4)
|
||||
expect_equal(m$panels[[4]]$row, 2)
|
||||
expect_equal(m$panels[[4]]$col, 2)
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(m[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "h", panelvar2 = "g"))
|
||||
expect_equal(m[[1]]$mapping, m[[2]]$mapping)
|
||||
expect_equal(m[[2]]$mapping, m[[3]]$mapping)
|
||||
expect_equal(m[[4]]$mapping, m[[4]]$mapping)
|
||||
expect_equal(m$panels[[1]]$mapping, list(x = "xvar", y = "yvar", panelvar1 = "h", panelvar2 = "g"))
|
||||
expect_equal(m$panels[[1]]$mapping, m$panels[[2]]$mapping)
|
||||
expect_equal(m$panels[[2]]$mapping, m$panels[[3]]$mapping)
|
||||
expect_equal(m$panels[[4]]$mapping, m$panels[[4]]$mapping)
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=0, right=15, bottom=10, top=40))
|
||||
)
|
||||
expect_equal(sortList(m[[1]]$domain), sortList(m[[2]]$domain))
|
||||
expect_equal(sortList(m[[2]]$domain), sortList(m[[3]]$domain))
|
||||
expect_equal(sortList(m[[3]]$domain), sortList(m[[4]]$domain))
|
||||
expect_equal(sortList(m$panels[[1]]$domain), sortList(m$panels[[2]]$domain))
|
||||
expect_equal(sortList(m$panels[[2]]$domain), sortList(m$panels[[3]]$domain))
|
||||
expect_equal(sortList(m$panels[[3]]$domain), sortList(m$panels[[4]]$domain))
|
||||
|
||||
# Check panel vars
|
||||
expect_equal(m[[1]]$panel_vars, list(panelvar1 = dat$h[1], panelvar2 = dat$g[1]))
|
||||
expect_equal(m[[2]]$panel_vars, list(panelvar1 = dat$h[2], panelvar2 = dat$g[1]))
|
||||
expect_equal(m[[3]]$panel_vars, list(panelvar1 = dat$h[1], panelvar2 = dat$g[2]))
|
||||
expect_equal(m[[4]]$panel_vars, list(panelvar1 = dat$h[2], panelvar2 = dat$g[2]))
|
||||
expect_equal(m$panels[[1]]$panel_vars, list(panelvar1 = dat$h[1], panelvar2 = dat$g[1]))
|
||||
expect_equal(m$panels[[2]]$panel_vars, list(panelvar1 = dat$h[2], panelvar2 = dat$g[1]))
|
||||
expect_equal(m$panels[[3]]$panel_vars, list(panelvar1 = dat$h[1], panelvar2 = dat$g[2]))
|
||||
expect_equal(m$panels[[4]]$panel_vars, list(panelvar1 = dat$h[2], panelvar2 = dat$g[2]))
|
||||
})
|
||||
|
||||
|
||||
@@ -265,12 +267,12 @@ test_that("ggplot coordmap with various data types", {
|
||||
scale_x_discrete(expand = c(0 ,0)) +
|
||||
scale_y_discrete(expand = c(0, 0))
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=1, right=3, bottom=1, top=4))
|
||||
)
|
||||
|
||||
@@ -283,12 +285,12 @@ test_that("ggplot coordmap with various data types", {
|
||||
scale_x_date(expand = c(0 ,0)) +
|
||||
scale_y_datetime(expand = c(0, 0))
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Check domain
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(
|
||||
left = as.numeric(dat$xvar[1]),
|
||||
right = as.numeric(dat$xvar[2]),
|
||||
@@ -308,12 +310,12 @@ test_that("ggplot coordmap with various scales and coords", {
|
||||
scale_x_continuous(expand = c(0 ,0)) +
|
||||
scale_y_reverse(expand = c(0, 0))
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Check domain (y reversed)
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=0, right=5, bottom=20, top=10))
|
||||
)
|
||||
|
||||
@@ -323,14 +325,14 @@ test_that("ggplot coordmap with various scales and coords", {
|
||||
scale_y_continuous(expand = c(0 ,0)) +
|
||||
coord_flip()
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Check mapping vars
|
||||
expect_equal(m[[1]]$mapping, list(x = "yvar", y = "xvar"))
|
||||
expect_equal(m$panels[[1]]$mapping, list(x = "yvar", y = "xvar"))
|
||||
# Check domain (y reversed)
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=10, right=20, bottom=0, top=5))
|
||||
)
|
||||
|
||||
@@ -341,17 +343,17 @@ test_that("ggplot coordmap with various scales and coords", {
|
||||
scale_y_continuous(expand = c(0, 0)) +
|
||||
coord_trans(y = "log2")
|
||||
png(tmpfile)
|
||||
m <- getGgplotCoordmap(print(p), 1, 72)
|
||||
m <- getGgplotCoordmap(print(p), 500, 400, 72)
|
||||
dev.off()
|
||||
|
||||
# Check log bases
|
||||
expect_equal(
|
||||
sortList(m[[1]]$log),
|
||||
sortList(m$panels[[1]]$log),
|
||||
sortList(list(x=10, y=2))
|
||||
)
|
||||
# Check domains
|
||||
expect_equal(
|
||||
sortList(m[[1]]$domain),
|
||||
sortList(m$panels[[1]]$domain),
|
||||
sortList(list(left=-1, right=3, bottom=-2, top=4))
|
||||
)
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user