关于openmv与stm32之间的串口通信实现

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

已经在研一度过快3个月了,研究生学习跟本科学习还是有很大区别的,要善于自己找资料善于自己总结,因此我也决定从现在开始时不时的写写博客总结后面每段时间遇到的各种困难以及解决方法,为以后工作积累经验也方便以后查阅。

这是我第一篇博客,之前都是在做关于树莓派和opencv的项目,前段时间老师也是给了我一个新项目的思路,也是要基于视觉处理的,但因为21年电赛刚过有些学弟在比赛时都用到了openmv,所以我也想试试用openmv来处理处理手上这个项目,也顺便重新认识认识老朋友stm32。

言归正传,基于openmv的图像处理可以说是非常简单的,官方给了各种库,但凡好好看看例子都能会用,但是openmv的引脚太少了以至于能实现的功能太单一,所以这时候openmv也就只能作为传感器,大多数功能还得靠stm32,既然openmv作为传感器,所以openmv与stm32之间必须实现通信,方式很多很多,我选择了最基础的串口通信。

虽然本科也干了不少STM32与各类传感器的通信,但这次依碰到一些小麻烦,在网上查了不少资料,但怎么说了要么就是给的代码不全不知道上下的联系,要么就是单纯在那讲STM32的串口通信跟题目根本不搭噶。

废话少说,直接边上代码边总结。(之前记得将openmv的P4接到stm32的PA10,P5接到PA9)

关于openmv的代码:

# Blob Detection and uart transport
import sensor, image, time,math
from pyb import UART
import json
# For color tracking to work really well you should ideally be in a very, very,
# very, controlled enviroment where the lighting is constant...
yellow_threshold   = (65, 100, -10, 6, 24, 51)
# You may need to tweak the above settings for tracking green things...
# Select an area in the Framebuffer to copy the color settings.

sensor.reset() # Initialize the camera sensor.
sensor.set_pixformat(sensor.RGB565) # use RGB565.
sensor.set_framesize(sensor.QQVGA) # use QQVGA for speed.
sensor.skip_frames(10) # Let new settings take affect.
sensor.set_auto_whitebal(False) # turn this off.
clock = time.clock() # Tracks FPS.

uart = UART(3, 115200)
def find_max(blobs):
    max_size=0
    for blob in blobs:
        if blob.pixels() > max_size:
            max_blob=blob
            max_size = blob.pixels()
    return max_blob

while(True):
    img = sensor.snapshot() # Take a picture and return the image.

    blobs = img.find_blobs([yellow_threshold])

    img_data=bytearray([0x2C,7,1,2,3,4,0X5B])

    uart.write(img_data)

这段代码原型是官方的寻找最大色块的代码,只是拿来简单做一下串口传输数据,因此删掉很多,核心成分在最后两行,其中要注意的是,用到了bytearry(),所以在开头要import math,其中第0位为开始标志,最后一位为结束标志,第1位为总位数7,其他为要传输的数据。

关于stm32的代码:

(1)usart.c

#include "sys.h"
#include "usart.h"	
#include "openmv.h"
#include "lcd.h"
// 	 
//如果使用ucos,则包括下面的头文件即可.
#if SYSTEM_SUPPORT_OS
#include "includes.h"					//ucos 使用	  
#endif
	  
 

//
//加入以下代码,支持printf函数,而不需要选择use MicroLIB	  
#if 1
#pragma import(__use_no_semihosting)             
//标准库需要的支持函数                 
struct __FILE 
{ 
	int handle; 
}; 

FILE __stdout;       
//定义_sys_exit()以避免使用半主机模式    
void _sys_exit(int x) 
{ 
	x = x; 
} 
//重定义fputc函数 
int fputc(int ch, FILE *f)
{ 	
	while((USART1->SR&0X40)==0);//循环发送,直到发送完毕   
	USART1->DR = (u8) ch;      
	return ch;
}
#endif
 
