rgl
plot3d
Le package rgl
permet de réaliser des graphiques interactifs en 3D et la représentation d’objets géométriques. Il a été réalisé principalement par Ducan Murdoch qui est professeur de statistique à l’University of Western Ontario et Daniel Adler. Ce package exploite l’API graphique OpenGL, permettant la production de graphiques interactifs en 2D et 3D, comme moteur de rendu.
Les avantages qui distinguent particulièrement ce package sont qu’il permet la création de scènes et l’ajout de contrôles permettant des actions dans une figure en trois dimensions. C’est-à-dire qu’il permet de programmer une série d’actions permettant de mettre en valeur certaines caractéristiques des graphiques générés grâce à celui-ci. Ce package permet aussi d’ajouter des contrôles, auxquels nous pouvons attribuer diverse actions permettant des manipulations contrôlées d’une figure.
Le package rgl
est conçu pour que son utilisation ressemble à la librairie graphique de base de R. Cela rend son utilisation très intuitive pour les connaisseurs de R. De plus, il permet de nombreuses fonctionnalités dont l’exportation des graphiques qu’il produit dans divers formats interactifs et statiques et, depuis peu de temps, l’intégration de ces graphiques dans une page web.
Puisque la création de graphique en 2D n’est pas la force de ce package et n’offre aucun avantage par rapport à la librairie graphique de base de R ou ggplot
par exemple, nous ne l’aborderons pas.
rgl
L’installation du package R rgl
s’effectue avec la commande suivante :
install.packages("rgl")
Pour charger le package dans votre environnement de travail, utilisez la fonction library
:
library(rgl)
Afin d’illustrer l’utilisation des principales fonctions du package, nous utiliserons le jeu de données quakes
du package datasets
. Il contient des informations sur 1000 séismes, d’une magnétude supérieure à 4 MB, survenus dans les alentours des Îles Fidji depuis 1964. Pour le bien de l’exercice, nous ajoutons deux nouvelles variables au jeu de données. Celles-ci sont générées à partir de variables déjà contenues dans le jeu de données quakes
. Voici des informations sur les données contenues dans le jeu quakes
:
#Création de la variable "magFactor"
quakes$magFactor <- factor(floor(quakes$mag))
#Création de la variable "region"
quakes$region <- factor(quakes$long >= 175, labels = c("Ouest", "Est"))
#Informations sur le jeu de données quakes
str(quakes)
## 'data.frame': 1000 obs. of 7 variables:
## $ lat : num -20.4 -20.6 -26 -18 -20.4 ...
## $ long : num 182 181 184 182 182 ...
## $ depth : int 562 650 42 626 649 195 82 194 211 622 ...
## $ mag : num 4.8 4.2 5.4 4.1 4 4 4.8 4.4 4.7 4.3 ...
## $ stations : int 41 15 43 19 11 12 43 15 35 19 ...
## $ magFactor: Factor w/ 3 levels "4","5","6": 1 1 2 1 1 1 1 1 1 1 ...
## $ region : Factor w/ 2 levels "Ouest","Est": 2 2 2 2 2 2 1 2 2 2 ...
plot3d
La fonction de base du package rgl
est plot3d
. À la base, chacune des figures produites par cette fonction sont interactives. C’est-à-dire qu’il est possible d’explorer l’environnement 3D de celles-ci, à l’aide d’une souris d’ordinateur. Les arguments minimaux à donner à la fonction plot3d
sont les suivants :
x
: un vecteur des valeurs des points pour l’axe des X.y
: un vecteur des valeurs des points pour l’axe des Y.z
: un vecteur des valeurs des points pour l’axe des Z.Voici un exemple de graphique de base produit par la fonction plot3d
si l’on ne fait que donner les arguments minimaux nécessaires :
## wgl
## 2
plot3d(x = quakes$long, y = quakes$lat, z = quakes$depth)
Pour modifier des éléments graphiques basiques, nous pouvons intégrer les arguments dans la fonction plot3d
, comme dans l’exemple qui suit. Nous pouvons aussi les intégrer dans la fonction decorate3d
incluse dans le package rgl
. Voici un tableau résumant les principaux arguments pouvant être passés aux fonctions plot3d
et decorate3d
:
Arguments | Éléments graphiques contrôlés |
---|---|
main |
titre de la figure |
sub |
sous-titre de la figure |
————————— | ———————– |
xlab , ylab , zlab |
noms des axes |
xlim , ylim , zlim |
étendue des axes |
————————— | ———————– |
type |
type de représentation (p = points, s = sphères, l = lignes, etc.) |
————————— | ———————– |
box |
si FALSE , retire la boite autour de la zone du graphique |
axes |
si FALSE , retire les axes de la zone graphique |
————————— | ———————– |
lwd |
épaisseur des lignes |
size |
épaisseur des points et des sphères. |
————————— | ———————– |
col |
couleur des éléments du graphique. |
Dans l’exemple qui suit, nous ajoutons des noms aux trois axes et un titre, retirons la boite autour de la figure (effectif dans une fenêtre interactive, pas dans un document HTML) et modifions la représentation et la taille des points de la figure précédente.
#Création d'une couleur associée à chaque niveau de magFactor
quakes$magCol <- ifelse(quakes$magFactor == 4, "red",
ifelse(quakes$magFactor == 5, "blue", "green"))
#Création du graphique
plot3d(x = quakes$long, y = quakes$lat, z = quakes$depth,
xlab = "longitude", ylab = "latitude", zlab = "profondeur (km)",
main = "Pronfondeur de 1000 seismes aux alentours de Fidji selon leur latitude et longitude",
col = quakes$magCol, type = "s", size = 1, box = FALSE)
Tout d’abord, dans la première sous-section, nous recréerons le graphique produit à l’exemple précédent, en le bonifiant quelque peu, à l’aide de fonctions permettant l’ajout de divers éléments dans une scène en 3 dimensions dans le but d’illustrer l’utilisation possible de celles-ci.
Par la suite, nous traiterons l’ajout de formes géométriques en 3D plus complexe à la sous-section suivante puisque leur utilisation dans R est légèrement différente des formes traitées dans la première sous-section. Nous ferons un exemple d’ajout de formes géométriques en 3 dimensions dans la figure créée précédemment.
Les manipulations des exemples qui suivent permettront de bonifier une scène vide en 3D générée à partir de la commande open3d
du package rgl
. Cependant, il est important de noter que ces manipulations auraient pu être effectuées sur n’importe quel graphique en 3 dimensions généré par une fonction du package.
Tout comme la librairie de production de graphique de base dans R, le package rgl
permet l’ajout de divers éléments dans une représentation. Le tableau suivant présente les principales fonctions permettant des ajouts à un graphique initialisé.
Fonction | Description |
---|---|
axes3d , axis3d |
ajout d’axes |
box3d , bbox3d |
ajout d’une boite autour du graphique |
title3d |
ajout d’un titre |
text3d |
ajout d’un texte dans la zone graphique |
mtext3d |
ajout d’un texte dans la marge |
decorate3d |
ajout d’éléments graphiques de base |
aspect3d |
définit les proportions du graphique |
bg3d , bgplot3d |
définit l’arrière plan du graphique |
show2d |
montre une représentation 2D d’une scène 3D |
legend3d |
ajout d’une légende à la scène |
grid3d |
ajout d’une grille de références |
————————— | ———————– |
points3d |
ajout de points |
lines3d |
ajout de lignes |
segments3d |
ajout de segments |
triangles3d |
ajout de triangles |
quads3d |
ajout de quadrilatères |
abclines3d |
ajout d’une ligne droite |
arc3d |
ajout d’arcs ou de spirales |
planes3d |
ajout de plans |
spheres3d |
ajout de sphères |
surface3d , terrain3d |
ajout de sufaces |
arrow3d |
ajout de flèches |
La première section du tableau contient les éléments qui influencent l’apparence du graphique, la seconde contient des fonctions qui permettent l’ajout de données selon diverses représentations en 3D ou de formes géométriques selon une formule donnée.
Dans l’exemple qui suit, nous commençons par simplement recréer le graphique produit par la fonction plot3d
à l’exemple précédent.
#Overture d'une scène 3D vide
open3d()
#Dimensionnement de la scène
#Nous revenons sur la fonction par3d plus tard dans le document
par3d(windowRect = c(0, 0, 512, 512))
#Ajout de sphères représentant les différents séismes
spheres3d(x = quakes$long, y = quakes$lat, z = quakes$depth, radius = 10, col = quakes$magCol )
#Redimensionnement du graphique pour qu'il forme un cube parfait
aspect3d(x = 1, y = 1, z = 1)
#Ajout d'axes au graphique
axes3d()
#Ajout d'un titre au graphique et aux axes
title3d(xlab = "longitude", ylab = "latitude", zlab = "profondeur (km)",
main = "Pronfondeur de 1000 seismes aux alentours de Fidji selon leur latitude et longitude")
À cette étape, nous utilisons le graphique que nous venons de construire et ajoutons certains éléments comme un plan séparant l’ouest et l’est et différents textes pour donner des exemples supplémentaires sur l’utilisation de fonctions permettant l’ajout d’éléments graphiques.
#Création d'un plan séparant le graphique selon l'est et l'ouest
planes3d(a = -1, b = 0, c = 0, d = 175, col = "blue", alpha = 0.3)
#Ajout de text identifiant les différentes sections du graphique
text3d(x = 187, y = -30, z = 600, text = "Est")
text3d(x = 168, y = -30, z = 600, text = "Ouest")
#Retrouve les informations du seisme le plus puissant du jeux de données
rowPlusGrosSeisme <- quakes[which.max(quakes$mag), ]
#Ajout d'une flèche qui pointe la sphère correspondant au seisme le plus puissant
arrow3d(p0 = c(170, -30, 490), p1 = c(rowPlusGrosSeisme$long, rowPlusGrosSeisme$lat, rowPlusGrosSeisme$depth),
type = "rotation", s = 1/30, n = 4)
#Ajout d'un texte donnant des informations sur la donnée pointée
text3d(x = 170, y = -30, z = 500, text = "Seisme le plus fort", cex = 0.8)
Cette sous-section présente les principales fonctions utiles à la construction de formes en 3D complexes et propose un exemple permettant d’illustrer la création de ces formes. Le tableau qui suit présente les fonctions de base permettant la création de formes complexes.
Fonction | Description |
---|---|
shape3d |
permet d’ajouter des forme géométrique |
polygon3d |
génère un polygone |
ellipse3d |
génère un élipse |
shapelist3d |
permet de générer un liste de formes |
Voici un exemple sur la création de deux ellipses représentant la variance et la covariance des données de l’est et de l’ouest.
#Création de jeux de données contenant les données selon leur position géographique
quakes_est <- quakes[quakes$region == "Est",]
quakes_ouest <- quakes[quakes$region == "Ouest",]
#Création d'une élipse à partir des informations sur la longitude, la latitude et
#de la profondeur des différents séismes contenus dans le jeux de données quakes
ellipse_est <- ellipse3d(
x = cov(cbind(quakes_est$long, quakes_est$lat, quakes_est$depth)),
centre = c(mean(quakes_est$long), mean(quakes_est$lat), mean(quakes_est$depth))
)
ellipse_ouest <- ellipse3d(
x = cov(cbind(quakes_ouest$long, quakes_ouest$lat, quakes_ouest$depth)),
centre = c(mean(quakes_ouest$long), mean(quakes_ouest$lat), mean(quakes_ouest$depth))
)
#Ajout de l'élipse dans le graphique en 3D
plot3d(ellipse_est, col = "orange", alpha = 0.2, add = TRUE, box = FALSE)
plot3d(ellipse_ouest, col = "yellow", alpha = 0.2, add = TRUE, box = FALSE)
aspect3d(x = 1, y = 1, z = 1)
L’ajout de contôles personnalisés est une particularité du package rgl
. Ceux-ci permettent des options plaisantes pouvant améliorer l’interactivité et les manipulations possibles de l’utilisateur vis-à-vis les graphiques produits. Le tableau suivant énumère quelques fonctions permettant l’ajout de contôles ainsi qu’une légère description de leur utilité propre.
Fonction | Description |
---|---|
subsetControl |
Contrôle quels objets sont affichés |
playWidget |
Affiche des contôles automatisés |
toggleWidget |
Affichage de boutons contrôlant les données affichées |
Polar |
Rotation du graphique selon les coordonnées polaires |
%>% |
Opérateur pipe importé du package magrittr |
figHeight , figWidth |
Dimensions des figures dans un document R Markdown |
rglMouse |
Change les mode de la souris dans une scène rgl |
asRow |
Fait l’arrangement de plusieurs objets dans un affichage HTML |
Les sous-sections qui suivent présentent des exemples d’utilisation de certaines de ces fonctions dans diverses situations.
Certains boutons peuvent être ajoutés pour aider les interactions avec le graphique. Comme vous le verrez dans l’exemple ci-dessous, la fonction playwidget
nous donne accès aux boutons “Reverse”,“Play”,“Slower”,“Faster” et “Reset” servant à lancer une vidéo. Le code suivant sert à créer une matrice de rotation afin que celle-ci soit utilisée pour faire tourner le graphique en trois dimensions durant la vidéo. L’option userMatrix
permet de créer une matrice 4 par 4 spécifiant le point de vue de l’utilisateur. Pour sa part, la fonction par3dinterp
permet d’ajuster au fil du temps des options par3d
et ainsi être utilisée dans une animation. Nous pouvons aussi voir de quelle façon nous ferons apparaître ce widget tout en lui assignant la matrice de rotation. Ici, la fonction par3dinterpControl
, sert à gérer toutes les options conçernant la vidéo comme la durée, la vitesse et bien plus.
#Création du graphique
plot3d(x = quakes$long, y = quakes$lat, z = quakes$depth, type = 's', col = quakes$magCol,
size = quakes$mag/4, main = "Longitude, latitude et profondeur des seismes selon la region")
#Créer la matrice du point de vue de l'utilisateur
MatriceVue <- r3dDefaults$userMatrix
#Créer les transformations, ici rotations de la matrice du point de vue
ModifParametre <- par3dinterp(time = (0:2), userMatrix = list(MatriceVue,
rotate3d(MatriceVue, pi/3, 5, 0, 4),
rotate3d(MatriceVue, pi/3, 0, 1, 2)) )
#Permet à la sortie d'être affichée en HTML
rglwidget() %>%
#Permet de rajouter les boutons pour démarer et contrôler l'animation
playwidget(par3dinterpControl(ModifParametre, 0, 4, steps=10),
step = 0.05, loop = TRUE, rate = 0.5)
Une autre fonction plus avancée est de séparer le jeu de données en plusieurs classes afin de pouvoir faire apparaitre et disparaitre certaines classes précises. Cela est démontré dans l’exemple ci-dessous, où trois classes ont été créées en fonction de la magnitude des séismes. Encore une fois, c’est grâce à des boutons que nous serons capable de contrôler les données voulues. C’est la fonction toggleWidget
qui nous sera utile pour cet exemple afin de faire apparaître différents boutons et de leur assigner une classe.
#Supprime les paramètres du graphique précédent
clear3d()
#Création de la variable Mag_4 contenant les données en 3D des séismes de magnitude 4
Mag_4 <- with(subset(quakes, magFactor == "4"),
spheres3d(x = long, y = lat, z = depth, col = magCol, radius = 6))
#Création de la variable Mag_5 contenant les données en 3D des séismes de magnitude 5
Mag_5 <- with(subset(quakes, magFactor == "5"),
spheres3d(x = long, y = lat, z = depth, col = magCol, radius = 6))
#Création de la variable Mag_6 contenant les données en 3D des séismes de magnitude 6
Mag_6 <- with(subset(quakes, magFactor == "6"),
spheres3d(x = long, y = lat, z = depth, col = magCol, radius = 6))
#Mise en forme des proportions du graphique
aspect3d(1,1,1)
#Rajout des options supplémentaires du graphique comme les titres et la forme des points
decorate3d(xlab = "longitude", ylab = "latitude", zlab = "profondeur (km)",
main = "Longitude, latitude et profondeur des seismes selon la region",
col = quakes$magCol, type = "s", size = quakes$mag/4 , box = FALSE)
#Permet à la sortie d'être affichée en HTML
rglwidget() %>%
#Rajout de 3 boutons côte à côte étant associés aux variables créées plus haut
toggleWidget(ids = Mag_4) %>%
toggleWidget(ids = Mag_5) %>%
toggleWidget(ids = Mag_6) %>%
asRow(last = 3)
La fonction rglMouse
nous permet de sélectionner l’interaction que nous voulons avoir avec le graphique. Par défaut, on y retrouve les options Selecting
, Trackball
,xAxis
,yAxis
,zAxis
,Polar
,Zoom
,Fov
et None
. Lorsqu’une option est sélectionnée, celle-ci peut être utilisée avec le clic gauche de la souris. L’option mouseMode
nous permet de choisir par défaut l’option que l’on veut au départ. Voici un petit tableau expliquant brièvement chaque option :
Options | Fonction réalisée par le clic gauche de la souris |
---|---|
Selecting |
Selection d’une portion des données du graphique |
Trackball |
Rotation du graphique selon n’importe quelles axes |
xAxis , yAxis , zAxis |
Rotation du graphique selon l’axe choisi |
Polar |
Rotation du graphique selon les coordonnées polaires |
Zoom , Fov |
Deux options de zoom, Fov étant plus rapide |
None |
Le clic gauche ne fait rien |
#Création du graphique
plot <- plot3d(x = quakes$long, y = quakes$lat, z = quakes$depth,
xlab = "longitude", ylab = "latitude", zlab = "profondeur (km)",
main = "Longitude, latitude et profondeur des seismes selon la region",
col = quakes$magCol, type = "s", size = 1, box = FALSE)
#Sélection de l'option par défault
par3d(mouseMode = "trackball")
#Nous permettons a l'option rglMouse d'intéragir avec les données du graphiques
rglwidget(shared = rglShared(plot["data"])) %>%
#Sélection des options contenus dans le boutons
rglMouse(choice = c("trackball", "xAxis", "yAxis", "zAxis", "polar", "zoom", "fov"))