feat: 添加RC522站点匹配逻辑及到站提示功能
This commit is contained in:
@@ -1,25 +1,4 @@
|
||||
#include "bsp_rc522.h"
|
||||
#include <string.h>
|
||||
|
||||
// 站点UID白名单(可扩展)
|
||||
static const uint8_t g_station_1_uid[] = STATION_1_UID;
|
||||
static const uint8_t g_station_2_uid[] = STATION_2_UID;
|
||||
|
||||
station_id_t rc522_match_station(const uint8_t *uid, uint8_t uid_len)
|
||||
{
|
||||
if (uid == NULL || uid_len == 0) return STATION_NONE;
|
||||
// 匹配站点1
|
||||
if (uid_len == sizeof(g_station_1_uid) && memcmp(uid, g_station_1_uid, uid_len) == 0) {
|
||||
return STATION_1;
|
||||
}
|
||||
// 匹配站点2
|
||||
if (uid_len == sizeof(g_station_2_uid) && memcmp(uid, g_station_2_uid, uid_len) == 0) {
|
||||
return STATION_2;
|
||||
}
|
||||
// 可继续添加更多站点匹配
|
||||
return STATION_NONE;
|
||||
}
|
||||
#include "bsp_rc522.h"
|
||||
|
||||
#include "spi.h"
|
||||
#include <string.h>
|
||||
@@ -630,3 +609,24 @@ void rc522_irq_callback(uint16_t GPIO_Pin)
|
||||
g_irq_pending = 1U;
|
||||
}
|
||||
}
|
||||
|
||||
/* 站点UID白名单(可扩展) */
|
||||
static const uint8_t g_station_1_uid[] = STATION_1_UID;
|
||||
static const uint8_t g_station_2_uid[] = STATION_2_UID;
|
||||
|
||||
station_id_t rc522_match_station(const uint8_t *uid, uint8_t uid_len)
|
||||
{
|
||||
if (uid == NULL || uid_len == 0U) {
|
||||
return STATION_NONE;
|
||||
}
|
||||
|
||||
if (uid_len == sizeof(g_station_1_uid) && memcmp(uid, g_station_1_uid, uid_len) == 0) {
|
||||
return STATION_1;
|
||||
}
|
||||
|
||||
if (uid_len == sizeof(g_station_2_uid) && memcmp(uid, g_station_2_uid, uid_len) == 0) {
|
||||
return STATION_2;
|
||||
}
|
||||
|
||||
return STATION_NONE;
|
||||
}
|
||||
|
||||
@@ -12,6 +12,8 @@
|
||||
#include "bsp_hall.h"
|
||||
#include "bsp_pid.h"
|
||||
#include "bsp_uart.h"
|
||||
#include "bsp_rc522.h"
|
||||
#include "bsp_beep.h"
|
||||
#include "checksum.h"
|
||||
#include "cmsis_os.h"
|
||||
#include "elog.h"
|
||||
@@ -46,6 +48,10 @@ static float target_v_w = 0; // 原地旋转分量
|
||||
static uint8_t car_running = 0; // 小车运行状态(1=运行,0=停止)
|
||||
static uint8_t car_speed_percent = 0; // 当前整体速度百分比(0~100)
|
||||
static uint16_t car_target_station = 0; // 目标站点编号
|
||||
static uint8_t car_target_reached = 0; // 到站锁存,避免重复触发
|
||||
|
||||
#define CAR_STATION_MIN ((uint16_t)STATION_1)
|
||||
#define CAR_STATION_MAX ((uint16_t)STATION_2)
|
||||
|
||||
/* 4个电机的 PID 控制器 */
|
||||
static PID_TypeDef motor_pid[MOTOR_COUNT];
|
||||
@@ -85,6 +91,46 @@ static void CarCtrl_StopAll(void)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 到站蜂鸣提示
|
||||
* @param times 蜂鸣次数
|
||||
*/
|
||||
static void CarCtrl_BeepTimes(uint8_t times)
|
||||
{
|
||||
for (uint8_t i = 0; i < times; i++) {
|
||||
BEEP_On();
|
||||
osDelay(120);
|
||||
BEEP_Off();
|
||||
osDelay(120);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 运行期间检测是否到达目标站点
|
||||
*/
|
||||
static void CarCtrl_CheckTargetStation(void)
|
||||
{
|
||||
rc522_card_info_t card;
|
||||
station_id_t station;
|
||||
|
||||
if (car_running == 0U || car_target_reached != 0U || car_target_station == 0U) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (rc522_get_new_card(&card) == 0U) {
|
||||
return;
|
||||
}
|
||||
|
||||
station = rc522_match_station(card.uid, card.uid_len);
|
||||
if ((uint16_t)station == car_target_station) {
|
||||
car_running = 0U;
|
||||
car_target_reached = 1U;
|
||||
CarCtrl_StopAll();
|
||||
elog_i(Protocol_TAG, "到达目标站点%u,停车并蜂鸣", car_target_station);
|
||||
CarCtrl_BeepTimes(3U);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 按当前 car_speed_percent 设置所有电机速度
|
||||
*/
|
||||
@@ -155,8 +201,8 @@ void CarCtrl_UpdateClosedLoop(void)
|
||||
const char* motor_names[] = {"LR", "LF", "RF", "RR"};
|
||||
static uint32_t last_log_time = 0;
|
||||
if (HAL_GetTick() - last_log_time > 500) {
|
||||
elog_d(Protocol_TAG, "M[%s] T:%.1f A:%.1f Pw:%d",
|
||||
motor_names[i], target_rpms[i], actual_rpm, (int16_t)final_pwm);
|
||||
elog_d(Protocol_TAG, "M[%s] T:%.1f A:%.1f Pw:%d",
|
||||
motor_names[i], target_rpms[i], actual_rpm, (int16_t)final_pwm);
|
||||
if (i == MOTOR_COUNT - 1) last_log_time = HAL_GetTick();
|
||||
}
|
||||
}
|
||||
@@ -184,11 +230,30 @@ static void CarCtrl_HandleCommand(const char *cmd_payload)
|
||||
// 启动/停止命令(仅作为自动循迹任务的启动/暂停信号,不直接控制电机)
|
||||
if (strncmp(cmd_payload, "ST", 2) == 0) {
|
||||
if (strcmp(arg + 1, "RUN") == 0) {
|
||||
if (car_target_reached != 0U) {
|
||||
car_running = 0U;
|
||||
CarCtrl_StopAll();
|
||||
elog_w(Protocol_TAG, "已到达站点,请先重新设置目标站点 (GS:xxx) 之后再启动");
|
||||
CarCtrl_BeepTimes(2U);
|
||||
return;
|
||||
}
|
||||
|
||||
if (car_target_station < CAR_STATION_MIN || car_target_station > CAR_STATION_MAX) {
|
||||
car_running = 0U;
|
||||
CarCtrl_StopAll();
|
||||
elog_w(Protocol_TAG, "未设置有效站点,拒绝启动。请先下发 GS:001 或 GS:002");
|
||||
CarCtrl_BeepTimes(2U);
|
||||
return;
|
||||
}
|
||||
|
||||
car_running = 1;
|
||||
car_target_reached = 0;
|
||||
elog_i(Protocol_TAG, "小车自动循迹启动, speed=%u%%, station=%u", car_speed_percent,
|
||||
car_target_station);
|
||||
} else if (strcmp(arg + 1, "STOP") == 0) {
|
||||
car_running = 0;
|
||||
car_target_reached = 0;
|
||||
CarCtrl_StopAll();
|
||||
elog_i(Protocol_TAG, "小车自动循迹暂停");
|
||||
} else {
|
||||
elog_w(Protocol_TAG, "未知启动/停止命令: %s", cmd_payload);
|
||||
@@ -225,12 +290,17 @@ static void CarCtrl_HandleCommand(const char *cmd_payload)
|
||||
|
||||
// 解析站点编号(0~999)
|
||||
if (sscanf(arg + 1, "%u", &station) == 1) {
|
||||
if (station > 999U) {
|
||||
station = 999U;
|
||||
if (station < CAR_STATION_MIN || station > CAR_STATION_MAX) {
|
||||
elog_w(Protocol_TAG, "站点%03u未配置,目前仅支持 %03u~%03u", station,
|
||||
CAR_STATION_MIN, CAR_STATION_MAX);
|
||||
CarCtrl_BeepTimes(2U);
|
||||
return;
|
||||
}
|
||||
|
||||
car_target_station = (uint16_t)station;
|
||||
car_target_reached = 0;
|
||||
elog_i(Protocol_TAG, "设置目标站点: %03u", car_target_station);
|
||||
CarCtrl_BeepTimes(1U);
|
||||
} else {
|
||||
elog_w(Protocol_TAG, "站点参数解析失败: %s", cmd_payload);
|
||||
}
|
||||
@@ -345,6 +415,9 @@ void CarCtrl_Task(void *argument) {
|
||||
CarCtrl_HandleCommand(cmd_payload);
|
||||
}
|
||||
|
||||
/* 1.1 运行中检查 RFID 是否到达目标站点 */
|
||||
CarCtrl_CheckTargetStation();
|
||||
|
||||
/* 2. 执行 PID 闭环控制更新 */
|
||||
CarCtrl_UpdateClosedLoop();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user