K210 UART串口通信介绍与 STM32通信

这篇具有很好参考价值的文章主要介绍了K210 UART串口通信介绍与 STM32通信。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

目录

K210-UART串口通信相关函数:

使用K210串口的时候需要映射引脚:

K210与STM32串口通信 

发送单字节:

K210端

STM32端

发送数据包

K210端

STM32端 

K210的UART模块支持全双工通信,可以同时进行数据的发送和接收。在K210上使用UART串口通信,你可以连接外部设备,如传感器、显示器、WiFi模块等,实现数据的交换和控制。

K210-UART串口通信相关函数:

1.machine.UART():该函数用于初始化一个UART串口对象。你可以指定串口的编号(如UART1)、波特率、数据位、校验位、停止位、TX引脚和RX引脚等参数。

import machine

# 初始化串口
uart = machine.UART(1, baudrate=115200, tx=12, rx=13)

在这个示例中,我们使用machine.UART()函数初始化了一个串口对象,指定了串口的编号(1)、波特率(115200)、TX引脚(12)和RX引脚(13)。

或者可以:

machine.UART(uart,baudrate,bits,parity,stop,timeout, read_buf_len)

machine.UART()函数是用于初始化一个UART串口对象的函数,它可以接受以下参数:

  • uart:串口编号,可以为1、2、3。
  • baudrate:波特率,用于指定串口通信的数据传输速率。
  • bits:数据位数,可以为5、6、7、8。
  • parity:校验位,可以为None、0、1、2。
  • stop:停止位,可以为1、2。
  • timeout:超时时间,单位为毫秒。
  • read_buf_len:读缓冲区长度,用于指定串口读取数据时的缓冲区大小。

其中,uart参数是必需的,其他参数都有默认值。下面分别介绍这些参数的含义和用法:

  • uart:串口编号,可以为1、2、3。如果你的开发板上有多个串口,需要指定使用哪个串口进行通信。
  • baudrate:波特率,用于指定串口通信的数据传输速率。常见的波特率有9600、115200等,需要根据实际情况进行设置。
  • bits:数据位数,可以为5、6、7、8。一般情况下使用8位数据位即可。
  • parity:校验位,可以为None、0、1、2。校验位用于检查数据传输中是否出现错误,一般情况下可以设置为None。
  • stop:停止位,可以为1、2。停止位用于指定每个数据帧的结束位置,一般情况下使用1个停止位即可。
  • timeout:超时时间,单位为毫秒。当读取串口数据时,如果在超时时间内没有读取到任何数据,则会返回None。
  • read_buf_len:读缓冲区长度,用于指定串口读取数据时的缓冲区大小。如果读取的数据量较大,可以适当增大该值,以避免数据丢失。


2.uart.write():该函数用于向串口发送数据。你可以发送字符串或者字节数据。

# 发送数据
uart.write('Hello, UART!')

3.uart.read():该函数用于从串口接收数据。它会阻塞程序直到接收到指定数量的数据或者超时

# 接收数据
data = uart.read(10)
print(data)

这段代码从串口读取最多10个字节的数据,并将其打印出来。

4.uart.any():该函数用于检查串口是否有未读取的数据。如果有,返回值为True;否则返回False。

# 检查是否有未读取的数据
if uart.any():
    data = uart.read()
    print(data)

这段代码首先调用uart.any()函数检查串口是否有未读取的数据,如果有,则调用uart.read()函数将数据读取并打印出来。

5.uart.flush():该函数用于清空串口的缓冲区,将所有未读取的数据丢弃

使用K210串口的时候需要映射引脚:

# IO6→RX1,IO7→TX1
fm.register(6, fm.fpioa.UART1_RX, force=True)
fm.register(7, fm.fpioa.UART1_TX, force=True)

fm.register()函数是用于配置FPIOA(Flexible Peripheral I/O Assignments)的函数,它可以将指定的引脚与相应的功能进行绑定。

K210与STM32串口通信 

K210与STM32串口通信发送分为两种:一种是发送单字节,一种是发送数据包。因为发送的数据不一样,从而K210的代码和STM32的代码都是不一样的。

