Différences entre versions de « Pololu-Zumo-Shield-Arduino-servo-arduino »

De MCHobby - Wiki
Sauter à la navigation Sauter à la recherche
 
(Une version intermédiaire par le même utilisateur non affichée)
Ligne 1 : Ligne 1 :
 
{{Pololu-Zumo-Shield-Arduino-NAV}}
 
{{Pololu-Zumo-Shield-Arduino-NAV}}
  
{{traduction}}
+
Le code d'exemple Arduino Uno ci-dessous montre comment contrôler un simple servo en utilisant le Timer 2. Nous utilisons le Timer 2 à la place du Timer 1 parce que le Timer 1 est utilisé par la bibliothèque  ZumoMotors (ce qui interfère avec la bibliothèque servo d'Arduino). Il nous faut donc gérer notre servo moteur nous même avec un autre timer (le Timer 2).
  
The example Arduino Uno code below shows how to control a single servo using Timer 2. Because it uses Timer 2 instead of Timer 1, this code does not interfere with the ZumoMotors library, but it will interfere with the ZumoBuzzer library, so you will not be able to use this and the buzzer at the same time. You can integrate this code with other code that drives the motors.
+
Utiliser le Timer 2 interfère avec la bibliothèque ZumoBuzzer, il ne sera donc pas possible d'utiliser le Buzzer et le Timer 2 en même temps. Vous pouvez intégrer ce code avec d'autre codes pilotant des moteurs.
  
 
<syntaxhighlight lang="c">
 
<syntaxhighlight lang="c">
/** Arduino Uno Timer 2 Servo Example
+
/** Exemple Servo Timer 2 sur Arduino Uno
This example code for the Arduino Uno shows how to use Timer 2 on
+
Ce code d'exemple est pour un Arduino Uno et montre comment utiliser le
the ATmega328P to control a single servo. This can be useful for
+
Timer 2 d'un ATmega328P pour controler un simple servo moteur.  
people who cannot use the Arduino IDE's Servo library. For
+
Cela est tule pour les gens qui ne peuvent pas utiliser la
example, the ZumoMotors library uses the same timer as the Servo
+
bibliotheque Servo d'Arduino IDE.
library (Timer 1), so the two libraries conflict.
+
Par exemple, la bibliotheque ZumoMotors utilise le même timer que
 +
la bibliotheque Servo (Timer 1). Il y a donc un conflit.
 
   
 
   
The SERVO_PIN macro below specifies what pin to output the
+
La macro SERVO_PIN ci-dessous spécifie la broche sur laquelle
servo on. This pin needs to be connected to the signal input
+
est branché le servo moteur. Cette broche doit être raccordée
line of the servo. The Arduino's GND needs to be connected to
+
sur l'entrée signal du servo. La masse du servo doit être connecté
the ground pin of the servo.  The servo's ground and power pins
+
sur la masse de votre Arduino (masse commune). Pour finir
need to be connected to an appropriate power supply.
+
la masse et broche d'alimentation du servo doivent être connecté
 +
sur une source d'alimentation adéquate.
 
*/
 
*/
 
   
 
   
// This line specifies what pin we will use for sending the
+
// Cette ligne indique quel est la broche utilisée pour envoyer
// signal to the servo. You can change this.
+
// le signal au servo moteur. Vous pouvez changer cette valeur.
 
#define SERVO_PIN 11
 
#define SERVO_PIN 11
 
   
 
   
// This is the time since the last rising edge in units of 0.5us.
+
// Le temps depuis le dernier flan montage (rising edge) en unités de 0.5us.
 
uint16_t volatile servoTime = 0;
 
uint16_t volatile servoTime = 0;
 
   
 
   
// This is the pulse width we want in units of 0.5us.
+
// Contient la largeur d impulsion désirée en unités de 0.5us.
 
uint16_t volatile servoHighTime = 3000;
 
uint16_t volatile servoHighTime = 3000;
 
   
 
   
// This is true if the servo pin is currently high.
+
// Vrai (true) si la broche servo est actuellement au niveau haut.
 
boolean volatile servoHigh = false;
 
