Contrôle moteur avec un pont en H

Ce tutoriel explique comment faire tourner un moteur dans deux sens de rotation avec un driver moteur et MicroPython.

Description

Un moteur, aussi simple soit-il, ne peut tourner que dans un seul sens s’il est connecté directement à la carte NUCLEO-WB55. A travers ce tutoriel nous allons voir comment faire tourner un moteur dans les deux sens.
Pour ce faire nous allons utiliser un driver moteur ; plus précisément un pont en H. C’est une structure constituée de 4 interrupteurs (transistors) couplés 2 par 2 permettant de faire circuler sur commande le courant dans un sens ou dans l’autre. En inversant le sens du courant on change tout simplement le sens de rotation du moteur. Si on décompose la structure du pont en H on obtient la figure suivante :


Decomposition du pont en H


La charge représente le moteur. Si on reprend l’explication, on obtient alors le sens de courant suivant dans les deux cas :


Décomposition du fonctionnement du pont en H


Crédit images : Wikimedia

Afin de réaliser le montage nous utiliserons un driver moteur de référence L293D ou de référence L298N de chez STMicroelectronics. Ces drivers sont capables de contrôler deux moteurs en même temps mais, dans notre cas, nous n’utiliserons qu’un seul moteur. Ces deux composants sont très similaires dans leur fonctionnement, seules quelques caractéristiques techniques les différencient. La documentation technique du L293D fournit le tableau de correspondance suivant :


Figure datasheet du L293D


Patte driver moteur Description
Enable 1 Met en arrêt (GND) ou en marche le moteur (VSS)
Input 1 Contrôle le sens du courant via la carte NUCLEO
Output 1 Connecté à une patte du moteur
GND Connecté à la masse (une seule suffit)
GND Commune au composant
Output 2 Connecté à l’autre patte du moteur
Input 2 Contrôle le sens du courant via la carte NUCLEO
VS Alimentation de la commande puissance (moteur)
VSS Alimentation de la commande logique (carte NUCLEO)

Ce driver trouve utilité par exemple pour faire avancer, reculer ou tourner un petit robot sur roues.

Dans notre cas nous souhaitons utiliser les trois boutons et les trois LED de la carte NUCLEO :

  • un bouton pour faire tourner le moteur dans le sens horaire (LED en bleu).
  • un bouton pour faire tourner le moteur dans le sens anti-horaire (LED en vert).
  • un bouton pour arrêter le moteur (LED en rouge).

Montage

En fonction du composant choisi, on utilise les schémas de câblage suivants. A noter que le principe reste le même, peu importe le driver moteur sélectionné.

Pour le L293D : nous câblons le montage de cette facon :


Schéma de montage moteur avec L293D


Pour le L298N : nous câblons le montage de cette facon :


Schéma de montage moteur avec L298N


Quel que soit le driver moteur utilisé, la correspondance entre les composants sera la suivante :

Driver moteur ST Nucleo Moteur Alim externe
Enable 1 D3    
Input 1 D4    
Output 1   Oui  
GND GND   GND
GND      
Output 2   Oui  
Input 2 D5    
VS     5V
VSS 3.3V    

Pour cet exercice nous utilisons une source d’alimentation externe pour le moteur (telle que des piles ou une batterie de 5V minimum). En effet la carte NUCLEO-WB55 n’est pas faite pour contrôler des éléments de puissance tel qu’un moteur, qui nécessite un courant plus important que celle qu’elle est capable de fournir, surtout à son démarrage.

Remarque 1 : Pensez bien à connecter les masses (GND) ensemble sous peine de dysfonctionnements.

Remarque 2 : La tension d’alimentation de puissance Vs peut être différente. Tout dépend de votre source d’alimentation et des caractéristiques du moteur que vous utilisez.

Le code MicroPython

Les scripts présentés ci-après sont disponibles dans la zone de téléchargement.

Editez maintenant le script main.py :

Etape 1 : On importe les bibliothèques dans notre code.

import pyb
from pyb import Pin, Timer
import time

Etape 2 : On définit des variables globales qui nous serviront à récupérer l’état des boutons poussoirs.

#Variables globales
BP1 = 0
BP2 = 0
BP3 = 1

Etape 3 : On fait l’initialisation des composants. On utilise une PWM sur la patte D3 (patte servant pour l’enable 1) afin de pouvoir contrôler la vitesse du moteur.

#BP (en entrée + pull up)
sw1 = pyb.Pin('SW1')
sw1.init(pyb.Pin.IN, pyb.Pin.PULL_UP, af=-1)
sw2 = pyb.Pin('SW2')
sw2.init(pyb.Pin.IN, pyb.Pin.PULL_UP, af=-1)
sw3 = pyb.Pin('SW3')
sw3.init(pyb.Pin.IN, pyb.Pin.PULL_UP, af=-1)

