例10:帧头为0x33 ,无帧尾,使用modbus_crc16校验,一次性传输4个灯的状态
注意
每个页面仅建议在一个定时器中读取串口缓冲区的数据,在多个定时器中读取串口缓冲区的数据容易照成逻辑混乱。
新建一个空白工程
在工程中新建一个定时器tmDecode,tim设置为50,en设置为1,用于定时解析串口数据
新建数字控件n1,n2,n3,n4,用于显示解析出来的数据
假设串口屏获取4个led灯的开关状态,串口屏需要解析的参数为灯的状态(开或关)
注意
16进制发送时,可以忽略大小写,ff和FF是一样的,AA和aa是一样的,但是请不要写成Ff,Ab这样大小写混用
//含义:4个灯状态分别为:开、开、开、开,modbus_crc16校验值为 B0 68
33 01 01 01 01 B0 68
//含义:4个灯状态分别为:关、关、关、关,modbus_crc16校验值为 20 04
33 00 00 00 00 20 04
//含义:4个灯状态分别为:关、开、关、开,modbus_crc16校验值为 B0 04
33 00 01 00 01 B0 04
//含义:4个灯状态分别为:开、关、开、关,modbus_crc16校验值为 20 68
33 01 00 01 00 20 68
program.s中的配置如图所示
1//以下代码只在上电时运行一次,一般用于全局变量定义和上电初始化数据
2//全局变量定义目前仅支持4字节有符号整形(int),不支持其他类型的全局变量声明,如需使用字符串类型可以在页面中使用变量控件来实现
3int sys0=0,sys1=0,sys2=0
4
5//frameLength:每帧数据长度
6//getFrameFlag:是否找到帧头或帧尾标记
7int frameLength=7,getFrameFlag,crcval2
8
9bauds=115200 //波特率115200
10recmod=1 //打开主动解析
11page 0 //上电刷新第0页
解析定时器(tim为50)中的代码如下图所示
1while(usize>=frameLength&&getFrameFlag==0)
2{
3 crcval2=0
4 ucopy crcval2,5,2,0
5 prints crcval2,2
6 crcrest 1,0xffff
7 crcputu 0,5
8 prints crcval,2
9 if(u[0]==0x33&&crcval==crcval2)
10 {
11 //找到帧头,退出循环
12 getFrameFlag=1
13 }else
14 {
15 //如果帧头不对,就一直删除1个字节,直到不满足条件退出循环
16 udelete 1
17 }
18}
19if(getFrameFlag==1)
20{
21 n1.val=u[1]
22 n2.val=u[2]
23 n3.val=u[3]
24 n4.val=u[4]
25 udelete frameLength //删除已经解析过的数据
26 getFrameFlag=0 //清空标记变量
27}
定长hex-示例10-样例工程下载
演示工程下载链接: