Aller au contenu principal

Les sorties : PWM et temps

Ce que ce chapitre apporte 5 points
  • Piloter une sortie numérique en respectant le courant qu'une broche peut fournir.
  • Expliquer ce que produit analogWrite : un signal carré, et non une tension continue.
  • Calculer la tension moyenne obtenue pour une valeur donnée, et la valeur à écrire pour une tension visée.
  • Savoir sur quelles broches analogWrite fonctionne, et ce qu'elle fait sur les autres.
  • Mesurer ce que coûte un delay : pendant la pause, le programme ne voit rien.

Une broche numérique ne connaît que deux tensions, 0 et 5 V. Pourtant une LED peut briller à moitié, un moteur tourner lentement. La carte n'invente pas de tension intermédiaire : elle bascule très vite entre les deux, et c'est la proportion du temps passé à 5 V qui fait l'effet. Ce chapitre explique ce mécanisme, la PWM, puis mesure ce que coûte l'instruction la plus employée des débutants, delay.

Une sortie numérique et ses limites

digitalWrite(broche, HIGH) impose 5 V sur la broche, LOW impose 0 V. La broche fournit alors du courant à ce qui y est branché, et ce courant est limité.

Une broche n'est pas une source idéale : elle se comporte comme une source réelle, une tension accompagnée d'une résistance interne de quelques dizaines d'ohms. Plus on lui demande de courant, plus sa tension s'affaisse. Sous une LED, l'effet est négligeable ; sous un moteur, le courant demandé dépasse de loin la limite de la broche, et la tension s'effondre en même temps : le moteur ne démarre pas, et la broche chauffe. C'est la raison physique de la règle qui suit.

Au fond, cet appel se ramène à une écriture mémoire : sur l'Uno, un bit dans le registre du port de la broche, un octet qui regroupe huit broches. digitalWrite ajoute autour une recherche en table, pour trouver le port et le bit de la broche, et coupe la PWM de la broche si elle en produisait. Le chapitre d'architecture Les entrées et sorties montre le principe en assembleur sur une machine plus simple, où chaque sortie occupe un octet.

Une broche n'alimente pas un moteur
Une broche de l'Uno fournit environ 20 mA en fonctionnement normal : de quoi allumer une LED, pas faire tourner un moteur, actionner un relais ou alimenter un ruban lumineux. Ces charges se commandent à travers un transistor, que la broche pilote et qui laisse passer le courant d'une alimentation séparée. Brancher un moteur directement sur une broche la détruit.
Vérification rapideon peut se reprendre

Pourquoi ne pas brancher un moteur directement sur une broche ?

La modulation de largeur d'impulsion

Définition

