Arduino Hack : Comment commander un servomoteur avec une carte Arduino et le logiciel Arduino IDE ?

Rédigé par tesla - - Aucun commentaire
Article terminé, j'ajouterai des vidéos "démonstration" des sketchs Arduino proposés

Qui dit Arduino dit aussi Arduino IDE

Il semble judicieux et logique de commencer cet article par la programmation de la carte Arduino dans le but de piloter un servo à l'aide de ce logiciel. 

Les élèves posent parfois la question ? Pourquoi IDE ? Eh bien, IDE est l'acronyme pour "Integrated Development Environment", c'est donc un environnement de développement dédié aux cartes Arduino et associées (ESP par exemple). 

Ce logiciel permet de televerser des programmes dans les cartes qui lui sont associées, d'analyser/vérifier ces programmes, d'observer à travers deux utilitaires ce qui se passe sur la liaison série (Moniteur et traceur), il permet aussi naturellement de créer et éditer des programme grâce à sa coloration syntaxique spécifique au langage Arduino qui est un dérivé de langage C/C++. Le must c'est que cet environnement intégre nativement les librairies et fonctions usuelles de ce langage dédié. 

Très franchement si le langage C++ vous semble accessible, vous n'aurez besoin de rien d'autre pour réaliser vos projets. 

Comment l'obtenir ? 
Télechargement officiel sur le site arduino.ccProcédure d'installation
Et comment apprendre à s'en servir ? 
Site franco-français arduino-france.com, une mine d'or de tutos et ressourcesopenclassrooms.com ex site du zéro : Cours en programmation Arduino en différents modules de plus de 40h ! Il y a de quoi faire...

Parlons code !

La librairie/bibliothèque Servo

Comme expliqué plus haut, Arduino IDE comprend de nombreuses librairies très utiles. Il existe une librairie nommée Servo et cerise sur le gateau, des codes "exemples" sont proposés. 

La librairie Servo permet d'utiliser des fonctions spécifiques à la programmation d'un servomoteur avec une carte Arduino. 

En réalité il est possible de le faire sans mais avec cette librairie on gagne vraiment pas mal de temps. 

Si vous souhaitez donc faire avec, il ne faudra pas oublier d'ajouter cette librairie à votre programme (on appelle ça un sketch en jargon Arduino)

Page officielle de la librairie Servo
Extrait de la page ci-dessus  Explications des fonctions principales

servo .attach (pin, min, max) permet d'attacher un pin (broche de la carte), min est la valeur en ms de la largeur d'impulsion pour un angle de 0° (par défaut 544 ms), max est la valeur en ms de la largeur d'impulsion pour un angle de 180° (par défaut 2400 ms).

servo .write (angle), il suffit de préciser un angle de 0° à 180°.

servo .writeMicroseconds (uS), il suffit de préciser la valeur en ms de la largeur d'impulsion.

servo .read () permet de retourner la position du servo

Knob est un exemple de programme qui permet de positionner un servo avec un potentiomètre donc une valeur analogique.

Sweep est un exemple de programme qui permet de déplacer indéfiniement un servo de 0° à 180° puis de 180° à 0°.

Positionner à différents angles un servomoteur SANS la librairie Servo

/*
Positionnement d'un servomoteur sans utiliser la librairie Servo
Cette méthode est plus fastidieuse et déconseillée sauf si vous souhaitez une précision extrême
Si besoin il existe des servomoteurs digitaux/numériques qui seront plus stables et précis. 
*/
#define servoSTI2D 2 /* On déclare ici une variable du nom de servoSTI2D et on l'affecte au pin digital numéro 2, 
le pin 2 se nomme à partir de maintenant servoSTI2D*/