#if EN_USART1_RX   //如果使能了接收
//串口1中断服务程序
//注意,读取USARTx->SR能避免莫名其妙的错误   	
u8 USART_RX_BUF[USART_REC_LEN];     //接收缓冲,最大USART_REC_LEN个字节.
//接收状态
//bit15,	接收完成标志
//bit14,	接收到0x0d
//bit13~0,	接收到的有效字节数目
u16 USART_RX_STA=0;       //接收状态标记	

//初始化IO 串口1 
//bound:波特率
void uart_init(u32 bound){
   //GPIO端口设置
  GPIO_InitTypeDef GPIO_InitStructure;
	USART_InitTypeDef USART_InitStructure;
	NVIC_InitTypeDef NVIC_InitStructure;
	
	RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA,ENABLE); //使能GPIOA时钟
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,ENABLE);//使能USART1时钟
 
	//串口1对应引脚复用映射
	GPIO_PinAFConfig(GPIOA,GPIO_PinSource9,GPIO_AF_USART1); //GPIOA9复用为USART1
	GPIO_PinAFConfig(GPIOA,GPIO_PinSource10,GPIO_AF_USART1); //GPIOA10复用为USART1
	
	//USART1端口配置
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9 | GPIO_Pin_10; //GPIOA9与GPIOA10
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;//复用功能
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;	//速度50MHz
	GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; //推挽复用输出
	GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; //上拉
	GPIO_Init(GPIOA,&GPIO_InitStructure); //初始化PA9,PA10

   //USART1 初始化设置
	USART_InitStructure.USART_BaudRate = bound;//波特率设置
	USART_InitStructure.USART_WordLength = USART_WordLength_8b;//字长为8位数据格式
	USART_InitStructure.USART_StopBits = USART_StopBits_1;//一个停止位
	USART_InitStructure.USART_Parity = USART_Parity_No;//无奇偶校验位
	USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//无硬件数据流控制
	USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;	//收发模式
  USART_Init(USART1, &USART_InitStructure); //初始化串口1
	
  USART_Cmd(USART1, ENABLE);  //使能串口1 
	
	//USART_ClearFlag(USART1, USART_FLAG_TC);
	
#if EN_USART1_RX	
	USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);//开启相关中断

	//Usart1 NVIC 配置
  NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;//串口1中断通道
	NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=3;//抢占优先级3
	NVIC_InitStructure.NVIC_IRQChannelSubPriority =3;		//子优先级3
	NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;			//IRQ通道使能
	NVIC_Init(&NVIC_InitStructure);	//根据指定的参数初始化VIC寄存器、

#endif
	
}


void USART1_IRQHandler(void)                	//串口1中断服务程序
{
	u8 Res;
#if SYSTEM_SUPPORT_OS 		//如果SYSTEM_SUPPORT_OS为真,则需要支持OS.
	OSIntEnter();    
#endif
	if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)  //接收中断(接收到的数据必须是0x0d 0x0a结尾)
	{
		Res =USART_ReceiveData(USART1);//(USART1->DR);	//读取接收到的数据
		Openmv_Receive_Data(Res);
		Openmv_Data();
		if((USART_RX_STA&0x8000)==0)//接收未完成
		{
			if(USART_RX_STA&0x4000)//接收到了0x0d
			{
				if(Res!=0x0a)USART_RX_STA=0;//接收错误,重新开始
				else USART_RX_STA|=0x8000;	//接收完成了 
			}
			else //还没收到0X0D
			{	
				if(Res==0x0d)USART_RX_STA|=0x4000;
				else
				{
					USART_RX_BUF[USART_RX_STA&0X3FFF]=Res ;
					USART_RX_STA++;
					if(USART_RX_STA>(USART_REC_LEN-1))USART_RX_STA=0;//接收数据错误,重新开始接收	  
				}		 
			}
		}   		 
  } 
#if SYSTEM_SUPPORT_OS 	//如果SYSTEM_SUPPORT_OS为真,则需要支持OS.
	OSIntExit();  											 
#endif
} 
#endif	

 



(2)usart.h

#ifndef __USART_H
#define __USART_H
#include "stdio.h"	
#include "stm32f4xx_conf.h"
#include "sys.h" 
#define USART_REC_LEN  			200  	//定义最大接收字节数 200
#define EN_USART1_RX 			1		//使能(1)/禁止(0)串口1接收
	  	
