Binome2017-9

De Wiki de bureau d'études PeiP

Binôme 9 saison 8: Raphaël Bonvalet, Damien Tillaux.


Projet Quireekoo

Le but du projet Quireekoo est de créer un robot communiquant avec d'autre via infra-rouge. Ce projet à eu lieux lors des bureaux d'étude de PEIP en IMA au S4 2018 de notre cursus pour devenir ingénieur. Voici la transcription phonétique de Quireekoo: /Kirikou/.

Cahier des charges

Kiki.jpg

Quireekoo sera un robot fait de A à Z. Le circuit imprimé sera totalement revu et sera guidé grâce à une ATMEGA-328. Le physique sera totalement design par nous même et son programme sera totalement autonome.

Quireekoo étant petit et vaillant est un véhicule de petite taille. A la défaut de jambe, Quireekoo ce déplace avec 2 servos moteurs continue. A la place des yeux, un sonar pour éviter ses obstacles et ne pas trébucher. Pour ses oreilles nous avons prévu 2 Tsop38238 pour pouvoir repérer et fuir ses ennemis.



Réalisation du projet

Voici les différentes étapes par lesquels nous sommes passer lors de la création de Quireekoo.


Réalisation de PCB

Idée principale

Nous voulions refaire nous même le PCB de Quireekoo mais nous n'avions pratiquement aucune base sur comment créer un circuit imprimé pour ce genre de projet. Du coups nous avons pris comme modèle, le modèle donnée sur la page principale du projet. (BE 2017-2018)

Voici le schématique sur lequel nous nous sommes basé.

Schématique original


Notre PCB

Notre PCB a été réalisé sur Fritzing. Nous avons créer ce circuit imprimé à notre image pour notre véhicule. Nous avons enlevé le driver de moteur et les sorties moteurs car nous voulions un robot de petite taille. Donc le moyen de déplacement choisi a alors été le servo-moteur. Pour les réceptions infra-rouge nous n'avons prévu que deux sorties pour des Tsop pour pouvoir laisser un plus grande chance au chasseur de ne pas être repéré, pour une approche plus vrai que nature. Pour savoir si un chasseur nous a attrapé, nous utilisons une sonde de Hall.

De plus, en cas de problème nous avons créé toutes les sorties du microcontrôleur. Si un problème apparaît sur une des pins utilisées, nous pourrons la relocaliser sur une autre sortie.

Un objectif supplémentaire était de réaliser un PCB le plus petit possible pour que le véhicule le soit aussi. Ce fut presque un succès, la carte est d'une taille environ de 5cm*5cm. Elle aurait pu être encore plus petite avec plus de travail mais nous ne pouvions pas nous le permettre si nous voulions tout faire.


Voici le schématique et le PCB de Quireekoo.

Schématique de Quireekoo
PCB de Quireekoo
]


Réalisation de la partie mécanique du véhicule

Pour la partie mécanique de Quireekoo on a choisi de le faire sur inkscape afin de pouvoir effectuer une découpe laser. Le robot est composé de deux plaques de plexiglas, une pour le châssis où il y a les servos moteur, la bille et le bloc de pile, et une pour placer le sonar, le circuit imprimée, les Tsop et la sonde de hall.

Voici à quoi ressemble la partie du bas sur inkscape :

Partie bas.jpg


Pour la partie du haut c'était un peu plus compliqué car il fallait trouver comment placer les tsop, la sonde de hall et le sonar. Pour pouvoir fixer ceux-ci on a choisi de faire des trous en forme de rectangles avec une taille égale à la taille des pins de chaque capteurs différents. Après il fallait aussi mettre les trous pour fixer le circuit imprimé au même endroit que ceux qui se trouve sur celui-ci. Pour ce faire, on a utilisé le fichier .svg donné par Fritzing. On a également mis des trous en forme de rectangle sur les côtés pour pouvoir laisser passer les fils.

Voici à quoi ressemble la partie du haut sur inkscape :

Partie haut.png

Pour finir il nous restait les roues à faire. On a opté pour garder les roues données avec les servos moteurs en y rajoutant des partie en plexiglas au pistolet à colle pour rendre celles-ci plus grandes.

Voici à quoi cela ressemble sur inkscape :

Roue.png

Le problème avec cette solution c'est que les roues ne sont pas adhérentes. De ce fait là, on a ajouté une partie d'élastique autour avec de la colle glue.

Voici a quoi le robot ressemble à la fin :

Quireekoo.jpg

Réalisation du code Arduino

Voici maintenant la présentation du code téléversé dans Quireekoo.

Le code

