Vous êtes sur la page 1sur 21

CENTRO UNIVERSITÁRIO SALESIANO de SÃO PAULO

UNIDADE de ENSINO de CAMPINAS

CAMPUS SÃO JOSÉ

Projeto Final
LINE CAR

Alunos: Maurício Santinon RA: 05030389


Leandro V. de Mendonça RA: 05030060
Filipe Castreze Silva RA: 05030348
Wanderson de Oliveira Mota RA: 05030481
Turma: GEEN6A
Professor: Wlamir

Eletrônica Digital I

11 / 2007
PROJETO_ELETRÔNICA DIGITAL I
LINE CAR
Introdução

O projeto consiste em criar um veículo independente, ou seja, não conectado ao


computador. O objetivo deste veículo é seguir uma linha desenhada representando um
circuito. Para realizar tal atividade serão utilizados sensores infravermelhos. O controle
do veículo será feito através de um microcontrolador.

Projeto Mecânico

O veículo a ser montado será construído sobre o chassi de um carrinho, este carrinho foi
adquirido pela equipe, pois a mesma verificou que o carrinho atende as principais
necessidades do projeto.
O veículo funcionará com quatro motores DC, que farão a tração das quatro rodas de
maneira independente. Os sensores utilizados para a orientação do veículo serão fotos
transistores, sendo feito o uso de três sensores para esta tarefa.

Projeto da pista

A pista de prova consistirá em uma cartolina branca onde será pintada uma linha preta
em diversas direções. A espessura da linha será definida de tal maneira que quando o
sensor passar sobre ela, o mesmo varia entre os níveis lógicos 0 e 1.

Modelo de pista
Esquema elétrico do projeto

Projeto eletromecânico

O veículo será movimentado através de quatro motores DC ligados às quatro rodas.


Para a alimentação destes motores será usada uma bateria de 9 v.
Para a medição do consumo dos motores foram feitos testes com o veículo em
movimento e parado, também foram feitos testes com o circuito de controle acionado e
não acionado. Um dos testes foi feito no piso do laboratório, outro com as rodas do
veículo suspensas. O controle do motor é realizado através de um sinal PWM gerado
pelo microcontrolador, tendo como drive e controle de polaridade um circuito integrado
que atua como ponte-H.

Projeto do microcontrolador

O microcontrolador utilizado foi o ATmega8. A escolha foi realizada por o mesmo


conter 3 controles PWM (Pulse width modulation), sendo dois deles de 16-bits e outro
de 8 bits. Além disso, este microcontrolador possui 8Kbytes de memória Flash, um
clock interno de 16 MHz, e 3 portas paralelas, o que é suficiente para geramos todos os
controles.

Projeto do sistema de alimentação

Para alimentar os quatro motores foi utilizada uma bateria de 9 v. Já os circuitos de


controle e os sensores são alimentados por duas pilhas de 3 v ligadas em série. Portanto,
através dos cálculos preliminares feitos durante o desenvolvimento do projeto, obtemos
um sistema coerente de alimentação que foi verificado na prática.

Projeto do software

O software de para este projeto, foi desenvolvido com base em um timer que gera o
processo de pulling, que funciona fazendo com que o microcontrolador execute funções
diferenciadas tendo uma base te tempo real como referencia. O software desenvolvido
neste projeto possui uma base de tempo de 10ms, que pode ser multiplicada de acordo
com a necessidade de cada tarefa a ser realizada.
Para o controle dos motores, foram usados os sinais PWM, no modo de Fast-PWM, que
que tem seu valor de Duty-cicle atualizado a cada 100ms.
A leitura dos sensores é realizada continuamente, sem base de tempo, para que qualquer
mudança detectada, seja rapidamente computada, gerando uma mudança no duty-cicle e
polaridade dos motores.
Este software possui 2 etapas principais:
• A primeira etapa tem duração de 2 segundos, e tem como objetivo controlar a
aceleração do carro, fazendo com que os motores alcancem sua velocidade
máxima.
• A segunda etapa consiste na leitura dos sensores, controle do PWM e polaridade
dos motores, com o objetivo de fazer o carro seguir a linha preta com maior
precisão possível.

CLK CLK/8 CLK/64 CLK/256 CLK/1024


Freq. (Hz) 8000000 1000000 125000 31250 7812,5
1,00E- 8,00E- 3,20E-
Periodo (s) 1,25E-07 06 06 05 1,28E-04
4,88E-10

