<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://wiki.bespokerobotsociety.org/index.php?action=history&amp;feed=atom&amp;title=Motor_Control_Basics</id>
	<title>Motor Control Basics - Revision history</title>
	<link rel="self" type="application/atom+xml" href="https://wiki.bespokerobotsociety.org/index.php?action=history&amp;feed=atom&amp;title=Motor_Control_Basics"/>
	<link rel="alternate" type="text/html" href="https://wiki.bespokerobotsociety.org/index.php?title=Motor_Control_Basics&amp;action=history"/>
	<updated>2026-04-25T08:43:25Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.43.5</generator>
	<entry>
		<id>https://wiki.bespokerobotsociety.org/index.php?title=Motor_Control_Basics&amp;diff=87&amp;oldid=prev</id>
		<title>John: Created page with &quot;{{Tutorial |name=Motor Control Basics |competency=Electronics |difficulty=Intermediate |time=3-5 hours |prerequisites=Electronics Fundamentals, basic understanding of digital signals and PWM |materials=Breadboard, DC motor, motor driver module (TB6612FNG or L298N), microcontroller (Raspberry Pi Pico or Arduino), power supply (6-9V), jumper wires, multimeter |next_steps=SimpleBot assembly, build Capability:Differential Drive, Sensor Interfacing }}  &#039;&#039;&#039;...&quot;</title>
		<link rel="alternate" type="text/html" href="https://wiki.bespokerobotsociety.org/index.php?title=Motor_Control_Basics&amp;diff=87&amp;oldid=prev"/>
		<updated>2025-10-11T20:16:34Z</updated>

		<summary type="html">&lt;p&gt;Created page with &amp;quot;{{Tutorial |name=Motor Control Basics |competency=&lt;a href=&quot;/wiki/Electronics&quot; title=&quot;Electronics&quot;&gt;Electronics&lt;/a&gt; |difficulty=Intermediate |time=3-5 hours |prerequisites=&lt;a href=&quot;/wiki/Electronics_Fundamentals&quot; title=&quot;Electronics Fundamentals&quot;&gt;Electronics Fundamentals&lt;/a&gt;, basic understanding of digital signals and PWM |materials=Breadboard, DC motor, motor driver module (TB6612FNG or L298N), microcontroller (Raspberry Pi Pico or Arduino), power supply (6-9V), jumper wires, multimeter |next_steps=&lt;a href=&quot;/wiki/SimpleBot&quot; title=&quot;SimpleBot&quot;&gt;SimpleBot&lt;/a&gt; assembly, build &lt;a href=&quot;/wiki/Capability:Differential_Drive&quot; title=&quot;Capability:Differential Drive&quot;&gt;Capability:Differential Drive&lt;/a&gt;, &lt;a href=&quot;/wiki/Sensor_Interfacing&quot; title=&quot;Sensor Interfacing&quot;&gt;Sensor Interfacing&lt;/a&gt; }}  &amp;#039;&amp;#039;&amp;#039;...&amp;quot;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;{{Tutorial&lt;br /&gt;