{

 #include <Servo.h>
 #include <IRremote.h>
 
 //déclaration des différentes pins
 
 #define SERVO1 11
 #define SERVO2 13
 #define ECHO 17
 #define TRIGG 18
 #define HALL A2
 #define IR 2
 #define VCCIR1 A0
 #define VCCIR2 A1
 
 //création de la classe Mouv pour le déplacement du robot
 
 class Mouv {
 
         Servo servo1;
         Servo servo2;
         int servo1Pin;
         int servo2Pin;
         
         int etatRotation;
         int etatSonnar;
         int etatHall;
         int etatTsop;
         
         long intervalTsop;
         
         long intervalMouvement1;
         long intervalMouvement2;
         long intervalMouvement3;
         long intervalMouvement4;
         
         unsigned long lastMillis;
         
         
   public:
     Mouv(int pin1 , int pin2){
       servo1Pin= pin1;
       servo2Pin = pin2;
       
       etatRotation = 0;
       etatSonnar = 0;
       etatHall = 0;
       etatTsop = 0;
       lastMillis = 0;
       
       intervalTsop = 500;
       
       intervalMouvement1 = 1500;
       intervalMouvement2 = 1700;
       intervalMouvement3 = 3200;
       intervalMouvement4 = 3400;
     }
   
     void attacher(){
       servo1.attach(servo1Pin);
       servo2.attach(servo2Pin);
     }
 
     void deplacementNormal(int distanceObstacle , int tsop , int hall, int* attraper){
       unsigned long currentMillis = millis();
       
       if (hall == 1){
         etatHall = 1;
         *attraper = 1;
       }
       else if (distanceObstacle < 200){
         etatSonnar = 1;
       }
       else if (tsop==1){
         etatTsop = 1;
         lastMillis = currentMillis;
       }
       
       if (etatHall == 1){
         servo1.write(90);
         servo2.write(90);
       }
       
       else if (etatSonnar ==1){
         if (etatRotation == 0){
           etatRotation = random(1,3);
         }
         if(etatRotation == 1){
           servo1.write(180);
           servo2.write(180);
         }
         else{
           servo1.write(0);
           servo2.write(0);
         }
         etatSonnar = 0 ;
         lastMillis = currentMillis;
       }
       
       else if (etatTsop == 1){
         if (etatRotation == 0){
           etatRotation = random(1,3);
         }
         
         if(etatRotation == 1){
           servo1.write(180);
           servo2.write(180);
         }
         else{
           servo1.write(0);
           servo2.write(0);
         }
         
         if (currentMillis - lastMillis >= intervalTsop){
           etatTsop = 0;
           lastMillis = currentMillis;
         }
       }   
       
       else{
         etatRotation = 0;
         if (currentMillis - lastMillis < intervalMouvement1){
           servo1.write(180);
           servo2.write(70);
         }
         else if ((currentMillis - lastMillis >= intervalMouvement2) &&  (currentMillis - lastMillis <= intervalMouvement3)){
           servo1.write(98);
           servo2.write(0);
         }
         else{
           servo1.write(180);
           servo2.write(0);
           if (currentMillis - lastMillis >= intervalMouvement4){
             lastMillis = currentMillis;
           }
         }
       }
     }
 };                                                         
 
 
 
 Mouv servo(SERVO1,SERVO2);
 
 //varibable pour le sonnar
 
 long lectureEcho;
 long distance;
 const float SOUND_SPEED = 340.0 / 1000;
 
 //varibable pour la sonde de hall
 
 int* attraper;
 
 //varibable pour les tsop
 
 unsigned long last_millis = 0; 
 long interval = 500;
 
 int broche_reception1 = VCCIR1;
 IRrecv reception_ir1(broche_reception1);
 decode_results decode_ir1;
 
 int broche_reception2 = VCCIR2;
 IRrecv reception_ir2(broche_reception2);
 decode_results decode_ir2; 
 
 //instance pour l'emmission infra-rouge
 
 IRsend emission_ir; 
 
 
 void setup() {
   pinMode(TRIGG,OUTPUT);
   digitalWrite(TRIGG,0);
   pinMode(ECHO,INPUT); 
   pinMode(IR,OUTPUT);
   digitalWrite(IR,1);
 
   servo.attacher();
   
   reception_ir1.enableIRIn(); // démarre la réception
   reception_ir2.enableIRIn();
   
   attraper = malloc(sizeof(int));
   *attraper = 0;
   
 }
 
 
 void loop() {
   servo.deplacementNormal(sonnar(),tsop(attraper),hall(),attraper);  
 }
 
 
 int sonnar() {
   digitalWrite(TRIGG, 1);
   delayMicroseconds(10);
   digitalWrite(TRIGG,0);
   long measure = pulseIn(ECHO, HIGH);
   
   float distance_mm = measure / 2.0 * SOUND_SPEED;
   return distance_mm; 
 }
 
 int tsop(int * attraper ){
   unsigned long current_millis = millis();
   int etatTsop = 0;
   if ((current_millis - last_millis >= interval)&&(*attraper == 0)){
      emission_ir.sendNEC(1, 32); 
      last_millis = current_millis; 
      reception_ir1.enableIRIn();
      reception_ir2.enableIRIn();
   }
   
   if (reception_ir1.decode(&decode_ir1)) 
   { 
     if(decode_ir1.value == 1){
       etatTsop = 1;
     }
 
     reception_ir1.resume();
     reception_ir2.enableIRIn();
   }
   if (reception_ir2.decode(&decode_ir2)) 
   { 
     if(decode_ir2.value == 1){
       etatTsop = 1;
     } 
     reception_ir2.resume();  
     reception_ir1.enableIRIn();
   }
   return etatTsop;
 }
 
 
 int hall(){
   int etatHall = 0;
   if(digitalRead(HALL) == 0){
     etatHall = 1;
   }
   return etatHall;
 }

}

Description de la structure du code