7) Fabriquer un objet

La programmation oriente objet a été inventée pour rendre plus facile le travail de développement. Il faut d’en rappeller avant de pousser des gémissement à l’idée d’apprendre "quelque chose de plus" en codage.

Précédent | 8/16 | Suivant

Imaginons que je veuille faire une animation dans laquelle un balle réagit lorsqu’elle est heurtée par la souris. La balle aura une position dans l’espace, une vitesse (à 0 par défaut). Si la balle est survolée par la souris, la vitesse de la souris est transmise à la balle. Et si la balle sort de la fenêtre de processing, elle revient de l’autre côté.

Ça donne ça :

float posx=100;
float posy=100;
float vitessex=ra0;
float vitessey=0;
float diametre=50;
// vitesse de la deceleration
float deceleration=0.97;

void setup(){
 size(600,600);
 noStroke();
 smooth();
}

void draw(){
 background(0);
 // tester si la souris est sur une balle
 if(abs(mouseX - posx) < (diametre/2) && abs(mouseY - posy) < (diametre/2)){
   // la souris sur la balle
   vitessex=mouseX-pmouseX;
   vitessey=mouseY-pmouseY;
 }

 // update la position
 posx +=vitessex;
 posy +=vitessey;

 // verifier si on sort du cadre
 if(posx > width + diametre/2) {  posx -= (width + diametre/2);  }
 if(posx < - diametre/2) { posx = (width + diametre/2); }
 if(posy > height + diametre/2) { posy -= (height + diametre/2); }
 if(posy < - diametre/2) {  posy = (height + diametre/2); }

 // decelere;
 vitessex *= deceleration;
 vitessey *= deceleration;

 // dessiner le cercle
 ellipse(posx,posy,diametre,diametre);
}

Pas parfait mais fonctionnel.
Maintenant, que se passe-t-il si je veux 50 de ces balles en même temps dans l’espace ? Je vais devoir multiplier le nombre de variables par 50, ou utiliser un array pour stocker toutes les informations de chaque points. Ce sera vite laborieux. Et si je veux faire un nuage de poussière, une nuée d’oiseaux, ce genre de truc que l’on trouve dans les effets 3D ? Il faut une autre méthode de programmation.
C’est là qu’intervient la programmation orienté objet.

Chacune des balles à un comportement similaire : elles ont des positions différentes, des vitesses différentes, mais elles réagissent toutes de la même manière. Dans le programme ci-dessus, on trouve des variables, des tests (if) et des comportements (accélération, décélération). La programmation d’un objet va nous fournir plusieurs avantages : elle va permettre de rassembler tout ce qui concerne l’objet dans une portion de code appelée "classe" et permettre d’en créer facilement un nombre indéfini.

Dans l’exemple plus haut, que fait le code :
- il donne une position initiale à la balle et une vitesse
- il vérifie si la balle n’est pas survolée par la souris, et si oui, il lui communique la vitesse de déplacement
- il vérifie que la balle ne sort pas des limites de la fenêtre, sinon la ramène
- il décélère la vitesse de la boule
- il la dessine

Fabriquer sa classe

Le code de notre classe boules_fuyantes (ou n’importe quel nom) sera :

class boule_fuyante {
// les variables necessaires à l'objet
 float posx;
 float posy;
 float vitessex;
 float vitessey;

 // le constructeur
 boule_fuyante(float px,float py){
   posx=px;
   posy=py;
   vitessex=0;
   vitessey=0;
 }
 
 // les méthodes
 void deplace(){
   // update la position
   posx +=vitessex;
   posy +=vitessey;

   // verifier si on sort du cadre
   if(posx > width + 25) {
     posx -= (width + 25);
   }
   if(posx < - 25) {
     posx = (width + 25);
   }
   if(posy > height + 25) {
     posy -= (height + 25);
   }
   if(posy < - 25) {
     posy = (height + 25);
   }

   // decelere;
   vitessex *= 0.97;
   vitessey *= 0.97;
 }

 void checke_souris(){
   if(abs(mouseX - posx) < (25) && abs(mouseY - posy) < (25)){
     // la souris sur une balle
     vitessex=mouseX-pmouseX;
     vitessey=mouseY-pmouseY;
   }
 }

 void dessine(){
   ellipse(posx,posy,50,50);
 }

}

A l’intérieur de l’objet, on commence par déclarer les variables nécessaire à l’objet. Ensuite on écrit le "constructeur", qui sera appelé au moment où on crée l’objet. Il donne a chaque variable utilisée par l’objet sa valeur de départ. On écrit ensuite les méthodes, des fonctions internes à l’objet, avec lesquelles on interagira avec lui de l’extérieur de l’objet.

Car un objet est comme une petite boite fermée, avec ses variables et ses méthodes "a l’intérieur". Dans cette programmation, notre objet a ses propres variables (posx, posy, vitessex, vitessey) et ses propres méthodes (deplace, checke_souris,dessine). Tout ça est concentré, au niveau du code, dans l’objet.

Instancier la classe

La classe en elle-même ne crée pas d’objet, elle est une matrice, un moule à gaufre d’objet (quelle métaphore !). On va donc créer des objets à partir d’elle :
(coller ce code au dessus du précédent)

boule_fuyante maboule; // declarer la balle

void setup(){
 size(600,600);
 noStroke();
 smooth();
 maboule=new boule_fuyante(random(width),random(height)); // construire notre balle
}

void draw(){
 background(0);
 maboule.checke_souris(); // appel de la méthode checke souris
 maboule.deplace(); // appel de la méthode deplace
 maboule.dessine(); // appel de la méthode dessine
}

Au dessus du setup, on déclare que l’on va utiliser la classe dans un objet que l’on appelle maboule (ou n’importe quoi).

Dans le setup, on construit notre boule, en lui donnant les paramètres nécessaire (ici le point de départ en x et y).

Dans le draw, on fait appel aux méthodes disponibles. Notez la syntaxe : on accède aux méthodes (maboule.deplace() par exemple) par un point, et les méthodes comme les fonctions se reconnaissent aux parenthèses, qui peuvent contenir des arguments.

On peut aussi accéder au variables de l’objet, par exemple

println(maboule.posx);

ecrira dans la console la position de la boule en x. On voit qu’il s’agit d’une variable car il n’y a pas de parenthèses derrière posx.

Plein de balles

Une fois l’objet créé, rien ne vous empêche plus de créer à partir de cette matrice deux, trois ou des centaines d’objets. Voici le code pour en faire 100 (n’oubliez pas de mettre le code de la classe en dessous) :

int nb_boules=100;

boule_fuyante[] maboule = new boule_fuyante[nb_boules];

void setup(){
 size(600,600);
 noStroke();
 smooth();
 for (int i=0;i<nb_boules;i++){
   maboule[i]=new boule_fuyante(random(width),random(height));
 }
}

void draw(){
 background(0);
 for(int i=0;i< nb_boules;i++){
   maboule[i].checke_souris();
   maboule[i].deplace();
   maboule[i].dessine();
 }
}

On a ici un array d’objets, dont le nombre est défini par la variable nb_boules.

Plus loin

A partir de ce code, on peut ajouter variables et méthodes, par exemple modifier le diamètre des boules, leur couleur, et détecter si deux boules s’entrechoquent.

Un autre didacticiel : celui de Douglas Edric Stanley sur le site de l’école d’Aix