本篇文章只涉及K210发送给STM32。

发送单字节:

K210端

from machine import UART, Timer
from fpioa_manager import fm

#映射串口引脚
fm.register(6, fm.fpioa.UART1_RX, force=True)
fm.register(7, fm.fpioa.UART1_TX, force=True)
while True:
    text=uart.read() #读取数据

    if text: #如果读取到了数据
        uart.write('1')

STM32端

void Usart3_Init(unsigned int baud)
{
    GPIO_InitTypeDef gpio_initstruct;
	USART_InitTypeDef usart_initstruct;
	NVIC_InitTypeDef nvic_initstruct;
	
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART3, ENABLE);
	
	//PA2	TXD
	gpio_initstruct.GPIO_Mode = GPIO_Mode_AF_PP;
	gpio_initstruct.GPIO_Pin = GPIO_Pin_10;
	gpio_initstruct.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB, &gpio_initstruct);
	
	//PA3	RXD
	gpio_initstruct.GPIO_Mode = GPIO_Mode_IN_FLOATING;
	gpio_initstruct.GPIO_Pin = GPIO_Pin_11;
	gpio_initstruct.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_Init(GPIOB, &gpio_initstruct);
	
	usart_initstruct.USART_BaudRate = baud;
	usart_initstruct.USART_HardwareFlowControl = USART_HardwareFlowControl_None;		
	usart_initstruct.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;						
	usart_initstruct.USART_Parity = USART_Parity_No;									
	usart_initstruct.USART_StopBits = USART_StopBits_1;								
	usart_initstruct.USART_WordLength = USART_WordLength_8b;							
	USART_Init(USART3, &usart_initstruct);
	USART_Cmd(USART3, ENABLE);	
	USART_ITConfig(USART3, USART_IT_RXNE, ENABLE);									
	nvic_initstruct.NVIC_IRQChannel = USART2_IRQn;
	nvic_initstruct.NVIC_IRQChannelCmd = ENABLE;
	nvic_initstruct.NVIC_IRQChannelPreemptionPriority = 0;
	nvic_initstruct.NVIC_IRQChannelSubPriority = 1;
	NVIC_Init(&nvic_initstruct);

}
if(USART_ReceiveData(USART3)=='1')//K210
{
        numbert++;
}

发送数据包

K210端

def str_int(data_str):
    bb = binascii.hexlify(data_str)
    bb = str(bb)[2:-1]
    #print(bb)
    #print(type(bb))
    hex_1 = int(bb[0])*16
    hex_2 = int(bb[1],16)
    return hex_1+hex_2


def send_data(x,y,w,h,msg):
    start = 0x24
    end = 0x23
    length = 5
    class_num = 0x05 #例程编号
    class_group = 0xBB #例程组
    data_num = 0x00 #数据量
    fenge = 0x2c #逗号
    crc = 0 #校验位
    data = [] #数据组

    #参数都为0
    if x==0 and y==0 and w==0 and h ==0:
        pass
    else:
        #x(小端模式)
        low = x & 0xFF #低位
        high = x >> 8& 0xFF #高位
        data.append(low)
        data.append(fenge) #增加","
        data.append(high)
        data.append(fenge) #增加","

        #y(小端模式)
        low = y & 0xFF #低位
        high = y >> 8& 0xFF #高位
        data.append(low)
        data.append(fenge) #增加","
        data.append(high)
        data.append(fenge) #增加","

        #w(小端模式)
        low = w & 0xFF #低位
        high = w >> 8& 0xFF #高位
        data.append(low)
        data.append(fenge) #增加","
        data.append(high)
        data.append(fenge) #增加","

        #h(小端模式)
        low = h & 0xFF #低位
        high = h >> 8& 0xFF #高位
        data.append(low)
        data.append(fenge) #增加","
        data.append(high)
        data.append(fenge) #增加","

    if msg !=None:
        #msg
        for i in range(len(msg)):
            hec = str_int(msg[i])
            data.append(hec)
            data.append(fenge) #增加","
        #print(data)

    data_num = len(data)
    length += len(data)
    #print(length)

    send_merr = [length,class_num,class_group,data_num]
    for i in range(data_num):
        send_merr.append(data[i])
    #print(send_merr)

    #不加上CRC位,进行CRC运算
    for i in range(len(send_merr)):
        crc +=send_merr[i]
    crc = crc%256

    send_merr.insert(0,start) #插入头部
    send_merr.append(crc)
    send_merr.append(end)

    #print(send_merr)
    global send_buf
    send_buf = send_merr