#LED (LED de la carte NUCLEO)
led_bleu = pyb.LED(3)
led_vert = pyb.LED(2)
led_rouge = pyb.LED(1)

#Driver moteur ("enable" + "input 1" et "input 2" en sorties)
moteur_enable = pyb.Pin('D3')
moteur_pin1 = pyb.Pin('D4', Pin.OUT_PP)
moteur_pin2 = pyb.Pin('D5', Pin.OUT_PP)

#PWM pour le moteur (Timer 1 channel 3, fréquence = 1kHz et sur "enable")
tim1 = Timer(1, freq=1000)
ch3 = tim1.channel(3, Timer.PWM, pin=moteur_enable)

Etape 4 : Afin de contrôler le moteur à n’importe quel instant on gère les boutons poussoirs avec des interruptions qui mettront à jour les variables globales définies précédemment.

#Interruption de SW1 (le moteur tourne dans le sens "avant")
def ITbutton1(line):
    #Variables globales
    global BP1
    global BP2
    global BP3
    #Incremente BP1, le reste à 0
    BP1 = BP1 + 1
    BP2 = 0
    BP3 = 0

#Interruption de SW2 (le moteur tourne dans le sens "arrière")
def ITbutton2(line):
    #Variable globales
    global BP1
    global BP2
    global BP3
    #Incremente BP2, le reste à 0
    BP1 = 0
    BP2 = BP2 + 1
    BP3 = 0

#Interruption de SW3 (arrête le moteur)
def ITbutton3(line):
    #Variables globales
    global BP1
    global BP2
    global BP3
    #Incremente BP3, le reste à 0
    BP1 = 0
    BP2 = 0
    BP3 = BP3 + 1

#Initialisation des routines de service / vecteurs des interruptions
irq_1 = pyb.ExtInt(sw1, pyb.ExtInt.IRQ_FALLING, pyb.Pin.PULL_UP, ITbutton1)
irq_2 = pyb.ExtInt(sw2, pyb.ExtInt.IRQ_FALLING, pyb.Pin.PULL_UP, ITbutton2)
irq_3 = pyb.ExtInt(sw3, pyb.ExtInt.IRQ_FALLING, pyb.Pin.PULL_UP, ITbutton3)

Etape 5 : On crée une fonction pour gérer le moteur. Celle-ci recoit en paramètre sa vitesse. Dans cette fonction on teste l’état de boutons et, en fonction du résultat, on active/désactive les LED, les pattes input 1 et input 2 et le signal PWM.

#Fonction qui gère le moteur
def etat_moteur(vitesse):
    #Variables globales
    global BP1
    global BP2
    global BP3

    #Si BP1 appuyé
    if((BP1 != 0) and (BP2 == 0) and (BP3 == 0)):
        #Allume la LED bleu
        led_bleu.on()
        #Allume l'enable 1 / Eteint l'enable 2
        moteur_pin1.high()
        moteur_pin2.low()
        #PWM pour régler la tension du moteur
        ch3.pulse_width_percent(vitesse)
    #Si BP2 appuyé
    if((BP1 == 0) and (BP2 != 0) and (BP3 == 0)):
        #Allume la LED verte
        led_vert.on()
        #Allume l'enable 2 / Eteint l'enable 1
        moteur_pin1.low()
        moteur_pin2.high()
        #PWM pour régler la tension du moteur
        ch3.pulse_width_percent(vitesse)
    #Si BP3 appuyé
    if((BP1 == 0) and (BP2 == 0) and (BP3 != 0)):
        #Allume la LED rouge
        led_rouge.on()
        #Eteint l'enable 1 et 2
        moteur_pin1.low()
        moteur_pin2.low()
        #PWM pour régler la tension du moteur
        ch3.pulse_width_percent(0)

Etape 6 : Finalement on définit la variable vitesse par un rapport cyclique de 100%.

#Variable pour gérer la vitesse de rotation du moteur
vitesse = 100

#Boucle infinie
while True:
    #Eteind toutes les LED par défaut
    led_bleu.off()
    led_vert.off()
    led_rouge.off()
    #Passe en parametre la vitesse souhaité
    etat_moteur(vitesse)

Résultat

Il ne vous reste plus qu’à enregistrer le code et redémarrer la carte NUCLEO-WB55. La LED rouge de la carte s’allume indiquant que le moteur est à l’arrêt. Appuyez sur un des boutons poussoirs SW1 ou SW2 pour faire tourner le moteur. Vous pouvez également vous amuser à changer la valeur (entre 0 et 100) de la variable vitesse et observer le comportement du moteur.

Pour d’autres exemples d’utilisation du moteur avec son driver vous pouvez vous reporter au tutoriel du Nunchuk dans la partie “pour aller plus loin”.

Remarque : il arrive parfois que le moteur bloque au démarrage et émette un léger sifflement. Cela se produit lorsqu’il est bloqué. Le cas échéant, vous devrez le faire tourner légérement à la main (et dans le bon sens) pour le lancer.