boolean volatile servoHigh = false;
 
   
 
   
Ligne 40 : Ligne 42 :
 
void loop()
 
void loop()
 
{
 
{
   servoSetPosition(1000);  // Send 1000us pulses.
+
   servoSetPosition(1000);  // Envoi une impulsion de 1000 us.
 
   delay(1000);   
 
   delay(1000);   
   servoSetPosition(2000);  // Send 2000us pulses.
+
   servoSetPosition(2000);  // Envoi une impulsion de 2000 us.
 
   delay(1000);
 
   delay(1000);
 
}
 
}
 
   
 
   
// This ISR runs after Timer 2 reaches OCR2A and resets.
+
// Cette routine d'interruption (ISR) est appelée après que
// In this ISR, we set OCR2A in order to schedule when the next
+
// le Timer 2 ait atteind OCR2A et resets.
// interrupt will happen.
+
// Dans cet ISR, nous initialisons OCR2A pour déterminer
// Generally we will set OCR2A to 255 so that we have an
+
// quand la prochaine interruption est déclenchée.
// interrupt every 128 us, but the first two interrupt intervals
+
// Généralement, nous fixons OCR2A à 255 pour avoir une
// after the rising edge will be smaller so we can achieve
+
// interruption toutes les 128 us, mais les deux premiers
// the desired pulse width.
+
// intervales d'interruption après le flan montant (rising edge)
 +
// seront plus petit ce qui nous empêche d'atteindre la
 +
// largeur d'impulsion désirée.
 
ISR(TIMER2_COMPA_vect)
 
ISR(TIMER2_COMPA_vect)
 
{
 
{
   // The time that passed since the last interrupt is OCR2A + 1
+
   // Le temps qui est passé depuis la dernière interruption est
   // because the timer value will equal OCR2A before going to 0.
+
  // égale à OCR2A + 1 parce que la valeur du timer sera égale
 +
   // à OCR2A avant de revenir à 0.
 
   servoTime += OCR2A + 1;
 
   servoTime += OCR2A + 1;
 
    
 
    
Ligne 69 : Ligne 74 :
 
     }
 
     }
 
   
 
   
     // The servo pin is currently high.
+
     // La broche du signal Servo est au niveau haut (high).
     // Check to see if is time for a falling edge.
+
     // Vérifier s'il est temps d'avoir le flan descendant
     // Note: We could == instead of >=.
