domingo, 11 de agosto de 2013

Como fazer um robô seguidor de linha com motores de passo usando Arduino?

Um dos problemas que encontramos quando usamos o Arduino é que a biblioteca do motor de passo roda um motor de cada vez e não roda motores sincronizados. Para tanto, desenvolvemos um programa usando o While que sincronizava dois motores de passo:
/*Uso do While em motores de passo */
    //pinos de saída digital
    //passo direito
    int passo1 = 8;
    int passo3 = 9;
    int passo2 = 10;
    int passo4 = 11;
    //passo esquerdo
    int passo5 = 4;
    int passo6 = 5;
    int passo7 = 6;
    int passo8 = 7;
    //tempo de passo
    int passo = 25;
    //tempo para girar 90°
    int giro = 0;
   
    // ————————————————————————— Setup
    void setup() {
    // Seleciona motores
    //motor direito
    pinMode(passo1, OUTPUT);
    pinMode(passo2, OUTPUT);
    pinMode(passo3, OUTPUT);
    pinMode(passo4, OUTPUT);
    //motor esquerdo
    pinMode(passo5, OUTPUT);
    pinMode(passo6, OUTPUT);
    pinMode(passo7, OUTPUT);
    pinMode(passo8, OUTPUT);
    }
    // ————————————————————————— Loop
    void loop () {
while(giro<5){
      //para frente
    digitalWrite (passo4, HIGH);
    digitalWrite (passo5, HIGH);
    delay (passo);
    digitalWrite (passo4, LOW);
    digitalWrite (passo5, LOW);
    digitalWrite (passo3, HIGH);
    digitalWrite (passo6, HIGH);
    delay (passo);
    digitalWrite (passo3, LOW);
    digitalWrite (passo6, LOW);
    digitalWrite (passo2, HIGH);
    digitalWrite (passo7, HIGH);
    delay (passo);
    digitalWrite (passo2, LOW);
    digitalWrite (passo7, LOW);
    digitalWrite (passo1, HIGH);
    digitalWrite (passo8, HIGH);
    delay (passo);
    digitalWrite (passo1, LOW);
    digitalWrite (passo8, LOW);
    giro++;
}
    while (giro<5){
    //frente
    digitalWrite (passo1, HIGH);
    digitalWrite (passo8, HIGH);
    delay (passo);
    digitalWrite (passo1, LOW);
    digitalWrite (passo8, LOW);
    digitalWrite (passo2, HIGH);
    digitalWrite (passo7, HIGH);
    delay (passo);
    digitalWrite (passo2, LOW);
    digitalWrite (passo7, LOW);
    digitalWrite (passo3, HIGH);
    digitalWrite (passo6, HIGH);
    delay (passo);
    digitalWrite (passo3, LOW);
    digitalWrite (passo6, LOW);
    digitalWrite (passo4, HIGH);
    digitalWrite (passo5, HIGH);
    delay (passo);
    digitalWrite (passo4, LOW);
    digitalWrite (passo5, LOW);
  giro++;
  }
    }  

Este programa funciona bem mas a variável giro não retorna a 0 e, portanto, os motores não são reiniciados. quando colocamos isso nos comandos para seguir linha não funcionava direito, o motor ficava vibrando e não se mexia.
Para corrigir o problema, após o fim do while colocamos um comando para retornar o valor do giro a 0, permitindo que o motor de passo recomeçasse o giro:
...
    digitalWrite (passo3, LOW);
    digitalWrite (passo6, LOW);
    digitalWrite (passo4, HIGH);
    digitalWrite (passo5, HIGH);
    delay (passo);
    digitalWrite (passo4, LOW);
    digitalWrite (passo5, LOW);
  giro++;
  }//fim do while
giro=0;
    }    //fim do comando do motor

Depois disso, inserimos comandos para que o motor tivesse o passo simples (1000, 0100, 0010 e 0001) e o passo completo (1010, 0110, 0101 e 1001).
Assim temos o programa abaixo para seguir linha:
/* Programa para Projeto Robô Seguidor de Linha com 2 motores de passo sincronizados
Equipe Pequenos Cientistas 2012
*/
//variavel dos pinos analogicos
int IR1=2;
int IR2=3;
//int IR3=12;
//variáveis que armazenam os dados dos pinos
int VR1;
int VR2;
int VR3;

