La formule est la suivante :
W:2; //Largeur des carreaux H:2; //Hauteur des carreaux NW:4; //Nombre de carreaux horizontalement NH:3; //Nombre de carreaux verticalement C1:#FF0000; //Couleur n°1 rouge C2:#0000FF; //Couleur n°2 bleu I:Tile(C1, W*NW, H*NH); // Création d'une image de couleur C1 de la bonne taille W2:W*2; // Calcul du modulo horizontal H2:W*2; // Calcul du modulo vertical If((X(I) mod W2>=W) = (Y(I) mod H2>=H), C1, C2) // Le damier
La syntaxe <variable> :<expression> permet de stocker une expression en mémoire et de pouvoir la récupérer ensuite dans une autre expression. La dernière ligne de la formule ou script ne doit pas être une variable mais une expression qui est le résultat final.
Les variables et les expressions sont toujours des images qui sont par exemple réduites à un seul point
Par exemple la première ligne W:2; crée une image appelée W qui sera représentée en mémoire de la façon suivante :
W, H:
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 2 | 2 | 2 |
La variable H est représentée de manière identique. NW et NH sont représenté de la manière suivante :
NW:
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 4 | 4 | 4 |
NH:
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 3 | 3 | 3 |
C1 et C2 sont également des images de taille 1x1 (réduites à un seul point)
C1:
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 255 | 0 | 0 |
C2:
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 0 | 0 | 255 |
A noter que si l’on renvoie ces images en tant que résultat final on obtient une image rouge et une image bleue de taille 1x1 réduite à un seul point.
Une fois les variables simples initialisées (elle permettent d’ailleurs ici de paramétrer le script) vient ensuite la première instruction qui va créer notre image : l’instruction Tile(<expression>,<largeur>,<hauteur>) que nous utilisons ici dans sa version à 3 paramètres permet de créer une image de taille <largeur>x<hauteur> remplie par le motif <expression>. Cette expression est, rappelons le, forcément une image car Arithmétique ne manipule en fait que des images.
L’instruction Tile(C1,W*NW,H*NH); se décompose de la manière suivante :
L’expression W*NW va être évaluée dans une image temporaire afin d’être transmise à la fonction Tile
L’image temporaire <largeur> obtenue est la suivante :
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 2*4=8 | 2*4=8 | 2*4=8 |
De même pour l’image temporaire <hauteur> suivante :
X | 0 | ||
---|---|---|---|
Y | R | V | B |
0 | 2*3=6 | 2*3=6 | 2*3=6 |
Ces 2 expressions temporaires ainsi que la variable C1 sont transmises à la fonction Tile
A noter que la fonction Tile n’utilisera que la composante Rouge du premier point de l’image pour largeur et la hauteur. Cela n’aura en général aucune importance car les 3 composantes devraient en toute logique être identiques.
La fonction Tile se charge donc de créer une nouvelle image en dupliquant le motif (ici réduit à un point) ce qui nous donne le résultat suivant qui sera stocké dans la variable I
I:
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
1 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
2 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
3 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
4 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
5 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
6 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
7 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 | 255 | 0 | 0 |
C’est en fait la représentation en mémoire d’une image entièrement rouge de taille 6x8
Les variable W2 et H2 contiennent respectivement le double de W et de H qui seront utilisés dans la dernière instruction qui réalise en fait le damier.
W2, H2 :
X | 1 | ||
---|---|---|---|
Y | R | V | B |
1 | 2*2=4 | 2*2=4 | 2*2=4 |
Le damier est réalisé par l’instruction suivante qui est la plus complexe de la formule :
If((X(I) mod W2>=W) = (Y(I) mod H2>=H), C1, C2)
C’est cette instruction qui constitue le résultat du script. C’est une instruction conditionnelle If(<condition>,<alors>,<sinon>). Elle permet de renvoyer un résultat <alors> lorsque l’expression <condition> est vrai et un autre résultat <sinon> lorsque l’expression n’est pas vraie.
Les trois expressions sont des images qui doivent être de la même taille
Les expressions <alors> ici C1 et <sinon> C2 sont simples et sont de taille 1x1 nous avons leur description dans les 2 tableaux.
L’expression conditionnelle est plus complexe nous ne connaissons par encore sa taille ni sa valeur mais nous allons le calculer :
Le centre de l’expression est le = cette instruction renvoie 255 lorsque les 2 expressions comparées sont identique ou 0 sinon. La comparaison est évaluée composante par composante.
Il reste à évaluer les 2 parties gauche et droite du égal :
Commençons par la partie gauche :
X(I) mod W2>=W
Nous connaissons déjà W et W2 et I par contre l’évaluation de X(I) ne nous est par encore connue. La fonction X(I) renvoie une image de la même taille que I mais où chacune des composante R,V,B contient la valeur de la coordonnée X du points ce qui donne pour I :
X(I):
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
1 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
2 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
3 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
4 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
5 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
6 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
7 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 4 | 4 | 4 | 5 | 5 | 5 |
X(I) nous est donc maintenant connu. Nous pouvons donc évaluer X(I) mod W2 :
W2 est une image de taille 1x1 et X(I) une image de taille 6x8. Le modulo est donc appliqué pour tous les points de l’image X(I) ce qui donne le résultat suivant :
X(I) mod W2:
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
1 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
2 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
3 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
4 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
5 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
6 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
7 | 0 | 0 | 0 | 1 | 1 | 1 | 2 | 2 | 2 | 3 | 3 | 3 | 0 | 0 | 0 | 1 | 1 | 1 |
Le modulo 4 est appliqué ce qui fait que les colonnes 4 et 5 sont remplacée par 4 mod 4=0 et 5 mod 4=1.
La partie gauche du égal n’est pas encore tout à fait terminée nous devons encore appliquer l’opérateur >= W.
Cette opérateur renvoie Vrai (ou 255) lorsque les points de l’images sont supérieur ou égal à W qui vaut 2 et 0 sinon. Par rapport au tableau précédent, les valeurs 2 et 3 sont remplacée par 255 et les valeurs 0 et 1 sont remplacées par 0
X(I) mod W2 >= W:
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
1 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
2 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
3 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
4 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
5 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
6 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
7 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
C’est le même principe pour la partie droite du égal. La fonction Y permet d’obtenir la coordonnée Y des points de l’image.
Y(I):
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 |
3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 |
4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 | 4 |
5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 | 5 |
6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 | 6 |
7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 | 7 |
Le modulo 4 est appliqué également donc 4,5,6,7 sont remplacé par 4 mod 4=0,5 mod 4=1,6 mod 4=2,7 mod 4=3.
Y(I) mod H2:
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 |
3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 |
4 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
5 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
6 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 | 2 |
7 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 | 3 |
Enfin l’opérateur >=H est appliqué. Comme H vaut 2 comme précédemment, les valeurs 2 et 3 sont remplacées par 255 et les valeurs 0 et 1 sont remplacé par 0.
Y(I) mod H2 >= H:
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
2 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 |
3 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 |
4 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
5 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
6 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 |
7 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 | 255 |
Nous connaissons désormais les 2 parties gauche et droite de l’instruction =. Les 2 images sont de la même taille. La comparaison va donc s’effectuer point par point et composante par composante. A chaque fois lorsque les 2 valeurs sont identique l’opérateur = renvoi 255 et 0 dans le cas contraire. Cela donne donc le résultat suivant :
(X(I) mod W2) = (Y(I) mod H2 >= H)
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 |
1 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 |
2 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
3 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
4 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 |
5 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 |
6 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
7 | 0 | 0 | 0 | 0 | 0 | 0 | 255 | 255 | 255 | 255 | 255 | 255 | 0 | 0 | 0 | 0 | 0 | 0 |
Cette image est déjà un damier mais en noir et blanc. Un damier noir ∓ blanc peut être obtenue directement en supprimant l’instruction If et en ne conservant donc que la <condition>.
Nous souhaitons obtenir un damier de couleur C1 et C2. C1 est la partie <alors> et sera donc associée à la valeur vraie de la <condition>. Cela revient par conséquent à remplacer les triplets (255,255,255) par la couleur C1(255,0,0). Partout ailleurs C2 sera associé. Cela revient par conséquent à remplacer tous les triplets (0,0,0) par C2(0,0,255). Avant d’appliquer le If les 3 images nécessaire sont redimensionnées en prenant le maximum des tailles de chacune des 3 images. La <condition> a une taille de 6x8 et C1 et C2 ont une taille de 1x1. 2 expressions temporaires sont donc construite afin d’agrandir C1 et C2 à la taille de la <condition>. Le remplacement est ensuite réalisé composante par composante ce qui donne le résultat final suivant :
X | 0 | 1 | 2 | 3 | 4 | 5 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
Y | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B | R | V | B |
0 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 |
1 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 |
2 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 |
3 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 |
4 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 |
5 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 |
6 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 |
7 | 0 | 0 | 255 | 0 | 0 | 255 | 255 | 0 | 0 | 255 | 0 | 0 | 0 | 0 | 255 | 0 | 0 | 255 |
Cette image est bien un damier avec des carreaux de taille 2x2 avec 3 carreaux horizontalement et 4 verticalement.