+
    // du signal (falling edge).
 +
     // Note: Nous pouvons utiliser == à la place de >=.
 
     if(servoTime >= highTimeCopy)
 
     if(servoTime >= highTimeCopy)
 
     {
 
     {
       // The pin has been high enough, so do a falling edge.
+
       // La broche est au niveau haut depuis assez longtemps
 +
      // donc on applique la flan descendant.
 
       digitalWrite(SERVO_PIN, LOW);
 
       digitalWrite(SERVO_PIN, LOW);
 
       servoHigh = false;
 
       servoHigh = false;
Ligne 82 : Ligne 89 :
 
   else
 
   else
 
   {
 
   {
     // The servo pin is currently low.
+
     // La broche du servo est au niveau bas (low).
 
      
 
      
 
     if(servoTime >= 40000)
 
     if(servoTime >= 40000)
 
     {
 
     {
       // We've hit the end of the period (20 ms),
+
       // Nous avons atteind la fin de la période (20 ms),
       // so do a rising edge.
+
       // Donc on applique un flan montant (rising edge) sur
 +
      // le signal.
 
       highTimeCopy = servoHighTime;
 
       highTimeCopy = servoHighTime;
 
       digitalWrite(SERVO_PIN, HIGH);
 
       digitalWrite(SERVO_PIN, HIGH);
Ligne 103 : Ligne 111 :
 
   pinMode(SERVO_PIN, OUTPUT);
 
   pinMode(SERVO_PIN, OUTPUT);
 
    
 
    
   // Turn on CTC mode. Timer 2 will count up to OCR2A, then
+
   // Passe en mode CTC. Le Timer 2 comptera jusqu'à OCR2A,  
   // reset to 0 and cause an interrupt.
+
   // puis se réinitialise à 0 et provoque une interruption.
 
   TCCR2A = (1 << WGM21);
 
   TCCR2A = (1 << WGM21);
   // Set a 1:8 prescaler. This gives us 0.5us resolution.
+
   // Initialiser le pre-scaler sur 1:8 . ce qui offre une
 +
  // résolution de 0.5us.
 
   TCCR2B = (1 << CS21);
 
   TCCR2B = (1 << CS21);
 
    
 
    
   // Put the timer in a good default state.
+
   // Mettre le timer dans le bon état par défaut.
 
   TCNT2 = 0;
 
   TCNT2 = 0;
 
   OCR2A = 255;
 
   OCR2A = 255;
 
    
 
    
   TIMSK2 |= (1 << OCIE2A);  // Enable timer compare interrupt.
+
   TIMSK2 |= (1 << OCIE2A);  // Activer le "timer compare interrupt".
   sei();  // Enable interrupts.
+
   sei();  // Activer les interruptions.
 
}
 
}
 
   
 
   
 
void servoSetPosition(uint16_t highTimeMicroseconds)
 
void servoSetPosition(uint16_t highTimeMicroseconds)
 
{
 
{
   TIMSK2 &= ~(1 << OCIE2A); // disable timer compare interrupt
+
   TIMSK2 &= ~(1 << OCIE2A); // Désactiver le "timer compare interrupt"
 
   servoHighTime = highTimeMicroseconds * 2;
 
   servoHighTime = highTimeMicroseconds * 2;
   TIMSK2 |= (1 << OCIE2A); // enable timer compare interrupt
+
   TIMSK2 |= (1 << OCIE2A); // Activer le "timer compare interrupt"
 
}
 
}
 
</syntaxhighlight>
 
</syntaxhighlight>
  
 
{{Pololu-Zumo-Shield-Arduino-TRAILER}}
 
{{Pololu-Zumo-Shield-Arduino-TRAILER}}

Version actuelle datée du 17 avril 2017 à 16:00

Le code d'exemple Arduino Uno ci-dessous montre comment contrôler un simple servo en utilisant le Timer 2. Nous utilisons le Timer 2 à la place du Timer 1 parce que le Timer 1 est utilisé par la bibliothèque ZumoMotors (ce qui interfère avec la bibliothèque servo d'Arduino). Il nous faut donc gérer notre servo moteur nous même avec un autre timer (le Timer 2).

Utiliser le Timer 2 interfère avec la bibliothèque ZumoBuzzer, il ne sera donc pas possible d'utiliser le Buzzer et le Timer 2 en même temps. Vous pouvez intégrer ce code avec d'autre codes pilotant des moteurs.

/** Exemple Servo Timer 2 sur Arduino Uno
Ce code d'exemple est pour un Arduino Uno et montre comment utiliser le 
Timer 2 d'un ATmega328P pour controler un simple servo moteur. 
Cela est tule pour les gens qui ne peuvent pas utiliser la
bibliotheque Servo d'Arduino IDE.
Par exemple, la bibliotheque ZumoMotors utilise le même timer que
la bibliotheque Servo (Timer 1). Il y a donc un conflit.
 
La macro SERVO_PIN ci-dessous spécifie la broche sur laquelle
est branché le servo moteur. Cette broche doit être raccordée 
sur l'entrée signal du servo. La masse du servo doit être connecté
sur la masse de votre Arduino (masse commune). Pour finir
la masse et broche d'alimentation du servo doivent être connecté
sur une source d'alimentation adéquate.
*/
 
// Cette ligne indique quel est la broche utilisée pour envoyer
// le signal au servo moteur. Vous pouvez changer cette valeur.
#define SERVO_PIN 11
 
// Le temps depuis le dernier flan montage (rising edge) en unités de 0.5us.
uint16_t volatile servoTime = 0;
 
// Contient la largeur d impulsion désirée en unités de 0.5us.
uint16_t volatile servoHighTime = 3000;
 
// Vrai (true) si la broche servo est actuellement au niveau haut.
boolean volatile servoHigh = false;
 
void setup()
{
  servoInit();
}
 
void loop()
{
  servoSetPosition(1000);  // Envoi une impulsion de 1000 us.
  delay(1000);  
  servoSetPosition(2000);  // Envoi une impulsion de 2000 us.
  delay(1000);
}
 
// Cette routine d'interruption (ISR) est appelée après que 
// le Timer 2 ait atteind OCR2A et resets.
// Dans cet ISR, nous initialisons OCR2A pour déterminer 
// quand la prochaine interruption est déclenchée.
// Généralement, nous fixons OCR2A à 255 pour avoir une 
// interruption toutes les 128 us, mais les deux premiers
// intervales d'interruption après le flan montant (rising edge)
// seront plus petit ce qui nous empêche d'atteindre la
// largeur d'impulsion désirée.
ISR(TIMER2_COMPA_vect)
{
  // Le temps qui est passé depuis la dernière interruption est
  // égale à OCR2A + 1 parce que la valeur du timer sera égale
  // à OCR2A avant de revenir à 0.
  servoTime += OCR2A + 1;
   
  static uint16_t highTimeCopy = 3000;
  static uint8_t interruptCount = 0;
   
  if(servoHigh)
  {
    if(++interruptCount == 2)
    {
      OCR2A = 255;
    }
 
    // La broche du signal Servo est au niveau haut (high).
    // Vérifier s'il est temps d'avoir le flan descendant
    // du signal (falling edge).
    // Note: Nous pouvons utiliser == à la place de >=.
    if(servoTime >= highTimeCopy)
    {
      // La broche est au niveau haut depuis assez longtemps
      // donc on applique la flan descendant.
      digitalWrite(SERVO_PIN, LOW);
      servoHigh = false;
      interruptCount = 0;
    }
  } 
  else
  {
    // La broche du servo est au niveau bas (low).
     
    if(servoTime >= 40000)
    {
      // Nous avons atteind la fin de la période (20 ms),
      // Donc on applique un flan montant (rising edge) sur
      // le signal.
      highTimeCopy = servoHighTime;
      digitalWrite(SERVO_PIN, HIGH);
      servoHigh = true;
      servoTime = 0;
      interruptCount = 0;
      OCR2A = ((highTimeCopy % 256) + 256)/2 - 1;
    }
  }
}
 
void servoInit()
{
  digitalWrite(SERVO_PIN, LOW);
  pinMode(SERVO_PIN, OUTPUT);
   
  // Passe en mode CTC. Le Timer 2 comptera jusqu'à OCR2A, 
  // puis se réinitialise à 0 et provoque une interruption.
  TCCR2A = (1 << WGM21);
  // Initialiser le pre-scaler sur 1:8 . ce qui offre une 
  // résolution de 0.5us.
  TCCR2B = (1 << CS21);
   
  // Mettre le timer dans le bon état par défaut.
  TCNT2 = 0;
  OCR2A = 255;
   
  TIMSK2 |= (1 << OCIE2A);  // Activer le "timer compare interrupt".
  sei();   // Activer les interruptions.
}
 
void servoSetPosition(uint16_t highTimeMicroseconds)
{
  TIMSK2 &= ~(1 << OCIE2A); // Désactiver le "timer compare interrupt"
  servoHighTime = highTimeMicroseconds * 2;
  TIMSK2 |= (1 << OCIE2A); // Activer le "timer compare interrupt"
}

Basé sur "Zumo Shield for Arduino" de Pololu (www.pololu.com/docs/0J57) - Traduit en Français par shop.mchobby.be CC-BY-SA pour la traduction
Toute copie doit contenir ce crédit, lien vers cette page et la section "crédit de traduction". Traduit avec l'autorisation expresse de Pololu (www.pololu.com)

Based on "Zumo Shield for Arduino" from Pololu (www.pololu.com/docs/0J57) - Translated to French by shop.mchobby.be CC-BY-SA for the translation
Copies must includes this credit, link to this page and the section "crédit de traduction" (translation credit). Translated with the Pololu's authorization (www.pololu.com)