Timer (ms) = 1,00E-02 Valor do timer 0


CLK 80000,00 79744
CLK/8 10000,00 9744
CLK/64 1250,00 994
CLK/256 312,50 -57
CLK/1024 78,13 178

Código fonte do projeto

#include <stdint.h>
#include <stdlib.h>
#include <avr/io.h>
#include <avr/pgmspace.h>
#include <avr/interrupt.h>
#include <math.h>
#include <string.h>
#include "timer.h"

#define IR1_atv bit_is_set(PINB,5) // sensores infra-red


#define IR2_atv bit_is_set(PINB,7)
#define IR3_atv bit_is_set(PINB,6)
#define IR1_des bit_is_clear(PINB,5) // sensores infra-red
#define IR2_des bit_is_clear(PINB,7)
#define IR3_des bit_is_clear(PINB,6)

#define front_left_light_atv PORTD = PORTD &~_BV(0); //luz dianteira esquerda


#define front_left_light_des PORTD = PORTD | _BV(0);

#define front_right_light_atv PORTD = PORTD &~_BV(1); //luz dianteira direita


#define front_right_light_des PORTD = PORTD | _BV(1);

#define rear_left_light_atv PORTD = PORTD &~_BV(2); //luz traseira esquerda


#define rear_left_light_des PORTD = PORTD | _BV(2);

#define rear_right_light_atv PORTD = PORTD &~_BV(3); //luz traseira direita


#define rear_right_light_des PORTD = PORTD | _BV(3);

#define front_beams_atv PORTD = PORTD &~_BV(4); // farois dianteiros


#define front_beams_des PORTD = PORTD | _BV(4);

#define foward_M1 PORTC = (PORTC & ~_BV(3))| _BV(2); //Movimentação Motor 1


- Traseiro esquerda
#define rewind_M1 PORTC = (PORTC & ~_BV(2))| _BV(3);
#define stop_M1 PORTC = (PORTC &~_BV(2)&~_BV(3));

#define foward_M2 PORTC = (PORTC & ~_BV(5))| _BV(4); //Movimentação Motor 2


- Traseiro direito
#define rewind_M2 PORTC = (PORTC & ~_BV(4))| _BV(5);
#define stop_M2 PORTC = (PORTC &~_BV(4)&~_BV(5));

#define foward_M3 PORTC = (PORTC &~_BV(1))| _BV(0); //Movimentação Motor 3


- Dianteiro esquerdo
#define rewind_M3 PORTC = (PORTC &~_BV(0))| _BV(1);
#define stop_M3 PORTC = (PORTC &~_BV(0)&~_BV(1));

#define foward_M4 PORTB = (PORTB &~_BV(4))| _BV(0); //Movimentação Motor 4


- Dianteiro direito
#define rewind_M4 PORTB = (PORTB &~_BV(0))| _BV(4);
#define stop_M4 PORTB = (PORTB &~_BV(0)&~_BV(4));

#define night_sensor_atv bit_is_set(PINC,6)

#define curva_direita 1
#define curva_esquerda 2
#define reta 3
#define usado 10
#define nao_usado 20

#define k_diminui_diant 12 // 5%
#define k_aumenta_diant 12 // 5%
#define k_diminui_tras 51 // 5%
#define k_aumenta_tras 51 // 5%

int valor_pwm,valor_pwm2,valor_pwm3,etapa_flag=0;
int status_direcao,status_freio;

void init_port(void)
{
PORTB = 0xe0;
PORTC = 0xc0;
PORTD = 0xff;
DDRB = _BV(4)|_BV(0);
DDRC = _BV(0)|_BV(1)|_BV(2)|_BV(3)|_BV(4)|_BV(5);
DDRD = _BV(0)|_BV(1)|_BV(2)|_BV(3)|_BV(4)|_BV(5)|_BV(6)|_BV(7);
}

void PWM_init(void)
{
ICR1H = 0x03; // set the TOP value for the PWM to 0x3FF = 10bit
ICR1L = 0xFF;

OCR1AH = 0x00;
OCR1AL = 0xF0; // set a initial value in the OCR1A-register
OCR1BH = 0x00;
OCR1BL = 0xF0; // set a initial value in the OCR1A-register

TCCR1A =
(1<<COM1A1)|(1<<COM1A0)|(1<<COM1B1)|(1<<COM1B0)|(1<<WGM11)|(1<<W
GM10); // set OC1A/B on upcounting, clear on downcounting
TCCR1B = (1<<WGM12) | (1<<CS10); // select Fast PWM mode, and set
CLK(I/O) (From prescaler)
}

