SBUS协议:SBUS解析与合成
在说协议之前,我想强调一点:信号要取反,硬件取反!!!!!至于为什么强调,我会在后面解释,你们先记住。
SBUS协议:使用的是串口的通讯,直接可以用串口发出,但有几点仍需要注意: 1.串口配置:100k波特率,8位数据位(在stm32中要选择9位),偶校验(EVEN),2位停止位,无控流,25个字节, 2.协议格式:(8字节) [startbyte] [data1][data2]…[data22][flags][endbyte] startbyte=0x0f; endbyte=0x00; flags标志位我没有用到; data1…data22:对应16个通道(ch1-ch16),每个通道11bit(228=1611=176); 数据范围在0-2047之间,基本上是1102~1927,中值为1500;
4.接下来要说的是它的间隔问题:它分两种模式(我记得是叫高速模式和普通模式) 高速模式:每隔7ms一帧数据,因为两帧的间隔只有超过3ms,才会被接受; 而根据波特率计算一下,发送25字节需要的时间+3~4ms=7ms 普通模式:每隔14ms一帧数据;
5.数据的解析跟合并我都下载了px4的源码,写成.c格式, 详细代码,我已经上传到我的博客下载页上,有兴趣的小伙伴,可以去下载一下;
#include "Sbus.h"
#include "bsp_usart1.h"
#include "string.h"
uint16_t values[16]={0};
void sbus_out(uint16_t num_values)
{
int i=0;
uint16_t value=0;
uint8_t byteindex = 1;
uint8_t offset = 0;
uint8_t oframe[25] = { 0 };
memset(oframe,0,25);
oframe[0]=0x0f;
oframe[24]=0x00;
for (i = 0; (i < num_values) && (i < 16); ++i)
{
value = (unsigned short)(((values[i] - SBUS_SCALE_OFFSET) / SBUS_SCALE_FACTOR) + .5f);
if (value > 0x07ff)
{
value = 0x07ff;
}
while (offset >= 8)
{
++byteindex;
offset -= 8;
}
oframe[byteindex] |= (value << (offset)) & 0xff;
oframe[byteindex + 1] |= (value >> (8 - offset)) & 0xff;
oframe[byteindex + 2] |= (value >> (16 - offset)) & 0xff;
offset += 11;
}
for (i=0;i<25;i++)
{
while(USART_GetFlagStatus(USART1,USART_FLAG_TC) == RESET);
USART_SendData(USART1, (uint16_t)oframe[i]);
}
}
void sbus_decode(unsigned char *frame)
{
unsigned int pick=0,channel=0,value1=0,piece=0;
const struct sbus_bit_pick *decode;
for (channel = 0; channel < 16; channel++)
{
value1 = 0;
for (pick = 0; pick < 3; pick++)
{
decode = &sbus_decoder[channel][pick];
if (decode->mask != 0)
{
piece = frame[1 + decode->byte];
piece >>= decode->rshift;
piece &= decode->mask;
piece <<= decode->lshift;
piece &= 0x07ff;
value1 |= piece;
}
}
values[channel] = (uint16_t)(value1 * SBUS_SCALE_FACTOR + .5f) + SBUS_SCALE_OFFSET;
if(channel==1)
{
values[channel]=3029-values[channel];
}
}
}
合成函数: void sbus_out(uint16_t num_values);//参数为通道数; values[16]就是对应的16个通道; 解析函数: void sbus_decode(unsigned char *frame); //frame为25个u8位数据;
看大家有几个问题,统一回答一下: 1.宏定义具体是多少: #define SBUS_FRAME_SIZE 25 #define SBUS_RANGE_MIN 200.0f #define SBUS_RANGE_MAX 1800.0f #define SBUS_TARGET_MIN 1000.0f #define SBUS_TARGET_MAX 2000.0f #define SBUS_SCALE_FACTOR ((SBUS_TARGET_MAX - SBUS_TARGET_MIN)/(SBUS_RANGE_MAX-SBUS_RANGE_MIN)) #define SBUS_SCALE_OFFSET (int)(SBUS_TARGET_MIN - (SBUS_SCALE_FACTOR * SBUS_RANGE_MIN + 0.5f))
2.下载页是多少: 需要下载积分,没有积分的兄弟给我发个邮件,我邮件给你:
3.flags标志位的具体作用: flags标志位是用来检测控制器与px4是否断开的标志位。 flags=1:控制器与接收器保持连接 flags=0:控制器与接收器断开(失控),px4会控制电机停转。 炸过一次机,就是因为遥控器与接收器之间断开连接了,结果这一位没有设置,导致四轴一直按照最后一次指令在飞。
