SENSOR DE APROXIMAÇÃO C/ INDICAÇÃO DE DISTÂNCIA COM LEDS – C/ PIC 16F628A E TSOP1838 (REF257)

Obtendo uma referência de distâncias por meio de indicação com leds…

Gostaria de fazer um sensor de aproximação que permita indicar a distância aproximada de um objeto detectado em seu campo de ação? Esta montagem experimental faz exatamente isto. Veja o esquema abaixo:

SENSOR_APROX_LED_IR

Usando um led emissor de infravermelho e um sensor integrado TSOP1838 ou similar, podemos ter um indicador de distância que poderá ser usado em muitas aplicações. Por exemplo, poderia ser aperfeiçoado para se tornar talvez um sensor de estacionamento para veículos.
Nesta montagem foi usado o PIC 16F628A, por ter internamente o módulo CCP, onde é configurado para se obter uma saída PWM no pino 9. Também dispõem de varias saídas para poder acionar os leds que formarão uma ‘barra’ em funcionamento.

FUNCIONAMENTO DESTE SENSOR

Realizando testes com este tipo de sensor notei que a sensibilidade é alterada grandemente pela corrente que circula no led infravermelho, entre outros fatores. Pensei: E se pudesse controlar a corrente com o próprio PIC ao invés de usar um potenciômetro? A distância seria então proporcional a esta corrente que circula! Fazendo os testes com o PWM do PIC 16f628A obtive sucesso além do esperado!
Em princípio, funciona assim:
O sensor faz leituras continuas. A cada leitura é verificado se foi detectado um objeto no campo de ação do sensor. Se a rotina ‘sensor_ir()’ retornar ‘1’, então tem um objeto, e se ‘0’ não tem.
Se retornar ‘1’ incrementamos um contador nomeado de ‘pwm’ até 255 e se retornar ‘0’ decrementamos até chegar a zero.
O valor deste contador nomeado de ‘pwm’ é carregado no registrador CCPR1L. Será gerado uma tensão no pino 9 de acordo com o valor deste contador. Note que o pino 9 alimenta o ânodo do led infravermelho (LD271), e irá controlar o alcance dele (sensibilidade).
O valor do contador ‘pwm’ também definirá quantos leds ficarão acesos. A cada leitura do sensor será atualizado também os leds.
Assim, quando não existe objeto detectado, todos os leds acenderão e o contador ‘pwm’ estará na máxima contagem (255).
Quando um objeto entra no campo de ação e permanece estático, a cada leitura o contador ‘pwm’ será decrementado resultando em diminuição da corrente do led. A sensibilidade cairá até que o objeto não seja mais detectado. Isto faz com que o contador volte a ser incrementado na próxima leitura do sensor. Dá para perceber que ficará oscilando entre incremento e decremento em cada leitura, para uma dada posição do objeto em relação ao sensor.
Se o objeto ficar mais próximo, menos sensibilidade é necessária e portanto menos corrente no led infravermelho. Os leds da ‘barra’ irão indicar isto. Temos 8 leds: Sem objeto no campo de ação todos irão acender. A medida que o objeto se aproxima, irá apagando um a um, até que fique aceso um único led. Este indica que a distância mínima foi alcançada.

LIMITAÇÕES
As medidas devem ser tomadas como aproximadas uma vez que depende muito da cor do objeto, seu grau de polimento, e também o tamanho. Objetos brancos e metálicos acionam os leds com distâncias maiores que objetos pretos ou opacos.
Como não fiz nenhum estudo profundo desta técnica, mas apenas testes práticos típicos de hobistas, poderá ter dificuldades que possam limitar seu uso em determinadas aplicações, especialmente as que envolvem segurança.

Obs. Esta montagem é experimental, sendo de caráter didático, montada apenas em placa experimental (do tipo “Breadboard”), sujeita a “bugs” ainda não detectados. Está sendo fornecido os arquivos para que cada hobista possa alterar o programa segundo suas necessidades.

Segue pasta zipada com os arquivos da montagem:

sensor_aprox_leds__

Abaixo temos um vídeo caseiro com o funcionamento da montagem:

Manuais:
PIC16F628A DATASHEET
TSOP1838 DATASHEET
LD271 DATASHEET

Curiosidades:
Esportes da antiguidade e a importância de vencer
Pneus — sua vida pode depender deles!
Histórias de sobreviventes do tsunami no Japão
Pouso de emergência!
Insetos comestíveis — uma refeição inesquecível
A bela cor do céladon de Koryo

Outros assuntos:
O que a Bíblia diz sobre as origens do Halloween?
A Bíblia contém um registro exato da vida de Jesus?
O que faz alguém ser um bom pai ou uma boa mãe?
Como ser feliz no casamento?
Quando uma amizade se torna íntima demais
Como se livrar do ressentimento

Vídeos:
Como enfrentar o bullying sem partir para a briga
Quem é o Autor da Bíblia?
Será que é amor ou paixão?
Tenha mais paciência
Fale a verdade
Eu me cansei das religiões

Até o próximo artigo!

7 comments on “SENSOR DE APROXIMAÇÃO C/ INDICAÇÃO DE DISTÂNCIA COM LEDS – C/ PIC 16F628A E TSOP1838 (REF257)

  1. Boa Tarde Larios! Como faço para fazer os led , só acenderem com a aproximação , ou seja , ao contrario de como foi apresentado. Desde já parabenizo pelo o seu blog !

    1. Olá Dumont!
      Tente alterar o arquivo C e recompilar com CCS C Compiler desta forma:
      /*******************************************************************************

      Sensor de Aproximação c/ Indicação Visual por Leds
      (Alterado para manter leds acesos e ao aproximar vai apagando um a um)

      c/ PIC 16F628A

      Autor: Cláudio Lários

      Data: 30/10/2016

      Funcionamento: Detectar objetos que passam na frente do sensor usando luz
      infravermelho e indicar sua distância aproximada por meio de 8 leds.
      Utiliza o método da reflexão.

      Usado compilador CCS C versão 3.200

      Uso didático

      Este arquivo é parte integrante do blog Lários.Tecnologia.WS

      ******************************************************************************/
      #include <16F628A.h>
      #use delay(clock=4000000)
      #fuses NOWDT,INTRC_IO, NOCPD, NOPROTECT, NOMCLR, NOPUT, NOBROWNOUT,NOLVP //configuração

      //bytes
      #byte TMR0 = 0x01
      #byte TRISA = 0x85
      #byte TRISB = 0x86
      #byte PORTA = 0x05
      #byte PORTB = 0x06

      #byte OPTION_REG = 0x81
      #byte CMCON = 0x19
      #byte PR2 = 0X92
      #byte CCP1CON = 0X17
      #byte CCPR1L = 0X15
      #byte T2CON = 0X12

      //bits
      #bit IN = 0x5.5 //entrada do fotoreceptor – pino 4
      #bit LEDIR = 0x6.2 //led emissor de infrared – pino 8

      #bit t0if = 0xb.2 //flag de over flow do timer0
      #bit f_int0 = 0xb.5

      #define FILTRO1 20 //49

      //variáveis globais
      unsigned int16 cont1;
      unsigned int8 pwm;
      unsigned cont_led;

      /*******************************************************************************
      Rotina do Sensor de Aproximação
      *******************************************************************************/

      unsigned int1 sensor_ir(){
      //Para TSOP1838 ou similar (KSM603LM,VS1838) de frequência = 38khz

      unsigned int8 pulso,b;
      pulso=0;

      for(b=0;b<60;b++){ //gera 80 pulsos na frequência próxima de 38 khz
      LEDIR=0;
      delay_us(12);
      LEDIR=1;
      if(!IN)pulso++; else delay_cycles( 2 );//testa se pulso chegou no receptor
      }
      LEDIR=0;
      delay_ms(8);
      if(pulso > FILTRO1) return (1); else return (0);

      }

      /*******************************************************************************
      ROTINA MAIN
      *******************************************************************************/

      void main() {

      setup_counters(RTCC_INTERNAL,RTCC_DIV_1);//n usado
      setup_comparator(NC_NC_NC_NC);//desliga comparadores internos
      setup_vref(FALSE);//desliga voltagem de referência
      TRISA=0B11110000;//ajusta saídas e entradas
      TRISB=0B00000011;//ajusta saídas e entradas
      cont1=0;//zera contador
      pwm=255;//ajusta para o máximo
      PR2=0XFF;
      T2CON=4;//liga timer 2 c/ prescaller/1
      CCPR1L=pwm;//duty cycle
      PORTA=00001111;//todos leds acesos
      PORTB=11110000;
      CCP1CON=0B00001111;
      delay_ms(10); //delay inicial
      /*******************************************************************************
      LAÇO PRINCIPAL DE REPETIÇÃO
      *******************************************************************************/

      for(;;){

      if(sensor_ir()){
      if(pwm>4)pwm-=4;
      }
      else{
      if(pwm<0xfc)pwm+=4;
      }

      CCPR1L=pwm;//atualiza o duty cycle

      if(pwm>=24){ //24
      cont_led= pwm/24;
      }
      else{
      cont_led=0;
      }

      //***************************************************************************************
      //alterações para obter leds que se apagam a medida que se aproxima um objeto

      // PORTA&=0XF0;//apaga todos leds
      PORTA|=0X0F;//acende todos leds

      // PORTB&=0X0F;//apaga todos leds
      PORTB|=0XF0;//acende todos leds

      if(cont_led>=2)cont_led-=2;//elimina

      //if(cont_led<=1){PORTB|=0B00010000;} if(cont_led<=1){PORTB&=0B11101111;} // else if(cont_led<=2){PORTB|=0B00110000;} else if(cont_led<=2){PORTB&=0B11001111;} //else if(cont_led<=3){PORTB|=0B01110000;} else if(cont_led<=3){PORTB&=0B10001111;} // else if(cont_led<=4){PORTB|=0B11110000;} else if(cont_led<=4){PORTB&=0B00001111;} // else if(cont_led<=5){PORTB|=0B11110000; PORTA|=0B00000001;} else if(cont_led<=5){PORTB&=0B00001111; PORTA&=0B11111110;} // else if(cont_led<=6){PORTB|=0B11110000; PORTA|=0B00000011;} else if(cont_led<=6){PORTB&=0B00001111; PORTA&=0B11111100;} //else if(cont_led<=7){PORTB|=0B11110000; PORTA|=0B00000111;} else if(cont_led<=7){PORTB&=0B00001111; PORTA&=0B11111000;} // else if(cont_led<=8){PORTB|=0B11110000; PORTA|=0B00001111;} else if(cont_led<=8){PORTB&=0B00001111; PORTA&=0B11110000;} //************************************************************************* }//for() }//main Infelizmente, não pude testar, pois ainda estou afastado das minhas atividades por motivos médicos. Cláudio Lários

      1. Muito obrigado, Cláudio Lários , o meu circuito já esta pronto , e funcionando perfeitamente, mas agora irei recopilar , com esta alteração .
        E assim, que possível, estarei informando os resultados aqui.
        Eu só tenho mesmo que lhe agradecer , pelo seu trabalho e por dividir os seus conhecimentos . Isso é muito nobre da sua parte!
        Desejo melhoras à você!
        E mais uma vez, obrigado!

  2. Boa tarde Larios… Gostaria de saber qual a versão do seu compilador CCS Compiler para não acontecer de na hora de eu compilar um arquivo.C do seu blog, não haver incompatibilidades com outros CCS Compiler de outras versões. Desde já parabenizo pelo blog e por sua atitude muito nobre de divulgar conhecimento.

    1. Olá Batmonstro!
      Uso V 3.200. Em outras versões poderá ter que configurar a saida padrão para rs232 mesmo que não use na sua aplicação. Veja o ajuda de seu compilador.
      Cláudio

Comments are closed.

Back To Top