Skip to content

由于IDF/FreeRTOS的大多数的API都是C语言开发的,使用起来过于繁琐 所以HXC队内有些对C语言API的二次封装库

仓库链接

HXC_CAN

HXC_CAN为接口类

下面的示例基于HXC_TWAI类

发送消息

发送消息使用esp_err_t send(HXC_CAN_message_t message) - HXC_CAN_message_t CAN消息结构体

//CAN消息结构体
struct HXC_CAN_message_t{
  bool extd=0;           /**< 扩展帧格式标志(29位ID) */
  bool rtr=0;            /**< 远程帧标志 */
  bool self=0;           /**< 自我接收请求。接收时无效。 */
  uint32_t identifier;                /**< 11或29位标识符 */
  uint8_t data_length_code;           /**< 数据长度代码 */
  uint8_t data[8];    /**< 数据字节(在RTR帧中无关) */
};

示例

HXC_TWAI twai(8,18,CAN_RATE_1MBIT);
twai.setup();

//创建发送数据结构体
HXC_CAN_message_t send_message;
send_message.identifier=0x01;
send_message.data_length_code=8;
for (size_t i = 0; i < send_message.data_length_code; i++){
send_message.data[i]=i;
}
auto ret=twai.send(&send_message);

接收CAN消息

接收消息被封装为了回调函数的形式 即每个你需要编写地址所对应的回调函数,当接收到对应地址的CAN消息时会自动调用CAN回调函数

void add_can_receive_callback_func(int addr, HXC_can_feedback_func func);

添加用户自定义的CAN消息接收回调函数,用于处理特定地址的CAN消息。

  • 参数:
  • addr: 要处理的消息的地址。
  • func: 回调函数,当收到对应地址的消息时执行,可以是lambda表达式、函数指针、静态类成员函数或std::function。 using HXC_can_feedback_func= std::function<void(HXC_CAN_message_t* can_message)>;

注册CAN回调函数示例

#include "HXC_TWAI.hpp"

HXC_TWAI CAN_BUS(/*TX=*/8, /*RX=*/18);

void func2(twai_message_t* can_message){
    //打印收到的数据
    for(int i=0;i<can_message->data_length_code;i++){
      Serial.print(can_message->data[i],HEX);
      Serial.print(" ");
    }
    Serial.println();
}

void setup(){
  CAN_BUS.setup();//必须初始化CAN总线才可以使用
  CAN_BUS.add_can_receive_callback_func(0x255,
    [](twai_message_t* can_message){//lamda表达式
      //打印收到的数据
      for(int i=0;i<can_message->data_length_code;i++){
        Serial.print(can_message->data[i],HEX);
        Serial.print(" ");
      }
      Serial.println();
    }
  );//收到0x255地址消息时自动调用这个lamda表达式

  CAN_BUS.add_can_receive_callback_func(0x245,func2);//收到0x245地址消息时自动调用func2
}

HXC::thread

基于FreeRTOS封装的类似std::thread的线程库 注意ESP32是支持std::thread的,但是使用起来较为麻烦,需要额外调用配置函数

使用指南

简单示例

//线程2
HXC::thread<void> hxcthread([](){
    while (1){
        Serial.println("task_func");
        delay(1000);
    }
});

void setup(){
    hxcthread.start();
}

注意 HXC::thread是个模板类,需要在创建类对象时指定传入参数的类型 HXC::thread<void>是不需要传参的类型 其他类型需要在start()函数中传递参数 下面是函数声明:

void start(
    ParamType parameter = {},
    const char *taskname=DEFAULT_TASK_NAME, 
    int stack_size = DEFAULT_STACK_SIZE, 
    UBaseType_t priority = DEFAULT_PRIORITY, 
    int core = tskNO_AFFINITY
)
  • parameter:传入线程函数的参数,当模板为void时无 start函数无这个参数
  • taskname:任务名称 有默认值
  • stack_size:堆栈大小 有默认值
  • priority:优先级 有默认值
  • core:运行核心 默认为任意核心

其他函数API

void stop():停止线程

void join():等待线程结束

xTaskHandle get_Handle():获取线程句柄