extern u8  USART_RX_BUF[USART_REC_LEN]; //接收缓冲,最大USART_REC_LEN个字节.末字节为换行符 
extern u16 USART_RX_STA;         		//接收状态标记	
//如果想串口中断接收,请不要注释以下宏定义
void uart_init(u32 bound);
#endif

采用的是官方已经包含的串口代码,但凡用过stm32的都有这段代码,只是在Res =USART_ReceiveData(USART1)后面增加了两行关于openmv的函数。

(3)openmv.c

#include "openmv.h"
#include "usart.h"
int openmv[7];//stm32接收数据数组
int16_t data1;
int16_t data2;
int16_t data3;
int16_t data4;



int i=0;

void Openmv_Receive_Data(int16_t data)//接收Openmv传过来的数据
{
	static u8 state = 0;
	if(state==0&&data==0x2C)
	{
		state=1;
		openmv[0]=data;
	}
	else if(state==1&&data==7)
	{
		state=2;
		openmv[1]=data;
	}
	else if(state==2)
	{
		state=3;
		openmv[2]=data;
	}
	else if(state==3)
	{
		state = 4;
		openmv[3]=data;
	}
	else if(state==4)
	{
        state = 5;
        openmv[4]=data;
	}
	else if(state==5)
	{
        state = 6;
        openmv[5]=data;
	}
	else if(state==6)		//检测是否接受到结束标志
	{
        if(data == 0x5B)
        {
            state = 0;
            openmv[6]=data;
            Openmv_Data();
        }
        else if(data != 0x5B)
        {
            state = 0;
            for(i=0;i<7;i++)
            {
                openmv[i]=0x00;
            }           
        }
	}    
	else
		{
			state = 0;
            for(i=0;i<7;i++)
            {
                openmv[i]=0x00;
            }
		}
}

void Openmv_Data(void)
{
    data1=openmv[0];
    data2=openmv[3];
    data3=openmv[4];
    data4=openmv[5];

}

(4)openmv.h

#include "sys.h"


extern int openmv[7];//stm32接收数据数组
extern int16_t data1;
extern int16_t data2;
extern int16_t data3;
extern int16_t data4;

void Openmv_Receive_Data(int16_t data);
void Openmv_Data(void);

(5)main.c

#include "sys.h"
#include "delay.h"
#include "usart.h"
#include "led.h"
#include "lcd.h"
#include "openmv.h"


int main(void)
{ 
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//设置系统中断优先级分组2
	delay_init(168);      //初始化延时函数
	uart_init(115200);		//初始化串口波特率为115200
	LED_Init();					  //初始化LED
 	LCD_Init();           //初始化LCD FSMC接口
	POINT_COLOR=RED;      //画笔颜色:红色				 	
  while(1) 
	{		 
		LCD_ShowNum(0,20,200,10,24);
		LCD_ShowNum(0,40,data1,10,24);
	} 
}

其中openmv[7]中的7与openmv代码中的bytearry()的总位数相同。

然后下载代码,可以在lcd显示屏上看到结果(lcd显示屏代码就不贴了,官方资料很详细)。

stm32与openmv串口通信,stm32,arm,嵌入式硬件

 文章来源地址https://www.toymoban.com/news/detail-620290.html

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

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

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

