Acelerômetro Digital via I²C
Autor: Jean Carlos | Publicado: 2013-01-19T18:12:00-08:00

Olá pessoal… depois do jejum de post’s resolvi postar algo um pouco mais complexo para me redimir um pouco… se bem que acredito que a leitura será interessante e muito agradável pois se trata de uma tecnologia atual e que já faz parte do nosso cotidiano, vamos implementar o uso de um acelerômetro digital com comunicação via I²C. Acelerômetro O acelerômetro consiste em um dispositivo micro eletromecânico (MEMS) que utiliza-se de nanotecnologia para construção de sensores que medem a grandeza de aceleração em objetos.  Para conseguir efetuar a leitura desta grandeza, este componente possui em seu interior uma massa móvel contendo várias placas que interagem com placas fixas ao ci, formando desta maneira um sistema capacitivo que altera o valor da capacitância conforme o movimento da massa móvel, ou seja, a cada movimento no componente temos uma informação disponível relacionada a um dos eixos.   A empresa ST Microeletronics desenvolve a muitos anos essa tecnologia e hoje conta com seus MEMS instalados em muitos equipamentos, desde pequenos brinquedos e controle de video games até os telefones de ultima geração.  Para este post, vamos utilizar o LIS3LV02DL que possui muitos recursos embutidos além de medir aceleração em três eixos e possuir comunicação via barramento I²C que é um dos mais utilizados para comunicação entre microcontroladores e seus periféricos, além de ter duas escalas de medição, uma medindo até 2 g e outra medindo até 6 g, sendo 1.0025 g o equivalente a uma aceleração de 9.8310 m/s². Este componente é fornecido pela ST Microeletronics em uma placa de avaliação comercializada pelo código STEVAL-MKI009V1.   Abaixo podemos observar a foto do acelerômetro LIS331, utilizado no iPhone 3GS comparado a uma moeda.  Os acelerômetros podem apresentar duas formas de interfaceamento, sendo, digital ou analógico, nos analógicos as saídas correspondentes aos eixos informam a grandeza variando o nível de tensão DC no pino correspondente ao seu eixo, já no caso dos acelerômetros digitais, esses valores são transferidos via comunicação serial, podendo ser utilizado I²C ou SPI.  Este componente ainda conta com uma interrupção por movimentos, sendo possível efetuar o ajuste do nível de sensibilidade. Curiosidade!!! Alguns computadores antigos da Apple, contam com uma função que detecta uma possível queda de nível, fazendo com que a agulha do HD fosse para a posição de descanso a fim de não danificar o disco antes do impacto acontecer, pois bem, como é possível efetuar a detecção de queda livre?  R. Como todos sabemos, todos os corpos na terra sofrem a ação da gravidade, portanto o acelerômetro sempre estará sofrendo esta força, quando em queda livre de maneira linear, esta força tende a se anular pois o corpo acelera em relação ao eixo da terra e é neste momento que se pode detectar a queda livre ou free fall.      Interfaceamento&nbsp; Para interfacear o acelerômetro, temos que atentar para o fato da tensão de alimentação do mesmo que é de 3.3V ser diferente da tensão de alimentação da placa, para isto vamos utilizar um regulador externo de 3.3V além de dois resistores de pull up, este é um diferencial da placa PK2Lab, pois foi construída com o intuito de trabalhar com periféricos I²C com tensões de 3.3V ou 5V de forma simples e direta. &nbsp; Vale lembrar que os microcontroladores PIC quando alimentados com uma tensão de 5V, entendem como nível lógico alto uma tensão superior a 2V, portanto podemos conectar os pinos TX e RX do acelerômetro nos pinos do microcontrolador que os níveis lógicos serão entendidos. &nbsp; Comunicação I²C &nbsp; A comunicação foi estabelecida pelo protocolo I²C na frequência de 100Khz&nbsp; a 3.3V sendo respeitado a tabela de tempos conforme datasheet. &nbsp; Para efetuarmos as leituras referentes aos eixos, primeiro precisamos configurar o acelerômetro para informar como desejamos receber os dados, para isto devemos seguir a seguinte sequência. &nbsp; # Inicializar o barramento # Informar o comando de escrita para o LIS3LV02DL # Escrever o conteúdo do registrador CTRL_REG1 (Já vem indexado)  # Escrever o conteúdo do registrador CTRL_REG2  &nbsp; Após este procedimento podemos efetuar as leituras propriamente ditas seguindo a sequência abaixo. # Inicializar o barramento # Informar o comando de escrita para o LIS3LV02DL # Informar qual o endereço desejamos ler inicialmente # Reinicializar o barramento novamente  # Informar o comando de leitura para o LIS3LV02DL # Efetuar a leitura de forma sequencialmente dos eixos Por fim, como a leitura do acelerômetro se dá em 12 bits, precisamos concatenar esses dois bytes para obtermos a informação desejada para enfim apresentarmos os resultados no display LCD&nbsp; e via porta serial. <!--EndFragment--> &nbsp; Alguns registradores internos ao Acelerômetro   WHO_AM_I Endereço padrão deste CI no barramento I²C…   CTRL_REG1Configurações para habilitação de leitura dos eixos, self test…   CTRL_REG2Seleção de escala, interrupções…   CTRL_REG3Ajuste de clock e filtros passa alta… &nbsp;     Software O software para este exemplo mede a aceleração dos 3 eixos em 12 bits apresentando os valores lidos no display LCD, e envia os dados periodicamente via porta serial para o terminal serial do PC a 9600bps. /****************************************************************************** &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; JL Audio Manutenção Eletrônica Data: 23/04/2011Autor: Jean CarlosProjeto: MEMS ST - Acelerômetro&nbsp; ( LIS3LV02DL )Microprocessador: PIC18F4550Clock do processador: 8MHzEstação de desenvolvimento: PK2Lab V1.1Versão atual:&nbsp; V 1.0Descrição: &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Este projeto demonstra o uso de um MEMS(Sistema Micro eletromecânico)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; da ST, modelo LIS3LV02DL que se trata de um acelerômetro digital&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; de 3 eixos (2G e 6G) *******************************************************************************///Variáveis Globais unsigned char XL,XH,YL,YH,ZL,ZH;unsigned int X,Y,J;char txt[7]; //****************************************************************//Rotinas Auxiliares void Le_Acelerometro()&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; {&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; I2C_Start();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; I2C_Wr(0x3A);&nbsp;&nbsp;&nbsp;&nbsp; // Endereço do acelerômetro para escrita.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; I2C_Wr(0xA8);&nbsp;&nbsp;&nbsp;&nbsp; // Endereço do registrador Eixo X Lower (0x28), ainda foi setado o sétimo bit do registrador para indicar a indexação automática do endereço.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; I2C_Repeated_Start();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; I2C_Wr(0x3B);&nbsp;&nbsp;&nbsp;&nbsp; // Endereço do acelerômetro para leitura.&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; XL = I2C_Rd(1);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; XH = I2C_Rd(1);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; YL = I2C_Rd(1);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; YH = I2C_Rd(1);&nbsp;&nbsp; // Carrega as informações referentes aos eixos&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ZL = I2C_Rd(1);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ZH = I2C_Rd(0);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; I2C_Stop();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp;&nbsp;&nbsp; void Envia_Serial()&nbsp;&nbsp;&nbsp;&nbsp; {&nbsp;&nbsp;&nbsp;&nbsp; Usart_Write(X);&nbsp;&nbsp;&nbsp;&nbsp; Usart_Write(Y);&nbsp;&nbsp;&nbsp;&nbsp; Usart_Write(J);&nbsp;&nbsp;&nbsp;&nbsp; }&nbsp;&nbsp;&nbsp;&nbsp; //****************************************************************//Rotina Principal void main()&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Início do programa principal{TRISA = 0b00000000;PORTA = 0b00000000;TRISB = 0b00000000;PORTB = 0b00000000;TRISC = 0b00000000;PORTC = 0b00000000;TRISD = 0b00000000;PORTD = 0b00000000;TRISE = 0b00000000;PORTE = 0b00000000;ADCON1 = 0X0F;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Entradas digitais. Lcd_Config(&amp;PORTB,2,3,1,7,6,5,4);&nbsp; // Configuração PK2Lab V.1.1Lcd_Cmd(Lcd_Cursor_Off);Lcd_Cmd(Lcd_Clear);Lcd_Out(1,1,"***&nbsp; PK2Lab&nbsp; ***");Lcd_Out(2,1,"&nbsp; Acelerometro&nbsp; ");Delay_ms(3000);Lcd_Cmd(Lcd_Clear);Lcd_Out(1,1,"X:");Lcd_Out(2,1,"Y:");Lcd_Out(2,9,"Z:"); Usart_Init(9600);&nbsp; // Inicia comunicação RS232I2C_Init(100000);&nbsp; // Inicia comunicação I2C &nbsp;&nbsp; I2C_Start();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Inicia comunicação I2C&nbsp;&nbsp; I2C_Wr(0x3A);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Endereço do LIS3LV02DL para escrita&nbsp;&nbsp; I2C_Wr(0xA0);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Primeira palavra de endereço inicia pelo registrador CTRL_REG1 (0x20) , escrita contínua…&nbsp;&nbsp; I2C_Wr(0xC7);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // 11000111 ---&gt; CTRL_REG1&nbsp; C7&nbsp;&nbsp; I2C_Wr(0x04);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // 00000100 ---&gt; CTRL_REG2&nbsp; 04&nbsp;&nbsp; I2C_Stop(); &nbsp; while(1){Le_Acelerometro();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Efetua a leitura de aceleração dos 3 eixos Delay_ms(100); X = (XH);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Concatena as partes altas e baixas dos registradores.X = (X&lt;&lt;8) + XL; Y = (YH);Y = (Y&lt;&lt;8) + YL; J = (ZH);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Foi usado J no lugar de Z pois Z o compilador usa como Zero J = (J&lt;&lt;8) + ZL; intToStr(X,txt);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; Lcd_Out(1,3,txt);intToStr(Y,txt);Lcd_Out(2,3,txt);intToStr(J,txt);Lcd_Out(2,11,txt); Envia_serial();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // Envia os dados pela porta serial a 9600bps }//while(1)}//main     Vídeos do projeto Neste vídeo podemos observar o projeto em funcionamento.  Neste outro vídeo, vemos o acelerômetro controlando um equipamento de iluminação profissional (Moving Head) onde controlamos PAN e TILT através da leitura dos eixos X e Y respectivamente.  &nbsp; Gostaria de agradecer imensamente ao Eng. André Braz, representante da empresa ST Microelectronics no Brasil, que gentilmente cedeu algumas peças destas incríveis máquinas assim como muita informação técnica! Valeu André!!! Bom pessoal, por hoje é isto, grande abraço a todos e bons projetos!