Eseliikuv auto

Katse Mootiri käivitamine L298N draiveriga.

Motor Shield on loodud L298N kiibi põhjal. See võimaldab juhtida kahte alalisvoolumootorit või ühte samm-mootorit. Maksimaalne voolutarve ei tohiks ületada 2 amprit.

Juhtivad järeldused on IN1 ja IN2, IN3 ja IN4, ENA ja ENB. Erineva tasemega signaalide vaheldumine (kõrge ja madal loogiline tase) paaridel väljunditel määrab mootorite pöörlemissuuna.

ENA (seotud IN1 ja IN2-ga) ja ENB (seotud IN3-ga ja IN4-ga) järeldused vastutavad kanalite lahushoidmise eest. Seda saab kasutada kahes režiimis:

1.Aktiivne režiim. Juhtimine lasub kontrolleril . Kõrge loogiline tase lubab mootorite pöörlemist, madal keelab, samas ei ole signaalitasemed «IN» väljunditel olulised. Andes «EN» SIM (PWM) signaali järeldustele, saate juhtida mootorite pöörlemiskiirust.

2. Passiivne režiim. «EN» järelduste ühendamine kõrge tasemega (+5 Volt). Selleks sulgeme hüppajate abil plaadile +5V ja EN nõelad. Sellises režiimis ei saa me enam mootorite kiirust reguleerida, nad töötavad alati täiskiirusel. Aga me säästame kahte mikrokontrolleri väljundit. Pöörlemise määrab ikkagi «IN» järelduste olek. Ja selleks, et mootor seisma panna, anname paarisaerulistele «IN» järeldustele ühe taseme signaali. Artikli lõpus olevates tarkvarakoodi näidetes on kõik need punktid kommentaarides üksikasjalikult lahti seletatud.

Toitepistik ja stabilisaatori töö.

Mootorite ühendamine L298N mooduliga

Esimeses näites ühe mootori ühendamine ilma kiiruse reguleerimiseta.

Kood:

int IN3 = 5; // Input3 подключен к выводу 5
int IN4 = 4;
 
void setup()
{
pinMode (IN4, OUTPUT);
pinMode (IN3, OUTPUT);
}
void loop()
{
// На пару выводов "IN" поданы разноименные сигналы, мотор вращается
digitalWrite (IN4, HIGH);
digitalWrite (IN3, LOW);
delay(4000);
// На пару выводов "IN" поданы одноименные сигналы, мотор не вращается
digitalWrite (IN4, LOW);
delay(500);
// На пару выводов "IN" поданы разноименные (и уже противоположные относительно первого случая) сигналы, мотор вращается
// относительно первого случая) сигналы, мотор вращается в другую сторону
digitalWrite (IN3, HIGH);
delay(4000);
// Снова на выводах "IN" появились одноименные сигналы, мотор не вращается
digitalWrite (IN3, LOW);
delay(5000);
}

Teises näites ühendame ENB SIM-i (D3) väljundiga.

Nii saame kasutada draiveri võimalust juhtida kiirust, muutes signaali SIM-i tõmmet. Puuraugu väärtuse määrab funktsioon analogWrite (pin, TÄHELEPANU), kus TÄHELEPANU muutub 0-255-ni, mis on otseselt võrdeline signaali puurauguga. Sketšis on valitud neli väärtust, kus mootor käivitub madalatel pööretel, kogub keskmisi, seejärel kõrgeid ja seiskub.

Kood:

int IN3 = 5; // Input3 подключен к выводу 5 
int IN4 = 4;
int ENB = 3;
void setup()
{
 pinMode (ENB, OUTPUT); 
 pinMode (IN3, OUTPUT);
 pinMode (IN4, OUTPUT);
}
void loop()
{
  // На пару выводов "IN" поданы разноименные сигналы, мотор готов к вращению
  digitalWrite (IN3, HIGH);
  digitalWrite (IN4, LOW);
  // подаем на вывод ENB управляющий ШИМ сигнал 
  analogWrite(ENB,55);
  delay(2000);
  analogWrite(ENB,105);
  delay(2000);
  analogWrite(ENB,255);
  delay(2000);
  // Останавливаем мотор, подав на вывод ENB сигнал низкого уровня. 
  // Состояние выводов "IN" роли не играет.
  analogWrite(ENB,0);
  delay(5000);
}

Kolmas näide

Kolmas näide pakub ühendada kaks mootorit kiiruse reguleerimine. Allolevas sketšis pööravad kaks mootorit sujuva kiiruse komplektiga

Kood:

