/**************************************************************/ //Contrôle de commande de moteur brushless "aviation" //Mesure par capteur infrarouge Sharp GP2Y0A41SK0F sur AN0. // Un ajustage de hauteur par potentiomètre // de quelques kilo ohms est possible. /*************************************************************/ // Declaration des variables globales int distance=0; int offset= 0; // un décalage de niveau ajustable par potentiomètre int dist_utile=0;// variable associée au capteur Sharp ou au potentiomètre unsigned int temps_pulse; // largeur d'impulsion de la sortie int sortie_servo=9; // numéro des PIN du module arduino utilisé en sortie pour la connexion // à la commande du contrôleur brushless . unsigned long debut_periode; // pour appliquer la période de 20 millisecondes qui doit séparer les // impulsions de commande du contrôleur brushless. int pinDistance =0,pinOffset=1; // numéro de PIN de conversion analogique digitale du module arduino // utilisé pour lire la tension du capteur et du réglage d'offset boolean flag_demarre=1; // valeur 1 pendant la séquence de démarrage // mis à 0 pour passer à la boucle de durée infinie // qui correspond au fonctionnement normal void mesures(void) // fontion appelée pour mesurer l'entrée analogique { distance=0; offset = 0; //la valeur de distance est moyennée for(int ii=0; ii<16; ii++) { distance += analogRead(pinDistance); offset += analogRead(pinOffset); } //distance est prise une 16 fois . //et divisé par 16 (en décalant 4 fois à droite) pour faire une moyenne // afin de limiter l'effet de certains relevés décalés par des parasites dist_utile = (distance >>4); // offset est divisé par 16,puis centré, il pourra donc faire + ou - 512 offset >>= 4; offset -=512; // en plus ou moins sur la valeur centrale // Si le capteur Sharp est utilisé la tension maximale est de l'ordre de 3V. // On la remet à l'ordre de 1023 unités par les instructions suivantes dist_utile = constrain(dist_utile,0,720); // éviter des débordements // la variation de gain est obtenue en modifiant la plage de conversion // la valeur de 1023 peut être réduite si la réserve d'air présente une // tendance au "pompage". Ceci revient à réduire le gain de la régulation. dist_utile = map(dist_utile,0,720,0,1023); //utiliser la ligne suivante si la tension augmente quand la réserve //d'air augmente, sinon il faut la mettre en // commentaire, //afin d'obtenir une variation dans le sens de la contre-réaction /************************************************/ /************************************************/ dist_utile = 1023 - dist_utile; /************************************************/ /************************************************/ // dist_utile sera comprise entre 0 et 1023 // Serial.print("Distance utile :"); // pour debugger éventuellement // Serial.println(dist_utile); // Affichage éventuel pour vérifier la mesure } // fonction appelée pour générer l'impulsion de commande //du contrôleur de moteur brushless void faire_pulse(int commande) { temps_pulse = (990 + constrain(commande,0,1023)); // constrain utilisé pour que la durée des impulsions reste dans les // limites de environ 1 à 2 msec, même en cas d'errer sur commande. digitalWrite(sortie_servo,HIGH); delayMicroseconds(temps_pulse); digitalWrite(sortie_servo,LOW); } void setup()//Initialise l'utilisation des PINs de l'arduino { pinMode(sortie_servo,OUTPUT); digitalWrite(sortie_servo,LOW); Serial.begin(9600);// pour déboggage éventuel analogReference(DEFAULT);// référence du convertisseur // est la tension d'alimentation } unsigned compte=0; // variable utilisée pour le comptage dans des boucles void loop() { // 6 secondes pour que le contrôleur brushless s'initialise // Il faut que pendant ce temps le contrôleur reçoive, avec une période de // 20 millisecondes des impulsions de durée minimale : approximativement // 1 milliseconde. while(flag_demarre)// boucle tant que flag_demarre est à 1 { debut_periode= micros();// la période durera 20 millisecondes faire_pulse(0); // l'impulsion doit être à sa valeur minimale // pendant toute la durée où le contrôleur du moteur fair // son initialisation. compte++; if(compte>300) // (300 x 20 msec = 6 sec) { compte = 0; //reset de compte pour une réutilisation possible flag_demarre = 0; // pour finir la boucle } while( (micros()-debut_periode) < 19999); // attendre les 20 millisecondes pour la période des impulsions. } //refaire une boucle pour une augmentation progressive de la puissance // afin de ne pas bousculer trop rapidement la réserve d'air. // On augmente la largeur d'impulsion de 1 microsecondes toutes les 20 millisecondes // jusqu'à ce que la valeur maximale soit atteinte, où que le niveau de signal // délivrer par le capteur de hauteur de la réserve d'air soit atteint. flag_demarre = 1; while(flag_demarre) { debut_periode = micros(); faire_pulse( compte ); compte++; if(compte > 1023) flag_demarre=0;//puissance max atteinte mesures(); if(compte > dist_utile+offset) flag_demarre = 0; // consigne atteinte if(compte < 100) flag_demarre= 1; //empêche la sortie prématurée de boucle pendant les 2 premières //secondes, laissant les effets de moyenne se stabiliser while( (micros()-debut_periode) < 19999){}; // attendre les 20 millisecondes pour la période des impulsions } // Passage en fonctionnement normal : boucle infinie while(1) { debut_periode = micros(); mesures(); // mesurer la hauteur de la réserve d'air faire_pulse(dist_utile + offset ); // ajuster la durée de l'impulsion de commande //du contrôleur du moteur brushless, en tenant compte du décalage de hauteur //ajustée manuellement par le potentiomètre de réglage connecté à l'entrée A1, //auquel est associé la variable nommée offset while( (micros()-debut_periode) < 19999); // attendre les 20 millisecondes pour la période des impulsions } }