串口直输型PID红外循迹模块/PID循迹

写在前面

 关于红外PID循迹模块的原理我之前写过一篇博客,大家没看过的话可以点此链接查看:PID循迹模块原理。此循迹模块可以根据传感器离黑线的距离输出线性值,但是配置起来比较麻烦,单片机必须带有AD采集功能,然后在代码中改配置参数比较麻烦。最近本人将之前的PID循迹模块更新了一下,在模块上加入了一个stm8的单片机,单片机通过AD采集数据后直接通过串口输出线性数据,大家只需按下按键即可配置循迹模块,再也不用手动改程序配置了。下面给大家介绍一下这款串口直输式PID红外循迹模块。

如果大家需要购买的话可以点此链接购买:串口直输式PID红外循迹模块
模块资料链接:
链接:https://pan.baidu.com/s/10IUagQXBHASeuqSnktP1tg
提取码:4tfa

1.模块特性

A.适合线宽范围广,黑线的宽度范围为1cm到4cm。
B.一键配置循迹模块参数,按下配置按键后从左到右移动模块即可配置完成。
C.循迹模块输出值根据模块距黑线距离从左到右,返回值从-1500到1500线性变化。
D.串口输出数据信息,单片机不需要AD采集功能即可通过此模块实现PID循迹,只要带串口的单片机都可以使用。
F.串口数据输出频率可通过串口设置,设置频率范围从10HZ到300HZ。
H.循迹模块适合多种车型,舵机转向车型和差速转向车型。

在这里插入图片描述

图1 循迹模块图示

2.模块参数

循迹黑线宽度:1cm-4cm
模块距黑线距离:1.5cm-4cm
数据输出方式:串口
数据输出频率:10HZ-300HZ
数据输出范围:-1500-1500
输入电压:3.3V-5.0V
模块参数配置方式:按键一键配置

在这里插入图片描述

图2 循迹模块接口图

3.模块参数配置流程

 模块正常工作时,工作指示灯会闪烁,串口输出循迹信息。按下配置按键工作指示灯常亮,将模块从黑线左边移动到黑线右边,移动完成后再次按下配置键,工作指示灯会灭0.5ms后再次闪烁,则表明循迹模块参数配置完成。
配置步骤:
①将循迹模块放置在黑线左边。
②按下循迹模块配置键,工作指示灯会常亮。
③如下图2所示,将模块从左到右缓慢滑动。
④完成步骤③后再次按下配置按键,0.5s后工作指示灯再次闪烁表明配置完成。

在这里插入图片描述

图3 循迹模块配置图示

4.模块配置

 串口配置需要加入结尾符’\r’ ’\n’,也就是换行,否者发送的命令不能识别。

设置数据输出频率:
设置输出频率为10HZ
串口发送:SetFre_10HZ
返回:ok

设置输出频率为50HZ
串口发送:SetFre_50HZ
返回:ok

设置输出频率为100HZ
串口发送:SetFre_100HZ
返回:ok

设置输出频率为100HZ
串口发送:SetFre_100HZ
返回:ok

设置输出频率为200HZ
串口发送:SetFre_200HZ
返回:ok

设置输出频率为300HZ
串口发送:SetFre_300HZ
返回:ok

停止数据输出:
停止数据输出
串口发送:Stop
返回:ok

开始数据输出:
开始数据输出
串口发送:Start
返回:ok

5.产品尺寸图