int IN1 = 5; // Input1 подключен к выводу 5 
int IN2 = 4;
int IN3 = 3;
int IN4 = 2;
int ENA = 9;
int ENB = 3;
int i;
void setup()
{
  pinMode (EN1, OUTPUT);
  pinMode (IN1, OUTPUT);
  pinMode (IN2, OUTPUT);
  pinMode (EN2, OUTPUT);
  pinMode (IN4, OUTPUT);
  pinMode (IN3, OUTPUT);
}
void loop()
{
  digitalWrite (IN2, HIGH);
  digitalWrite (IN1, LOW); 
  digitalWrite (IN4, HIGH);
  digitalWrite (IN3, LOW); 
  for (i = 50; i <= 180; ++i)
  {
      analogWrite(EN1, i);
      analogWrite(EN2, i);
      delay(30);
  }
  analogWrite (EN1, 0);
  analogWrite (EN2, 0);
  delay(500);
  digitalWrite (IN1, HIGH);
  digitalWrite (IN2, LOW); 
  digitalWrite (IN3, HIGH);
  digitalWrite (IN4, LOW);
  for (i = 50; i <= 180; ++i)
  {
      analogWrite(EN1, i);
      analogWrite(EN2, i);
      delay(30);
  }
  analogWrite (EN1, 0);
  analogWrite (EN2, 0);
  delay(8000);
}

Veel natuke infot mootorite laialiajamise kohta ENABLE järelduste abil. Käivitamisel tarbib mootor voolu keskmiselt 4-6 korda rohkem kui nimiväärtus, järsul reversil aga veelgi rohkem. Sellist hüpet saab vähendada või üldse eemaldada, kui mootor sujuvalt mingi aja jooksul laiali ajada. Ülaltoodud sketš näitab just sellist lähenemist.

Eseliikuv auto

Komponendid:

  • 2- Vasak mootor;
  • L298N Mootori driver;
  • Patarei pesa;
  • 6 — Patarei;
  • Lüliti;
  • Arduino Uno R3;
  • 3 — Ultrasonic Distance Sensor (4-pin);
  • Juhtmed;

Tööpõhimõte:

Ühendamise skeem:

Kood:

// Robi v2.7

// Control of 2WD-1 robot platform using Arduino UNO.
// with obstacle avoidance using three HC-SR04 ultrasonic sensors.

// DISTANCE VARIABLES
const int trigPinFront = 3;
const int echoPinFront = 2;
const int trigPinLeft = 12;
const int echoPinLeft = 13;
const int trigPinRight = 8;
const int echoPinRight = 9;

// MOTORS VARIABLES
const int mot1f = 6;
const int mot1b = 5;
const int mot2f = 11;
const int mot2b = 10;
int mot_speed = 200; // motors speed

// LOGICS VARIABLES
const int dist_stop = 15;
const int side_stop = 9;

// TIMING VARIABLES
unsigned long previousMillis = 0;
const long interval = 100;  // interval in milliseconds

// INITIALIZATION
void setup() {
  pinMode(trigPinFront, OUTPUT);
  pinMode(echoPinFront, INPUT);
  pinMode(trigPinLeft, OUTPUT);
  pinMode(echoPinLeft, INPUT);
  pinMode(trigPinRight, OUTPUT);
  pinMode(echoPinRight, INPUT);
  
  pinMode(mot1f, OUTPUT);
  pinMode(mot1b, OUTPUT);
  pinMode(mot2f, OUTPUT);
  pinMode(mot2b, OUTPUT);
  Serial.begin(9600);
}

// BASIC PROGRAM CYCLE
void loop() {
  delay(3000);
  goto start;

  start:
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    previousMillis = currentMillis;
    
    int distanceFront = ping(trigPinFront, echoPinFront);
    int distanceLeft = ping(trigPinLeft, echoPinLeft);
    int distanceRight = ping(trigPinRight, echoPinRight);

    if (distanceFront <= dist_stop || distanceLeft <= side_stop || distanceRight <= side_stop) {
      motors_back();
      delay(300);
      motors_stop();
      delay(100);
      
      if (distanceFront <= dist_stop) {
        if (distanceLeft > distanceRight) {
          motors_left();
        } else {
          motors_right();
        }
        delay(140);
        motors_stop();
        delay(100);
      }
      
      if (distanceLeft <= side_stop || distanceRight <= side_stop) {
        if (distanceLeft > distanceRight) {
          motors_left();
        } else {
          motors_right();
        }
        delay(140);
        motors_stop();
        delay(100);
      }
    } else {
      motors_forward();
      delay(100);
    }
  }
  goto start;
}

// FUNCTION TO CHECK DISTANCE
int ping(int trigPin, int echoPin) {
  int distances[3];
  for (int i = 0; i < 3; i++) {
    digitalWrite(trigPin, LOW);
    delayMicroseconds(2);
    digitalWrite(trigPin, HIGH);
    delayMicroseconds(10);
    digitalWrite(trigPin, LOW);
    long duration = pulseIn(echoPin, HIGH);
    distances[i] = duration / 58;
  }
  
  // Sort the array and find the median
  for (int i = 0; i < 2; i++) {
    for (int j = i + 1; j < 3; j++) {
      if (distances[i] > distances[j]) {
        int temp = distances[i];
        distances[i] = distances[j];
        distances[j] = temp;
      }
    }
  }
  return distances[1];  // Median value
}

// MOTOR CONTROL FUNCTIONS
void motors_forward() {
  analogWrite(mot1f, mot_speed);
  analogWrite(mot2f, mot_speed);
  digitalWrite(mot1b, LOW);
  digitalWrite(mot2b, LOW);
}