|name=Motor Control Basics&lt;br /&gt;
|competency=[[Electronics]]&lt;br /&gt;
|difficulty=Intermediate&lt;br /&gt;
|time=3-5 hours&lt;br /&gt;
|prerequisites=[[Electronics Fundamentals]], basic understanding of digital signals and PWM&lt;br /&gt;
|materials=Breadboard, DC motor, motor driver module (TB6612FNG or L298N), microcontroller (Raspberry Pi Pico or Arduino), power supply (6-9V), jumper wires, multimeter&lt;br /&gt;
|next_steps=[[SimpleBot]] assembly, build [[Capability:Differential Drive]], [[Sensor Interfacing]]&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Motor Control Basics&amp;#039;&amp;#039;&amp;#039; teaches you how to control DC motors in robotics applications. You&amp;#039;ll learn about H-bridges, PWM speed control, motor driver ICs, and differential drive systems. By the end of this tutorial, you&amp;#039;ll understand how SimpleBot controls its motors and be able to implement motor control in your own robots.&lt;br /&gt;
&lt;br /&gt;
This tutorial builds on [[Electronics Fundamentals]] - you should understand voltage, current, PWM, and digital signals before proceeding.&lt;br /&gt;
&lt;br /&gt;
== Why Motor Control Matters ==&lt;br /&gt;
&lt;br /&gt;
Motors are the primary actuators in mobile robotics. Understanding motor control is essential for:&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Speed control&amp;#039;&amp;#039;&amp;#039; - Make your robot go faster or slower&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Direction control&amp;#039;&amp;#039;&amp;#039; - Forward, reverse, turning&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Precise motion&amp;#039;&amp;#039;&amp;#039; - Differential drive, straight-line driving, rotation in place&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Energy efficiency&amp;#039;&amp;#039;&amp;#039; - Maximize battery life with proper motor control&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Protection&amp;#039;&amp;#039;&amp;#039; - Prevent damage to motors and electronics&lt;br /&gt;
&lt;br /&gt;
Without proper motor control knowledge, you risk burning out motors, draining batteries rapidly, or damaging your microcontroller.&lt;br /&gt;
&lt;br /&gt;
== Part 1: DC Motor Fundamentals ==&lt;br /&gt;
&lt;br /&gt;
=== How DC Motors Work ===&lt;br /&gt;
&lt;br /&gt;
A &amp;#039;&amp;#039;&amp;#039;DC (Direct Current) motor&amp;#039;&amp;#039;&amp;#039; converts electrical energy into rotational motion:&lt;br /&gt;
&lt;br /&gt;
* Apply voltage across motor terminals → motor spins&lt;br /&gt;
* Higher voltage = faster speed (generally)&lt;br /&gt;
* Reverse polarity → motor spins in opposite direction&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Key characteristics:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;No-load speed&amp;#039;&amp;#039;&amp;#039; - Maximum RPM when nothing is attached to the shaft&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Stall current&amp;#039;&amp;#039;&amp;#039; - Current drawn when motor is blocked (highest current)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Operating voltage&amp;#039;&amp;#039;&amp;#039; - Typical range (e.g., 3V-6V for hobby motors)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Rated current&amp;#039;&amp;#039;&amp;#039; - Typical current during normal operation&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Torque&amp;#039;&amp;#039;&amp;#039; - Rotational force the motor can produce&lt;br /&gt;
&lt;br /&gt;
=== Current Draw and Power ===&lt;br /&gt;
&lt;br /&gt;
Motors draw &amp;#039;&amp;#039;&amp;#039;variable current&amp;#039;&amp;#039;&amp;#039; depending on load:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;No load&amp;#039;&amp;#039;&amp;#039; - Minimum current (50-100mA typical for small motors)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Normal operation&amp;#039;&amp;#039;&amp;#039; - Moderate current (200-500mA typical)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Stall&amp;#039;&amp;#039;&amp;#039; (blocked shaft) - Maximum current (1-3A typical)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Startup&amp;#039;&amp;#039;&amp;#039; - Brief high current spike when starting&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Example: SimpleBot TT Motor&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* No-load current: ~60mA at 6V&lt;br /&gt;
* Normal operation: ~200mA at 6V&lt;br /&gt;
* Stall current: ~1.5A at 6V&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Why this matters:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* You cannot power motors directly from microcontroller GPIO pins (typically limited to 10-20mA)&lt;br /&gt;
* Motors need dedicated power supply (not the 3.3V regulator powering your microcontroller)&lt;br /&gt;
* Motor drivers must handle stall current without overheating&lt;br /&gt;
&lt;br /&gt;
=== Back-EMF (Electromotive Force) ===&lt;br /&gt;
&lt;br /&gt;
When a motor spins, it acts as a generator and produces voltage in the opposite direction:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Back-EMF&amp;#039;&amp;#039;&amp;#039; increases with motor speed&lt;br /&gt;
* Can damage circuits when motor suddenly stops or reverses&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Protection required&amp;#039;&amp;#039;&amp;#039;: Diodes (flyback diodes) or motor driver ICs with built-in protection&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;What happens without protection:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
# Motor spinning at full speed&lt;br /&gt;
# You cut power to motor&lt;br /&gt;
# Motor&amp;#039;s inertia keeps it spinning briefly&lt;br /&gt;
# Motor generates voltage spike (back-EMF)&lt;br /&gt;
# Voltage spike can damage transistors, microcontrollers, or other components&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Solution:&amp;#039;&amp;#039;&amp;#039; Use motor driver ICs (like TB6612FNG) with built-in protection, or add flyback diodes across motor terminals.&lt;br /&gt;
&lt;br /&gt;
== Part 2: H-Bridge Motor Drivers ==&lt;br /&gt;
&lt;br /&gt;
=== What is an H-Bridge? ===&lt;br /&gt;
&lt;br /&gt;
An &amp;#039;&amp;#039;&amp;#039;H-bridge&amp;#039;&amp;#039;&amp;#039; is a circuit that allows you to control motor direction by switching the polarity of voltage across the motor:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
        +V&lt;br /&gt;
         |&lt;br /&gt;
    [SW1] [SW2]&lt;br /&gt;
         |     |&lt;br /&gt;
         +--M--+  (Motor)&lt;br /&gt;
         |     |&lt;br /&gt;
    [SW3] [SW4]&lt;br /&gt;
         |&lt;br /&gt;
        GND&lt;br /&gt;
