草庐IT

基于FPGA:运动目标检测(原理图+源码+硬件选择,可用毕设)

千歌叹尽执夏 2023-10-30 原文

目录

一、先看效果

    话不多说,先上视频看效果。

基于FPGA:运动目标检测

二、硬件选择

开发板Altera:EP4CE10F17C8
摄像头:OV5640
缓存数据:SDRAM
板子是自制的

三、目标追踪帧差法原理

    根据帧差法的实现流程,设计的双端口SDRAM控制器,一侧读写端口用做帧缓存,另一个端口用来缓存视频流,如图所示。

    在使用SDRAM双端口时,只要合理控制好读写地址,即可实现SDRAM两个读写端口独立运行。其中,SDRAM1端口用来作为帧缓存,SDRAM2端口用来测试算法的效果。
    首先,摄像头的输出格式是RGB565格式,经过颜色空间的转换转化为灰度数据流,写入到SDRAM1端口侧,等到延时一帧时刻到来,从第二帧开始两帧图像做差分。
    但此时得到的差分后的二值图像,由于光照背景的变化会有很大的噪声,因此还需要进行了形态学滤波。然后求得包围盒左上角和右下角像素坐标,与原始RGB图像叠加后重新写入到SDRAM2端口,此时VGA就可以显示处理后的图像的效果。

四、rgb2yuv灰度化处理(可参考正点原子说明书)

    从公式中(1)可以看到:由于FPGA不善于处理浮点数;这里完成了浮点数向定点数的转换;各个系数均扩大256倍,最后在计算完之后除以256,如公式(2)。

Y = 0.299 R + 0.587 G + 0.114 B
U = - 0.1687 R - 0.3313 G + 0.5 B + 128	(1)
V = 0.5 R - 0.4187 G - 0.0813 B + 128
Y=(77*R+150*G+29*B)»8;
U =(-43R-85G+128B+128*256)»8	(2)
V=(128R-107G-21B+128*256)»8

    在Verlog里面,使用组合逻辑不能直接按上述公式(2)在计算,不然组合逻辑延时太大,导致时序不收敛,这里就需要添加寄存器来切割流水线;利用FPGA 并行处理的特点加速计算。这里分三级流水线处理:第一级流水线计算所有乘法; 第二级流水线计算所有加法,把正的和负的分开进行加法;第三级流水线计算最终的和,若为负数取0。输入到输岀有三个clock的时延仿真波形如下图所示:

五、差分处理模块

    差分处理模块主要含有gary_shfit和 Diff_frame两个模块,对应图1的延时一帧和差分处理方框;摄像头数据一路数据写入sdram写口1侧,做为帧缓存,另一路是当前的图像数据,通过场信号控制延时从sdram 读口1侧读数据,这样,如下所示,sdr_rd为sdram读信号。

//延时读sdram控制

reg rd_en;
always@ (posedge clk or negedge resetb) begin
	if ( !resetb)
		rd_en <-#ck2q o;
	else if(~ivsync & ivsync_do)
		rd _en <-#ck2q l'bl;
	end
assign sdr_rd = rd_en & clken;
assign sdr_nwr -rd_en ;

    然后可完成两帧图像数据data_next - data_cur 差分。大于设定阈值threshold为 15 则认为时目标区域,设置为255;注意阈值可以根据需要调节控制。

