Questo controllo della Toshiba permette di pilotare due motori DC (in corrente continua) con un’alimentazione massima di 15 V con quattro modalità di funzionamento : CW (ClockWise, senso orario), CCW (CounterClockWise, senso antiorario), short brake e stop. Inoltre, la velocità di ciascun motore può essere variata attraverso un segnale PWM (Pulse Width Modulation) modificandone il duty cycle.
Sul sito della Sparkfun è disponibile un’utilissima breakout board che monta il controllo motori e ne rende facilmente accessibili i pin.
Il driver managed
Il driver managed che ne permette l’utilizzo è rappresentato dalla classe TB6612FNG che mette a disposizione due costruttori attraverso i quali poter decidere se utilizzare solo uno oppure entrambi i motori. Per ciascun motore è definito un canale (A e B) caratterizzato da :
-
2 segnali di ingresso attraverso i quali poter impostare le quattro modalità di funzionamento suddette (vedere tabella datasheet);
-
1 segnale PWM per la variazione della velocità;
I primi due segnali sono rappresentati da due istanze della classe OutputPort per ciascun canale mentre l’ultimo segnale è rappresentato da un’istanza della classe PWM.
Il costruttore più semplice permette di utilizzare solo il canale A mentre quello più complesso prepara l’oggetto all’utilizzo di entrambi i motori (richiamando anche il costruttore più semplice).
public TB6612FNG(Cpu.Pin aIn1, Cpu.Pin aIn2, Cpu.PWMChannel aPwmChannel, Cpu.Pin bIn1, Cpu.Pin bIn2, Cpu.PWMChannel bPwmChannel, Cpu.Pin standby = Cpu.Pin.GPIO_NONE) : this(aIn1, aIn2, aPwmChannel, standby) { this.bIn1Port = new OutputPort(bIn1, false); this.bIn2Port = new OutputPort(bIn2, false); this.bPwm = new PWM(bPwmChannel, DEFAULT_PWM_FREQUENCY, 0, false); this.IsMotorEnabledB = true; this.MotorModeB = MotorMode.Stop; this.bPwm.Start(); }
L’applicativo che utilizza il driver può interagire con il controllo motori attraverso delle proprietà (e non dei metodi) per abilitarli, impostare la modalità di funzionamento e la velocità. Se facciamo riferimento al canale A abbiamo a disposizione la proprietàIsMotorEnabledA, MotorModeA e MotorSpeedA rispettivamente. Ciascuno di queste proprietà agisce sui pin dedicati alle OutputPort di cui sopra (per la modalità di funzionamento) e sul pin PWM (per la velocità, con un valore da 0 a 100).
/// <summary> /// Mode for Motor A /// </summary> public MotorMode MotorModeA { get { if (this.IsMotorEnabledA) return this.motorModeA; else throw new ApplicationException("Motor A is disabled !!"); } set { switch (value) { case MotorMode.CCW: this.motorModeA = MotorMode.CCW; this.aIn1Port.Write(false); this.aIn2Port.Write(true); break; case MotorMode.CW: this.motorModeA = MotorMode.CW; this.aIn1Port.Write(true); this.aIn2Port.Write(false); break; case MotorMode.ShortBrake: this.motorModeA = MotorMode.ShortBrake; this.aIn1Port.Write(true); this.aIn2Port.Write(true); break; case MotorMode.Stop: this.motorModeA = MotorMode.Stop; this.aIn1Port.Write(false); this.aIn2Port.Write(false); break; default: break; } } } /// <summary> /// Speed for Motor A /// </summary> public int MotorSpeedA { get { if (this.IsMotorEnabledA) return this.motorSpeedA; else throw new ApplicationException("Motor A is disabled !!"); } set { if ((value >= 0) && (value <= 100)) this.motorSpeedA = value; this.aPwm.DutyCycle = (double)this.motorSpeedA / 100; } }
Ad esempio, nel caso di un robot con due ruote e quindi due motori pilotati da questo controllo, potremmo realizzare un metodo che li attivi entrambi nello stesso senso per far avanzare o arretrare il robot oppure un metodo che li attivi in versi opposti per farlo girare.
// both motors in counter clockwise mode this.tb6612fng.MotorModeA = MotorMode.CCW; this.tb6612fng.MotorModeB = MotorMode.CCW; //... this.tb6612fng.MotorModeA = MotorMode.CW; this.tb6612fng.MotorModeB = MotorMode.CCW;
La libreria passa così alla versione 2.2 e come sempre è disponibile su Nuget e su CodePlex. Purtroppo il supporto è garantito dal .Net Micro Framework 4.2 in poi e viene esclusa la versione 4.1, poichè non è disponibile la classe PWM.