library(ggplotly)
check <- function(gg, expected, name=NULL){
if(is.null(name)){
m <- match.call()
name <- as.character(m$gg)
}
list(ggplot=gg, expected=expected, name=name)
}
check.named <- function(expected, generated, trace){
for(L in list(expected, generated)){
stopifnot(is.list(L))
stopifnot(!is.null(names(L)))
if(any(names(L) == "")){
print(names(L))
stop("un-named elements")
}
}
for(name in names(expected)){
this.trace <- c(trace, name)
e <- expected[[name]]
g <- generated[[name]]
bad <- function(msg="did not generate what we expected"){
if(missing(msg)){
print(list(expected=e, generated=g))
}
print(this.trace)
stop(msg)
}
if(is.list(e)){
if(!is.list(g)){
bad()
}
check.named(e, g, this.trace)
}else if(is.atomic(e)){
if(!is.atomic(g) || length(g) != length(e)) {
bad()
}
if(is.numeric(e)){
if(!is.numeric(g)){
bad()
}
char.if.different <- all.equal(e, g)
if(is.character(char.if.different)){
print(rbind(expected=e, generated=g))
print(char.if.different)
bad("not numerically equal")
}
}else if(is.character(e) || is.factor(e)){
if(any(e != g)){
bad()
}
}else{
print(e)
stop("do not know what to do with this expectation")
}
}else{
print(e)
stop("do not know what to do with this expectation")
}
}
}
## Generate lineplot data.
set.seed(1)
n.groups <- 20
Groups <- data.frame(x=rep(1:10, times=n.groups),
group = rep(1:n.groups, each=10))
Groups$lt <- c("even", "odd")[(Groups$group%%2+1)] # linetype
Groups$group <- as.factor(Groups$group)
Groups$y <- rnorm(length(Groups$x), Groups$x, .5) +
rep(rnorm(n.groups, 0, 2), each=10)
## Simple black lineplot.
AllBlack <- ggplot(Groups) +
geom_line(aes(x=x, y=y, group=group)) +
ggtitle("geom_line")
group.list <- split(Groups, Groups$group)
AllBlack.expected <- list()
for(group.i in seq_along(group.list)){
g <- group.list[[group.i]]
AllBlack.expected[[group.i]] <-
list(x=g$x, y=g$y, type="scatter", mode="lines",
line=list(color="black"))
}
## A ggplot with 6 different automatic types should be converted to
## plotly's 6 types.
Types <- ggplot(subset(Groups, as.integer(group)<=6)) +
geom_line(aes(x=x, y=y, group=group, linetype=group))+
ggtitle("geom_line + scale_linetype automatic")
Types.expected <- AllBlack.expected[1:6]
dash <-
c("solid",
"dash",
"dot",
"dashdot",
"longdash",
"longdashdot")
for(trace.i in seq_along(Types.expected)){
Types.expected[[trace.i]]$line$dash <- dash[[trace.i]]
}
## Canada city population map.
library(maps)
data(canada.cities)
DefaultCities <- ggplot(canada.cities, aes(long, lat))+
borders(regions="canada", name="borders")+
coord_equal()+
geom_point(aes(text=name, size=pop), colour="red",
alpha=1/2, name="cities")
b <- borders(regions="canada")$data
group.list <- split(b, b$group)
line.df <- data.frame()
for(group.i in seq_along(group.list)){
g <- group.list[[group.i]]
line.df <- rbind(line.df, g, NA)
}
normalize <- function(x, m, M){
x <- na.omit(x)
zero.one <- (x-min(x))/(max(x)-min(x))
stopifnot(range(zero.one) == c(0,1))
m.M <- zero.one*(M-m) + m
stopifnot(range(m.M) == c(m, M))
m.M
}
DefaultCities.expected <-
list(list(x=line.df$long, y=line.df$lat,
type="scatter", mode="lines", name="borders",
line=list(dash="solid", color="grey50")),
with(canada.cities,{
list(x=long, y=lat, text=name, type="scatter", mode="markers",
name="cities",
marker=list(opacity=1/2, color="red", size=pop))
}))
## different ways to define the iris scatterplot, these should all
## give the same result.
iris.plots <-
list(global=ggplot(iris,aes(Petal.Width, Sepal.Width, color=Species))+
geom_point(),
point=ggplot(iris)+
geom_point(aes(Petal.Width, Sepal.Width, color=Species)),
qplot=qplot(Petal.Width, Sepal.Width, color=Species, data=iris),
qplot=qplot(Petal.Width, Sepal.Width, colour=Species, data=iris),
qplot=qplot(Petal.Width, Sepal.Width, col=Species, data=iris))
igroups <- split(iris, iris$Sp)
iris.expected <- list()
colors3 <- c("rgb(0,186,56)","rgb(248,118,109)","rgb(97,156,255)")
inames <- c("versicolor", "setosa", "virginica")
for(species.i in seq_along(inames)){
iname <- inames[[species.i]]
sp <- igroups[[iname]]
iris.expected[[species.i]] <-
list(x=sp$Petal.Width, y=sp$Sepal.Width, name=as.character(sp$Sp[1]),
type="scatter", mode="markers",
marker=list(color=rep(colors3[[species.i]], nrow(sp))))
}
## Checklist.
to.check <-
list(check(AllBlack, AllBlack.expected),
check(DefaultCities, DefaultCities.expected),
check(Types, Types.expected))
## TODO: check.unordered function!
for(name in names(iris.plots)){
full.name <- sprintf("iris.%s", name)
to.check[[length(to.check)+1]] <-
check(iris.plots[[name]], iris.expected, full.name)
}
for(L in to.check){
generated <- gg2list(L$gg)
for(trace.i in seq_along(L$expected)){
e <- L$exp[[trace.i]]
g <- generated[[trace.i]]
check.named(e, g, c(L$name, trace.i))
}
}
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.