//差分处理
reg[7:0]data_diff;
wire [7:0]data;
assign data=(data_next>data_cur) ?((data_next-data_cur > threshold)? 8'd255 :8'd0):( (data_next==data_our)? 8'd0:((data_cur-data_next 5 threshold) ? 8'd255 :8 'd0));

    如下图所示,可以看到 data_next - data_cur = 8’d130时,大于设定阈值15则输出数据post_img_Bit为255。

六、腐蚀和膨胀形态学滤波

    由于侦查法受环境影响,处理之后会有噪声,由于是二值图像,这里采用形态学滤波,先进行腐蚀处理就是去除小边界和孤立点﹔再进行膨胀处理,填充空洞。
    本次采用33窗口实现腐蚀和膨胀操作,如图1.6及1.7所示:

    如下图所示,得到的是matrix_p11~matrix_p339个像素数据组成3x3图像模板,这里通过行缓存设计(缓存了2行图像数据),延时时两行数据后,在如下黄线后第3行,得到完整的3x3图像模板。部分代码如下所示。

always@(posedge clk or negedge rst_n)
begin
	if(!rst_n)
		begin
		{matrix_p11, matrix_p12, matrix_p13} <= 3'b0;
		{matrix_p21, matrix_p22, matrix_p23} <= 3'b0;
		{matrix_p31, matrix_p32, matrix_p33} <= 3'b0;
		end
	else if(read_frame_href)
		begin
		if(read_frame_clken)	//Shift_RAM data read clock enable
			begin
			{matrix_p11, matrix_p12, matrix_p13} <= {matrix_p12, matrix_p13, row1_data};	//1th shift input
			{matrix_p21, matrix_p22, matrix_p23} <= {matrix_p22, matrix_p23, row2_data};	//2th shift input
			{matrix_p31, matrix_p32, matrix_p33} <= {matrix_p32, matrix_p33, row3_data};	//3th shift input
			end
		else
			begin
			{matrix_p11, matrix_p12, matrix_p13} <= {matrix_p11, matrix_p12, matrix_p13};
			{matrix_p21, matrix_p22, matrix_p23} <= {matrix_p21, matrix_p22, matrix_p23};
			{matrix_p31, matrix_p32, matrix_p33} <= {matrix_p31, matrix_p32, matrix_p33};
			end	
		end

腐蚀膨胀仿真波形图:

七、包围盒处理

    包围盒处理如上图的 boundary 灰度帧差法的得到二值图像,然后设计包围盒得到上下左右4点像素坐标,框出目标区域。
    通过行场信号,设计行列计数器,从而可以获取图像每个像素点的坐标信息,然后设计4个寄存器分别是edg_up 、 edg_down、edg_left、edg_right目标的上下左右四个点,实时与行列计数器比较,也就是求最大值( edg_down和edg_right)和最小值(edg_up和edg_left),代码如下所示:

always@(posedge clk or negedge rst_n)
begin
    if(!rst_n) begin
      edg_up    <=  10'd479;
      edg_down  <=  10'd0;
      edg_left  <=  10'd639;
      edg_right <=  10'd0;
	 end
	else if(vsync_rising) begin
	   edg_up    <=  10'd479;
      edg_down  <=  10'd0;
      edg_left  <=  10'd639;
      edg_right <=  10'd0;
	end
   else if(per_frame_clken & per_frame_href)begin
	  if(per_img_Y == 1'b1) begin
	     if(edg_up > v_cnt)
	       edg_up  <=v_cnt ;
	     else 
          edg_up  <=edg_up ;	
	
	     if(edg_down < v_cnt)
	       edg_down  <=v_cnt ;
	     else 
          edg_down  <=edg_down ;	
			 
		  if(edg_left > h_cnt)
	       edg_left  <= h_cnt ;
	     else 
          edg_left  <=edg_left ;	
	
	     if(edg_right < h_cnt)
	       edg_right  <=h_cnt ;
	     else 
          edg_right  <=edg_right ;			 
	  end
	end
end 

八、板子原理图及源码工程获取

①:直接点链接全费获取:基于FPGA的运动目标检测(硬件+原理图+源码+仿真+设计文档)
②:私信我或者添加微信半价获取(完整原理图、硬件、源码工程、技术指导)

有关基于FPGA:运动目标检测(原理图+源码+硬件选择,可用毕设)的更多相关文章

  1. ruby-on-rails - 如何使辅助方法在 Rails 集成测试中可用? - 2

    我在app/helpers/sessions_helper.rb中有一个帮助程序文件,其中包含一个方法my_preference,它返回当前登录用户的首选项。我想在集成测试中访问该方法。例如,这样我就可以在测试中使用getuser_path(my_preference)。在其他帖子中,我读到这可以通过在测试文件中包含requiresessions_helper来实现,但我仍然收到错误NameError:undefinedlocalvariableormethod'my_preference'.我做错了什么?require'test_helper'require'sessions_hel

  2. 叮咚买菜基于 Apache Doris 统一 OLAP 引擎的应用实践 - 2

    导读:随着叮咚买菜业务的发展,不同的业务场景对数据分析提出了不同的需求,他们希望引入一款实时OLAP数据库,构建一个灵活的多维实时查询和分析的平台,统一数据的接入和查询方案,解决各业务线对数据高效实时查询和精细化运营的需求。经过调研选型,最终引入ApacheDoris作为最终的OLAP分析引擎,Doris作为核心的OLAP引擎支持复杂地分析操作、提供多维的数据视图,在叮咚买菜数十个业务场景中广泛应用。作者|叮咚买菜资深数据工程师韩青叮咚买菜创立于2017年5月,是一家专注美好食物的创业公司。叮咚买菜专注吃的事业,为满足更多人“想吃什么”而努力,通过美好食材的供应、美好滋味的开发以及美食品牌的孵

  3. FOHEART H1数据手套驱动Optitrack光学动捕双手运动(Unity3D) - 2

    本教程将在Unity3D中混合Optitrack与数据手套的数据流,在人体运动的基础上,添加双手手指部分的运动。双手手背的角度仍由Optitrack提供,数据手套提供双手手指的角度。 01  客户端软件分别安装MotiveBody与MotionVenus并校准人体与数据手套。MotiveBodyMotionVenus数据手套使用、校准流程参照:https://gitee.com/foheart_1/foheart-h1-data-summary.git02  数据转发打开MotiveBody软件的Streaming,开始向Unity3D广播数据;MotionVenus中设置->选项选择Unit

  4. 基于C#实现简易绘图工具【100010177】 - 2

    C#实现简易绘图工具一.引言实验目的:通过制作窗体应用程序(C#画图软件),熟悉基本的窗体设计过程以及控件设计,事件处理等,熟悉使用C#的winform窗体进行绘图的基本步骤,对于面向对象编程有更加深刻的体会.Tutorial任务设计一个具有基本功能的画图软件**·包括简单的新建文件,保存,重新绘图等功能**·实现一些基本图形的绘制,包括铅笔和基本形状等,学习橡皮工具的创建**·设计一个合理舒适的UI界面**注明:你可能需要先了解一些关于winform窗体应用程序绘图的基本知识,以及关于GDI+类和结构的知识二.实验环境Windows系统下的visualstudio2017C#窗体应用程序三.

  5. kvm虚拟机安装centos7基于ubuntu20.04系统 - 2

    需求:要创建虚拟机,就需要给他提供一个虚拟的磁盘,我们就在/opt目录下创建一个10G大小的raw格式的虚拟磁盘CentOS-7-x86_64.raw命令格式:qemu-imgcreate-f磁盘格式磁盘名称磁盘大小qemu-imgcreate-f磁盘格式-o?1.创建磁盘qemu-imgcreate-fraw/opt/CentOS-7-x86_64.raw10G执行效果#ls/opt/CentOS-7-x86_64.raw2.安装虚拟机使用virt-install命令,基于我们提供的系统镜像和虚拟磁盘来创建一个虚拟机,另外在创建虚拟机之前,提前打开vnc客户端,在创建虚拟机的时候,通过vnc

  6. ruby-on-rails - self 在 Rails 模型中的值(value)是什么?为什么没有明显的实例方法可用? - 2

    我的rails3.1.6应用程序中有一个自定义访问器方法,它为一个属性分配一个值,即使该值不存在。my_attr属性是一个序列化的哈希,除非为空白,否则应与给定值合并指定了值,在这种情况下,它将当前值设置为空值。(添加了检查以确保值是它们应该的值,但为简洁起见被删除,因为它们不是我的问题的一部分。)我的setter定义为:defmy_attr=(new_val)cur_val=read_attribute(:my_attr)#storecurrentvalue#makesureweareworkingwithahash,andresetvalueifablankvalueisgiven

  7. ruby-on-rails - (Ruby,Rails) 基于角色的身份验证和用户管理...? - 2

    我正在寻找用于Rails的优质管理插件。似乎大多数现有的插件/gem(例如“restful_authentication”、“acts_as_authenticated”)都围绕着self注册等展开。但是,我正在寻找一种功能齐全的基于管理/管理角色的解决方案——但不是简单地附加到另一个非基于角色的解决方案。如果我找不到,我想我会自己动手......只是不想重新发明轮子。 最佳答案 RyanBates最近做了两个关于授权的railscast(注意身份验证和授权之间的区别;身份验证检查用户是否如她所说的那样,授权检查用户是否有权访问资源

  8. ruby - 在 Rakefile 中动态生成 Rake 测试任务(基于现有的测试文件) - 2

    我正在根据Rakefile中的现有测试文件动态生成测试任务。假设您有各种以模式命名的单元测试文件test_.rb.所以我正在做的是创建一个以“测试”命名空间内的文件名命名的任务。使用下面的代码,我可以用raketest:调用所有测试require'rake/testtask'task:default=>'test:all'namespace:testdodesc"Runalltests"Rake::TestTask.new(:all)do|t|t.test_files=FileList['test_*.rb']endFileList['test_*.rb'].eachdo|task|n

  9. ruby - 如何使用 Ruby 基于字母数字字符串生成颜色? - 2

    我想要像“嘿那里”这样的东西变成,例如,#316583。我希望将任意长度的字符串“归结”为十六进制颜色。我不知道从哪里开始。我在想,每个字符串的MD5散列都是不同的-但如何将该散列转换为十六进制颜色数字? 最佳答案 你可以只取几位前几位:require'digest/md5'color=Digest::MD5.hexdigest('Mytext')[0..5] 关于ruby-如何使用Ruby基于字母数字字符串生成颜色?,我们在StackOverflow上找到一个类似的问题:

  10. 建模分析 | 平面2R机器人(二连杆)运动学与动力学建模(附Matlab仿真) - 2

    目录0专栏介绍1平面2R机器人概述2运动学建模2.1正运动学模型2.2逆运动学模型2.3机器人运动学仿真3动力学建模3.1计算动能3.2势能计算与动力学方程3.3动力学仿真0专栏介绍?附C++/Python/Matlab全套代码?课程设计、毕业设计、创新竞赛必备!详细介绍全局规划(图搜索、采样法、智能算法等);局部规划(DWA、APF等);曲线优化(贝塞尔曲线、B样条曲线等)。?详情:图解自动驾驶中的运动规划(MotionPlanning),附几十种规划算法1平面2R机器人概述如图1所示为本文的研究本体——平面2R机器人。对参数进行如下定义:机器人广义坐标

随机推荐