首先是 str_int 函数,它的作用是将输入的字符串转换为整数。具体实现上,它使用了 Python 的标准库中的 binascii.hexlify 方法将输入的字符串 data_str 转换为十六进制表示的字节串,然后对于每一个字节,分别将其高四位和低四位转换成十进制数,并进行一定的运算,最终返回一个整数。

接下来是 send_data 函数,它的作用是组装一个特定格式的数据包。函数接受五个参数 x, y, w, h, msg,其中 x, y, w, h 是四个整数,msg 是一个字符串。根据这些参数,函数构建了一个包含起始标识、长度、例程编号、例程组、数据量、数据内容以及校验位的数据包。

在函数内部,首先定义了一些常量,如起始标识、结束标识、长度、例程编号、例程组等。然后根据传入的参数判断是否需要加入 x, y, w, h 这四个整数。如果这四个整数全部为 0,那么就不将它们加入数据包中,否则将它们按照小端模式(即低位在前、高位在后的顺序)加入到数据中。接下来是对传入的字符串 msg 进行处理,将其中每个字符转换为整数后加入数据中。

接着计算数据量和长度,并将所有数据组装成一个列表 send_merr。最后,计算校验位并将其加入到 send_merr 中,同时在开头和结尾分别加上起始标识和结束标识,最终得到一个完整的数据包。

STM32端 

char buf_msg[100] = {'\0'};
u8 new_flag = 0;
u8 r_index = 0;
u16 buf_crc = 0;
u8 tou_flag = 0;
u8 len_flag = 0;
u8 buf_len = 0;
char data[50];

void recv_k210msg(uint8_t recv_msg)
{
    if (recv_msg == '$')
    {
        new_flag = 1;
    }

    if (recv_msg == '#')
    {
        if (buf_len == r_index)
        {
            new_flag = 0;
            tou_flag = 0;
            len_flag = 0;

            buf_crc -= buf_msg[r_index - 1];
            buf_crc %= 256;

            if (buf_crc == buf_msg[r_index - 1])
            {
                deal_recvmsg();
            }
            else
            {
                r_index = 0;
                buf_crc = 0;
            }
        }
    }

    if (new_flag == 1)
    {
        if (recv_msg == '$' && tou_flag == 0)
        {
            tou_flag = 1;
        }
        else
        {
            buf_msg[r_index++] = recv_msg;
            buf_crc += recv_msg;
            if (len_flag == 0)
            {
                buf_len = buf_msg[0];
                len_flag = 1;
            }
        }
    }
}

void deal_recvmsg(void)
{
    u8 index, data_i = 0;
    u8 eg_num = buf_msg[1];
    u8 number = buf_msg[3];
    u8 i_duo = 0;
  
    if (r_index != buf_len)
    {
        buf_len = 0;
        return;
    }

    for (index = 0; index < number; index++)
    {
        if (buf_msg[4 + index] == 0x2c && i_duo == 0)
        {
            i_duo = 1;
            continue;
        }
        data[data_i++] = buf_msg[4 + index];
        i_duo = 0;
    }

    buf_crc = 0;
    r_index = 0;

    memset(buf_msg, 0, sizeof(buf_msg));
    deal_data(eg_num);
}