在这里插入图片描述

  • 2
    点赞
  • 63
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
以下是基于MSP432单片机的5路红外循迹模块PID控制的代码示例: ```c #include "msp.h" #include <stdint.h> #include <stdbool.h> #define SENSOR_THRESHOLD 1000 // 红外传感器的阈值 #define MAX_SPEED 100 // 最大速度 #define KP 0.2 // 比例常数 #define KD 0.1 // 微分常数 int32_t sensor_values[5]; // 存储传感器读数的数组 int32_t last_error = 0; // 上一次误差 int32_t integral_error = 0; // 积分误差 int32_t motor_speed_left = 0; // 左电机速度 int32_t motor_speed_right = 0; // 右电机速度 void init_motor() { // 初始化PWM输出 P2->SEL0 |= BIT4 | BIT5; // P2.4和P2.5选择PWM功能 P2->SEL1 &= ~(BIT4 | BIT5); P2->DIR |= BIT4 | BIT5; // P2.4和P2.5设置为输出模式 TIMER_A0->CTL = TIMER_A_CTL_SSEL__SMCLK | TIMER_A_CTL_MC__UP | TIMER_A_CTL_CLR; // 选择SMCLK作为计数时钟,向上计数模式,清除计数器 TIMER_A0->CCR[0] = 30000; // 设置计数器上限为30000 TIMER_A0->CCR[1] = 0; // 设置初始占空比为0 TIMER_A0->CCR[2] = 0; TIMER_A0->CCTL[1] = TIMER_A_CCTLN_OUTMOD_7; // 设置PWM输出模式为Reset/Set TIMER_A0->CCTL[2] = TIMER_A_CCTLN_OUTMOD_7; TIMER_A0->CTL |= TIMER_A_CTL_ID__8; // 选择8分频 } void set_motor_speed(int32_t left, int32_t right) { // 将速度限制在[-100, 100]之间 if (left > MAX_SPEED) left = MAX_SPEED; if (left < -MAX_SPEED) left = -MAX_SPEED; if (right > MAX_SPEED) right = MAX_SPEED; if (right < -MAX_SPEED) right = -MAX_SPEED; // 根据速度设置占空比 TIMER_A0->CCR[1] = left * 300 / MAX_SPEED + 1500; TIMER_A0->CCR[2] = right * 300 / MAX_SPEED + 1500; // 根据速度设置方向 if (left > 0) P2->OUT &= ~BIT4; else P2->OUT |= BIT4; if (right > 0) P2->OUT &= ~BIT5; else P2->OUT |= BIT5; } void read_sensor_values() { // 读取红外传感器的读数 sensor_values[0] = ADC14->MEM[0]; sensor_values[1] = ADC14->MEM[1]; sensor_values[2] = ADC14->MEM[2]; sensor_values[3] = ADC14->MEM[3]; sensor_values[4] = ADC14->MEM[4]; } int32_t calculate_pid() { int32_t error = 0; int32_t derivative_error = 0; // 计算误差 for (int i = 0; i < 5; i++) { if (sensor_values[i] < SENSOR_THRESHOLD) { error += (i - 2) * 1000; } } // 计算微分误差 derivative_error = error - last_error; // 计算积分误差 integral_error += error; // 更新上一次误差 last_error = error; // 计算PID控制量 return KP * error + KD * derivative_error + integral_error / 1000; } void main() { WDT_A->CTL = WDT_A_CTL_PW | WDT_A_CTL_HOLD; // 停用看门狗 // 初始化ADC ADC14->CTL0 &= ~ADC14_CTL0_ENC; // 禁用ADC ADC14->CTL0 |= ADC14_CTL0_SHT0_4 | ADC14_CTL0_SHP | ADC14_CTL0_ON | ADC14_CTL0_MSC; ADC14->CTL1 |= ADC14_CTL1_RES__14BIT | ADC14_CTL1_CSTARTADD__ADC14MEM0 | ADC14_CTL1_MSC; ADC14->MCTL[0] |= ADC14_MCTLN_INCH_0; ADC14->MCTL[1] |= ADC14_MCTLN_INCH_1; ADC14->MCTL[2] |= ADC14_MCTLN_INCH_2; ADC14->MCTL[3] |= ADC14_MCTLN_INCH_3; ADC14->MCTL[4] |= ADC14_MCTLN_INCH_4 | ADC14_MCTLN_EOS; ADC14->IER0 |= ADC14_IER0_IE4; // 使能ADC14中断 NVIC_EnableIRQ(ADC14_IRQn); // 初始化电机 init_motor(); // 启动ADC ADC14->CTL0 |= ADC14_CTL0_ENC | ADC14_CTL0_SC; while (1) { read_sensor_values(); int32_t pid = calculate_pid(); motor_speed_left = MAX_SPEED - pid; motor_speed_right = MAX_SPEED + pid; set_motor_speed(motor_speed_left, motor_speed_right); } } ``` 注意,此代码示例仅供参考。实际应用中可能需要根据具体情况进行修改。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值