void setup()//Boucle de paramétrage , remarquez aussi qu'il est possible de commenter sur une ligne en utilisant //
/* Ou alors de commenter sur plusieurs lignes en utilisant "/*.....*/
{
  pinMode(servoSTI2D, OUTPUT); /* On utilise la fonction pinMode pour déclarer le pin 2 comme étant une sortie*/
}
void loop() 
{
   /* Le servomoteur s'attend à recevoir un signal toutes les 20 ms, le positionnement du servo correspond à 
   une pulsation de 544 ms (pour 0°) à 2,4 ms (180°)*/
    digitalWrite(servoSTI2D, HIGH); // On active le pin digital 2 à l'état haut
    delayMicroseconds(544); // pendant une temporisation de 544us
    digitalWrite(servoSTI2D, LOW); //On desactive le pin digital 2 donc il passe à l'état bas
    delayMicroseconds(19456); /* On déduit les 544 us qui correspondent à 0.544 ms des 20ms (20000us) de la séquence totale
    durant laquelle le servo attend une durée d'impulsion, 20000 us-544 us =19456 us, c'est la durée de l'état bas*/
    // Durée des pulsations pour différents dégrés et pour le servomoteur que j'utilise : 544 us pour  0°; 1472 us pour 90°; 2400 pour 180°

//En reprenant les informations ci-dessus, on peut donc en exemple, positionner le servo à 90°
    digitalWrite(servoSTI2D, HIGH); 
    delayMicroseconds(1472); 
    digitalWrite(servoSTI2D, LOW); 
    delayMicroseconds(18528);
//Puis ci-dessous à 180°
    digitalWrite(servoSTI2D, HIGH); 
    delayMicroseconds(2400); 
    digitalWrite(servoSTI2D, LOW); 
    delayMicroseconds(17600);
}

Positionner à différents angles un servomoteur AVEC la librairie Servo

#include <Servo.h> // On ajoute la librairie Servo afin d'utiliser ses fonctions. 

Servo servoSTI2D;  // on a crée un objet servo et on l'a nommé servoSTI2D


void setup() // Boucle de paramétrage
{
  servoSTI2D.attach(2, 544, 2400);  /*Le servo est relié au pin digital 2, si on connait les largeurs de modulation 
min et max de son servo, on peut les ajouter ici sinon elles seront de 544 us et 2400 us comme expliqué plus haut dans l'article. 
Attention les valeurs min et max sont en micro secondes.*/
}

void loop() // Boucle principale du programme, elle se répète à l'infini sans indications contraires
{

  servoSTI2D.write(0);  // Le servo se positionne à 0°
  delay(500);          // On laisse le temps au servo de rejoindre la position demandée
  
  servoSTI2D.write(90); // Le servo se positionne à 90°           
  delay(500);           // On laisse le temps au servo de rejoindre la position demandée
  
  servoSTI2D.write(135);// Le servo se positionne à 135°            
  delay(500);           // On laisse le temps au servo de rejoindre la position demandée
  
  servoSTI2D.write(180);// Le servo se positionne à 180°            
  delay(500);          // On laisse le temps au servo de rejoindre la position demandée       
               
}

Approfondissions avec les exemples Knob et Sweep de la librairie Servo

L'exemple du sketch Sweep (balayage)

/*
Version commentée en français
Ci-dessous, présentation de l'auteur officiel

Ce programme est simple mais pratique, il permet de déplacer à une certaine vitesse un servomoteur de 0 à 180° puis de 180° à 0° 
indéfiniment, c'est donc un balayage comme le ferait une caméra de surveillance motorisée. 
Je l'ai un peu modifié mais l'original fonctionne très bien. 
*/

/* Sweep
 by BARRAGAN <http://barraganstudio.com>
 This example code is in the public domain.

 modified 8 Nov 2013
 by Scott Fitzgerald
 http://www.arduino.cc/en/Tutorial/Sweep
*/

#include <Servo.h>   //On ajoute la librairie Servo

Servo servoMalraux;  // On crée ici un objet servo nommé servoMalraux

int pos = 0;    /* On crée une variable nommée pos de type int, (integer en anglais, c'est une entier standard, sa valeur peut aller 
de -32768 à +32767 et occupe deux octets 2p16) que l'on initialise à 0.*/