void motors_back() {
  digitalWrite(mot1f, LOW);
  digitalWrite(mot2f, LOW);
  analogWrite(mot1b, mot_speed);
  analogWrite(mot2b, mot_speed);
}

void motors_stop() {
  digitalWrite(mot1f, LOW);
  digitalWrite(mot2f, LOW);
  digitalWrite(mot1b, LOW);
  digitalWrite(mot2b, LOW);
}

void motors_left() {
  analogWrite(mot1f, mot_speed);
  digitalWrite(mot2f, LOW);
  digitalWrite(mot1b, LOW);
  analogWrite(mot2b, mot_speed);
}

void motors_right() {
  digitalWrite(mot1f, LOW);
  analogWrite(mot2f, mot_speed);
  analogWrite(mot1b, mot_speed);
  digitalWrite(mot2b, LOW);
}

FOTO

Video

Kommentaatorid (uued võimalused):

analogWrite ()

Arduino analogWrite () funktsiooni kasutatakse analoogsignaalide genereerimiseks SIM-i pin-il. See funktsioon võimaldab määrata šim-signaali analoogväärtuse 0-st (täiesti välja lülitatud) kuni 255-ni (täiesti sisse lülitatud). Seda funktsiooni kasutatakse mootorite pöörlemiskiiruse juhtimiseks, kus tuleb muuta võimsustaset. Samamoodi kasutatakse LED-ide heleduse juhtimiseks.

IN1 ja IN2, IN3 ja IN4, ENA ja ENB.

Need on juhtivad järeldused.

IN1, IN2, IN3 ja IN4 — sisendpinnid (Input Pins), ENA ja ENB — sisendid mootori kiiruse juhtimiseks (Enable Pins).

IN1, IN2, IN3 ja IN4 on kasutusel, mootori pöörlemissuuna juhtimiseks ning ENA ja ENB kiiruse juhtimiseks.

for (i = 50; i <= 180; ++i)
 {
     analogWrite(EN1, i);
     analogWrite(EN2, i);
     delay(30);
 }

Antud kood Arduino jaoks kasutab tsüklit for, et muuta analoogsignaali väärtust EN1 ja EN2
piikidel 50 kuni 180 iga iteratsiooni vahel 30 millisekundilise
hilinemisega. See võimaldab järk-järgult suurendada pöörlemiskiirust 50
kuni 180. Niisamuti on LED-ide heledus tasapisi ära vajunud.

unsigned long previousMillis = 0;
const long interval = 100;

See kood on osa programmist Arduino IDE-le, mis aitab jälgida aega muutuja «previousMillis» ja «intervali» konstandi abil. Muutuv «previousMillis» hoiab eelmist aega ning konstant «interval» seab ajaintervalli, mille kaudu toimingud sooritatakse.

start:
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    previousMillis = currentMillis;

Selles koodis luuakse muutuja «currentMillis», mis saab jooksva aja funktsiooniga «millis () «. Seejärel kontrollitakse tingimust, kui praeguse aja ja eelmise aja vahe on suurem või võrdne intervalliga, siis uuendatakse «previousMillis» väärtust jooksvalt.

int ping(int trigPin, int echoPin) {
  int distances[3];

Massiiv kolme distantsimõõtmise hoidmiseks

for (int i = 0; i < 2; i++) {
    for (int j = i + 1; j < 3; j++) {
      if (distances[i] > distances[j]) {
        int temp = distances[i];
        distances[i] = distances[j];
        distances[j] = temp;
      }
    }
  }
  return distances[1];

See kood kogub esmalt kolm distantsimõõtu, sorteerib need kasvamise järgi ja tagastab keskmise. Keskmine väärtus tagab püsivama tulemuse, välistades võimalikud heited (ebanormaalsed mõõtmised).

||

Koodis on see või

if (distanceFront <= dist_stop || distanceLeft <= side_stop || distanceRight <= side_stop) {
      motors_back();
      delay(300);
      motors_stop();
      delay(100);

See koodijupp juhib robotseadet, sundides seda tagasi sõitma ja peatuma, kui avastatakse takistus liiga lähedal ees, vasakul või paremal.

Kasutamisvõimalused tavaelus:

Mootiri L298N

Mootiri L298N on elus kasutusel erinevates projektides, kus on vaja juhtida mootorite, näiteks robootika, automatiseerimise, modelleerimise ja muude elektroonikaseadmete pöörlemiskiirust ja -suunda, kus on vaja täpset ja tõhusat mootorijuhtimist.

Mootiri L298N on kasutusel erinevates seadmetes nagu robotid, automootori juhtimissüsteemid, automaatikasüsteemid, mobiiliplatvormid ja muud elektroonikaseadmed, kus on vaja mootorijuhtimist.

Mängumasin, masin juhtpuldil.

Arduino masinat saab tavaelus kasutada nutikate seadmete loomiseks, koduprotsesside automatiseerimiseks, meelelahutuseks, valgustuse, turvasüsteemide ja paljude muude ülesannete juhtimiseks.

Scroll to Top