当前位置:   article > 正文

基于stm32循迹小车使用mpu6050转弯

基于stm32循迹小车使用mpu6050转弯

本人第一次制作循迹小车,如果想法有不合理处,还请大佬指点

起初,我的想法是使用双轮的差速进行转弯,但是对于数据的不了解,作为初学者,我突然有一个更有趣的想法。

为了提高循迹小车的转弯速度,在识别到需要转弯的路口进行mpu6050使能,通过z轴的角速度的近似积分运算;

因为我们都知道,在比较短的时间内,转过的角=角加速度*时间;当我启用定时器,对角速度进行快速的取值,在乘对应的时间,我就会得出一个短时间内相对准确的偏航角。

显然,仅仅将一秒分为9份,图形的线下面积就已经很接近于偏航角的准确值了;

但是如果精度太高,会造成硬件的压力增大,所以适当进行提高精度就可以计算一个比较稳定的偏航角;

 

void MPU6050_GetZ(int16_t *GyroX);
  1. void MPU6050_GetZ(int16_t *GyroZ)
  2. {
  3. uint8_t DataH, DataL;
  4. DataH = MPU6050_ReadReg(MPU6050_GYRO_ZOUT_H);
  5. DataL = MPU6050_ReadReg(MPU6050_GYRO_ZOUT_L);
  6. *GyroZ = (DataH << 8) | DataL;
  7. }

这是对z轴角速度进行取值;

  1. void Angel_Calcu_Init(void)
  2. {
  3. RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM4, ENABLE);
  4. TIM_InternalClockConfig(TIM4);
  5. TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
  6. TIM_TimeBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;
  7. TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up;
  8. TIM_TimeBaseInitStructure.TIM_Period = 20000 - 1;
  9. TIM_TimeBaseInitStructure.TIM_Prescaler = 72 - 1;//在此设置精度
  10. TIM_TimeBaseInitStructure.TIM_RepetitionCounter = 0;
  11. TIM_TimeBaseInit(TIM4, &TIM_TimeBaseInitStructure);
  12. TIM_ClearFlag(TIM4, TIM_FLAG_Update);
  13. TIM_ITConfig(TIM4, TIM_IT_Update, ENABLE);
  14. NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
  15. NVIC_InitTypeDef NVIC_InitStructure;
  16. NVIC_InitStructure.NVIC_IRQChannel = TIM4_IRQn;
  17. NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
  18. NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
  19. NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
  20. NVIC_Init(&NVIC_InitStructure);
  21. TIM_Cmd(TIM4, ENABLE);
  22. }
  23. void acculary_Z (void)
  24. {
  25. MPU6050_GetZ(&gyroz);
  26. // if(Gyro_z<32768) Gyro_z=-(Gyro_z/16.4);
  27. // if(Gyro_z>32768) Gyro_z=+(65535-Gyro_z)/16.4;
  28. Gyro_z = gyroz;
  29. float temp;
  30. temp=((Angle_Z_Start + Gyro_z)/2)*0.0121 ; //进行积分运算
  31. Angle_Z_Start = Gyro_z;
  32. Angle_Z_Final += temp ; //加入结果
  33. }

 以下是定时器对结果的运算;

  1. void TIM4_IRQHandler(void)
  2. {
  3. if (TIM_GetITStatus(TIM4, TIM_IT_Update) == SET)
  4. {
  5. Angle_Calcu();
  6. acculary_Z();
  7. TIM_ClearITPendingBit(TIM4, TIM_IT_Update);
  8. }
  9. }

别忘了在头文件中添加extern float Angle_Z_Final;

如果小车遇到了路口,我们就使能定时器

  1. void turn_start(void)
  2. {
  3. TIM_Cmd(TIM4, ENABLE);
  4. }

如果角度达到了90,我们就关闭定时器,同时清零数据,以免影响下一次转弯的结果

  1. void turn_stop(void)
  2. {
  3. TIM_Cmd(TIM4, DISABLE);
  4. Gyro_z=0;
  5. Angle_Z_Start=0;
  6. Angle_Z_Final=0;
  7. }

这就是我对于小车使用mpu6050进行快速转弯的理解

我们只需要识别角度,调整轮子pwm进行差速转弯,得到更理想的效果。

本人刚刚接触32单片机,如果做的不好请大佬见谅。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/我家自动化/article/detail/404249
推荐阅读
相关标签
  

闽ICP备14008679号