전자 회로 입문 3축 가속도 센서

소개



에 따라 계속 진행해 갑니다.

3축 가속도 센서



X, Y, Z의 3축의 가속도를 계측할 수 있는 센서입니다.
멀티콥터에는 9축 센서를 얹거나 합니다. (가속도+자이로+자기)

가속도에서 기울기를 구할 수도 있습니다. (계산하면… 이번은 그만두겠습니다)

사용 부품


  • PSoC 5LP
  • 저항 (1k,2kΩ)

  • PCA9306  (J4, J5를 납땜)

  • LIS3DH  (A, B, C를 납땜)

  • 회로도



    전회, 가속도 센서는 SPI 통신이 좋다고 말한 생각이 듭니다만, I2C로 실행합니다.



    프로그램



    별로 깨끗하지 않을지도… 언젠가 고치자. (;´・ω・)

    사양서에는 슬레이브 주소가 0x30, 0x31이라고 써 있습니다만, 맨 아래의 bit는 Read/Write용 같기 때문에, 거기엔은 PSoC로 마음대로 후부하는 것일까? 그래서, 오른쪽으로 1개 시프트한(Read/Write의 bit 없음) 0x18을 사용합니다.
    Arduino나 라즈베리 파이에서도 마찬가지였다고 생각합니다.

    0x30, 0x31을 오른쪽으로 한 시프트하면 0x180x31(0b110001) → 0x18(0b11000)
    #include "project.h"
    #include <stdio.h>
    #include <stdlib.h>
    
    
    char imp[255];
    
     uint8 I2C_Write(uint8 SlaveAddress, uint8 *DataAddress, uint8 Byte_Count, uint8 I2C_Mode){
        uint8 temp;
        temp = I2C_1_MasterWriteBuf(SlaveAddress,DataAddress,Byte_Count,I2C_Mode);
        while (temp != I2C_1_MSTR_NO_ERROR);
        while(I2C_1_MasterStatus() & I2C_1_MSTAT_XFER_INP);
        temp = I2C_1_MasterClearStatus();
        return (temp);
    }
    
     uint8 I2C_Read(uint8 SlaveAddress, uint8 *DataAddress, uint8 Byte_Count, uint8 I2C_Mode){
        uint8 temp;
        temp = I2C_1_MasterWriteBuf(SlaveAddress,DataAddress,1,I2C_Mode);
        while (temp != I2C_1_MSTR_NO_ERROR);
        while(I2C_1_MasterStatus() & I2C_1_MSTAT_XFER_INP);
        temp = I2C_1_MasterClearStatus();
    
        temp = I2C_1_MasterReadBuf(SlaveAddress,DataAddress,Byte_Count, I2C_Mode);
        while (temp != I2C_1_MSTR_NO_ERROR);
        while(I2C_1_MasterStatus() & I2C_1_MSTAT_XFER_INP);
        temp = I2C_1_MasterClearStatus();
        return (temp);
    }
    
    int main(void)
    {
        CyGlobalIntEnable;
    
        UART_1_Start();
        I2C_1_Start();
        CyDelay(2000);
        uint8 wr_buff[6]={0,0,0,0,0,0};
        for(;;)
        {
            wr_buff[0] = 0x0F;
            I2C_Read(0x18,wr_buff,1,I2C_1_MODE_COMPLETE_XFER);
            if(wr_buff[0] == 0x33){break;}
        }
        wr_buff[0] = 0x20;
        wr_buff[1] = 0x77;
        I2C_Write(0x18,wr_buff,2,I2C_1_MODE_COMPLETE_XFER);
        I2C_Read(0x18,wr_buff,1,I2C_1_MODE_COMPLETE_XFER);
        UART_1_PutString("start \n");
        for(;;)
        {
            short x,y,z;
            uint8 wr_buffa[6]={0,0,0,0,0,0};
            wr_buff[0] = 0x28;
            I2C_Read(0x18,wr_buff,1,I2C_1_MODE_COMPLETE_XFER);
            wr_buffa[0] = 0x29;
            I2C_Read(0x18,wr_buffa,1,I2C_1_MODE_COMPLETE_XFER);
            int p = 0;
            if((wr_buffa[0] >> 7) == 1){p = 0xF;}else{p = 0;}
            x = (p << 12) | (wr_buffa[0] << 4) | (wr_buff[0] >> 4);
            wr_buff[0] = 0x2A;
            I2C_Read(0x18,wr_buff,1,I2C_1_MODE_COMPLETE_XFER);
            wr_buffa[0] = 0x2B;
            I2C_Read(0x18,wr_buffa,1,I2C_1_MODE_COMPLETE_XFER);
            if((wr_buffa[0] >> 7) == 1){p = 0xF;}else{p = 0;}
            y = (wr_buffa[0] << 4) | (wr_buff[0] >> 4);
            wr_buff[0] = 0x2C;
            I2C_Read(0x18,wr_buff,1,I2C_1_MODE_COMPLETE_XFER);
            wr_buffa[0] = 0x2D;
            I2C_Read(0x18,wr_buffa,1,I2C_1_MODE_COMPLETE_XFER);
            if((wr_buffa[0] >> 7) == 1){p = 0xF;}else{p = 0;}
            z = (wr_buffa[0] << 4) | (wr_buff[0] >> 4);
            sprintf(imp,"%hd,%hd,%hd\n",x,y,z);
            UART_1_PutString(imp);
            CyDelay(1000);
        }
    }
    

    결과



    좋은 웹페이지 즐겨찾기