&lt;br /&gt;
Legend: SW = Switch, M = Motor, +V = Battery positive&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The circuit forms an &amp;quot;H&amp;quot; shape - hence the name.&lt;br /&gt;
&lt;br /&gt;
=== H-Bridge Operation ===&lt;br /&gt;
&lt;br /&gt;
By controlling four switches (typically transistors), you can control motor direction:&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
! SW1 !! SW2 !! SW3 !! SW4 !! Motor Action&lt;br /&gt;
|-&lt;br /&gt;
| OFF || ON || ON || OFF || Forward (current flows left-to-right)&lt;br /&gt;
|-&lt;br /&gt;
| ON || OFF || OFF || ON || Reverse (current flows right-to-left)&lt;br /&gt;
|-&lt;br /&gt;
| OFF || OFF || OFF || OFF || Coast (motor freewheels)&lt;br /&gt;
|-&lt;br /&gt;
| OFF || ON || OFF || ON || Brake (both terminals connected to +V)&lt;br /&gt;
|-&lt;br /&gt;
| ON || OFF || ON || OFF || Brake (both terminals connected to GND)&lt;br /&gt;
|-&lt;br /&gt;
| ON || ON || OFF || OFF || SHORT CIRCUIT! Never do this!&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Critical rule:&amp;#039;&amp;#039;&amp;#039; Never turn on SW1 and SW3 at the same time, or SW2 and SW4 at the same time - this creates a short circuit from +V to GND!&lt;br /&gt;
&lt;br /&gt;
=== Building an H-Bridge (Educational - Not Recommended) ===&lt;br /&gt;
&lt;br /&gt;
You &amp;#039;&amp;#039;&amp;#039;could&amp;#039;&amp;#039;&amp;#039; build an H-bridge using discrete transistors (4× MOSFETs), but:&lt;br /&gt;
&lt;br /&gt;
* Requires careful gate driver design&lt;br /&gt;
* No built-in protection&lt;br /&gt;
* Easy to make mistakes that destroy components&lt;br /&gt;
* Takes up significant board space&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Better approach:&amp;#039;&amp;#039;&amp;#039; Use integrated H-bridge driver ICs like the TB6612FNG, L298N, or DRV8833. These have built-in protection, current limiting, and thermal shutdown.&lt;br /&gt;
&lt;br /&gt;
== Part 3: PWM Speed Control ==&lt;br /&gt;
&lt;br /&gt;
=== How PWM Controls Motor Speed ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;PWM (Pulse Width Modulation)&amp;#039;&amp;#039;&amp;#039; controls motor speed by rapidly switching power on and off:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;100% duty cycle&amp;#039;&amp;#039;&amp;#039; - Always ON → full speed&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;50% duty cycle&amp;#039;&amp;#039;&amp;#039; - ON half the time → ~half speed&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;25% duty cycle&amp;#039;&amp;#039;&amp;#039; - ON quarter of the time → ~quarter speed&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;0% duty cycle&amp;#039;&amp;#039;&amp;#039; - Always OFF → motor stopped&lt;br /&gt;
&lt;br /&gt;
The motor&amp;#039;s inertia smooths out the pulses, resulting in variable speed.&lt;br /&gt;
&lt;br /&gt;
=== PWM Frequency Selection ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Typical PWM frequencies for motor control:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;1 kHz - 20 kHz&amp;#039;&amp;#039;&amp;#039; - Most common range&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Too low&amp;#039;&amp;#039;&amp;#039; (&amp;lt;100 Hz) - Motor produces audible whine, rough motion&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Too high&amp;#039;&amp;#039;&amp;#039; (&amp;gt;50 kHz) - Switching losses in driver increase, less efficient&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;SimpleBot uses 1 kHz PWM&amp;#039;&amp;#039;&amp;#039; - good balance between smoothness and efficiency.&lt;br /&gt;
&lt;br /&gt;
=== PWM and Direction Control Combined ===&lt;br /&gt;
&lt;br /&gt;
To control both speed and direction:&lt;br /&gt;
&lt;br /&gt;
# Set direction using H-bridge control pins (IN1, IN2)&lt;br /&gt;
# Apply PWM signal to enable/PWM pin&lt;br /&gt;
# Result: Motor spins at variable speed in chosen direction&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Example: TB6612FNG control&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Set AIN1=LOW, AIN2=HIGH → Forward direction&lt;br /&gt;
* Apply PWM to PWMA pin → Variable speed forward&lt;br /&gt;
* Change to AIN1=HIGH, AIN2=LOW → Reverse direction&lt;br /&gt;
&lt;br /&gt;
=== Non-Linear Speed Response ===&lt;br /&gt;
&lt;br /&gt;
Motor speed is &amp;#039;&amp;#039;&amp;#039;not&amp;#039;&amp;#039;&amp;#039; linearly proportional to PWM duty cycle:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Below ~20% duty cycle&amp;#039;&amp;#039;&amp;#039; - Motor may not turn at all (not enough torque to overcome friction)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;20-80% duty cycle&amp;#039;&amp;#039;&amp;#039; - Approximately linear speed response&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;80-100% duty cycle&amp;#039;&amp;#039;&amp;#039; - Speed approaches maximum, less sensitivity to changes&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Practical implication:&amp;#039;&amp;#039;&amp;#039; You may need to calibrate motor control in software:&lt;br /&gt;
* Dead zone compensation (start at 25% instead of 0%)&lt;br /&gt;
* Speed mapping function (non-linear duty cycle to achieve linear speed)&lt;br /&gt;
* Different motors may need different calibration&lt;br /&gt;
&lt;br /&gt;
== Part 4: Motor Driver ICs ==&lt;br /&gt;
&lt;br /&gt;
=== The TB6612FNG Motor Driver ===&lt;br /&gt;
&lt;br /&gt;
The &amp;#039;&amp;#039;&amp;#039;TB6612FNG&amp;#039;&amp;#039;&amp;#039; is SimpleBot&amp;#039;s motor driver. It&amp;#039;s a dual H-bridge driver that can control two DC motors independently.&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Key specifications:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Motor voltage: 4.5V - 13.5V&lt;br /&gt;
* Logic voltage: 2.7V - 5.5V (3.3V compatible!)&lt;br /&gt;
* Continuous current: 1.2A per channel&lt;br /&gt;
* Peak current: 3.2A per channel&lt;br /&gt;
* Low voltage drop: ~0.3V (very efficient)&lt;br /&gt;
* Built-in protection: Thermal shutdown, low-voltage detection&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Control pins per motor:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;PWM&amp;#039;&amp;#039;&amp;#039; - Speed control (PWM signal)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;IN1&amp;#039;&amp;#039;&amp;#039; - Direction control bit 1&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;IN2&amp;#039;&amp;#039;&amp;#039; - Direction control bit 2&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;STBY&amp;#039;&amp;#039;&amp;#039; - Standby (must be HIGH to enable driver)&lt;br /&gt;
&lt;br /&gt;
=== TB6612FNG Truth Table ===&lt;br /&gt;
&lt;br /&gt;
For each motor (A or B):&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
! IN1 !! IN2 !! PWM !! Motor Output&lt;br /&gt;
|-&lt;br /&gt;
| LOW || HIGH || PWM || Forward (CCW)&lt;br /&gt;
|-&lt;br /&gt;
| HIGH || LOW || PWM || Reverse (CW)&lt;br /&gt;
|-&lt;br /&gt;
| LOW || LOW || any || Coast (freewheeling)&lt;br /&gt;
|-&lt;br /&gt;
| HIGH || HIGH || any || Brake (short brake)&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Brake vs Coast:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Brake&amp;#039;&amp;#039;&amp;#039; (IN1=HIGH, IN2=HIGH) - Motor terminals shorted together, motor stops quickly&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Coast&amp;#039;&amp;#039;&amp;#039; (IN1=LOW, IN2=LOW) - Motor terminals disconnected, motor coasts to a stop&lt;br /&gt;
&lt;br /&gt;
=== Wiring the TB6612FNG ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
Raspberry Pi Pico → TB6612FNG:&lt;br /&gt;
- GP14 → AIN1  (Motor A direction bit 1)&lt;br /&gt;
- GP15 → AIN2  (Motor A direction bit 2)&lt;br /&gt;
- GP16 → PWMA  (Motor A speed - PWM capable pin)&lt;br /&gt;
- GP17 → BIN1  (Motor B direction bit 1)&lt;br /&gt;
- GP18 → BIN2  (Motor B direction bit 2)&lt;br /&gt;
- GP19 → PWMB  (Motor B speed - PWM capable pin)&lt;br /&gt;
- GP20 → STBY  (Standby - enable driver)&lt;br /&gt;
- GND → GND    (Logic ground)&lt;br /&gt;
&lt;br /&gt;
Power Supply:&lt;br /&gt;
- 6V Battery (+) → VM    (Motor power)&lt;br /&gt;
- 3.3V → VCC             (Logic power from Pico)&lt;br /&gt;
- GND → GND (Power)      (Shared ground)&lt;br /&gt;
&lt;br /&gt;
Motors:&lt;br /&gt;
- Left Motor → AO1, AO2&lt;br /&gt;
- Right Motor → BO1, BO2&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Important:&amp;#039;&amp;#039;&amp;#039; Logic ground (from Pico) and power ground (from battery) must be connected together!&lt;br /&gt;
&lt;br /&gt;
=== Code Example: TB6612FNG Control (MicroPython) ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;python&amp;quot;&amp;gt;&lt;br /&gt;
from machine import Pin, PWM&lt;br /&gt;
&lt;br /&gt;
class Motor:&lt;br /&gt;
    &amp;quot;&amp;quot;&amp;quot;Control a single motor on TB6612FNG&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