相关文章

  • stm32f103与openmv串口通信

    串口通信是指通过串行通信接口进行数据传输的一种通信方式。在串口通信中,数据被分成一个个的字节,按照一定的顺序依次发送和接收。串口通信通常使用UART(通用异步收发传输)协议进行数据传输。 串口通信在嵌入式系统中应用非常广泛,其主要用途包括: 调试和监

    2024年02月13日
    浏览(34)
  • Openmv识别Apriltag码并与stm32进行串口通信

            本文使用带有独立处理图像模块的摄像头Openmv进行Apriltag码的识别,并将Openmv与stm32进行串口通信,将Apriltag码的ID、中心位置相对于Openmv摄像头中心坐标的偏移量、以及Apriltag码相对于Openmv镜头的距离通过串口通信传输给stm32。         接线图Openmv通过电脑USB口

    2024年04月27日
    浏览(23)
  • openmv和STM32串口通信识别条形码、二维码(HAL库)

    因为自己的毕设用到了条形码识别,所以在这里写一篇关于使用openmv识别条形码和二维码并且与STM32实现串口通讯,希望能帮到以后用到这一模块的同学,STM32方面我使用的是STM32F103RCT6,并且使用HAL进行编写代码。 OpenMV端:由图知UART_RX—P5 ------ UART_TX—P4 2.STM32端:这里我使用

    2023年04月13日
    浏览(36)
  • 关于openmv与stm32通信数据传输遇到的问题

      遇到smt32与openmv无法通信,或者数据对不上。 上面的是openmv端发给stm32端的数据 %c4 b‘  ’:是stm32打印接收到的数据  逐个排查: openmv与pc端串口助手正常发收。stm32与pc端也可以正常发,但是接收数据的时候不能正常接收。 利用LED灯debug。   确定问题出在stm32端的中断服

    2024年02月15日
    浏览(21)
  • STM32串口通信详解(嵌入式学习)

    时钟信号在电子领域中是指用于同步和定时电路操作的周期性信号。它在数字系统和通信系统中起着至关重要的作用,用于协调各个组件之间的数据传输和操作。 时钟信号有以下几个重要的方面: 频率:时钟信号的频率是指单位时间内信号周期的数量。它通常以赫兹(Hz)为

    2024年02月09日
    浏览(58)
  • 树莓派与STM32之间串口通信

    目录 一、树莓派串口通信模块介绍 二、树莓派蓝牙、串口引脚映射对换步骤 1.启动串口 2. 禁用蓝牙(硬件串口与mini串口映射对换) 3.验证是否交换成功 三、树莓派安装mini串口调试助手 四、树莓派与电脑串口调试 五、树莓派与STM32串口调试 树莓派串口通信与蓝牙模块的基

    2024年02月16日
    浏览(64)
  • 【嵌入式学习-STM32F103-USART串口通信】

    4-1 基本流程 4-2 整体代码 4-2-1 main.c 4-2-2 Serial.c 4-2-3 Serial.h 5-1 查询 5-2 中断 5-3 整体代码 5-3-1 main.c 5-3-2 Serial.c 5-3-3 Serial.h 6-1 使用状态机接收数据包的思路 6-2 串口收发HEX数据包 6-2-1 main.c 6-2-2 Serial.c 6-2-3 Serial.h 6-3串口收发文本数据包 6-3-1 main.c 6-3-2 Serial.c 6-3-3 Serial.h 全双工:打

    2024年02月15日
    浏览(46)
  • K210视觉循迹,STM32之间串口通信 #智能车

    目录 个人感慨与感悟 K210视觉循迹 本人是一名大二的二本学生,本篇文章记录一下我这一年多的学习历程(主要还是针对标题的内 容)。 下面是我的一些经历和感悟,不感兴趣的可以直接跳过 -——————————        高考完之后,在我收到录取通知书之后,父母让

    2024年01月19日
    浏览(27)
  • 【嵌入式知识08】STM32的USART串口通信,给上位机连续发送Hello Windows!

    本文主要介绍串口协议和RS-232、485标准,以及RS232、485电平与TTL电平的区别,了解\\\"USB/TTL转232\\\"模块的工作原理;并完成一个STM32的USART串口通讯程序。   串口通信(Serial Communication)的概念非常简单,串口按位(bit)发送和接收字节的通信方式。尽管比按字节(byte)的并行通信

    2024年02月13日
    浏览(39)
  • 嵌入式毕设分享 stm32与openmv的目标跟踪系统

    文章目录 0 前言 课题简介 设计框架 3 硬件设计 4 软件设计 判断被测物体所在区域 5 最后 🔥 这两年开始毕业设计和毕业答辩的要求和难度不断提升,传统的毕设题目缺少创新和亮点,往往达不到毕业答辩的要求,这两年不断有学弟学妹告诉学长自己做的项目系统达不到老师

    2024年02月13日
    浏览(35)

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

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

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

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

二维码1

领取红包

二维码2

领红包