通过stm32cubemax完成配置,与mpu6050通信并读取数据,将数据通过串口打印出来
单片机源程序如下:
- /* USER CODE END Header */
- /* Includes ------------------------------------------------------------------*/
- #include "main.h"
- #include "i2c.h"
- #include "stm32f4xx_hal.h"
- #include "usart.h"
- #include "gpio.h"
- #include "stdio.h"
- /* Private includes ----------------------------------------------------------*/
- #include "inv_mpu.h"
- #include "inv_mpu_dmp_motion_driver.h"
- #include <math.h>
- #define ADDRESS_W 0xD0 //写地址 0x68
- #define ADDRESS_R 0xD1 //读地址 0x69
- #define MPU_PWR_MGMT1_REG 0X6B //电源管理寄存器1
- #define MPU_GYRO_CFG_REG 0X1B //陀螺仪配置寄存器
- #define MPU_ACCEL_CFG_REG 0X1C //加速度计配置寄存器
- #define MPU_SAMPLE_RATE_REG 0X19 //陀螺仪采样频率分频器
- #define MPU_INT_EN_REG 0X38 //中断使能寄存器
- #define MPU_USER_CTRL_REG 0X6A //用户控制寄存器
- #define MPU_FIFO_EN_REG 0X23 //FIFO使能寄存器
- #define MPU_INTBP_CFG_REG 0X37 //中断/旁路设置寄存器
- #define MPU_DEVICE_ID_REG 0X75 //器件ID寄存器
- #define MPU_PWR_MGMT2_REG 0X6C //电源管理寄存器2
- #define MPU_CFG_REG 0X1A //配置寄存器 低通滤波器配置寄存器
- #define MPU_TEMP_OUTH_REG 0X41 //温度值高八位寄存器
- #define MPU_TEMP_OUTL_REG 0X42 //温度值低8位寄存器
- #define MPU_ACCEL_XOUTH_REG 0X3B //加速度值,X轴高8位寄存器
- #define MPU_ACCEL_XOUTL_REG 0X3C //加速度值,X轴低8位寄存器
- #define MPU_ACCEL_YOUTH_REG 0X3D //加速度值,Y轴高8位寄存器
- #define MPU_ACCEL_YOUTL_REG 0X3E //加速度值,Y轴低8位寄存器
- #define MPU_ACCEL_ZOUTH_REG 0X3F //加速度值,Z轴高8位寄存器
- #define MPU_ACCEL_ZOUTL_REG 0X40 //加速度值,Z轴低8位寄存器
- #define MPU_GYRO_XOUTH_REG 0X43 //陀螺仪值,X轴高8位寄存器
- #define MPU_GYRO_XOUTL_REG 0X44 //陀螺仪值,X轴低8位寄存器
- #define MPU_GYRO_YOUTH_REG 0X45 //陀螺仪值,Y轴高8位寄存器
- #define MPU_GYRO_YOUTL_REG 0X46 //陀螺仪值,Y轴低8位寄存器
- #define MPU_GYRO_ZOUTH_REG 0X47 //陀螺仪值,Z轴高8位寄存器
- #define MPU_GYRO_ZOUTL_REG 0X48 //陀螺仪值,Z轴低8位寄存器
- //定义输出速度
- #define DEFAULT_MPU_HZ (100) //100Hz
- //q30格式,long转float时的除数.
- #define q30 1073741824.0f
- /* USER CODE END Includes */
- /* Private typedef -----------------------------------------------------------*/
- /* USER CODE BEGIN PTD */
- /* USER CODE END PTD */
- /* Private define ------------------------------------------------------------*/
- /* USER CODE BEGIN PD */
- /* USER CODE END PD */
- /* Private macro -------------------------------------------------------------*/
- /* USER CODE BEGIN PM */
- /* USER CODE END PM */
- /* Private variables ---------------------------------------------------------*/
- void MPU_6050_Init(void);
- unsigned char MPU_Set_LPF(unsigned short lpf);
- //DMP库需要的函数
- unsigned char HAL_i2c_write(unsigned char slave_addr, unsigned char reg_addr, unsigned char length, unsigned char const *data);
- unsigned char HAL_i2c_read(unsigned char slave_addr, unsigned char reg_addr, unsigned char length, unsigned char const *data);
- //读取 温度传感器 陀螺仪 加速度数据
- void read_all(void);
- //陀螺仪方向控制
- unsigned short inv_orientation_matrix_to_scalar(const signed char *mtx);
- //方向转换
- unsigned short inv_row_2_scale(const signed char *row);
- //MPU6050自测试
- //返回值:0,正常
- // 其他,失败
- unsigned char run_self_test(void);
- //mpu6050,dmp初始化
- //返回值:0,正常
- // 其他,失败
- unsigned char mpu_dmp_init(void);
- //得到dmp处理后的数据(注意,本函数需要比较多堆栈,局部变量有点多)
- //pitch:俯仰角 精度:0.1° 范围:-90.0° <---> +90.0°
- //roll:横滚角 精度:0.1° 范围:-180.0°<---> +180.0°
- //yaw:航向角 精度:0.1° 范围:-180.0°<---> +180.0°
- //返回值:0,正常
- // 其他,失败
- unsigned char mpu_dmp_get_data(float *pitch,float *roll,float *yaw);
- /* USER CODE BEGIN PV */
- /* USER CODE END PV */
- /* Private function prototypes -----------------------------------------------*/
- void SystemClock_Config(void);
- /* USER CODE BEGIN PFP */
- /* USER CODE END PFP */
- /* Private user code ---------------------------------------------------------*/
- /* USER CODE BEGIN 0 */
- static signed char gyro_orientation[9] = { 1, 0, 0,
- 0, 1, 0,
- 0, 0, 1};
- float pitch,roll,yaw; //欧拉角
- //串口1发送1个字符
- //c:要发送的字符
- void usart1_send_char(uint8_t c)
- {
- while(__HAL_UART_GET_FLAG(&huart1,UART_FLAG_TC)==RESET){};
- USART1->DR=c;
- }
- //传送数据给匿名四轴上位机软件(V2.6版本)
- //fun:功能字. 0X01~0X1C
- //data:数据缓存区,最多28字节!!
- //len:data区有效数据个数
- void usart1_niming_report(uint8_t fun,uint8_t*data,uint8_t len)
- {
- uint8_t send_buf[32];
- uint8_t i;
- if(len>28)return; //最多28字节数据
- send_buf[len+3]=0; //校验数置零
- send_buf[0]=0XAA; //帧头
- send_buf[1]=0XAA; //帧头
- send_buf[2]=fun; //功能字
- send_buf[3]=len; //数据长度
- for(i=0;i<len;i++)send_buf[4+i]=data[i]; //复制数据
- for(i=0;i<len+4;i++)send_buf[len+4]+=send_buf[i]; //计算校验和
- for(i=0;i<len+5;i++)usart1_send_char(send_buf[i]); //发送数据到串口1
- }
- //发送加速度传感器数据+陀螺仪数据(传感器帧)
- //aacx,aacy,aacz:x,y,z三个方向上面的加速度值
- //gyrox,gyroy,gyroz:x,y,z三个方向上面的陀螺仪值
- void mpu6050_send_data(short aacx,short aacy,short aacz,short gyrox,short gyroy,short gyroz)
- {
- uint8_t tbuf[18];
- tbuf[0]=(aacx>>8)&0XFF;
- tbuf[1]=aacx&0XFF;
- tbuf[2]=(aacy>>8)&0XFF;
- tbuf[3]=aacy&0XFF;
- tbuf[4]=(aacz>>8)&0XFF;
- tbuf[5]=aacz&0XFF;
- tbuf[6]=(gyrox>>8)&0XFF;
- tbuf[7]=gyrox&0XFF;
- tbuf[8]=(gyroy>>8)&0XFF;
- tbuf[9]=gyroy&0XFF;
- tbuf[10]=(gyroz>>8)&0XFF;
- tbuf[11]=gyroz&0XFF;
- tbuf[12]=0;//因为开启MPL后,无法直接读取磁力计数据,所以这里直接屏蔽掉.用0替代.
- tbuf[13]=0;
- tbuf[14]=0;
- tbuf[15]=0;
- tbuf[16]=0;
- tbuf[17]=0;
- usart1_niming_report(0X02,tbuf,18);//传感器帧,0X02
- }
- //通过串口1上报结算后的姿态数据给电脑(状态帧)
- //roll:横滚角.单位0.01度。 -18000 -> 18000 对应 -180.00 -> 180.00度
- //pitch:俯仰角.单位 0.01度。-9000 - 9000 对应 -90.00 -> 90.00 度
- //yaw:航向角.单位为0.1度 0 -> 3600 对应 0 -> 360.0度
- //csb:超声波高度,单位:cm
- //prs:气压计高度,单位:mm
- void usart1_report_imu(short roll,short pitch,short yaw,short csb,int prs)
- {
- uint8_t tbuf[12];
- tbuf[0]=(roll>>8)&0XFF;
- tbuf[1]=roll&0XFF;
- tbuf[2]=(pitch>>8)&0XFF;
- tbuf[3]=pitch&0XFF;
- tbuf[4]=(yaw>>8)&0XFF;
- tbuf[5]=yaw&0XFF;
- tbuf[6]=(csb>>8)&0XFF;
- tbuf[7]=csb&0XFF;
- tbuf[8]=(prs>>24)&0XFF;
- tbuf[9]=(prs>>16)&0XFF;
- tbuf[10]=(prs>>8)&0XFF;
- tbuf[11]=prs&0XFF;
- usart1_niming_report(0X01,tbuf,12);//状态帧,0X01
- }
- /* USER CODE END 0 */
- /**
- * @brief The application entry point.
- * @retval int
- */
- int main(void)
- {
- /* USER CODE BEGIN 1 */
- unsigned char DMP_INT_FLAG=0;
- unsigned char rev_flag=0;
- /* USER CODE END 1 */
-
- /* MCU Configuration--------------------------------------------------------*/
- /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
- HAL_Init();
- /* USER CODE BEGIN Init */
- /* USER CODE END Init */
- /* Configure the system clock */
- SystemClock_Config();
- /* USER CODE BEGIN SysInit */
- /* USER CODE END SysInit */
- /* Initialize all configured peripherals */
- MX_GPIO_Init();
- MX_I2C3_Init();
- MX_USART1_UART_Init();
- /* USER CODE BEGIN 2 */
- HAL_Delay(5000);
- printf("MPU6050test\n");
- MPU_6050_Init();// 可以尝试 直接打开FIFO
- //初始化DMP
- DMP_INT_FLAG=mpu_dmp_init();
- printf("DMP_INT_FLAG %d \n",DMP_INT_FLAG);
- /* USER CODE END 2 */
- /* Infinite loop */
- /* USER CODE BEGIN WHILE */
- while (1)
- {
- if((rev_flag=mpu_dmp_get_data(&pitch,&roll,&yaw))==0)
- {
- printf("俯仰角 = %.2f\r\n",pitch);
- printf("偏航角 = %.2f\r\n",roll);
- printf("翻滚角 = %.2f\r\n",yaw);
- }
- // else
- // {
- // printf("rev_flag %d\n",rev_flag);
- // HAL_Delay(100);//读取频率不能太慢 防止FIFO溢出
- // }
- read_all();
- HAL_Delay(100);
- /* USER CODE END WHILE */
- /* USER CODE BEGIN 3 */
- }
- /* USER CODE END 3 */
- }
- /**
- * @brief System Clock Configuration
- * @retval None
- */
- void SystemClock_Config(void)
- {
- RCC_OscInitTypeDef RCC_OscInitStruct = {0};
- RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
- /** Configure the main internal regulator output voltage
- */
- __HAL_RCC_PWR_CLK_ENABLE();
- __HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);
- /** Initializes the CPU, AHB and APB busses clocks
- */
- RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
- RCC_OscInitStruct.HSIState = RCC_HSI_ON;
- RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
- RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
- RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI;
- RCC_OscInitStruct.PLL.PLLM = 8;
- RCC_OscInitStruct.PLL.PLLN = 96;
- RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2;
- RCC_OscInitStruct.PLL.PLLQ = 4;
- if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
- {
- Error_Handler();
- }
- /** Initializes the CPU, AHB and APB busses clocks
- */
- RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
- |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
- RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
- RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
- RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV2;
- RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;
- if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_3) != HAL_OK)
- {
- Error_Handler();
- }
- }
- /* USER CODE BEGIN 4 */
- void MPU_6050_Init(void)
- ……………………
- …………限于本文篇幅 余下代码请从51黑下载附件…………
复制代码
所有资料51hei提供下载:
F411-MPU6050.7z
(6.76 MB, 下载次数: 27)
|