This is very similar to Ben Bolker's answer, but I'm demonstrating how one might add a bit of an aura to the crystal ball by using some mystical coloring:

library(rgl) lapply(seq(0.01, 1, by=0.01), function(x) rgl.spheres(0,0,0, rad=1.1*x, alpha=.01, col=colorRampPalette(c("orange","blue"))(100)[100*x])) rgl.spheres(0,0,0, radius=1.11, col="red", alpha=.1) rgl.spheres(0,0,0, radius=1.12, col="black", alpha=.1) rgl.spheres(0,0,0, radius=1.13, col="white", alpha=.1) xyz <- matrix(rnorm(3*100), ncol=3) xyz <- xyz * runif(100)^(1/3) / sqrt(rowSums(xyz^2)) rgl.spheres(xyz[1:50,], rad=.02, col="blue") rgl.spheres(xyz[51:100,], rad=.02, col="red") rgl.bg(col="black") rgl.viewpoint(zoom=.75) rgl.snapshot("crystalball.png")

The only difference between the two is in the lapply call. You can see that just by changing the colors in colorRampPalette you can change the look of the crystal ball significantly. The one on the left uses the lapply code above, the one on the right uses this instead:

lapply(seq(0.01, 1, by=0.01), function(x) rgl.spheres(0,0,0,rad=1.1*x, alpha=.01, col=colorRampPalette(c("orange","yellow"))(100)[100*x])) ...code from above

Here is a different approach where you can define your own texture file and use that to color the crystal ball:

# create a texture file, get as creative as you want: png("texture.png") x <- seq(1,870) y <- seq(1,610) z <- matrix(rnorm(870*610), nrow=870) z <- t(apply(z,1,cumsum))/100 # Swirly texture options: # Use the Simon O'Hanlon's roll function from this answer: # http://stackoverflow.com/questions/18791212/equivalent-to-numpy-roll-in-r/18791252#18791252 # roll <- function( x , n ){ # if( n == 0 ) # return( x ) # c( tail(x,n) , head(x,-n) ) # } # One option # z <- mapply(function(x,y) roll(z[,x], y), x = 1:ncol(z), y=1:ncol(z)) # # Another option # z <- mapply(function(x,y) roll(z[,x], y), x = 1:ncol(z), y=rep(c(1:50,51:2), 10))[1:870, 1:610] # # One more # z <- mapply(function(x,y) roll(z[,x], y), x = 1:ncol(z), y=rep(seq(0, 100, by=10), each=5))[1:870, 1:610] par(mar=c(0,0,0,0)) image(x, y, z, col = colorRampPalette(c("cyan","black"))(100), axes = FALSE) dev.off() xyz <- matrix(rnorm(3*100), ncol=3) xyz <- xyz * runif(100)^(1/3) / sqrt(rowSums(xyz^2)) rgl.spheres(xyz[1:50,], rad=.02, col="blue") rgl.spheres(xyz[51:100,], rad=.02, col="red") rgl.spheres(0,0,0, rad=1.1, texture="texture.png", alpha=0.4, back="cull") rgl.viewpoint(phi=90, zoom=.75) # change the view if need be rgl.bg(color="black")

!

The first image on the top left is what you get if you just run the code above, the other three are the results of using the different options in the commented out code.