//variavel dos pinos digitais
//pinos de ativação dos motores
int L1 = 4;
int L2 = 5;
int L3 = 6;
int L4 = 7;
//pinos do passo
int L5 = 8;
int L6 = 9;
int L7 = 10;
int L8 = 11;
//tempo do passo
int passo = 20; //aumenta ou diminui a velocidade do motor

//valor de leitura do ir para branco
int maximo = 900;

//varíaveis que controlam o motor de passo
int passosporvolta=48;//distância que o motor percorre
int giro=0;

void setup() {
// configura o pino como saida
pinMode(L1, OUTPUT);
pinMode(L2, OUTPUT);
pinMode(L3, OUTPUT);
pinMode(L4, OUTPUT);
pinMode(L5, OUTPUT);
pinMode(L6, OUTPUT);
pinMode(L7, OUTPUT);
pinMode(L8, OUTPUT);

// configura o pino como entrada sensores
pinMode(IR1, INPUT);
pinMode(IR2, INPUT);
//pinMode(IR3, INPUT);

Serial.begin (9600);
}
void loop(){
giro==0;
// Faz a leitura do sensor
VR1 = digitalRead(IR1);
VR2 = digitalRead(IR2);
//VR3 = digitalRead (IR3);

Serial.print (VR1);
Serial.print (" ,");
Serial.print (VR2);
Serial.print (" ,");
//Serial.print (VR3);
//Serial.print (" ,");
Serial.println (giro);

if (VR1 < maximo||VR2 < maximo) {// if para branco
Serial.println ("Branco");
Serial.println ("Frente");
frente();
}//fim do if para branco

if (VR2 >= maximo||VR2 >= maximo){//if para preto
Serial.println ("Preto");
Serial.println ("Re");
re();
Serial.println ("Direita");
direita();
}//fim do if preto
}//fim do loop

void frente(){
while (giro<passosporvolta){
digitalWrite(L1, HIGH);
digitalWrite(L5, HIGH);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, HIGH);
digitalWrite(L6, HIGH);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, HIGH);
digitalWrite(L7, HIGH);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, HIGH);
delay (passo);
giro++;
  }//fim do while
  giro=0;
}//fim da função frente
void re(){
while (giro<2*passosporvolta){
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, HIGH);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, HIGH);
digitalWrite(L7, HIGH);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, HIGH);
digitalWrite(L6, HIGH);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, HIGH);
digitalWrite(L5, HIGH);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
giro++;
Serial.println (giro);
  }//fim do while
giro=0;
}//fim da função re

void direita(){
while (giro<2*passosporvolta){
digitalWrite(L1, HIGH);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, HIGH);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, HIGH);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, HIGH);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, HIGH);
digitalWrite(L3, HIGH);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, HIGH);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, LOW);
delay (passo);
giro++;
Serial.println (giro);
  }//fim do while
  giro=0;
}//fim da função direita

void esquerda(){
  while (giro<2*passosporvolta){
digitalWrite(L1, LOW);
digitalWrite(L5, HIGH);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, HIGH);
digitalWrite(L3, HIGH);
digitalWrite(L7, LOW);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, HIGH);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, HIGH);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, HIGH);
digitalWrite(L5, LOW);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, HIGH);
delay (passo);
Serial.println (giro);
  }//fim do while
 giro=0;
 }//fim da função esquerda

void ataque(){
while (giro<passosporvolta){
digitalWrite(L1, HIGH);
digitalWrite(L5, HIGH);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, HIGH);
digitalWrite(L7, HIGH);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, HIGH);
digitalWrite(L6, HIGH);
digitalWrite(L3, HIGH);
digitalWrite(L7, HIGH);
digitalWrite(L4, LOW);
digitalWrite(L8, LOW);
delay (passo);
digitalWrite(L1, LOW);
digitalWrite(L5, LOW);
digitalWrite(L2, HIGH);
digitalWrite(L6, HIGH);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, HIGH);
delay (passo);
digitalWrite(L1, HIGH);
digitalWrite(L5, HIGH);
digitalWrite(L2, LOW);
digitalWrite(L6, LOW);
digitalWrite(L3, LOW);
digitalWrite(L7, LOW);
digitalWrite(L4, HIGH);
digitalWrite(L8, HIGH);
delay (passo);
giro++;
Serial.println (giro);
  }//fim do while
  giro=0;
}//fim da função frente

Vídeo do teste:


Nenhum comentário:

Postar um comentário