La PWM (modulation de largeur d'impulsion) produit un signal carré de fréquence fixe, dont on règle la proportion du temps passé à l'état haut. Cette proportion s'appelle le rapport cyclique.

analogWrite(broche, valeur) produit ce signal, avec une valeur de 0 à 255 : 0 donne un rapport cyclique de 0 %, 255 de 100 %. Sur l'Uno, la fréquence est d'environ 490 Hz sur la plupart des broches PWM, et d'environ 980 Hz sur les broches 5 et 6 : une période dure environ 2 ms, et 1 ms sur les broches 5 et 6.

250 µs par bit4 000 bauds24 bits, 6 ms en tout
valeur 64110000001100000011000000valeur 128111100001111000011110000valeur 19111111100111111001111110002 ms4 ms6 ms
Trois valeurs d'analogWrite, sur trois périodes d'environ deux millisecondes. La fréquence ne change pas : seule la largeur des impulsions varie, de 25 % à 75 % du temps.

Une LED alimentée ainsi s'allume et s'éteint près de 500 fois par seconde, bien trop vite pour que l'œil le perçoive : il ne voit que la moyenne.

L'œil et le moteur moyennent parce qu'ils sont lents devant la période du signal. Un circuit électrique peut faire la même chose, et c'est ainsi qu'on obtient une vraie tension continue à partir d'une PWM : une résistance et un condensateur dont la constante de temps dépasse largement les deux millisecondes de la période. Le condensateur n'a pas le temps de suivre chaque créneau et se stabilise à la moyenne. Ce montage est un filtre passe-bas : il laisse passer la moyenne et arrête l'oscillation. Un moteur, par son inertie, fait de même. D'où la règle de calcul :

tension moyenne=5×valeur255valeur=255×tension viseˊe5\text{tension moyenne} = 5 \times \frac{\text{valeur}}{255} \qquad \text{valeur} = 255 \times \frac{\text{tension visée}}{5}

analogWrite(9, 128) donne une tension moyenne de 2,51 V. Pour obtenir 3 V en moyenne, on écrit 153.

Ce n'est pas une tension continue
Un voltmètre ordinaire affiche bien la moyenne, mais la broche ne délivre jamais 2,5 V : elle passe d'un instant à l'autre de 0 à 5 V. Un composant qui a besoin d'une vraie tension continue, un capteur alimenté par cette broche par exemple, reçoit une succession d'impulsions à 5 V. Le nom analogWrite trompe sur ce point.
Vérification rapideon peut se reprendre

Que produit analogWrite(9, 128) sur la broche ?

Sur quelles broches

analogWrite ne produit de PWM que sur les broches marquées ~ : 3, 5, 6, 9, 10 et 11 sur l'Uno. Sur une autre broche, elle se comporte comme digitalWrite : une valeur inférieure à 128 donne LOW, une valeur de 128 ou plus donne HIGH. Le programme compile, la LED ne varie pas, et rien ne signale l'erreur.

Un fondu

Faire varier la valeur progressivement produit un fondu, parce que chaque nouvelle valeur ne dure que le temps d'un delay.

Arduino
const int LED = 9; // une broche PWM
void setup() {
pinMode(LED, OUTPUT);
}
void loop() {
for (int niveau = 0; niveau <= 255; niveau++) { // 256 niveaux
analogWrite(LED, niveau);
delay(5);
}
for (int niveau = 255; niveau >= 0; niveau--) {
analogWrite(LED, niveau);
delay(5);
}
}

Chaque montée compte 256 niveaux de 5 ms : elle dure 1 280 ms. Ici, <= 255 est correct, puisque 255 est une valeur valide et que l'on veut l'atteindre : c'est la borne d'un intervalle de valeurs, pas le nombre d'éléments d'un tableau. Le compteur, lui, doit rester un int : avec un byte, qui ne dépasse pas 255, niveau++ repasse de 255 à 0, la condition niveau <= 255 reste toujours vraie, et la boucle ne s'arrête jamais.

Une LED pilotée par un potentiomètre combine les deux chapitres : analogRead lit la position, map la ramène de 0 à 255, analogWrite fixe la luminosité.

Arduino
void setup() {
pinMode(9, OUTPUT);
}
void loop() {
int position = analogRead(A0); // de 0 à 1023
analogWrite(9, map(position, 0, 1023, 0, 255)); // de 0 à 255
}
Vérification rapideon peut se reprendre

1.Quelle valeur d'analogWrite donne une tension moyenne d'environ 3 V ?

2.Que fait analogWrite sur une broche qui n'est pas marquée ~ ?

Ce que coûte un delay

delay(100) ne fait pas « attendre un peu » : il suspend le programme pendant cent millisecondes. Aucune ligne de loop() ne s'exécute, aucune broche n'est lue. Le matériel, lui, continue : la PWM garde sa valeur, ce qui fait fonctionner le fondu plus haut, les octets reçus sur la liaison série s'accumulent dans un tampon, et le compteur de millis() continue d'avancer.

Arduino
void setup() {
Serial.begin(9600);
pinMode(2, INPUT_PULLUP);
}
void loop() {
if (digitalRead(2) == LOW) {
Serial.println("appui vu");
}
delay(100); // la broche n'est lue que dix fois par seconde
}

Ce programme lit le bouton une fois toutes les 100 ms. Un appui bref, de 60 ms, qui tombe entre deux lectures n'est jamais vu. Simulé sur vingt instants d'appui répartis sur une période, il est manqué huit fois : 40 % des appuis de 60 ms sont perdus, soit exactement la part de la période que l'appui ne recouvre pas.

La vraie limite de delay. Un seul delay ne pose aucun problème dans un programme qui ne fait qu'une chose. Il devient un défaut dès que le programme doit faire deux choses en même temps : clignoter et surveiller un bouton, faire un fondu et mesurer une température. Le chapitre suivant remplace delay par une autre façon de compter le temps.

Vérification rapideon peut se reprendre

Pendant un delay(500), la carte lit-elle ses entrées ?

Mettre en pratique

analogWrite(9, 64) : quel rapport cyclique, et quelle tension moyenne ?

Rapport cyclique : 64/255≈2564 / 255 \approx 25 %. Tension moyenne : 5×64/255≈1,255 \times 64 / 255 \approx 1{,}25 V.

La broche, elle, ne délivre jamais 1,25 V : elle passe environ un quart du temps à 5 V et trois quarts à 0 V, près de 500 fois par seconde.

Une LED branchée sur la broche 7 ne varie pas quand analogWrite passe de 0 à 255 : elle est éteinte, puis s'allume d'un coup vers la moitié. Pourquoi ?

La broche 7 n'est pas une broche PWM. analogWrite s'y comporte comme digitalWrite : LOW en dessous de 128, HIGH à partir de 128.

La LED doit être déplacée sur une broche marquée ~ : 3, 5, 6, 9, 10 ou 11.

Un fondu parcourt les niveaux de 0 à 255 de 5 en 5, avec un delay(5) par niveau. Combien dure la montée ?

Les niveaux pris sont 0, 5, 10, et ainsi de suite jusqu'à 255 : 52 valeurs. À 5 ms chacune, la montée dure 260 ms.

Le piège est de diviser 255 par 5 et de trouver 51 : les deux bornes, 0 et 255, sont toutes deux atteintes, ce qui ajoute une valeur.

Un programme lit un bouton puis appelle delay(100) à chaque tour. Quelle part des appuis de 60 ms manque-t-il ?

La broche est lue une fois par période de 100 ms. Un appui de 60 ms n'est vu que si une lecture tombe pendant ces 60 ms, ce qui arrive dans 60 % des cas : 40 % des appuis sont perdus.

La simulation du programme sur vingt instants d'appui confirme ce calcul : huit appuis manqués. Raccourcir le delay réduit la perte sans l'annuler ; seule une boucle qui ne bloque pas la supprime.

Chapitre révisé en octobre 2026 · Une erreur dans ce chapitre ?

Dans la bibliothèque d'exercices