void deal_data(u8 egnum)
{
    u16 x, y, w, h;
    u8 msg[20] = {'\0'};
    u8 icopy = 0;
    u16 id = 999;
    switch (egnum)
    {
        case 1:
        case 5:
        case 6:
            x = data[1] << 8 | data[0];
            y = data[3] << 8 | data[2];
            w = data[5] << 8 | data[4];
            h = data[7] << 8 | data[6];
            break;

        case 2:
        case 3:
            x = data[1] << 8 | data[0];
            y = data[3] << 8 | data[2];
            w = data[5] << 8 | data[4];
            h = data[7] << 8 | data[6];
            while (*(data + 8 + icopy) != '\0')
            {
                msg[icopy] = *(data + 8 + icopy);
                icopy++;
            }
            break;

        case 4:
            x = data[1] << 8 | data[0];
            y = data[3] << 8 | data[2];
            w = data[5] << 8 | data[4];
            h = data[7] << 8 | data[6];
            id = data[8] << 8 | data[9];

            while (*(data + 10 + icopy) != '\0')
            {
                msg[icopy] = *(data + 10 + icopy);
                icopy++;
            }

            break;

        case 7:
        case 8:
            x = data[1] << 8 | data[0];
            y = data[3] << 8 | data[2];
            w = data[5] << 8 | data[4];
            h = data[7] << 8 | data[6];
            id = data[8];

            break;

        case 9:
            x = data[1] << 8 | data[0];
            y = data[3] << 8 | data[2];
            w = data[5] << 8 | data[4];
            h = data[7] << 8 | data[6];
            while (*(data + 8 + icopy) != '\0')
            {
                msg[icopy] = *(data + 8 + icopy);
                icopy++;
            }
            break;

        case 10:
        case 11:
            id = data[0];
            break;
    }
    
    k210_msg.class_n = egnum;
    k210_msg.x = x;
    k210_msg.y = y;
    k210_msg.w = w;
    k210_msg.h = h;
    k210_msg.id = id;
    strcpy((char*)k210_msg.msg_msg, (char*)msg);

    memset(data, 0, sizeof(data));
}
void USART2_IRQHandler(void)
{
	uint8_t Rx2_Temp;
	if (USART_GetITStatus(USART2, USART_IT_RXNE) != RESET)
	{
		Rx2_Temp = USART_ReceiveData(USART2);
		recv_k210msg(Rx2_Temp);
	}
}
  1. recv_k210msg 函数用于接收 K210 模块传来的消息,并根据特定的起始符号 $ 和结束符号 # 进行消息解析。具体流程如下:

    • 当接收到 $ 符号时,表示开始接收新的消息,将 new_flag 置为 1。
    • 当接收到 # 符号时,表示消息接收完毕,进行消息处理。如果消息长度符合要求,计算消息校验和并调用 deal_recvmsg 进行处理。
    • 在接收到其他字符时,如果处于接收新消息状态,将字符存入缓冲区 buf_msg 中,并更新校验和 buf_crc
  2. deal_recvmsg 函数用于对接收到的消息进行处理,主要是根据消息类型和内容进行解析,并调用 deal_data 函数进行进一步处理。具体流程如下:

    • 根据消息中指定的格式提取数据,并调用 deal_data 函数进行处理。
    • 处理完成后,清空缓冲区 buf_msg 和相关标志位,以便接收下一条消息。
  3. deal_data 函数用于根据不同类型的消息对数据进行解析和处理。具体流程如下:

    • 根据消息的类型进行不同的数据解析操作,提取出消息中的有用信息,并赋值给 k210_msg 结构体。
    • 结构体 k210_msg 包含了消息的分类、位置信息、ID 信息以及消息内容。
    • 处理完成后,清空数据缓冲区 data

 有读者看到这里可能会想问,能不能用单字节的方式发送字符串,STM32中USART_ReceiveData(USART3)=='1'此处没法等于字符串。文章来源地址https://www.toymoban.com/news/detail-842662.html