void PWM2_init(void)
{
OCR2 = 0xFF; // set a initial value in the OCR2

TCCR2 =
(1<<COM21)|(1<<COM20)|(1<<WGM21)|(1<<WGM20)|(1<<WGM21)|(1<<CS20); //
set OC1A/B on upcounting, clear on downcounting
// select Fast PWM mode, and set
CLK(I/O) (From prescaler)
}

void saida(void)
{
int Offset_OCR1;
unsigned char PWM_8LSB;
unsigned char PWM_2MSB;
Offset_OCR1 =valor_pwm; // copy the OFFSET to the Offset_OCR1A
// fill up the 10 bit in the OCR1A register
if(Offset_OCR1 > 0x03FF) // if the Offset_OCR1A is beyond the maximum
value of OCR1A in 10-bit mode
Offset_OCR1 = 0x03FF; // write 0x3FF to it.

PWM_8LSB = Offset_OCR1; // load the 8LSB to PWM_8LSB


Offset_OCR1 >>= 8; // move the value in Offset_OCR1 8 times to the
right
PWM_2MSB = Offset_OCR1; // load the 2MSB int

OCR1AH =PWM_2MSB; // write the high byte of the OCR1A/B registers


OCR1AL =PWM_8LSB; // write the low byte of the OCR1A/B registers

Offset_OCR1 =valor_pwm2; // copy the OFFSET to the Offset_OCR1A


// fill up the 10 bit in the OCR1A register
if(Offset_OCR1 > 0x03FF) // if the Offset_OCR1A is beyond the maximum
value of OCR1A in 10-bit mode
Offset_OCR1 = 0x03FF; // write 0x3FF to it.

PWM_8LSB = Offset_OCR1; // load the 8LSB to PWM_8LSB


Offset_OCR1 >>= 8; // move the value in Offset_OCR1 8 times to the
right
PWM_2MSB = Offset_OCR1; // load the 2MSB int

OCR1BH =PWM_2MSB; // write the high byte of the OCR1A/B registers


OCR1BL =PWM_8LSB; // write the low byte of the OCR1A/B registers
}

void saida2(void)
{
OCR2 = valor_pwm3;
}

void zera_tempo1(void)
{
if (tempo[1] > 10)
tempo[1]=0;
}

void zera_tempo3(void)
{
if (tempo[3] > 100)
tempo[3]=0;
}

void night_mode(void)
{
if (night_sensor_atv)
{
front_beams_atv;
rear_left_light_atv;
rear_right_light_atv;
}
}

