I have a polygon which I would like to convert to a cylindrical 3D object for an illustration:
x <- structure(list(x = c(7.99, 6.25, -1.77, -1.8, -0.48, 3.93, 7.99
), y = c(2.84, 2.31, 2.43, 2.98, 3.19, 3.26, 2.84)), row.names = c(NA,
7L), class = "data.frame")
plot(x$x, x$y, type = "n")
polygon(x$x, x$y, col = "blue")
points(x$x, x$y)
I cannot get my head around how to add z-axis with values 2 and 5 for example:
library(rgl)
lines3d(x = rep(x$x, 2), y = rep(x$y, 2), z = rep(c(2, 5), each = nrow(x)))
I would like to make the faces colored and connected. Something like the cylinders on Wikipedia illustrations, but naturally not round ends, but those polygons instead. tringles3d
or polygon3d
functions are probably what I should use if I used the rgl package, but I don't understand how to restructure my data.frame. I do not need to do this in rgl. That was just the R package which seemed most feasible for this task. How should I reorganize my data to plot the 3D cylinder?
You need to use extrude3d
to create an "extrusion" of your polygon.
For example, with x
as defined in the question,
x[-1,] %>%
extrude3d(thickness = 3, material = list(col = rainbow(14)),
meshColor = "faces") %>%
translate3d(x = 0, y = 0, z = 2) %>%
shade3d()
produces this image (after some manual rotation):
It uses x[-1,]
, because you repeated the first vertex at the end: it wants unique vertices.
The coloring is kind of funny: to draw the hexagons on each end, rgl
draws 4 triangles, and each is treated as a separate face for the purpose of coloring. If you want solid colors there, remember that the ends are drawn first: so use something like
material = list(col = rainbow(8)[c(1,1,1,1,2,2,2,2:8)])
instead.
The other funny argument to extrude3d
is thickness
: the polyhedron is drawn between z=0
and z=thickness
. Since you wanted z
from 2 to 5, the thickness
is 3, and the result needs to be translated up 2 units in z.
There's also cylinder3d
, which is used for generating tubular structures, but extrude3d
is simpler to use if you only want your polygon to show up in two places at right angles to the sides.