到了这里,关于K210 UART串口通信介绍与 STM32通信的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 电赛备赛日记(一):K210与STM32串口通信

       拖更了n久的备赛日记终于来啦,最近实现了关于K210图像识别并将所需数据(即目标类别,目标在图像中的加权坐标)其中,加权坐标指K210识别到的目标并框出的框的宽和高与框左上顶点的坐标加权,希望以此来判断目标所处的位置并方便后续进行诸如寻迹,目标跟随等

    2024年02月04日
    浏览(60)
  • 亚博k210视觉模块与stm32双向通信

    【K210模块】使用UART模块发送和接收数据_KevinGuo457的博客-CSDN博客 K210的串口_uart_a.write_飞鸟211的博客-CSDN博客 ①每隔1s终端以及串口助手收到消息并显示 ②通过串口助手发送123,K210收到数据并显示 这里如果想要指定K210接收的数据,判断条件不能直接用==(原因参考上面的链接

    2024年04月23日
    浏览(100)
  • STM32CubeMx学习与K210串口通信+识别橘色色块——点亮小灯

     K210模块的串口发送代码 识别色块 +数字处理 这里zz是4个数字的数,则需要分成千百位和低二位传输 zz是距离。也映射了距离的算法 整体K210代码 STM32串口接受端函数 判断帧头帧尾 如果数据正常 判断 数据是否合格 若合格则点灯 否则灭灯 不要忘记加入

    2024年02月14日
    浏览(50)
  • STM32通过K210进行PID巡线,使用蓝牙模块与电脑通信从而进行P,I,D参数的调节

    目录 一.前言部分(废话部分) 二.K210色块识别 1.必要知识 2.色块识别 3.单片机的接收代码 三.通过蓝牙连接在电脑上实现PID的调参 我使用的是HAL库,如果你使用的是标准库的话可以根据对应标准库的函数进行更改即可 因为之前使用灰度传感器进行巡线,即使用上PID,最后的效果也

    2024年02月14日
    浏览(43)
  • K210追小球程序与STM32最小系统板通信(自主学习)

    本人先通过学习OPENMV,再延申到K210中。(主要是OPENMV我还没买屏幕,但是K210有)在OPENMV官网中,有相关追小球的函数,但是是用OPENMV单片机来进行调试的。在网上找到的相关源码,加载到OPENMV后发现帧数很慢。 学校实训的要求是要做出能追一定物体的平衡小车,我的小车的

    2024年02月16日
    浏览(40)
  • 【K210】K210学习笔记五——串口通信

    本人大四学生,电赛生涯已经走到尽头,一路上踩过不少坑,但运气也不错拿了两年省一,思来想去,决定开始写博客,将电赛经验分享一二,能力有限,高手轻喷。 往期的博客讲述了 K210 的感光元件模块 sensor 的配置,机器视觉模块 image 中部分函数的使用(目前是用 find

    2024年04月28日
    浏览(46)
  • STM32如何通过K210进行物体识别(1.开发环境搭建)

    本来参加智能物流机器人比赛是要用OpenMV的,但无奈于诸多因素只有K210可以使用,这也算是不幸中的万幸吧。这篇文章也作为我这一段时间的学习K210进行物体识别的复习与总结(因为种种原因,比赛也面临无法完成,大哭;人工智能小白一枚,欢迎各路大神指正,求轻喷)

    2023年04月10日
    浏览(41)
  • k210——maix bit串口通信

    k210 一共有 3个 uart ,每个 uart 可以进行自由的引脚映射。 一、API函数介绍 1.1 register(pin, function, force=True) K210 可以通过映射来改变引脚功能,设置引脚(pin)对应的外设功能(func),默认启用强制绑定参数(force=True) pin: 功能映射引脚 function: 芯片功能 force: 默认为Tru

    2024年02月15日
    浏览(43)
  • K210串口接收数据包

    目录 1.前言 2.代码部分 1.调用自带的库文件 2.将I/O19设置为UART1_RX功能并设置串口 3.数据接收函数 4.主程序             之前更新了K210与STM32之间的串口通信,是K210发送信息STM32接收信息,这篇博客讲解一下K210 DOCK接收数据包。  在使用 uart1 前,我们需要使用 fm 来对芯片引脚

    2024年02月15日
    浏览(45)
  • 【单片机】基于STM32的UART串口通信

    简单讲解一下UART通信协议,以及UART能够实现的一些功能,还有有关使用STM32CubeMX来配置芯片的一些操作。实验内容基于 正点原子精英板 开发板,单片机芯片为 STM32F103ZET6 。 在后面我会以我使用的STM32F429开发板来举例讲解(其他STM32系列芯片大多数都可以按照这些步骤来操作

    2024年01月17日
    浏览(70)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包