&lt;br /&gt;
    def __init__(self, pwm_pin, in1_pin, in2_pin, freq=1000):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Initialize motor control pins&lt;br /&gt;
&lt;br /&gt;
        Args:&lt;br /&gt;
            pwm_pin: GPIO pin number for PWM control&lt;br /&gt;
            in1_pin: GPIO pin number for direction bit 1&lt;br /&gt;
            in2_pin: GPIO pin number for direction bit 2&lt;br /&gt;
            freq: PWM frequency in Hz (default 1000)&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.pwm = PWM(Pin(pwm_pin))&lt;br /&gt;
        self.pwm.freq(freq)&lt;br /&gt;
        self.in1 = Pin(in1_pin, Pin.OUT)&lt;br /&gt;
        self.in2 = Pin(in2_pin, Pin.OUT)&lt;br /&gt;
&lt;br /&gt;
    def forward(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Drive motor forward at specified speed&lt;br /&gt;
&lt;br /&gt;
        Args:&lt;br /&gt;
            speed: 0-65535 (0 = stopped, 65535 = full speed)&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.in1.value(0)&lt;br /&gt;
        self.in2.value(1)&lt;br /&gt;
        self.pwm.duty_u16(speed)&lt;br /&gt;
&lt;br /&gt;
    def reverse(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Drive motor reverse at specified speed&lt;br /&gt;
&lt;br /&gt;
        Args:&lt;br /&gt;
            speed: 0-65535 (0 = stopped, 65535 = full speed)&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.in1.value(1)&lt;br /&gt;
        self.in2.value(0)&lt;br /&gt;
        self.pwm.duty_u16(speed)&lt;br /&gt;
&lt;br /&gt;
    def brake(self):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Brake motor (short brake - stops quickly)&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.in1.value(1)&lt;br /&gt;
        self.in2.value(1)&lt;br /&gt;
        self.pwm.duty_u16(0)&lt;br /&gt;
&lt;br /&gt;
    def coast(self):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Coast motor (freewheeling - stops gradually)&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.in1.value(0)&lt;br /&gt;
        self.in2.value(0)&lt;br /&gt;
        self.pwm.duty_u16(0)&lt;br /&gt;
&lt;br /&gt;
# Initialize standby pin&lt;br /&gt;
stby = Pin(20, Pin.OUT)&lt;br /&gt;
stby.value(1)  # Enable motor driver&lt;br /&gt;
&lt;br /&gt;
# Initialize motors&lt;br /&gt;
left_motor = Motor(pwm_pin=16, in1_pin=14, in2_pin=15)&lt;br /&gt;
right_motor = Motor(pwm_pin=19, in1_pin=17, in2_pin=18)&lt;br /&gt;
&lt;br /&gt;
# Example: Drive forward at 50% speed&lt;br /&gt;
left_motor.forward(32768)   # 50% of 65535&lt;br /&gt;
right_motor.forward(32768)&lt;br /&gt;
&lt;br /&gt;
# Stop after 2 seconds&lt;br /&gt;
import time&lt;br /&gt;
time.sleep(2)&lt;br /&gt;
left_motor.brake()&lt;br /&gt;
right_motor.brake()&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Alternative: L298N Motor Driver ===&lt;br /&gt;
&lt;br /&gt;
The &amp;#039;&amp;#039;&amp;#039;L298N&amp;#039;&amp;#039;&amp;#039; is an older, more common motor driver. It&amp;#039;s less efficient than the TB6612FNG:&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;L298N characteristics:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Voltage drop: 2-4V (vs 0.3V for TB6612FNG)&lt;br /&gt;
* Maximum voltage: 46V (good for larger motors)&lt;br /&gt;
* Continuous current: 2A per channel&lt;br /&gt;
* Larger size, generates more heat&lt;br /&gt;
* Often includes onboard voltage regulator&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;When to use L298N:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Larger motors that need &amp;gt;1.2A continuous current&lt;br /&gt;
* Higher voltage motors (&amp;gt;13.5V)&lt;br /&gt;
* You already have one available&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;When to use TB6612FNG:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Battery-powered robots (efficiency matters)&lt;br /&gt;
* Small to medium motors (&amp;lt;1A typical)&lt;br /&gt;
* Space-constrained designs&lt;br /&gt;
* 3.3V logic (no level shifters needed)&lt;br /&gt;
&lt;br /&gt;
== Part 5: Differential Drive ==&lt;br /&gt;
&lt;br /&gt;
=== What is Differential Drive? ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Differential drive&amp;#039;&amp;#039;&amp;#039; is a robot motion system using two independently-controlled wheels:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Left wheel&amp;#039;&amp;#039;&amp;#039; and &amp;#039;&amp;#039;&amp;#039;right wheel&amp;#039;&amp;#039;&amp;#039; on opposite sides of robot&lt;br /&gt;
* No steering mechanism - turns are created by speed differential&lt;br /&gt;
* Simple, effective, and commonly used in mobile robots&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;SimpleBot uses differential drive&amp;#039;&amp;#039;&amp;#039; with two TT motors and wheels.&lt;br /&gt;
&lt;br /&gt;
=== Differential Drive Motion Control ===&lt;br /&gt;
&lt;br /&gt;
By varying the speed of left and right wheels, you can create different motions:&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot;&lt;br /&gt;
! Left Motor !! Right Motor !! Robot Motion&lt;br /&gt;
|-&lt;br /&gt;
| Forward 50% || Forward 50% || Straight forward&lt;br /&gt;
|-&lt;br /&gt;
| Reverse 50% || Reverse 50% || Straight reverse&lt;br /&gt;
|-&lt;br /&gt;
| Forward 100% || Forward 50% || Gentle turn right (arc)&lt;br /&gt;
|-&lt;br /&gt;
| Forward 50% || Forward 100% || Gentle turn left (arc)&lt;br /&gt;
|-&lt;br /&gt;
| Forward 50% || Stop || Sharp turn right&lt;br /&gt;
|-&lt;br /&gt;
| Forward 50% || Reverse 50% || Rotate clockwise (pivot turn)&lt;br /&gt;
|-&lt;br /&gt;
| Stop || Stop || Stopped&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Key insight:&amp;#039;&amp;#039;&amp;#039; The difference in wheel speeds determines turn radius. Equal speeds = straight line.&lt;br /&gt;
&lt;br /&gt;
=== Implementing Differential Drive ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;python&amp;quot;&amp;gt;&lt;br /&gt;
class DifferentialDrive:&lt;br /&gt;
    &amp;quot;&amp;quot;&amp;quot;Differential drive robot control&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
&lt;br /&gt;
    def __init__(self, left_motor, right_motor):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Initialize with two Motor objects&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.left = left_motor&lt;br /&gt;
        self.right = right_motor&lt;br /&gt;
&lt;br /&gt;
    def drive(self, left_speed, right_speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Drive with independent wheel speeds&lt;br /&gt;
&lt;br /&gt;
        Args:&lt;br /&gt;
            left_speed: -65535 to 65535 (negative = reverse)&lt;br /&gt;
            right_speed: -65535 to 65535 (negative = reverse)&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        # Left motor&lt;br /&gt;
        if left_speed &amp;gt; 0:&lt;br /&gt;
            self.left.forward(left_speed)&lt;br /&gt;
        elif left_speed &amp;lt; 0:&lt;br /&gt;
            self.left.reverse(-left_speed)&lt;br /&gt;
        else:&lt;br /&gt;
            self.left.coast()&lt;br /&gt;
&lt;br /&gt;
        # Right motor&lt;br /&gt;
        if right_speed &amp;gt; 0:&lt;br /&gt;
            self.right.forward(right_speed)&lt;br /&gt;
        elif right_speed &amp;lt; 0:&lt;br /&gt;
            self.right.reverse(-right_speed)&lt;br /&gt;
        else:&lt;br /&gt;
            self.right.coast()&lt;br /&gt;
&lt;br /&gt;
    def forward(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Drive straight forward&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.drive(speed, speed)&lt;br /&gt;
&lt;br /&gt;
    def reverse(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Drive straight reverse&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.drive(-speed, -speed)&lt;br /&gt;
&lt;br /&gt;
    def turn_left(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Turn left (arc) by slowing left wheel&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.drive(speed // 2, speed)&lt;br /&gt;
&lt;br /&gt;
    def turn_right(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Turn right (arc) by slowing right wheel&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.drive(speed, speed // 2)&lt;br /&gt;
&lt;br /&gt;
    def rotate_left(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Rotate left in place (pivot turn)&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.drive(-speed, speed)&lt;br /&gt;
&lt;br /&gt;
    def rotate_right(self, speed):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Rotate right in place (pivot turn)&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.drive(speed, -speed)&lt;br /&gt;
&lt;br /&gt;
    def stop(self):&lt;br /&gt;
        &amp;quot;&amp;quot;&amp;quot;Stop both motors&amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
        self.left.brake()&lt;br /&gt;
        self.right.brake()&lt;br /&gt;
&lt;br /&gt;
# Initialize differential drive&lt;br /&gt;
robot = DifferentialDrive(left_motor, right_motor)&lt;br /&gt;
&lt;br /&gt;
# Drive straight forward at 50% speed&lt;br /&gt;
robot.forward(32768)&lt;br /&gt;
time.sleep(2)&lt;br /&gt;
&lt;br /&gt;
# Turn right&lt;br /&gt;
robot.turn_right(32768)&lt;br /&gt;
time.sleep(1)&lt;br /&gt;
&lt;br /&gt;
# Rotate in place&lt;br /&gt;
robot.rotate_left(32768)&lt;br /&gt;
time.sleep(1)&lt;br /&gt;
&lt;br /&gt;
# Stop&lt;br /&gt;
robot.stop()&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Straight-Line Driving Challenge ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Problem:&amp;#039;&amp;#039;&amp;#039; Even with equal PWM duty cycles, motors rarely spin at exactly the same speed due to:&lt;br /&gt;
* Manufacturing tolerances&lt;br /&gt;
* Different friction in gearboxes&lt;br /&gt;
* Voltage drop differences&lt;br /&gt;
* Wheel diameter differences&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Result:&amp;#039;&amp;#039;&amp;#039; Robot drifts left or right instead of going straight.&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Solutions:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
1. &amp;#039;&amp;#039;&amp;#039;Calibration&amp;#039;&amp;#039;&amp;#039; - Measure actual wheel speeds, adjust PWM to compensate&lt;br /&gt;
2. &amp;#039;&amp;#039;&amp;#039;Closed-loop control&amp;#039;&amp;#039;&amp;#039; - Use encoders (see [[Capability:Optical Odometry]]) to measure and correct speed&lt;br /&gt;
3. &amp;#039;&amp;#039;&amp;#039;Trim adjustment&amp;#039;&amp;#039;&amp;#039; - Add offset to one motor&amp;#039;s speed in software&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Example: Simple trim adjustment&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;python&amp;quot;&amp;gt;&lt;br /&gt;
# If robot drifts right, left motor is slower - add trim&lt;br /&gt;
LEFT_MOTOR_TRIM = 1.05   # Left motor needs 5% more power&lt;br /&gt;
&lt;br /&gt;
def forward_with_trim(speed):&lt;br /&gt;
    left_speed = int(speed * LEFT_MOTOR_TRIM)&lt;br /&gt;
    right_speed = speed&lt;br /&gt;
    robot.drive(left_speed, right_speed)&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Turn Radius Calculation ===&lt;br /&gt;
&lt;br /&gt;
For a differential drive robot:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;math&amp;gt;R = \frac{L}{2} \times \frac{v_L + v_R}{v_R - v_L}&amp;lt;/math&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Where:&lt;br /&gt;
* R = turn radius&lt;br /&gt;
* L = distance between wheels (track width)&lt;br /&gt;
* v_L = left wheel velocity&lt;br /&gt;
* v_R = right wheel velocity&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Special cases:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* v_L = v_R → R = infinity (straight line)&lt;br /&gt;
* v_L = -v_R → R = 0 (rotation in place)&lt;br /&gt;
* v_L = 0 or v_R = 0 → R = L/2 (pivot around one wheel)&lt;br /&gt;
&lt;br /&gt;
== Part 6: Power Management and Protection ==&lt;br /&gt;
&lt;br /&gt;
=== Separate Power Supplies ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Best practice:&amp;#039;&amp;#039;&amp;#039; Use separate power for motors and logic:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Motor power&amp;#039;&amp;#039;&amp;#039; - Battery (6V, 9V, 12V depending on motors)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Logic power&amp;#039;&amp;#039;&amp;#039; - Regulated 3.3V or 5V from voltage regulator&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Shared ground&amp;#039;&amp;#039;&amp;#039; - All grounds connected together&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Why separate?&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Motors create voltage spikes and noise&lt;br /&gt;
* Motor current draw can cause voltage sag&lt;br /&gt;
* Microcontroller needs stable, clean voltage&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;SimpleBot power system:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* 4× AA batteries (6V) → MP1584 buck converter → 5V regulated&lt;br /&gt;
* 5V → Raspberry Pi Pico onboard regulator → 3.3V for microcontroller&lt;br /&gt;
* Battery 6V → TB6612FNG VM pin → Motor power&lt;br /&gt;
* 3.3V → TB6612FNG VCC pin → Logic power&lt;br /&gt;
&lt;br /&gt;
=== Decoupling Capacitors ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Always add capacitors:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;0.1µF ceramic capacitor&amp;#039;&amp;#039;&amp;#039; near every IC&amp;#039;s power pins (VCC to GND)&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;100-1000µF electrolytic capacitor&amp;#039;&amp;#039;&amp;#039; across motor power supply&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Purpose:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Filter high-frequency noise&lt;br /&gt;
* Provide local energy storage for current spikes&lt;br /&gt;
* Prevent voltage droops during motor startup&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Placement matters:&amp;#039;&amp;#039;&amp;#039; Place decoupling capacitors as close to IC power pins as possible.&lt;br /&gt;
&lt;br /&gt;
=== Current Limiting ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Protect your system:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Use motor drivers rated above your motor&amp;#039;s stall current&lt;br /&gt;
* Add fuses or resettable fuses (PTC) in power supply line&lt;br /&gt;
* Monitor battery voltage to prevent over-discharge&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Example:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* SimpleBot TT motors: 1.5A stall current&lt;br /&gt;
* TB6612FNG rating: 1.2A continuous, 3.2A peak&lt;br /&gt;
* Result: Motors protected during brief stalls, but extended stalls will trigger thermal shutdown&lt;br /&gt;
&lt;br /&gt;
=== Thermal Management ===&lt;br /&gt;
&lt;br /&gt;
Motor drivers generate heat, especially at high currents:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Heatsinks&amp;#039;&amp;#039;&amp;#039; - Attach to motor driver IC if handling &amp;gt;1A continuously&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Airflow&amp;#039;&amp;#039;&amp;#039; - Don&amp;#039;t enclose motor driver in sealed box&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Thermal shutdown&amp;#039;&amp;#039;&amp;#039; - Most modern drivers shut down automatically if overheating&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Duty cycle&amp;#039;&amp;#039;&amp;#039; - If driver gets too hot, reduce motor duty cycle or add cooling&lt;br /&gt;
&lt;br /&gt;
== Part 7: Troubleshooting Motor Control ==&lt;br /&gt;
&lt;br /&gt;
=== Motor Not Spinning ===&lt;br /&gt;
&lt;br /&gt;
Check:&lt;br /&gt;
1. Power supply connected? (Measure voltage at VM pin)&lt;br /&gt;
2. Standby pin enabled? (STBY = HIGH)&lt;br /&gt;
3. PWM signal present? (Use oscilloscope or LED on PWM pin)&lt;br /&gt;
4. Direction pins set correctly? (Not both HIGH or both LOW for some drivers)&lt;br /&gt;
5. Motor connected? (Check continuity of motor wires)&lt;br /&gt;
6. Driver overheated? (Let cool down, check for thermal shutdown)&lt;br /&gt;
&lt;br /&gt;
=== Motor Spins Wrong Direction ===&lt;br /&gt;
&lt;br /&gt;
Fix:&lt;br /&gt;
* Swap motor wire connections (AO1 ↔ AO2)&lt;br /&gt;
* Or swap IN1/IN2 control in software&lt;br /&gt;
&lt;br /&gt;
=== Motors Work Individually But Not Together ===&lt;br /&gt;
&lt;br /&gt;
Likely causes:&lt;br /&gt;
* Insufficient current from power supply (voltage sags when both motors run)&lt;br /&gt;
* Wiring error (check all ground connections)&lt;br /&gt;
* Shared PWM channel (each motor needs independent PWM)&lt;br /&gt;
&lt;br /&gt;
=== Motors Run Erratically or Stall ===&lt;br /&gt;
&lt;br /&gt;
Check:&lt;br /&gt;
* Battery voltage sufficient? (Use multimeter under load)&lt;br /&gt;
* Stall current within driver rating?&lt;br /&gt;
* Decoupling capacitors installed?&lt;br /&gt;
* Mechanical binding? (Wheels rubbing, gears jammed)&lt;br /&gt;
&lt;br /&gt;
=== Robot Drives Straight But Won&amp;#039;t Turn ===&lt;br /&gt;
&lt;br /&gt;
Debug:&lt;br /&gt;
* Test each motor independently (forward, reverse, variable speed)&lt;br /&gt;
* Check that both motors are receiving different commands during turns&lt;br /&gt;
* Verify IN1/IN2 pins controlling direction correctly&lt;br /&gt;
* Ensure motors can reverse (not just stop)&lt;br /&gt;
&lt;br /&gt;
=== Robot Veers to One Side ===&lt;br /&gt;
&lt;br /&gt;
Solutions:&lt;br /&gt;
* Calibrate motor speeds (add trim adjustment)&lt;br /&gt;
* Check wheel diameter (uneven wheels cause drift)&lt;br /&gt;
* Use encoders for closed-loop speed control&lt;br /&gt;
* Verify both motors receiving same PWM value when driving straight&lt;br /&gt;
&lt;br /&gt;
== Part 8: Advanced Topics ==&lt;br /&gt;
&lt;br /&gt;
=== Motor Speed Measurement ===&lt;br /&gt;
&lt;br /&gt;
To achieve precise speed control, measure actual motor speed:&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Optical encoders&amp;#039;&amp;#039;&amp;#039; - Count pulses from slotted wheel (see [[Capability:Optical Odometry]])&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Hall effect sensors&amp;#039;&amp;#039;&amp;#039; - Count magnet passes&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Back-EMF sensing&amp;#039;&amp;#039;&amp;#039; - Measure motor&amp;#039;s generated voltage when coasting&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Why measure speed?&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Compensate for manufacturing differences&lt;br /&gt;
* Implement PID control for precise motion&lt;br /&gt;
* Measure distance traveled&lt;br /&gt;
* Detect wheel slip or stalls&lt;br /&gt;
&lt;br /&gt;
=== PID Control for Motors ===&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;PID (Proportional-Integral-Derivative)&amp;#039;&amp;#039;&amp;#039; control maintains consistent motor speed:&lt;br /&gt;
&lt;br /&gt;
* Measure actual speed (using encoders)&lt;br /&gt;
* Compare to desired speed (setpoint)&lt;br /&gt;
* Calculate error and adjust PWM duty cycle&lt;br /&gt;
* Result: Motor maintains target speed despite varying load&lt;br /&gt;
&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Benefits:&amp;#039;&amp;#039;&amp;#039;&lt;br /&gt;
* Straight-line driving without drift&lt;br /&gt;
* Consistent speed regardless of battery voltage&lt;br /&gt;
* Precise turns and rotations&lt;br /&gt;
&lt;br /&gt;
This is an advanced topic - start with open-loop control (no feedback), then add encoders later.&lt;br /&gt;
&lt;br /&gt;
=== Acceleration and Deceleration ===&lt;br /&gt;
&lt;br /&gt;
Instant speed changes stress motors and can cause wheel slip. Instead, ramp speed gradually:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;python&amp;quot;&amp;gt;&lt;br /&gt;
def ramp_speed(motor, target_speed, steps=20, delay_ms=50):&lt;br /&gt;
    &amp;quot;&amp;quot;&amp;quot;Gradually increase motor speed to target&lt;br /&gt;
&lt;br /&gt;
    Args:&lt;br /&gt;
        motor: Motor object&lt;br /&gt;
        target_speed: Desired final speed (0-65535)&lt;br /&gt;
        steps: Number of incremental steps&lt;br /&gt;
        delay_ms: Delay between steps in milliseconds&lt;br /&gt;
    &amp;quot;&amp;quot;&amp;quot;&lt;br /&gt;
    current_speed = 0&lt;br /&gt;
    step_size = target_speed // steps&lt;br /&gt;
&lt;br /&gt;
    for i in range(steps):&lt;br /&gt;
        current_speed += step_size&lt;br /&gt;
        motor.forward(current_speed)&lt;br /&gt;
        time.sleep_ms(delay_ms)&lt;br /&gt;
&lt;br /&gt;
    # Final step to exact target&lt;br /&gt;
    motor.forward(target_speed)&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Regenerative Braking ===&lt;br /&gt;
&lt;br /&gt;
Some motor drivers support &amp;#039;&amp;#039;&amp;#039;regenerative braking&amp;#039;&amp;#039;&amp;#039; - converting motor&amp;#039;s kinetic energy back into electrical energy:&lt;br /&gt;
&lt;br /&gt;
* Motor acts as generator when coasting&lt;br /&gt;
* Energy charges battery or dissipates in brake resistor&lt;br /&gt;
* More efficient than friction braking&lt;br /&gt;
* Requires specialized motor driver with regen support&lt;br /&gt;
&lt;br /&gt;
Most hobby motor drivers (including TB6612FNG) use &amp;#039;&amp;#039;&amp;#039;dynamic braking&amp;#039;&amp;#039;&amp;#039; (short brake) instead - motor energy dissipates as heat in the motor and driver.&lt;br /&gt;
&lt;br /&gt;
== Part 9: Practical Skills Checklist ==&lt;br /&gt;
&lt;br /&gt;
By now, you should be able to:&lt;br /&gt;
&lt;br /&gt;
* ☐ Explain how DC motors work and why they draw variable current&lt;br /&gt;
* ☐ Describe what back-EMF is and why protection is needed&lt;br /&gt;
* ☐ Understand how H-bridges enable direction control&lt;br /&gt;
* ☐ Explain how PWM controls motor speed&lt;br /&gt;
* ☐ Wire a TB6612FNG motor driver to a microcontroller and motors&lt;br /&gt;
* ☐ Write code to drive motors forward, reverse, and stop&lt;br /&gt;
* ☐ Implement differential drive motion (forward, turn, rotate)&lt;br /&gt;
* ☐ Troubleshoot common motor control problems&lt;br /&gt;
* ☐ Understand the importance of separate power supplies&lt;br /&gt;
* ☐ Calculate current requirements for motor selection&lt;br /&gt;
&lt;br /&gt;
If you can check most of these boxes, you&amp;#039;re ready to build robots with motor control!&lt;br /&gt;
&lt;br /&gt;
== Next Steps ==&lt;br /&gt;
&lt;br /&gt;
=== Build SimpleBot ===&lt;br /&gt;
Apply your motor control knowledge:&lt;br /&gt;
* [[SimpleBot]] - Complete robot build guide with TB6612FNG motor control&lt;br /&gt;
* [[SimpleBot:Line Following Implementation]] - Use motors to follow a line&lt;br /&gt;
* [[SimpleBot:Dead Reckoning Implementation]] - Combine motors with encoders for precise motion&lt;br /&gt;
&lt;br /&gt;
=== Add Sensors ===&lt;br /&gt;
Combine motor control with sensing:&lt;br /&gt;
* [[Sensor Interfacing]] - Learn I2C, SPI, and analog sensors&lt;br /&gt;
* [[Capability:Optical Odometry]] - Measure wheel rotation for precise distance&lt;br /&gt;
* [[Capability:IMU Sensing]] - Add gyroscope for accurate turning&lt;br /&gt;
&lt;br /&gt;
=== Expand Capabilities ===&lt;br /&gt;
* [[Capability:Differential Drive]] - Full documentation of this motion system&lt;br /&gt;
* [[Capability:Encoder Sensing]] - Closed-loop motor speed control&lt;br /&gt;
* Build your own custom robot with motor control&lt;br /&gt;
&lt;br /&gt;
== Common Mistakes and Pitfalls ==&lt;br /&gt;
&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Powering motors from microcontroller pins&amp;#039;&amp;#039;&amp;#039; - GPIO pins cannot supply enough current; always use motor driver&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;No standby pin control&amp;#039;&amp;#039;&amp;#039; - TB6612FNG requires STBY=HIGH to enable; forgetting this means motors won&amp;#039;t work&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Separate grounds&amp;#039;&amp;#039;&amp;#039; - Logic ground and motor ground must be connected together&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Insufficient decoupling&amp;#039;&amp;#039;&amp;#039; - Missing capacitors cause erratic behavior and voltage spikes&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Exceeding current rating&amp;#039;&amp;#039;&amp;#039; - Using motors with stall current higher than driver rating damages driver&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;No back-EMF protection&amp;#039;&amp;#039;&amp;#039; - If building H-bridge from transistors, must add flyback diodes&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;PWM frequency too low&amp;#039;&amp;#039;&amp;#039; - Causes audible motor whine and rough motion&lt;br /&gt;
* &amp;#039;&amp;#039;&amp;#039;Forgetting motor trim&amp;#039;&amp;#039;&amp;#039; - Robots rarely drive perfectly straight without calibration&lt;br /&gt;
&lt;br /&gt;
== Resources and Further Reading ==&lt;br /&gt;
&lt;br /&gt;
=== BRS Wiki Pages ===&lt;br /&gt;
* [[TB6612FNG]] - Detailed motor driver specifications&lt;br /&gt;
* [[Electronics]] - Full electronics competency overview&lt;br /&gt;
* [[Capability:Differential Drive]] - Motion system documentation&lt;br /&gt;
* [[SimpleBot]] - Complete robot using motor control&lt;br /&gt;
&lt;br /&gt;
=== External Resources ===&lt;br /&gt;
* [https://www.ti.com/lit/an/slva842/slva842.pdf TI Motor Driver Basics] (PDF)&lt;br /&gt;
* [https://learn.sparkfun.com/tutorials/motors-and-selecting-the-right-one SparkFun Motor Selection Guide]&lt;br /&gt;
* [https://www.pololu.com/docs/0J15 Pololu Motor Selection Guide]&lt;br /&gt;
&lt;br /&gt;
== See Also ==&lt;br /&gt;
&lt;br /&gt;
* [[Electronics Fundamentals]] - Prerequisite tutorial&lt;br /&gt;
* [[Sensor Interfacing]] - Next tutorial in electronics learning path&lt;br /&gt;
* [[Capability:Encoder Sensing]] - Measure motor speed&lt;br /&gt;
* [[Behavior:PID Control]] - Advanced motor speed regulation&lt;br /&gt;
&lt;br /&gt;
[[Category:Tutorials]]&lt;br /&gt;
[[Category:Electronics]]&lt;br /&gt;
[[Category:Intermediate]]&lt;/div&gt;</summary>
		<author><name>John</name></author>
	</entry>
</feed>