WebGL - Shaders : Un guide pour les débutants

Bonjour, futurs programmeurs ! Aujourd'hui, nous allons entreprendre un voyage passionnant à travers le monde des Shaders WebGL. Ne vous inquiétez pas si vous n'avez jamais écrit une ligne de code auparavant - je serai votre guide amical à travers ce paysage coloré de la graphique informatique.

WebGL - Shaders

Qu'est-ce que les Shaders ?

Avant de plonger dedans, comprenons ce que sont les shaders. Imaginez que vous peignez une image. Le canevas est votre écran d'ordinateur, et les shaders sont comme des pinceaux magiques qui disent à l'ordinateur comment colorer chaque pixel. Cool, non ?

Types de données

Dans le monde des shaders, nous avons quelques types de données spéciaux avec lesquels travailler. Jetons un œil :

Type de données Description Exemple
float Un nombre à virgule flottante simple précision 3.14
vec2 Un vecteur 2D vec2(1.0, 2.0)
vec3 Un vecteur 3D vec3(1.0, 2.0, 3.0)
vec4 Un vecteur 4D vec4(1.0, 2.0, 3.0, 4.0)
mat2 Une matrice 2x2 mat2(1.0, 2.0, 3.0, 4.0)
mat3 Une matrice 3x3 mat3(1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0)
mat4 Une matrice 4x4 mat4(1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 11.0, 12.0, 13.0, 14.0, 15.0, 16.0)

Ne vous inquiétez pas si ceux-ci semblent impressionnants - nous les utiliserons étape par étape !

Qualificateurs

Les qualificateurs sont comme des étiquettes spéciales que nous mettons sur nos variables. Ils disent au shader comment traiter ces variables. Voici les principaux :

Qualificateur Description
attribute Valeurs d'entrée qui changent par sommet
uniform Valeurs d'entrée qui restent constantes pour tous les sommets
varying Valeurs passées du shader de sommet au shader de fragment

Shader de sommet

Le shader de sommet est comme le squelette de notre modèle 3D. Il calcule où chaque point (sommet) de notre modèle devrait être à l'écran. Voici un shader de sommet simple :

attribute vec3 aVertexPosition;
uniform mat4 uModelViewMatrix;
uniform mat4 uProjectionMatrix;

void main(void) {
gl_Position = uProjectionMatrix * uModelViewMatrix * vec4(aVertexPosition, 1.0);
}

Reprenons cela :

  1. Nous déclarons un attribute appelé aVertexPosition - c'est la position de notre sommet.
  2. Nous avons deux matrices uniform - celles-ci nous aident à positionner et projeter notre modèle 3D sur un écran 2D.
  3. Dans la fonction main, nous calculons la position finale de notre sommet.

Shader de fragment

Si le shader de sommet est le squelette, le shader de fragment est la peau. Il décide de la couleur de chaque pixel. Voici un shader de fragment simple :

precision mediump float;

void main(void) {
gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);
}

Ce shader peint tout en rouge ! La vec4(1.0, 0.0, 0.0, 1.0) représente du rouge complet, pas de vert, pas de bleu, et pleine opacité.

Stockage et compilation des programmes de shaders

Maintenant que nous avons écrit nos shaders, nous devons informer WebGL à leur sujet. Voici comment nous faisons cela en JavaScript :

function getShader(gl, id) {
const shaderScript = document.getElementById(id);
if (!shaderScript) return null;

const str = shaderScript.text;
let shader;

if (shaderScript.type === "x-shader/x-fragment") {
shader = gl.createShader(gl.FRAGMENT_SHADER);
} else if (shaderScript.type === "x-shader/x-vertex") {
shader = gl.createShader(gl.VERTEX_SHADER);
} else {
return null;
}

gl.shaderSource(shader, str);
gl.compileShader(shader);

if (!gl.getShaderParameter(shader, gl.COMPILE_STATUS)) {
alert(gl.getShaderInfoLog(shader));
return null;
}

return shader;
}

Cette fonction fait quelques choses :

  1. Elle trouve notre code de shader dans le document HTML.
  2. Elle crée un shader du bon type (sommet ou fragment).
  3. Elle compile le shader et vérifie les erreurs.

Programme combiné

Enfin, nous devons combiner nos shaders de sommet et de fragment en un programme :

const shaderProgram = gl.createProgram();
gl.attachShader(shaderProgram, vertexShader);
gl.attachShader(shaderProgram, fragmentShader);
gl.linkProgram(shaderProgram);

if (!gl.getProgramParameter(shaderProgram, gl.LINK_STATUS)) {
alert("Impossible d'initialiser les shaders");
}

gl.useProgram(shaderProgram);

Ce code crée un programme, attache nos shaders, lie le programme, et indique à WebGL de l'utiliser.

Et voilà ! Vous avez刚刚 fait vos premiers pas dans le monde des shaders WebGL. Souvenez-vous, comme pour apprendre toute nouvelle langue, cela prend de la pratique. Ne soyez pas découragé si cela ne vous vient pas tout de suite - continuez à expérimenter et bientôt vous serez capable de créer des graphiques 3D incroyables dans votre navigateur web !

Dans mes années d'enseignement, j'ai vu des centaines d'étudiants passer de complets débutants à des maîtres des shaders. L'un de mes étudiants a même utilisé ces compétences pour créer une galerie d'art virtuelle pour son projet final - imaginez vous promener dans un musée 3D directement dans votre navigateur web !

Alors, que créerez-vous avec vos nouvelles compétences en shaders ? La seule limite est votre imagination ! Bon codage, futurs gourous de la graphique !

Credits: Image by storyset