如何实现Qt上位机软件串口的按字节数据处理?

1 篇文章 0 订阅

1.Qt串口类的选择

最近在做一个小项目,需要用到Qt做上位机软件,本人也是边学边做,买了本《QtCreator快速入门》看了看就动手了,由于初学不是很了解Qt5的官方资源,一开始串口开发使用的是第三方串口类QExtSerialPort,但是后来发现这个第三方串口类似乎不提供串口信息的查询,就果断放弃了。
同时也发现Qt5本身是提供串口类的,所以就用了官方资源,官方的串口类是提供串口信息查询,也就可以实现上位机软件的的串口号查找功能了,人性化很多。

2.如何实现Qt上位机软件串口的按字节数据处理?

这部分我在网上找了许多资料都不太管用,一些常见的学习资料,基本上都是说,在槽函数里使用QByteArray类型变量直接读出串口对象的全部数据,资料范例如下:

void Widget::readMyCom() //读取串口数据并显示出来
{
	QByteArray temp = myCom->readAll();
	//读取串口缓冲区的所有数据给临时变量 temp
	ui->textBrowser->insertPlainText(temp);
	//将串口的数据显示在窗口的文本浏览器中
}

在我这个项目里,需要从STM32(下位机)的串口接收6字节长度的数据,然后上位机软件接收数据,再做进一步处理工作。 显然上面的方法不适合,因为以上读出来的数据是一个流式文本,时长时短,不好控制长度。经过我仔细地检索信息,功夫不负有心人,终于找到了解决办法,大家可以参考这个知乎问答:

https://www.zhihu.com/question/46717728?sort=created

3.我的例子

首先是下位机部分,我这里测试时是在定时器更新中断中完成串口发送的,代码如下:

char num = 0;
int SHU = 0;
char DataBuff[6]={0x00};
float i = 0.0;
void TIM2_IRQHandler( void )
{
	if( TIM_GetITStatus( TIM2,TIM_IT_Update )!= RESET )
	{
		TIM_ClearITPendingBit( TIM2,TIM_IT_Update );
		
		SHU = i*100;//取四个整数和两个小数,i放大100倍,方便取小数
		//注意取出来的数必须加0x30
		//要以字符的形式发送才行,上位机软件才可以用qDebug()打印出来
		DataBuff[0] =     SHU/100000+0x30;
		DataBuff[1] = (   SHU%100000)/10000+0x30;
		DataBuff[2] = ((  SHU%100000)%10000)/1000+0x30;
		DataBuff[3] = ((( SHU%100000)%10000)%1000)/100+0x30;
		DataBuff[4] = ((((SHU%100000)%10000)%1000)%100)/10+0x30;
		DataBuff[5] = ((((SHU%100000)%10000)%1000)%100)%10+0x30;
		
		USART1->SR;//空读SR,避免硬件上电后,首字节发送丢失
		for( num=0;num<6;num++ )
		{
			USART_SendData( USART1,DataBuff[num]);
			while( USART_GetFlagStatus(USART1,USART_FLAG_TC)==RESET );
			USART_ClearFlag( USART1,USART_FLAG_TC );
		}
		if(i==1500) i=0;
		else i++;
	}
}

再是Qt上位机软件的信号和槽函数连接:

//连接信号至槽函数:串口有数据就读串口
connect(mycom,SIGNAL(readyRead()),this,SLOT(MyReadData()));

最后是槽函数和打印信息:

char DataBuff[6] = {0x00};//在类中定义
unsigned char cnt = 0;    //在类中定义
float distance = 0.0;     //在类中定义
void MainWindow::MyReadData( void )
{
    char ch = 0;
    while( mycom->read(&ch,1) )
    {
        DataBuff[cnt] = ch;
        cnt++;
        if( cnt == 6 )
        {
            cnt = 0;
            distance = (DataBuff[0]-0x30)*1000+(DataBuff[1]-0x30)*100+(DataBuff[2]-0x30)*10+
                       (DataBuff[3]-0x30)+     (DataBuff[4]-0x30)*0.1+(DataBuff[5]-0x30)*0.01;
            qDebug("%4.2f",distance);
            qDebug()<<DataBuff;
        }
    }
}

调试信息

  • 0
    点赞
  • 55
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 7
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Hi,Man go!

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值