Table des matières

Objet animé complexe

Dans Suivi de trajectoire, c'est un point qui se déplace.

Supposons que l'on veuille déplacer un objet plus compliqué à dessiner qu'un point. Pour l'exemple, prenons ce poisson :

Définir un objet

Pour cela on définit une classe Poisson qui permettra de prendre en charge tout le tracé d'un poisson.

class Poisson {
  float size;
  Poisson(float s) { // constructeur
    /* size permettra de régler la taille du Poisson.
       1 pour une taille de base, 2 pour une taille double...
    */
    size = s; // contrairement à Python, pas besoin de préciser self.
              // c'est une syntaxe Java
  }
  
  void display(float x, float y, float angle){
    /* pour le tracer du poisson on précise a position x, y et son orientation */
    pushMatrix();
    translate(x, y);
    rotate(angle);
    scale(size);
    line(0,0, -10,-5);
    line(-10,-5,-10,5);
    line(-10,5,0,0);
    bezier(0,0,10,10,20,10,20,0);
    bezier(0,0,10,-10,20,-10,20,0);
    popMatrix();
  }
}

utilisation de pushMmatrix()

Pour le tracer, deux fonctions sont très importantes : pushMatrix() et popMatrix().

Le principe est le suivant :

Par matrix il faut comprendre que les opérations effectuées sont calculées avec des matrices de transformation. Les matrices sont un moyen commode de calculer les transformations de ce type.

Le programme entier

float t = 0;
Poisson p;

void setup() {
  size(640, 400);
  stroke(0,0,0);
  p = new Poisson(1.0);
}

void draw(){
  background(250,200,200);
  t += 0.02;
  float x = 320 + 120*cos(t);
  float y = 200 + 80*sin(t - PI/3);
  float angle = atan2(80*cos(t-PI/3), -120*sin(t));
  p.display(x, y, angle);
}

class Poisson {
  float size;
  Poisson(float s) {
    size = s;
  }
  
  void display(float x, float y, float angle){
    pushMatrix();
    translate(x, y);
    rotate(angle);
    scale(size);
    line(0,0, -10,-5);
    line(-10,-5,-10,5);
    line(-10,5,0,0);
    bezier(0,0,10,10,20,10,20,0);
    bezier(0,0,10,-10,20,-10,20,0);
    popMatrix();
  }
}

Dans la fonction draw on calcule les positions x et y et l'orientation angle. On fournit ces données à l'objet p pour qu'il mette à jour son affichage.

new

Vous pouvez noter que p est définit comme un objet de type Poisson mais n'est pas initialisé au début. On choisit de l'initialiser dans setup et pour cela on doit préciser new pour annoncer que l'on demande à réserver l'espace mémoire de ce nouvel objet.

On aurait tout aussi bien pu initialiser p dès le début.

atan2

L'orientation du poisson se fait suivant la tangente de la trajectoire. On doit donc calculer $$\begin{cases}x(t) = 320 + 120 \cos(t)\\y(t) = 200 + 80 \sin\left(t + \frac{\pi}{3}\right)\end{cases} \Rightarrow \begin{cases}x'(t) = -120 \sin(t)\\y'(t) = 80 \cos\left(t + \frac{\pi}{3}\right)\end{cases}$$

L'angle sera celui du vecteur de coordonnées $(x'(t);y'(t))$. C'est un calcul d'arctangente : $\arctan\left(\frac{y'(t)}{x'(t)}\right)$. Malheureusement ce calcul pose problème si $x'(t) = 0$. C'est pour cette raison que Processing fournit la fonction atan2.