MPU-6050为全球首例整合性6轴运动处理组件,相较于多组件方案,免除了组合陀螺仪与加速器时之轴间差的问题,减少了大量的封装空间。能测量三个方向的加速度,角加速度,角度以及温度。这篇文章介绍如何使用瑞萨单片机使用MPU6050。模块的工作原理不多说,介绍如何使用。
MPU-6050可以使用UART通信和I2C通信,这里使用UART通信波特率9600。使用MPU-6050时可以先用上位机,把波特率设为9600,他会掉电保存这个设置。9600波特率时MPU6050每隔50个ms和回复一个数据包,在串口中断中解析它。
引脚分配:
P02 TXD1接MPU6050的RX
P03 RXD1接MPU6050的TX
下面是代码生成器的设置。
主函数中没有什么内容初始化,仅仅写初始化函数就行然后等待中断,我用定时器产生了一个1ms的中断,在中断中,让GlobalTime加1,作为全局时间戳。P13.0是测试用LED灯。
/*********************************************************************************************************************** * File Name : r_main.c * Version : CodeGenerator for RL78/G13 V2.00.00.07 [22 Feb 2013] * Device(s) : R5F100LE * Tool-Chain : CA78K0R * Description : This file implements main function. * Creation Date: 2015/7/15 ***********************************************************************************************************************/ /*********************************************************************************************************************** Pragma directive ***********************************************************************************************************************/ /* Start user code for pragma. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ /*********************************************************************************************************************** Includes ***********************************************************************************************************************/ #include "r_cg_macrodriver.h" #include "r_cg_cgc.h" #include "r_cg_port.h" #include "r_cg_serial.h" #include "r_cg_timer.h" /* Start user code for include. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ #include "r_cg_userdefine.h" /*********************************************************************************************************************** Global variables and functions ***********************************************************************************************************************/ /* Start user code for global. Do not edit comment generated here */ extern uint32_t GlobalTime; /* End user code. Do not edit comment generated here */ void R_MAIN_UserInit(void); /*********************************************************************************************************************** * Function Name: main * Description : This function implements main function. * Arguments : None * Return Value : None ***********************************************************************************************************************/ void main(void) { /* Start user code. Do not edit comment generated here */ uint32_t nowTime=0, lastTime=0; R_MAIN_UserInit(); R_TAU0_Channel0_Start(); R_UART1_Start(); while (1U) { nowTime=GlobalTime; if((nowTime-lastTime)>500) { lastTime = GlobalTime; P13.0 = ~P13.0; } } /* End user code. Do not edit comment generated here */ } /*********************************************************************************************************************** * Function Name: R_MAIN_UserInit * Description : This function adds user code before implementing main function. * Arguments : None * Return Value : None ***********************************************************************************************************************/ void R_MAIN_UserInit(void) { /* Start user code. Do not edit comment generated here */ EI(); /* End user code. Do not edit comment generated here */ } /* Start user code for adding. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */
定时器用户文件r_cg_time_user.c,仅仅自加GlobalTime。
/*********************************************************************************************************************** * File Name : r_cg_timer_user.c * Version : CodeGenerator for RL78/G13 V2.00.00.07 [22 Feb 2013] * Device(s) : R5F100LE * Tool-Chain : CA78K0R * Description : This file implements device driver for TAU module. * Creation Date: 2015/7/15 ***********************************************************************************************************************/ /*********************************************************************************************************************** Pragma directive ***********************************************************************************************************************/ #pragma interrupt INTTM00 r_tau0_channel0_interrupt /* Start user code for pragma. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ /*********************************************************************************************************************** Includes ***********************************************************************************************************************/ #include "r_cg_macrodriver.h" #include "r_cg_timer.h" /* Start user code for include. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ #include "r_cg_userdefine.h" /*********************************************************************************************************************** Global variables and functions ***********************************************************************************************************************/ /* Start user code for global. Do not edit comment generated here */ uint32_t GlobalTime; /* End user code. Do not edit comment generated here */ /*********************************************************************************************************************** * Function Name: r_tau0_channel0_interrupt * Description : This function is INTTM00 interrupt service routine. * Arguments : None * Return Value : None ***********************************************************************************************************************/ __interrupt static void r_tau0_channel0_interrupt(void) { /* Start user code. Do not edit comment generated here */ ++GlobalTime; /* End user code. Do not edit comment generated here */ } /* Start user code for adding. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */
最关键的数据解析中串口中断函数中,注意这里改写了中断服务函数,没有用代码生成器给的中断接收函数。采集的数据放在全局变量中,注意用了一个自定义的函数MPU6050RecvEnd(),要在头文件中声明。
double Acceleration[3]={0};//XYZ轴的加速度 double AngularAcceleration[3]={0};//XYZ 轴的角加速度 double Angle[3]={0};//XYZ轴的角度 double Temperature=0;//温度
/*********************************************************************************************************************** * File Name : r_cg_serial_user.c * Version : CodeGenerator for RL78/G13 V2.00.00.07 [22 Feb 2013] * Device(s) : R5F100LE * Tool-Chain : CA78K0R * Description : This file implements device driver for Serial module. * Creation Date: 2015/7/15 ***********************************************************************************************************************/ /*********************************************************************************************************************** Pragma directive ***********************************************************************************************************************/ #pragma interrupt INTST1 r_uart1_interrupt_send #pragma interrupt INTSR1 r_uart1_interrupt_receive /* Start user code for pragma. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ /*********************************************************************************************************************** Includes ***********************************************************************************************************************/ #include "r_cg_macrodriver.h" #include "r_cg_serial.h" /* Start user code for include. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ #include "r_cg_userdefine.h" /*********************************************************************************************************************** Global variables and functions ***********************************************************************************************************************/ extern volatile uint8_t * gp_uart1_tx_address; /* uart1 send buffer address */ extern volatile uint16_t g_uart1_tx_count; /* uart1 send data number */ extern volatile uint8_t * gp_uart1_rx_address; /* uart1 receive buffer address */ extern volatile uint16_t g_uart1_rx_count; /* uart1 receive data number */ extern volatile uint16_t g_uart1_rx_length; /* uart1 receive data length */ /* Start user code for global. Do not edit comment generated here */ double Acceleration[3]={0}; double AngularAcceleration[3]={0}; double Angle[3]={0}; double Temperature=0; /* End user code. Do not edit comment generated here */ /*********************************************************************************************************************** * Function Name: r_uart1_interrupt_receive * Description : This function is INTSR1 interrupt service routine. * Arguments : None * Return Value : None ***********************************************************************************************************************/ __interrupt static void r_uart1_interrupt_receive(void) { /* Start user code. Do not edit comment generated here */ uint8_t rx_data, sum=0, j=0; static uint8_t rightFlag = 0, recvData[11]={0}, i=0; rx_data = RXD1; if(rx_data == 0x55 || rightFlag) { rightFlag = 1; recvData[i]=rx_data; if(++i == 11) { rightFlag = 0; i=0; for(j=0; j<10; j++) sum += recvData[j]; if(sum == recvData[10]) MPU6050RecvEnd(recvData); } } /* End user code. Do not edit comment generated here */ } /*********************************************************************************************************************** * Function Name: r_uart1_interrupt_send * Description : This function is INTST1 interrupt service routine. * Arguments : None * Return Value : None ***********************************************************************************************************************/ __interrupt static void r_uart1_interrupt_send(void) { if (g_uart1_tx_count > 0U) { TXD1 = *gp_uart1_tx_address; gp_uart1_tx_address++; g_uart1_tx_count--; } else { r_uart1_callback_sendend(); } } /*********************************************************************************************************************** * Function Name: r_uart1_callback_receiveend * Description : This function is a callback function when UART1 finishes reception. * Arguments : None * Return Value : None ***********************************************************************************************************************/ static void r_uart1_callback_receiveend(void) { /* Start user code. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ } /*********************************************************************************************************************** * Function Name: r_uart1_callback_softwareoverrun * Description : This function is a callback function when UART1 receives an overflow data. * Arguments : rx_data - * receive data * Return Value : None ***********************************************************************************************************************/ static void r_uart1_callback_softwareoverrun(uint16_t rx_data) { /* Start user code. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ } /*********************************************************************************************************************** * Function Name: r_uart1_callback_sendend * Description : This function is a callback function when UART1 finishes transmission. * Arguments : None * Return Value : None ***********************************************************************************************************************/ static void r_uart1_callback_sendend(void) { /* Start user code. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ } /*********************************************************************************************************************** * Function Name: r_uart1_callback_error * Description : This function is a callback function when UART1 reception error occurs. * Arguments : err_type - * error type value * Return Value : None ***********************************************************************************************************************/ static void r_uart1_callback_error(uint8_t err_type) { /* Start user code. Do not edit comment generated here */ /* End user code. Do not edit comment generated here */ } /* Start user code for adding. Do not edit comment generated here */ static void MPU6050RecvEnd(uint8_t data[]) { switch(data [1]) { case 0x51: Acceleration[0] = ((short)(data [3]<<8| data [2]))/32768.0*16*9.8; Acceleration[1] = ((short)(data [5]<<8| data [4]))/32768.0*16*9.8; Acceleration[2] = ((short)(data [7]<<8| data [6]))/32768.0*16*9.8; Temperature = ((short)(data [9]<<8| data [8]))/340.0+36.25; break; case 0x52: AngularAcceleration[0] = ((short)(data [3]<<8| data [2]))/32768.0*2000; AngularAcceleration[1] = ((short)(data [5]<<8| data [4]))/32768.0*2000; AngularAcceleration[2] = ((short)(data [7]<<8| data [6]))/32768.0*2000; Temperature = ((short)(data [9]<<8| data [8]))/340.0+36.25; break; case 0x53: Angle[0] = ((short)(data [3]<<8| data [2]))/32768.0*180; Angle[1] = ((short)(data [5]<<8| data [4]))/32768.0*180; Angle[2] = ((short)(data [7]<<8| data [6]))/32768.0*180; Temperature = ((short)(data [9]<<8| data [8]))/340.0+36.25; break; } } /* End user code. Do not edit comment generated here */
瑞萨单片机R5F100LE使用MPU6050cubesuite+工程链接。