ACCUEIL | ARDUINO > S'INSTALLER > DEBUTER > APPROFONDIR | PROCESSING | MECATRONIQUE | MATERIEL | OUTILS | TESTS | Plus...|
Python > Shell > ATELIERS Python + Qt > PyQt apps > PyQt+Arduino | Mes Robots | RepRap | Mes lib'Arduino | Mes shields Arduino | Mes distros | Les Mini-PC |
ATELIERS ARDUINO| VIDEOS | COMPRENDRE | REFERENCES | CODER | TECHNIQUE | GNU/LINUX | LIENS | Rien à voir |
Suivi de balle par une tourelle pan (1 servomoteur) à partir d'une interface Processing - avec GSVideo et JavacvProPar X. HINAULT - Page créée le : 23/03/2012.
On this page... (hide) 1. Présentation
Ce programme utilise les fonctionnalités suivantes :
Ressources utiles associées à ce programme :
Pour info, j'ai utilisé ici :
2. Schéma fonctionnel![]()
3. Matériel Nécessaire3.1 L'espace de développement Arduino
![]() 3.2 Le matériel électronique suivant pour réaliser le montage associé
![]() 3.3 Le matériel mécanique suivant pour réaliser la mécanique associée
![]()
![]() ![]() ![]() ![]() ![]() ![]() ![]()
![]() 4. Instructions de montage
Pour plus de détails, voir : Principes d'utilisation des alimentations avec une carte Arduino et des servomoteurs 5. Le schéma théorique du montageLe schéma théorique du montage (cliquer pour agrandir) 6. Le circuit du montageLe schéma du montage à réaliser (cliquer pour agrandir) 7. Explication du programme
8. Mise en oeuvre du programme8.1 Préparation du montage et programmation de la carte Arduino :
8.2 Fonctionnement
9. Le programme complet en langage ArduinoA copier/coller directement dans l'éditeur Arduino Ce programme Arduino pourra être très simplement testé à partir du Terminal Série avant de lancer l'interface Processing. // --- Programme Arduino --- // Trame de code générée par le générateur de code Arduino // du site www.mon-club-elec.fr // Auteur du Programme : X. HINAULT - Tous droits réservés // Programme écrit le : 12/08/2011. Mis à jour Arduino 1.0 le 23/03/2012 // ------- Licence du code de ce programme ----- // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, // or any later version. // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // You should have received a copy of the GNU General Public License // along with this program. If not, see <http://www.gnu.org/licenses/>. // //////////////////// PRESENTATION DU PROGRAMME //////////////////// // -------- Que fait ce programme ? --------- /*Un servomoteurs connectés à la carte Arduino est contrôlé à partir du PC (interface Processing) Controle par chaine de la forme : * servoPan(000) avec 000 = angle absolu en degrés pour un positionnement immédiat * servoPanTo(000) avec 000 = angle absolu en degrés pour un positionnement progressif avec delai vitesse * servoPanToR(000) avec 000 = angle relatif en degrés pour un positionnement progressif avec delai vitesse * vitesse(000) avec 000 = delai en millisecondes à utiliser entre 2 positions intermédiaires (10 = rapide, 50 = lent) */ //cette version du programme vise à optimiser au maximum la vitesse de réactivité des servomoteurs // --- Fonctionnalités utilisées --- // Utilise / fonctionne avec une interface Processing coté PC // Utilise 2 servomoteurs // -------- Circuit à réaliser --------- // ******* ATTENTION : il est possible de connecter directement 2 ou 3 servomoteurs sur la carte Arduino // Connecter un servomoteur PAN sur la broche 8 // Connecter un servomoteur TILT sur la broche 9 // /////////////////////////////// 1. Entête déclarative /////////////////////// // A ce niveau sont déclarées les librairies incluses, les constantes, les variables, les objets utiles... // --- Déclaration des constantes --- // --- Inclusion des librairies --- #include <Servo.h> // librairie pour servomoteur // --- Déclaration des constantes utiles --- const int APPUI=LOW; // constante pour tester état BP //--- Constantes utilisées avec le servomoteur const int ANGLE_MIN=0; // angle position MIN en degrés const int POS_MIN=550; // largeur impulsion pour position ANGLE_MIN degrés du servomoteur // POS_MIN=550 pour ANGLE_MIN=0 avec un futaba S3003 const int ANGLE_MAX=172; // angle position MAX en degrés int POS_MAX=2400; // largeur impulsion pour position ANGLE_MAX degrés du servomoteur // POS_MAX=2400 pour ANGLE_MAX=172 pour futaba S3003 // pour étalonner un servomoteur, voir la page : //http://www.mon-club-elec.fr/pmwiki_mon_club_elec/pmwiki.php?n=MAIN.ArduinoExpertSerieDepuisPCPositionServomoteur // --- Déclaration des constantes des broches E/S numériques --- const int broche_servoPan=2; // Constante pour la broche // --- Déclaration des constantes des broches analogiques --- // --- Déclaration des variables globales --- int octetReception=0; // variable de stockage des valeurs reçues sur le port Série long nombreReception=0; // variable de stockage du nombre reçu sur le port Série long nombreReception0=0; // variable de stockage du dernier nombre reçu sur le port Série String chaineReception=""; // déclare un objet String vide pour reception chaine int valeur=0; // variable utile long param=0; // paramètre transmis float angleServoPan=90; // variable de position du servo Pan en degrés float angleServoPan0=90; // variable de la dernière position du servo Pan en degrés int vitesse=0; // variable utilisée pour délai entre 2 lecture port Série // --- Déclaration des objets utiles pour les fonctionnalités utilisées --- //--- Création objet servomoteur Servo servoPan; // crée un objet servo pour contrôler le servomoteur 1 // ////////////////////////// 2. FONCTION SETUP = Code d'initialisation ////////////////////////// // La fonction setup() est exécutée en premier et 1 seule fois, au démarrage du programme void setup() { // debut de la fonction setup() // --- ici instructions à exécuter 1 seule fois au démarrage du programme --- // ------- Initialisation fonctionnalités utilisées ------- Serial.begin(115200); // initialise connexion série à 115200 bauds // IMPORTANT : régler le terminal côté PC avec la même valeur de transmission //--- Initialisation Servomoteur servoPan.attach(broche_servoPan); // attache l'objet servo à la broche de commande du servomoteur Pan // se positione à 90° par défaut // ------- Broches en sorties numériques ------- pinMode (broche_servoPan,OUTPUT); // Broche broche_servoPan configurée en sortie // ------- Broches en entrées numériques ------- // ------- Activation si besoin du rappel au + (pullup) des broches en entrées numériques ------- // ------- Initialisation des variables utilisées ------- // ------- Codes d'initialisation utile ------- servoPan.writeMicroseconds(angle(angleServoPan)); // crée impulsion à partir valeur angle - plus précis que write() Serial.println("Arduino OK"); // debug delay(200); } // fin de la fonction setup() // ******************************************************************************** ////////////////////////////////// 3. FONCTION LOOP = Boucle sans fin = coeur du programme ////////////////// // la fonction loop() s'exécute sans fin en boucle aussi longtemps que l'Arduino est sous tension void loop(){ // debut de la fonction loop() //---- code type réception chaine sur le port série --- while (Serial.available()>0) { // tant qu'un octet en réception octetReception=Serial.read(); // Lit le 1er octet reçu et le met dans la variable if (octetReception==10) { // si Octet reçu est le saut de ligne Serial.print ("Chaine recue="),Serial.print(chaineReception); // affiche la chaine recue analyseChaine(chaineReception); // appelle la fonction d'analyse de la chaine en réception chaineReception=""; //RAZ le String de réception break; // sort de la boucle while } else { // si le caractère reçu n'est pas un saut de ligne chaineReception=chaineReception+char(octetReception); // ajoute le caratère au String } } // fin tant que octet réception //----- une fois que le saut de ligne est reçu, on sort du While et on se positionne ici //chaineReception=""; //------------- fin analyse chaine --------------- //delay(vitesse); } // fin de la fonction loop() - le programme recommence au début de la fonction loop sans fin // ******************************************************************************** // ////////////////////////// FONCTIONS DE GESTION DES INTERRUPTIONS //////////////////// // ////////////////////////// AUTRES FONCTIONS DU PROGRAMME //////////////////// //------------- fonction calibrage impulsion servomoteur à partir valeur angle en degrés //------- mieux avec float ----- float angle(float valeur_angle) { float impuls=0; impuls=map(valeur_angle,ANGLE_MIN,ANGLE_MAX,POS_MIN, POS_MAX); return impuls; } // fin fonction impulsion servomoteur //------------- fonction d'analyse de la chaine reçue sur le port série ---- //------------ analyseChaine --------------- void analyseChaine(String chaineRecue) { // fonction d'analyse de la chaine recue // ---- analyse de la chaine recue sur le port Série ---- //chaineReception=chaineReception.trim(); // enlève les espaces chaineReception.trim(); // enlève les espaces - Arduino 1.0 //xxxxxxxxxxxxxxxxxxx instructions sans paramètres xxxxxxxxxxxx //xxxxxxxxxxxxxxxxxxxx instructions avec paramètres xxxxxxxxxxxxxxx // info : la valeur numérique extraite par testInstruction() est stockée dans variable globale param //================= instructions paramètres généraux ============= //-------------- test instruction vitesse(xxx) ----------- if (testInstruction("vitesse(")==true) { // si instruction reçue valide vitesse=param; // change valeur vitesse (= durée delay en ms) Serial.print("vitesse = "), Serial.println(vitesse); } // fin test vitesse(xxx) //================ instructions servo Pan ========= //-------------- test instruction servoPan(xxx) ----------- if (testInstruction("servoPan(")==true) { // si instruction reçue valide servoPan.writeMicroseconds(angle(param)); // crée impulsion à partir valeur angle - plus précis que write() angleServoPan0=param; // mémorise angle actuel } // fin test genouD(xxx) //-------------- test instruction servoPanto(xxx) ----------- // positionnement progressif if (testInstruction("servoPanTo(")==true) { // si instruction reçue valide // void servoTo( Servo toServo, float fromAngle, float toAngle, int toVitesse, int toPas) servoTo( servoPan, angleServoPan0, param, vitesse, 1); //--- positionnement progressif par pas fixe de 1 degré --- angleServoPan0=param; // met à jour l'angle courant servo avec valeur extraite par testInstruction() //Serial.print("angleServoPan0 = "), Serial.println(angleServoPan0); } // fin test genouDto(xxx) //-------------- test instruction servoPantoR(xxx) ----------- // positionnement progressif if (testInstruction("servoPanToR(")==true) { // si instruction reçue valide // void servoToR( Servo toServo, float fromAngle, float toAngle, int toVitesse, int toPas) servoToR( servoPan, angleServoPan0, param, vitesse, 1); //--- positionnement progressif par pas fixe de 1 degré --- angleServoPan0=param+angleServoPan0; // met à jour l'angle courant servo //Serial.print("angleServoPan0 = "), Serial.println(angleServoPan0); } // fin test servoPantoR(xxx) } // ---------------- fin fonction analyse chaine ---------------------- //--------------- testInstruction : test si instruction de la forme instruction(xxx) ------------ boolean testInstruction(String chaineTest) { // reçoit chaine et renvoie true si instruction valide long posRef=chaineTest.length();// position de référence pour analyse (xxx) if (chaineReception.substring(0,posRef)==chaineTest) { // si reçoit l'instruction chaineTest(000) // nb substring : dernier caractere exclu //Serial.print("Arduino va executer : "); //Serial.print(chaineTest); // affiche if (chaineReception.substring(posRef,posRef+1)=="-") { // si signe - présent on décale de 1 position la prise en compte du nombre xxx param=(-1)*stringToLong(chaineReception.substring(posRef+1,posRef+4)); // extraction valeur 3 chiffres à partir caractères et * par -1 posRef=posRef+1; // modif valeur posRef } // fin if else { // si pas de signe - param=stringToLong(chaineReception.substring(posRef,posRef+3)); // extraction valeur 3 chiffres à partir caractères } // fin else //Serial.print(param); // affiche if (chaineReception.substring(posRef+3,posRef+4)==")") { // si fermeture parenthèse = instruction valide //Serial.println(")"); // affiche //Serial.println("Instruction valide !"); // affiche return(true); // renvoie true si instruction valide } // fin si fermeture parenthèse else { //Serial.println("Instruction invalide !"); // affiche return(false); // renvoie false si instruction invalide } // fin else } // fin si reçoit l'instruction chaineTest(000) } // fin fonction testInstruction //------------------- fin test instruction ------------ // ---------- fonction de conversion d'un String numérique en long long stringToLong(String chaineLong) { // fonction conversion valeur numérique String en int long nombreLong=0; // variable locale int valeurInt=0; // variable locale for (int i=0; i<chaineLong.length(); i++) { // défile caractères de la chaine numérique valeurInt=chaineLong.charAt(i); // extrait le caractère ASCII à la position voulue - index 0 est le 1er caractère valeurInt=valeurInt-48; // obtient la valeur décimale à partir de la valeur ASCII if (valeurInt>=0 && valeurInt<=9) { // si caractère est entre 0 et 9 nombreLong=(nombreLong*10)+valeurInt; } // fin si caractère est entre 0 et 9 } // fin for défile caractères return (nombreLong); // renvoie valeur numérique } // ---------- fin stringToLong ------------ //--- fonction de positionnement progressif du servomoteur par pas fixe ----- void servoTo( Servo toServo, float fromAngle, float toAngle, int toVitesse, int toPas) { //--- positionnement progressif par pas fixe de 1 degré --- int delta=toAngle-fromAngle; // variation d'angle // Serial.print("delta = "), Serial.println(delta); if (delta>=0) { // si variation positive for (int i=0; i<delta; i++) { // defile n positions pour atteindre angle final dans sens positif fromAngle=fromAngle+1; // ajoute cran toServo.writeMicroseconds(angle(fromAngle)); // crée impulsion à partir valeur angle - plus précis que write() //Serial.print("angle courant servo = "), Serial.println(fromAngle); delay(vitesse); // pause entre chaque positionnement } // fin for } // fin if else { // si variation négative for (int i=-delta; i>0; i--) { // defile n positions pour atteindre angle final dans sens négatif fromAngle=fromAngle-1; // ajoute cran toServo.writeMicroseconds(angle(fromAngle)); // crée impulsion à partir valeur angle - plus précis que write() //Serial.print("angle courant servo = "), Serial.println(fromAngle); delay(vitesse); // pause entre chaque positionnement } // fin for } // fin else } //--- fonction de positionnement progressif du servomoteur par pas fixe - angle relatif à la position courante ----- void servoToR( Servo toServo, float fromAngle, float toAngle, int toVitesse, int toPas) { //--- positionnement progressif par pas fixe de 1 degré --- int delta=toAngle; // variation d'angle correspond à l'angle transmis //Serial.print("delta = "), Serial.println(delta); if (delta>=0) { // si variation positive for (int i=0; i<delta; i++) { // defile n positions pour atteindre angle final dans sens positif fromAngle=fromAngle+1; // ajoute cran toServo.writeMicroseconds(angle(fromAngle)); // crée impulsion à partir valeur angle - plus précis que write() //Serial.print("angle courant servo = "), Serial.println(fromAngle); delay(vitesse); // pause entre chaque positionnement } // fin for } // fin if else { // si variation négative for (int i=-delta; i>0; i--) { // defile n positions pour atteindre angle final dans sens négatif fromAngle=fromAngle-1; // ajoute cran toServo.writeMicroseconds(angle(fromAngle)); // crée impulsion à partir valeur angle - plus précis que write() //Serial.print("angle courant servo = "), Serial.println(fromAngle); delay(vitesse); // pause entre chaque positionnement } // fin for } // fin else } // ////////////////////////// Fin du programme //////////////////// 10. Le programme Processing10.1 Description
10.2 Ressources utiles
10.3 Le programme complet en langage ProcessingA copier/coller directement dans l'éditeur Processing // Programme processing // généré avec le générateur de code Processing // du site www.mon-club-elec.fr // par X. HINAULT - tous droits réservés // Programme écrit le : 26/10/2011. // ------- Licence du code de ce programme : GPL v3----- // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, // or any later version. // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // You should have received a copy of the GNU General Public License // along with this program. If not, see <http://www.gnu.org/licenses/>. /////////////// Description du programme //////////// // Utilise la librairie GSVideo de capture et lecture vidéo // Utilise la librairie javacvPro de traitement d'image et reconnaissance visuelle /* Détection et suivi de balle à partir d'un flux vidéo webcam à l'aide de la librairie javacvPro */ // XXXXXXXXXXXXXXXXXXXXXX ENTETE DECLARATIVE XXXXXXXXXXXXXXXXXXXXXX // inclusion des librairies utilisées import codeanticode.gsvideo.*; // importe la librairie vidéo GSVideo qui implémente GStreamer pour Processing (compatible Linux) // librairie comparable à la librairie native vidéo de Processing (qui implémente QuickTime..)- Voir Reference librairie Video Processing // cette librairie doit être présente dans le répertoire modes/java/libraries du répertoire Processing (1-5) // voir ici : http://gsvideo.sourceforge.net/ // et ici : http://codeanticode.wordpress.com/2011/05/16/gsvideo-09-release import monclubelec.javacvPro.*; // importe la librairie javacvPro qui implémente le traitement d'image avancé et la reconnaissance visuelle pour Processing // cette librairie se base sur les fonctions java de la librairie javacv par Samuel Audet : http://code.google.com/p/javacv/ // javacv implémente en Java les centaines de fonctions natives de la librairie OpenCV (2500 algorithmes) ! // la librairie javacvPro doit être présente dans le répertoire modes/java/libraries du répertoire Processing (1-5) // dispo ici : http://www.mon-club-elec.fr/pmwiki_reference_lib_javacvPro/pmwiki.php // nécessite également que la librairie native OpenCV 2.3.1 soit installée sur votre ordinateur // NB : compatibilité avec la plupart des fonctions de la librairie OpenCV pour Processing : http://ubaa.net/shared/processing/opencv/ import processing.serial.*; // importe la librairie série processing // déclaration objets // --- port Série --- Serial myPort; // Création objet désignant le port série PImage imgSrc, imgDest; // déclare un/des objets PImage (conteneur d'image Processing) GSCapture cam1; // déclare un objet GSCapture représentant une webcam // L'objet GSCapture étend PImage - se comporte comme un conteneur des frames issues de la webcam OpenCV opencv; // déclare un objet OpenCV principal Blob[] blobs=null; // tableau pour la détection des blobs (contour de forme) // déclaration variables globales // déclaration variables globales //int xmin, xmax, ymin, ymax; // coordonnées de la zone à tester int comptImg=0; // variable de comptage des images pour moyenne centre int nbImg=2; // nombre images à prendre en compte avant mouvement //--- plus on prend en compte d'image, plus c'est stable, mais c'est moins rapide long moyX=0; // pour calcul moyenne X long moyY=0; // pour calcul moyenne Y //------ déclaration des variables de couleur utiles ---- int jaune=color(255,255,0); int vert=color(0,255,0); int rouge=color(255,0,0); int bleu=color(0,0,255); int noir=color(0,0,0); int blanc=color(255,255,255); int bleuclair=color(0,255,255); int violet=color(255,0,255); // variable pour la taille de la capture video int widthCapture=320; // largeur capture int heightCapture=240; // hauteur capture int fpsCapture=20; // framerate (image/secondes) pour la capture video long millis0=0; // variable mémorisation millis() // XXXXXXXXXXXXXXXXXXXXXX Fonction SETUP XXXXXXXXXXXXXXXXXXXXXX void setup(){ // fonction d'initialisation exécutée 1 fois au démarrage // ---- initialisation paramètres graphiques utilisés colorMode(RGB, 255,255,255); // fixe format couleur R G B pour fill, stroke, etc... fill(0,0,255); // couleur remplissage RGB - noFill() si pas de remplissage stroke (0,0,0); // couleur pourtour RGB - noStroke() si pas de pourtour rectMode(CORNER); // origine rectangle : CORNER = coin sup gauche | CENTER : centre imageMode(CORNER); // origine image : CORNER = coin sup gauche | CENTER : centre ellipseMode(CENTER); // origine cercles / ellipses : CENTER : centre (autres : RADIUS, CORNERS, CORNER //strokeWeight(0); // largeur pourtour frameRate(30);// Images par seconde - The default rate is 60 frames per second // --- initialisation fenêtre de base --- size(widthCapture, heightCapture); // ouvre une fenêtre xpixels x ypixels background(0,0,0); // couleur fond fenetre // --- initialisation des objets et fonctionnalités utilisées --- //------------- initialisation port série ---- println(Serial.list()); // affiche dans la console la liste des ports séries // Vérifier que le numéro du port série utilisé est le meme que celui utilisé avec Serial.list()[index] myPort = new Serial(this, Serial.list()[0], 115200); // Initialise une nouvelle instance du port Série //myPort = new Serial(this, "/dev/ttyACM0", 115200); // Initialise une nouvelle instance du port Série myPort.bufferUntil('\n'); // attendre arrivée d'un saut de ligne pour générer évènement série //======== Initialisation Objets GSVideo (capture et/ou lecture video ========= // GSCapture(this, int requestWidth, int requestHeight, [int frameRate], [String sourceName], [String cameraName]) // cam1 = new GSCapture(this, widthCapture, heightCapture,fpsCapture,"v4l2src","/dev/video0"); // Initialise objet GSCapture désignant webcam - avant GSVideo 1.0 cam1 = new GSCapture(this, widthCapture, heightCapture,"v4l2src","/dev/video1", fpsCapture); // Initialise objet GSCapture désignant webcam - depuis GSVideo 1.0 // largeur et hauteur doivent être compatible avec la webcam - typiquement 160x120 ou 320x240 ou 640x480... // Meilleurs résultats avec framerate webcam entre 20 et 30 et frameRate programme idem ou multiple plus grand (40 pour 20 par ex) // la liste des webcam installées sous Ubuntu (Gnu/Linux) est donnée par la commande : ls /dev/video* // cam1.play(); // démarre objet GSCapture = la webcam - version GSVideo avant 0.9 cam1.start(); // démarre objet GSCapture = la webcam - version GSVideo après 0.9 //======== Initialisation Objets OpenCV (librairie javacvPro : traitement d'image et reconnaissance visuelle) ========= opencv = new OpenCV(this); // initialise objet OpenCV à partir du parent This opencv.allocate(widthCapture,heightCapture); // crée les buffers image de la taille voulue //======== initialisation paramètres servomoteurs ======== myPort.write("vitesse(000)\n");// vitesse pour le servomoteur } // fin fonction Setup // XXXXXXXXXXXXXXXXXXXXXX Fonction Draw XXXXXXXXXXXXXXXXXXXX void draw() { // fonction exécutée en boucle // Code type capture GSVideo - utilisation possible aussi de captureEvent() if (cam1.available() == true) { // si une nouvelle frame est disponible sur la webcam cam1.read(); // acquisition d'un frame //image(cam1, 0, 0); // affiche image //set(0, 0, cam); // affiche image - plus rapide imgSrc=cam1.get(); // récupère l'image GS video dans Pimage opencv.copy(imgSrc); // charge l'image dans le buffer openCV //opencv.copy(cam1.get()); // autre possibilité - charge directement l'image GSVideo dans le buffer openCV millis0=millis(); // pour analyse durée - mémorise debut //opencv.mixerRGBGray(); // applique mixeur RGBGray sur le buffer principal OpenCV avec paramètres par défaut (1.0, 1.5,-2.0 opencv.mixerRGBGray(1.0,1.5, -2.0); // mixerRGBGray appliqué sur objet IplImage avec paramètres - ici détection couleur orangée opencv.threshold(0.70,"BINARY"); // applique seuillage binaire pour éliminer tout ce qui n'est pas orange //image(opencv.image(), 0, 0); // affiche image traitée - utile pour debug ou comprendre image(imgSrc, 0, 0); // affiche image de départ avant tracé des formes détectées blobs=opencv.blobs(); // détection des formes - renvoie tableau de blobs //blobs=opencv.blobs(opencv.area()/1024,opencv.area(),1000, true, 1000,false); // forme détaillée - applique blobs au buffer principal avec paramètres et renvoie tableau d'objets Blob //blobs=opencv.selectBallBlobs(blobs); // sélectionne que les formes compatibles avec une balle // void drawRectangleBlobs (Blob[] blobsIn, int xRefIn, int yRefIn, float scaleIn, int colorStrokeIn, int strokeWeightIn, boolean fillIn, int colorFillIn) //opencv.drawRectBlobs(blobs); // javacvPro : trace le rectangle de tous les blobs détectés opencv.drawRectBlobs(blobs, 0,0,1,vert,2,false,0); // forme détaillée - javacvPro : trace le rectangle de tous les blobs détectés // void drawBlobs (Blob[] blobsIn, int xRefIn, int yRefIn, float scaleIn, int radius, int colorStrokeIn, int strokeWeightIn, boolean fillIn, int colorFillIn, int mode) //opencv.drawBlobs (blobs); // javacvPro : trace le contour de tous les blobs détectés opencv.drawBlobs (blobs, 0,0,1,5,rouge,1,true,jaune,1); // forme détaillée - javacvPro : trace le contour de tous les blobs détectés // nb : mettre dessin centre après dessin blob, sinon invisible // void drawCentroidBlobs (Blob[] blobsIn, int xRefIn, int yRefIn, float scaleIn, int radius, int colorStrokeIn, int strokeWeightIn, boolean fillIn, int colorFillIn) //opencv.drawCentroidBlobs( blobs); // javacvPro : trace le centre de tous les blobs détectés opencv.drawCentroidBlobs( blobs, 0,0,1,10,jaune,1,true,rouge); // forme détaillée -javacvPro : trace le centre de tous les blobs détectés //println("Durée traitement d'1 frame = "+(millis()-millis0) + "ms soit fps max théorique de " + (1000/(millis()-millis0))+" fps !"); // pour analyse - affiche durée traitement image //---- détection du "centre" de l'objet ---- if (blobs.length>0) { int centreX= blobs[0].centroid.x; // centroid renvoie un objet Point qui fournit x et y int centreY= blobs[0].centroid.y; // centroid renvoie un objet Point qui fournit x et y //--------------- gestion centre pour servomoteur ---------- // moyenne des X et des Y moyX=moyX+centreX; comptImg=comptImg+1; if (comptImg>=nbImg) { // si le nombre d'image à prendre en compte dépassé //println("X = "+ centreX); //println("Total X = "+ moyX); //println("comptImg="+comptImg); moyX=moyX/(comptImg); // calcule moyenne centre X //println ("Moyenne X = "+ moyX); //--- positionnement servomoteur --- if (moyX<((width/2)-15)) { // si on est vers la droite - la valeur retranchée évite oscillation sur centre... //--- plus l'angle utilisé ici est grand, plus c'est rapide... mais si trop grand, trop par "à coup"... 2 ou 3 degrès = bon compromis) myPort.write("servoPanToR(002)\n");// on incrémente la position de l'angle du servomoteur //println("servoPanToR(002)\n"); } if (moyX>((width/2)+15)) { // si on est vers la droite - la valeur retranchée évite oscillation sur centre... myPort.write("servoPanToR(-002)\n");// on incrémente la position de l'angle du servomoteur //println("servoPanToR(-002)\n"); } comptImg=0; // RAZ comptage images moyX=0; // RAZ moyX } } // fin if blob pas null } // fin if available } // fin de la fonction draw() // XXXXXXXXXXXXXXXXXXXXXX Autres Fonctions XXXXXXXXXXXXXXXXXXXXXX //------------- Fonction d'arret de Processing ---- public void stop(){ // fonction d'arrêt de Processing cam1.delete(); // efface l'objet GScapture super.stop(); // obligatoire } // fin fonction stop() //XXXXXXXXXXXXXXXXXX Fin du programme XXXXXXXXXXXXXXXXX |