Créer une animation avec découpe et applique
Dans cet article, on voit comment créer des animations grâce à des opérations de découpe et d'applique.
Une animation grâce à des découpes
Dans cet exemple, on anime des carrés grâce aux méthodes scissor()
et clear()
. Ensuite, on crée à nouveau une boucle d'animation grâce aux timers. Cette fois-ci, la position du carré (la zone de découpe) est mise à jour à chaque frame (on a environ une frame rafraîchie toutes les 17 millisecondes, ce qui correspond environ à 60fps (frame per second ou frame par seconde).
En revanche, la couleur du carré (définie avec clearColor
) est uniquement mise à jour lorsqu'un nouveau carré est créé. On voit ici que WebGL est un automate. Pour chaque carré, on définit sa couleur une fois puis on met à jour sa position à chaque frame. L'état lié à la couleur reste tel quel jusqu'à ce qu'un nouveau carré soit créé.
"use strict";
window.addEventListener("load", setupAnimation, false);
// Voici les variables qui permettront de
// manipuler le contexte WebGL, la couleur
// et la position des carrés.
var gl,
color = getRandomColor(),
position;
function setupAnimation(evt) {
window.removeEventListener(evt.type, setupAnimation, false);
if (!(gl = getRenderingContext())) return;
gl.enable(gl.SCISSOR_TEST);
gl.clearColor(color[0], color[1], color[2], 1.0);
// À la différence de la fenêtre du navigateur,
// l'axe vertical de WebGL va dans le sens croissant
// du bas vers le haut. Dans cette position, on indique
// que la position initiale du carré est en haut à gauche
// du contexte de dessin
position = [0, gl.drawingBufferHeight];
var button = document.querySelector("button");
var timer;
function startAnimation(evt) {
button.removeEventListener(evt.type, startAnimation, false);
button.addEventListener("click", stopAnimation, false);
document.querySelector("strong").innerHTML = "arrêter";
timer = setInterval(drawAnimation, 17);
drawAnimation();
}
function stopAnimation(evt) {
button.removeEventListener(evt.type, stopAnimation, false);
button.addEventListener("click", startAnimation, false);
document.querySelector("strong").innerHTML = "lancer";
clearInterval(timer);
}
stopAnimation({ type: "click" });
}
// Les variables qui permettront de stocker la taille
// et la vitesse du carré.
var size = [60, 60],
velocity = 3.0;
function drawAnimation() {
gl.scissor(position[0], position[1], size[0], size[1]);
gl.clear(gl.COLOR_BUFFER_BIT);
// À chaque frame, on définit une position plus basse
// pour le carré, c'est cela qui crée une illusion
// de mouvement.
position[1] -= velocity;
// Lorsque le carré atteint le bas, on crée un nouveau
// carré avec une nouvelle vitesse et une nouvelle
// couleur.
if (position[1] < 0) {
// La position horizontale est choisie aléatoirement.
// La position verticale correspond au haut
// du buffer de dessin.
position = [
Math.random() * (gl.drawingBufferWidth - size[0]),
gl.drawingBufferHeight,
];
// Ici on détermine une vitesse aléatoire
// comprise entre 1.0 et 7.0
velocity = 1.0 + 6.0 * Math.random();
color = getRandomColor();
gl.clearColor(color[0], color[1], color[2], 1.0);
}
}
function getRandomColor() {
return [Math.random(), Math.random(), Math.random()];
}
Le code source de cet exemple est également disponible sur GitHub.