void main(void)
{

init_port();//inicializa portas
PWM_init();//inicializa PWM1
PWM2_init();//inicializa PWM2
Timer0_init();//inicializa timer0
tempo[0]=0;// zera constantes de tempo
tempo[1]=0;
tempo[2]=0;
tempo[3]=0;
tempo[4]=0;
sei();//ativa interrupções

valor_pwm=0x0000;
valor_pwm2=0x0000;
saida();
valor_pwm3=0x00;
saida2();

stop_M1;
stop_M2;
stop_M3;
stop_M4;

while(1)
{

//night_mode();

front_beams_atv;
rear_left_light_atv;
rear_right_light_atv;

if (tempo[2] > 100)


tempo[2]=0;

if (tempo[0]<=200 && etapa_flag == 0) //2s Estado inicial


{
zera_tempo1();
if(IR1_atv) // curva a esquerda
{
rewind_M1;
foward_M2;
stop_M3;
foward_M4

front_left_light_atv
front_right_light_des

if (valor_pwm3 < 127)//PWM2 ++5%:50% traseiro


{
if(tempo[1] == 10)//100 ms
{
valor_pwm3=valor_pwm3+k_aumenta_diant;
saida2();
tempo[1]=0;
}
}
if (valor_pwm2 < 255)// PWM1A ++5%:50%, PWM1B ++5%:25%
dianteiro
{
if(tempo[1] == 10)
{
valor_pwm= valor_pwm+(k_aumenta_tras*2);
valor_pwm2=valor_pwm2+k_aumenta_tras;
saida();
tempo[1]=0;
}
}
}

if(IR2_atv && IR1_des || IR3_des) //linha reta


{
foward_M1;
foward_M2;
foward_M3;
foward_M4;

front_left_light_des
front_right_light_des

if (valor_pwm3 < 127)//PWM2 ++10%:50%


{
if(tempo[1] == 10)
{
valor_pwm3=valor_pwm3+k_aumenta_diant;
saida2();
tempo[1]=0;

}
}
if(tempo[1] == 10)
{
if (valor_pwm < 511)// PWM1A ++5%:50%, PWM1B
++5%:50%
{
valor_pwm= valor_pwm + k_aumenta_tras;
valor_pwm2=valor_pwm2 + k_aumenta_tras;
saida();
tempo[1]=0;
}
}
}
if(IR3_atv) // curva a direita
{

foward_M1;
rewind_M2;
foward_M3;
stop_M4;

front_left_light_des
front_right_light_atv

if (valor_pwm3 < 127)//PWM2 ++5%:50%


{
if(tempo[1] == 10)
{
valor_pwm3=valor_pwm3+ k_aumenta_diant;
saida2();
tempo[1]=0;
}
}
if (valor_pwm2 < 255)// PWM1A ++5%:25%, PWM1B ++5%:50%
{
if(tempo[1] == 10)
{
valor_pwm2= valor_pwm2 + (k_aumenta_tras*2);
valor_pwm=valor_pwm + k_aumenta_tras;
saida();
tempo[1]=0;
}
}
}
if( IR2_des )
{
stop_M1;
stop_M2;
stop_M3;
stop_M4;
valor_pwm=0x0000;
valor_pwm2=0x0000;
valor_pwm3=0x0000;
saida();
saida2();
}

else // Estado de movimento


{
zera_tempo1();
etapa_flag=1;
if(IR1_atv ) // curva a esquerda
{
status_direcao = curva_esquerda;

if ((status_direcao == reta || status_direcao == curva_direita) &&


status_freio == nao_usado)
{

zera_tempo3();
if(tempo[3] < 100) //freia durante 500ms
{
status_freio=nao_usado;
rewind_M3;
rewind_M4;
tempo[3]=0;

}
if(tempo[3] == 100)
{
status_freio=usado;
stop_M3;
foward_M4;
}
}

rewind_M1;
foward_M2;
rewind_M3;
foward_M4;

front_left_light_atv
front_right_light_des

if (valor_pwm3 != 255)//PWM2 --5%:15%


{

if(tempo[1] == 10)//100 ms
{
valor_pwm3=valor_pwm3 + k_aumenta_diant;
saida2();
tempo[1]=0;
}
}
if (valor_pwm != 1023)// PWM1A 50%, PWM1B -5%:10%
{
if(tempo[1] == 10)
{
valor_pwm = valor_pwm - k_aumenta_tras;
saida();
tempo[1]=0;
}
}
}

if(IR2_atv && (IR1_des && IR3_des)) //linha reta


{
status_direcao = reta;

foward_M1;
foward_M2;
foward_M3;
foward_M4;

front_left_light_des
front_right_light_des

if (valor_pwm3 < 255)//PWM2 ++5%:50%


{
if(valor_pwm3 < 255 )

if(tempo[1] == 10)
{
valor_pwm3=valor_pwm3 + k_aumenta_diant;
saida2();
tempo[1]=0;
}
}
if(tempo[1] == 10)
{
if (valor_pwm < 1023)// PWM1A ++5%:50%, PWM1B
++5%:50%
{
valor_pwm= valor_pwm + k_aumenta_tras;
valor_pwm2=valor_pwm2 + k_aumenta_tras;
saida();
tempo[1]=0;
}
}
}
if(IR3_atv) // curva a direita
{

status_direcao = curva_direita;

if ((status_direcao == reta || status_direcao == curva_esquerda) &&


status_freio == nao_usado )
{
status_freio=usado;
zera_tempo3();
if(tempo[3] <= 100) //freia durante 1s
{
status_freio=nao_usado;
rewind_M3;
rewind_M4;
tempo[3]=0;
}
if(tempo[3] == 100)
status_freio=usado;
}

foward_M1;
rewind_M2;
foward_M3;
rewind_M4;

front_left_light_des
front_right_light_atv

if (valor_pwm3 > 39)//PWM2 --5%:15%


{

if(tempo[1] == 10)//100 ms
{
valor_pwm3=valor_pwm3 = k_aumenta_diant;
saida2();
tempo[1]=0;
}
}
if (valor_pwm2 > 102)// PWM1A --5%:5%, PWM1B 50%
{
if(tempo[1] == 10)
{
valor_pwm2 = valor_pwm2 - k_aumenta_tras;
saida();
tempo[1]=0;
}
}*/
}

if( IR2_des && (IR1_des || IR2_des))


{
stop_M1;
stop_M2;
stop_M3;
stop_M4;
valor_pwm=0x0000;
valor_pwm2=0x0000;
valor_pwm3=0x0000;
saida();
saida2();
}

}
}//fim while
}//fim do main
Esquema elétrico do gravador AVR para o software

Componentes utilizados na montagem do projeto

QTD. Descrição
1 Conector DB9
4 LED_Branco
2 LED_laranja
4 LED_red
5 Resistor, 560Ohm_5%
2 Resistor, 510Ohm_5%
5 Resistor, 330Ohm_5%
3 Resistor, 100Ohm_5%
3 Resistor, 2.2kOhm_5%
3 Transistor_NPN, BC548B
16 Diodo, 1N4001
Microcontrolador
1 ATmega8
2 L293
1 Socket DIP-28
2 Socket DIP-16
4 Motores DC 9V
Fluxogramas do projeto

Inicialização: M1,M2,M3 e M4 = 00
Bibliotecas,Defines, PWM1A,PWM1B e
Funções PWM2 = 0%
Inicia leituras
sensores IR

Case dos sensores IR


Estado incial

Case: IR1 e IR2 true: Case: IR2 true: Case: IR2 e IR3 true:
Curva à esquerda Linha reta Curva à direita
A cada 100ms: A cada 100ms: A cada 100ms:
PWM2 ++ 2% : 100% PWM2 ++ 10% :100% PWM2 ++ 2% :
PWM1A ++ 10% : 100% PWM1A ++ 10%:100% PWM1A ++ 10% : 100%
PWM1B ++ 5% : 50% PWM1B ++ 10% :100% PWM1B ++ 5% : 50%

2s rodando

Case dos sensores IR


Estado movimento

Case: IR1 e IR2 true: Case: IR2 true: Case: IR2 e IR3 true:
Curva à esquerda Linha reta Curva à direita
A cada 100ms: A cada 100ms: A cada 100ms:
PWM2 -- 2% : 30% PWM2 ++ 10% :100% PWM2 --2% : 30%
PWM1A mantém 100% PWM1A ++ 10%:100% PWM1B mantém 100%
PWM1B -- 5% : 5% PWM1B ++ 10% PWM1A ++ 5% : 50%
:100%
IR1 IR2 IR3

M3 M4

M1 M2
Conclusões e dificuldades encontradas pela equipe de desenvolvimento
Após o término do projeto, concluímos que o resultado final foi satisfatório. Durante as
etapas tivemos vários problemas com relação à montagem do carro, pois a idéia em
princípio era utilizar dois motores DC nas rodas traseiras e uma roda “boba” na
dianteira, mas devido ao peso da carcaça do carro isso foi inviável.
A opção então foi utilizar mais dois motores DC na dianteira, mas isso aumentou o
custo do projeto, pois tivemos que construir mais um circuito driver para controlar estes
motores e também mudanças no software, se tornando mais complexo.
Outra grande dificuldade na montagem do projeto foi adequar as placas de circuito ao
carro, pois foram diversas placas (dois driver’s, sensores, alimentação) interligadas.
Também houve algumas dificuldades no ajuste de sensibilidade do sensor, uma vez que
é usado um divisor de tensão para polarizar o transistor, foi preciso calcular os valores
de resistência, fazendo vários testes levando em conta a luminosidade do ambiente e a
altura em que instalaríamos o sensor no carro.
Posteriormente, partimos para os testes práticos, sendo somente necessários ajustes no
software, tal como velocidade do carro, reversão das rodas nas curvas. Após isto,
percebemos um funcionamento quase ideal, pois o mesmo apresentou dificuldades na
hora de realizar curvas.
Fotos do Projeto

Vous aimerez peut-être aussi