## Warning: These vignettes assume pandoc version 1.13.1; older versions may ## give poor formatting.
rgl package is used to produce interactive 3-D plots. It contains high-level graphics commands modelled loosely after classic R graphics, but working in three dimensions. It also contains low level structure inspired by (but incompatible with) the
This document gives an overview. See the help pages for details.
This document was written in R Markdown, using the
knitr package for production. It corresponds to rgl version 0.95.1441.
Most of the highlighted function names are HTML links. The internal links should work in any browser; the links to help topics should work if you view the vignette from within the R help system.
The WebGL figures were produced using the
rglwidget package, version 0.1.1434.
can be used to plot three columns of the
with(iris, plot3d(Sepal.Length, Sepal.Width, Petal.Length, type="s", col=as.numeric(Species)))
"p", "l", "h", "s", meaning points, lines, segments from z=0, and spheres. There’s a lot of flexibility in specifying the coordinates; the
xyz.coordsfunction from the
grDevicespackage is used for this.
You can use your mouse to manipulate the plot. The default is that if you click and hold with the left mouse button, you can rotate the plot by dragging it. The right mouse button is used to resize it, and the middle button changes the perspective in the point of view.
The other high level function is
persp3d to draw surfaces. It is similar to the classic
persp function, but with greater flexibility. First, any of
z can be specified using matrices, not just
z. This allows parametric surfaces to be plotted. An even simpler specification is possible:
x may be a function, in which case
persp3d will work out the grid itself. See ?persp3d.function for details. For example, the
MASS package estimates Gamma parameters using maximum likelihood in a ?MASS::fitdistr example. Here we show the log likelihood surface.
library(MASS) # from the fitdistr example set.seed(123) x <- rgamma(100, shape = 5, rate = 0.1) fit <- fitdistr(x, dgamma, list(shape = 1, rate = 0.1), lower = 0.001) loglik <- function(shape, rate) sum(dgamma(x, shape=shape, rate=rate, log=TRUE)) loglik <- Vectorize(loglik) xlim <- fit$estimate+4*fit$sd*c(-1,1) ylim <- fit$estimate+4*fit$sd*c(-1,1) mfrow3d(1, 2, sharedMouse = TRUE) persp3d(loglik, xlim = xlim, ylim = ylim, n = 30) zlim <- fit$loglik + c(-qchisq(0.99, 2)/2, 0) next3d() persp3d(loglik, xlim = xlim, ylim = ylim, zlim = zlim, n = 30)
On the left, the whole surface over a range of the parameters; on the right, only the parts of the surface with log likelihood values near the maximum.
Note: this example used the
knitr hook functions (see
setupKnitr) to insert the scene into this vignette; the previous example used the
rglwidget function from the package of the same name. We generally recommend the newer
Just as we have
lines in classic graphics, there are a number of low level functions in
rgl to add graphical elements to the currently active plot. The “primitive” shapes are those that are native to OpenGL:
||adds line segments|
Each of the above functions takes arguments
z, again using
xyz.coords for flexibility. They group successive entries as necessary. For example, the
triangles3d function takes each successive triple of points as the vertices of a triangle.
You can use these functions to annotate the current graph, or to construct a figure from scratch.
rgl also has a number of objects which it constructs from the primitives.
||adds straight lines to plot (like
||adds planes to plot|
||add clipping planes to plot|
||add sprites (fixed shapes or images) to plot|
||a surface (as used in
The following low-level functions control the look of the graph:
||add axes to plot|
||add box around plot|
||add title to plot|
||add marginal text to plot|
||add multiple “decorations” (scales, etc.) to plot|
||set the aspect ratios for the plot|
||set the background of the scene|
||show a 2D plot or image in a 3D scene|
||set a legend for the scene|
||add a reference grid to a graph|
For example, to plot three random triangles, one could use
triangles3d(cbind(x=rnorm(9), y=rnorm(9), z=rnorm(9)), col = "green") decorate3d() bg3d("lightgray") aspect3d(1,1,1)
*3d functions mentioned above, there are even lower-level functions
You should avoid using these functions, which do not work well with the higher level
*3d functions. See the ?r3d help topic for details.
In most scenes, objects are “lit”, meaning that their appearance depends on their position and orientation relative to lights in the scene. The lights themselves don’t normally show up, but their effect on the objects does.
light3d function to specify the position and characteristics of a light. Lights may be infinitely distant, or may be embedded within the scene. Their characteristics include
specular components, all defaulting to white. The
ambient component appears the same from any direction. The
diffuse component depends on the angle between the surface and the light, while the
specular component also takes the viewer’s position into account.
The mental model used in
rgl is that the objects being shown in scenes are physical objects in space, with material properties that affect how light reflects from them (or is emitted by them). These are mainly controlled by the
material3d function, or by arguments to other functions that are passed to it.
The material properties that can be set by calls to
material3d are described in detail in the ?material3d help page. Here we give an overview.
|color||white||vector of surface colors to apply to successive vertices for diffuse light|
|alpha||1||transparency: 0 is invisible, 1 is opaque|
|lit||TRUE||whether lighting calculations should be done|
|ambient||black||color in ambient light|
|specular||white||color in specular light|
|emission||black||color emitted by the surface|
|shininess||50||controls the specular lighting: high values look shiny|
|smooth||TRUE||whether shading should be interpolated between vertices|
|texture||NULL||optional path to a “texture” bitmap to be displayed on the surface|
|front, back||fill||should polygons be filled, or outlined?|
|size||3||size of points in pixels|
|lwd||1||width of lines in pixels|
Other properties include “texmipmap”, “texmagfilter”, “texminfilter”, “texenvmap”, “fog”, “point_antialias”, “line_antialias”, “depth_mask”, and “depth_test”; see the help page for details.
There is also an
rgl.material function that works at a lower level; users should normally avoid it.
par3d function, modelled after the classic graphics
par function, sets or reads a variety of different
rgl internal parameters. Some parameters are completely read-only; others are fixed at the time the window is opened, and others may be changed at any time.
|antialias||fixed||Amount of hardware antialiasing|
|cex||Default size for text|
|family||Device-independent font family name; see ?text3d|
|font||Integer font number|
|useFreeType||Should FreeType fonts be used if available?|
|fontname||read-only||System-dependent font name set by
|FOV||Field of view, in degrees. Zero means isometric perspective|
|maxClipPlanes||read-only||How many clip planes can be defined?|
|modelMatrix||read-only||The OpenGL ModelView matrix; partly set by
|projMatrix||read-only||The OpenGL Projection matrix|
|bbox||read-only||Current bounding-box of the scene|
|viewport||Dimensions in pixels of the scene within the window|
|windowRect||Dimensions in pixels of the window on the whole screen|
|listeners||Which subscenes respond to mouse actions in the current one|
|mouseMode||What the mouse buttons do. See
|observer||read-only||The position of the observer; set by
|scale||Rescaling for each coordinate; see
|zoom||Magnification of the scene|
r3dDefaults list and the
getr3dDefaults function control defaults in new windows opened by
The function looks for the variable in the user’s global environment, and if not found there, finds the one in the
rgl namespace. This allows the user to override the default settings for new windows.
rgl includes a number of functions to construct and display various solid shapes. These generate objects of class
"shapelist3d". The details of the classes are described below. We start with functions to generate them.
These functions generate specific shapes. Optional arguments allow attributes such as colour or transformations to be specified.
open3d() cols <- rainbow(7) layout3d(matrix(1:16, 4,4), heights=c(1,3,1,3)) text3d(0,0,0,"tetrahedron3d"); next3d() shade3d(tetrahedron3d(col=cols)); next3d() text3d(0,0,0,"cube3d"); next3d() shade3d(cube3d(col=cols)); next3d() text3d(0,0,0,"octahedron3d"); next3d() shade3d(octahedron3d(col=cols)); next3d() text3d(0,0,0,"dodecahedron3d"); next3d() shade3d(dodecahedron3d(col=cols)); next3d() text3d(0,0,0,"icosahedron3d"); next3d() shade3d(icosahedron3d(col=cols)); next3d() text3d(0,0,0,"cuboctahedron3d"); next3d() shade3d(cuboctahedron3d(col=cols)); next3d() text3d(0,0,0,"oh3d"); next3d() shade3d(oh3d(col=cols))
These functions generate new shapes:
||generate a tube or cylinder|
||generate a flat polygon by triangulation|
||generate an “extrusion” of a polygon|
||generate a solid of rotation|
||generate an ellipsoid in various ways|
||generate a shape from vertices and faces|
||generate a shape by combining other shapes|
A related function is
triangulate, which takes a two dimensional polygon and divides it up into triangles using the “ear-clipping” algorithm.
"shape3d" is the basic abstract type. Objects of this class can be displayed by
shade3d (which shades faces),
wire3d (which draws edges), or
dot3d (which draws points at each vertex.) Note that
dot3d only work within R; in HTML output from
shade3d is supported.
"mesh3d" is a descendant type. Objects of this type contain the following fields:
|vb||A 4 by n matrix of vertices in homogeneous coordinates. Each column is a point.|
|it||(optional) A 3 by t matrix of vertex indices. Each column is a triangle.|
|ib||(optional) A 4 by q matrix of vertex indices. Each column is a quadrilateral.|
|material||(optional) A list of material properties.|
|normals||(optional) A matrix of the same shape as vb, containing normal vectors at each vertex.|
|texcoords||(optional) A 2 by n matrix of texture coordinates corresponding to each vertex.|
rgl has several functions to support displaying multiple different “subscenes” in the same window. The high level functions are
||Multiple figures (like par(“mfrow”)|
||Multiple figures (like
||Move to the next figure (like
||List all the subscenes in the current layout|
||Clear the current list and revert to the previous one|
There are also lower level functions.
||Create a new subscene, with fine control over what is inherited from the parent|
||Report on the active subscene|
||Get information on current subscene|
||Make a different subscene active|
||Add objects to a subscene, or delete them|
||Do “garbage collection”: delete objects that are not displayed in any subscene|
rgl detects and handles mouse clicks within your scene, and uses these to control its appearance. You can find out the current handlers using the following code:
## left right middle wheel ## "trackball" "zoom" "fov" "pull"
c("left", "right", "middle") refer to the buttons on a three button mouse, or simulations of them on other mice.
"wheel" refers to the mouse wheel.
The button actions generally correspond to click and drag operations. Possible values for
“mouseMode” for buttons or the wheel are as follows:
||The mouse acts as a virtual trackball. Clicking and dragging rotates the scene|
||The mouse affects rotations by controlling polar coordinates directly|
||The mouse is being used by the
||The mouse zooms the display|
||The mouse affects perspective by changing the field of view|
||Rotating the mouse wheel towards the user “pulls the scene closer”|
||The same rotation “pushes the scene away”|
||A user action set by
The following functions make use of the mouse for selection within a scene.
||like the classic graphics
||returns a function that tests whether a coordinate was selected|
||selects from specific objects|
rgl has several functions that can be used to construct animations. These are based on functions that update the scene according to the current real-world time, and repeated calls to those. The functions are:
||Repeatedly call the update function|
||Update the display by rotating at a constant rate|
||Compute new values of some
movie3d function for a way to output an animation to a file on disk.
Animations are not currently supported in the HTML written by
writeWebGL, though the
rglwidget::playwidget function provides equivalent functionality.
rgl contains several functions to write scenes to disk for use by other software, or to read them in.
In order from highest fidelity to lowest, the functions are:
||Save a scene to an R variable, which can be saved and reloaded|
||Write PLY files (commonly used in 3D printing)|
||Read or write OBJ files (commonly used in 3D graphics)|
||Read or write STL files (also common in 3D printing)|
||A helper function for setting a NULL device|
See the help page
rgl.useNULL for instructions on how to use
rgl on a “headless” system.
There are also functions to save snapshots or other recordings of a scene, without any 3D information being saved:
||Save a PNG file bitmap of the scene|
||Save a Postscript, LaTeX, PDF, SVG or PGF vector rendering of the scene|
||Save a series of bitmaps to be assembled into a movie|
||Obtain pixel-level information about the scene in an R variable|
||Driver function for inserting a snapshot into a Sweave document.|
||Function to set up
There are currently two schemes for exporting a scene to a web page. Both require the
rglwidget package and use the same underlying code.
The recommended approach works with the
htmlwidgets framework (see http://www.htmlwidgets.org/). In an R Markdown document in
knitr, use the chunk option
webgl=TRUE, or the
rglwidget::rglwidget() function. More details are given in the vignette User Interaction in WebGL.
The older approach uses the
||insert a slider to make changes to a scene|
||insert a slider to control a clipping plane|
||insert a slider to control which objects are displayed|
||insert a button to toggle some items|
||function to modify properties|
||function to choose subsets|
||function to “age” vertices|
||function to modify individual vertices|
||function to modify matrices|
rgl maintains internal structures for all the scenes it displays. The following functions allow users to find information about them and manipulate them.
||open a new window|
||close the current window|
||bring the current window to the top|
||id of the active device|
||ids of all active devices|
||set a particular device to be active|
||ids and types of all current objects|
||attributes of objects in the scene|
||delete an object from the scene|
||delete all objects of certain classes|
||return information about the current projection|
||convert between coordinates in the current projection|
rgl functions work internally with “homogeneous” coordinates. In this system, 3-D points are represented with 4 coordinates, generally called (x, y, z, w). The corresponding Euclidean point is (x/w, y/w, z/w), if w is nonzero; zero values of w correspond to “points at infinity”. The advantage of this system is that affine transformations including translations and perspective shifts become linear transformations, with multiplication by a 4 by 4 matrix.
rgl has the following functions to work with homogeneous coordinates:
||convert between homogeneous and Euclidean coordinates|
||apply a transformation|
||apply a general transformation|
||compute the transformation matrix|
||return a 4 x 4 identity matrix|
This vignette is in a preliminary form. Many aspects of the rgl package are not described, or do not have examples. There may even be functions that are missed completely, if the following list is not empty:
The following functions and constants are described in this document: