# 'enhanced' persp -- return value has attributes containing
# x,y,z ranges
perspx <- function(x,y,z,...) {
if (missing(z)) {
if (!missing(x)) {
if (is.list(x)) {
z <- x$z
y <- x$y
x <- x$x
}
else {
z <- x
x <- seq.int(0, 1, length.out = nrow(z))
}
}
else stop("no 'z' matrix specified")
}
else if (is.list(x)) {
y <- x$y
x <- x$x
}
p <- persp(x,y,z,...)
attr(p,"ranges") <- list(x=range(x),y=range(y),z=range(z))
p
}
psegments3d <- function(x, y = NULL, z = NULL, pmat, ...) {
if (is.null(y) && is.null(z)) {
z <- x$z
y <- x$y
x <- x$x
}
xy <- trans3d(x,y,z,pmat)
# translate from 'segments3d' (successive pairs) to
# 'segments' (x0,x1,y0,y1) format
n <- length(xy$x)
x0 <- xy$x[seq(1,n,by=2)]
x1 <- xy$x[seq(2,n,by=2)]
y0 <- xy$y[seq(1,n,by=2)]
y1 <- xy$y[seq(2,n,by=2)]
segments(x0=x0,x1=x1,y0=y0,y1=y1,...)
}
ptext3d <- function(x, y = NULL, z = NULL, texts, pmat, ...) {
if (is.null(y) && is.null(z)) {
z <- x$z
y <- x$y
x <- x$x
}
do.call(text,c(trans3d(x,y,z,pmat),list(label=texts,...)))
}
if (FALSE) {
pp <- persp(x=1:3,y=1:3,z=matrix(1:9,nrow=3),col="gray")
ptext3d(2,2,5,"a",pp,col="red")
}
get_axispos3d <- function(edge,pmat,at,pos=NULL, dist=0) {
ranges <- attr(pmat,"ranges")
edge <- c(strsplit(edge, "")[[1]], "-", "-")[1:3]
coord <- match(toupper(edge[1]), c("X", "Y", "Z"))
if (coord == 2)
edge[1] <- edge[2]
else if (coord == 3)
edge[1:2] <- edge[2:3]
mpos <- matrix(NA, 3, length(at))
if (edge[1] == "+")
mpos[1, ] <- ranges$x[2]
else mpos[1, ] <- ranges$x[1]
if (edge[2] == "+")
mpos[2, ] <- ranges$y[2]
else mpos[2, ] <- ranges$y[1]
if (edge[3] == "+")
mpos[3, ] <- ranges$z[2]
else mpos[3, ] <- ranges$z[1]
offset <- dist * (mpos[, 1] - c(mean(ranges$x), mean(ranges$y),
mean(ranges$z)))
offset[coord] <- 0
mpos <- sweep(mpos,1,offset,"+")
if (!is.null(pos))
mpos <- matrix(pos, 3, length(at))
mpos[coord, ] <- at
mpos
}
mtext3d <- function (edge, pmat, labels = TRUE, at = NULL, dist=0.3, xpd=NA, ...) {
ranges <- attr(pmat,"ranges")
edge.orig <- edge # hack
edge <- c(strsplit(edge, "")[[1]], "-", "-")[1:3]
coord <- match(toupper(edge[1]), c("X", "Y", "Z"))
range <- ranges[[coord]]
if (is.null(at)) {
at <- mean(range)
}
mpos <- get_axispos3d(edge.orig,pmat,at,dist=dist)
ptext3d(mpos[1, ],mpos[2,],mpos[3,],
labels, pmat, xpd=xpd, ...)
}
paxis3d <-
function (edge, pmat,
at = NULL, labels = TRUE, tick = TRUE,
pos = NULL, nticks = 5, ticklen=0.05,labdist=0.15,
xpd=NA, ...)
{
ranges <- attr(pmat,"ranges")
edge.orig <- edge # hack
edge <- c(strsplit(edge, "")[[1]], "-", "-")[1:3]
coord <- match(toupper(edge[1]), c("X", "Y", "Z"))
range <- ranges[[coord]]
if (is.null(at)) {
at <- pretty(range, nticks)
at <- at[at >= range[1] & at <= range[2]]
}
if (is.logical(labels)) {
if (labels)
labels <- format(at)
else labels <- NA
}
mpos <- get_axispos3d(edge.orig,pmat,at,pos,dist=0)
# draw axes
x <- c(mpos[1, 1], mpos[1, length(at)])
y <- c(mpos[2, 1], mpos[2, length(at)])
z <- c(mpos[3, 1], mpos[3, length(at)])
psegments3d(x,y,z,pmat, xpd=xpd, ...)
if (tick) {
mpos_tick <- get_axispos3d(edge.orig,pmat,at,dist=ticklen)
x <- c(as.double(rbind(mpos[1, ], mpos_tick[1, ])))
y <- c(as.double(rbind(mpos[2, ], mpos_tick[2, ])))
z <- c(as.double(rbind(mpos[3, ], mpos_tick[3, ])))
psegments3d(x,y,z,pmat, xpd=xpd, ...)
}
if (!is.null(labels)) {
mpos_lab <- get_axispos3d(edge.orig,pmat,at,dist=labdist)
ptext3d(mpos_lab[1, ],mpos_lab[2,],mpos_lab[3,],
labels, pmat, xpd=xpd, ...)
}
}
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.