void setup() {
  servoMalraux.attach(9);  // On déclare le servomoteur donc l'objet servoMalraux connecté au pin digital/numérique D9
}

void loop() {
  for (pos = 0; pos <= 180; pos += 1) { /* On dit que pos est égal à 0 (comprenez par là aussi 0°) et que pour chaque tour de boucle, sa valeur sera incrémentée de 1 (comprenez +1)
    tant que la valeur de pos est inférieure ou égale à 180 (comprenez par là 180° d'angle). Clairement à chaque tour, le servo se déplace d'1° d'angle supplémentaire jusqu'à rejoindre 180° */
    // On se déplace donc par "pas" de 1°
    servoMalraux.write(pos);              // notre servo execute et se place à la valeur de pos
    delay(15);                       // On temporise 15ms pour que le servo rejoigne sa position
  }
  for (pos = 180; pos >= 0; pos -= 1) { // Cette fois-ci c'est le chemin inverse, on part du principe que nous somme sortis de la condition ci-dessus et que les 180° sont atteints
    servoMalraux.write(pos);              // notre servo se place à la valeur de pos
    delay(15);                       // On temporise 15ms pour que le servo rejoigne sa position
  }
  //Est-ce terminé ? non ce balayage est réalisé indéfiniment, on retourne au début du sketch/programme
}

L'exemple du sketch Knob (potentiomètre)

/*
Version commentée en français
Ci-dessous, présentation de l'auteur officiel

Ce programme est simple mais pratique, il permet d'ajuster la position d'un servomoteur en fonction de la position d'un potentiomètre. 
Je l'ai un peu modifié mais l'original fonctionne très bien. 
*/
/*
 Controlling a servo position using a potentiometer (variable resistor)
 by Michal Rinott <http://people.interaction-ivrea.it/m.rinott>

 modified on 8 Nov 2013
 by Scott Fitzgerald
 http://www.arduino.cc/en/Tutorial/Knob
*/

#include <Servo.h>

Servo servoSTI2D;  // on crée un objet servo que l'on nomme servoSTI2D

int potpin = A0;  // On crée une variable potpin et on lui affecte le pin analogique A0, le pin A0 s'appellera potpin à partir de maintenant
int val;    /* On crée une variable val qui servira à stocker la valeur lue sur l'entrée analogique A0 (de 0 à 1023 car 2p10=1024),ce n'est pas obligatoire
il est aussi possible de lire directement A0 sans avoir à le renommer ou lui associer une variable. */

void setup() {
  servoSTI2D.attach(9);  // Le servomoteur nommé servoSTI2D dans le sketch/programme est relié au pin digital D9.
}

void loop() {
  val = analogRead(potpin);            // val est une valeur comprise entre 0 à 1023 lue sur A0 qui dépend donc de la position de notre potentiomètre
  int angle = map(val, 0, 1023, 0, 180);     /* Utilisation d'une fonction très utile, la fonction map qui permet de faire un produit en croix,
  on appelle la source des données donc la valeur du potentiométre stockée dans val dont la valeur min est 0 et la valeur max 1023 ensuite on donne
  les valeurs min et max des position de notre servo, ici de 0° à 180°, on vient donc de convertir la valeur analogique sur A0 en angle/position pour notre servo*/
  servoSTI2D.write(angle);             // Le servo se positionne à la valeur de la variable angle calculée ci-dessus.
  delay(15);                           // On temporise pour laisser le servo rejoindr sa position
}
/*
En résumé : 
Le servo est connecté à D9
Potpin est le nom de l'entrée analogique A0
val stocke la valeur sur A0 (entre 0 et 1023)
angle convertit la valeur de val (entre 0 et 1023) en une position de 0 à 180° pour le servo et grâce à la fonction map qui est ni plus ni moins
qu'un produit en croix. 
la fonction nomdemonservo.write(pos) permet de positionner à un angle (pos) précis votre servo (nomdemonservo)
*/
Professeur SII option génie électrique

Écrire un commentaire

Quelle est la première lettre du mot utgcb ?