树莓派4B_OpenCv学习笔记13:OpenCv颜色追踪_程序手动调试HSV色彩空间_检测圆

今日继续学习树莓派4B 4G:(Raspberry Pi,简称RPi或RasPi)

 本人所用树莓派4B 装载的系统与版本如下:

 版本可用命令 (lsb_release -a) 查询:

 Opencv 版本是4.5.1:

 OpenCv颜色追踪_程序手动调试HSV色彩空间_检测灰度图中的圆

今日学习的程序主要是为了能够手动微调整好更为适合多变环境的HSV色彩空间

文章提供测试代码讲解,整体代码贴出、测试效果图

目录

实验目的:

实验大致过程视频:

完整实例代码贴出:

代码小结:

代码实验操作与测试结果图:

应用HSV阈值函数 cv2.inRange():

组合HSV阈值 cv2.bitwise_and():

形态学操作函数:(膨胀/腐蚀/开运算/闭运算):

高斯模糊cv2.GaussianBlur():

 霍夫圆变换来检测圆形:

网上查阅资料贴出:


实验目的:

实时地从视频流中检测特定颜色范围内的圆形物体。

用户可以通过Trackbars调整HSV颜色阈值来指定要检测的HSV颜色范围。使得程序对特定颜色小球的检测更为准确

检测到的圆形物体将在原始帧上被绘制出来,并根据其大小以不同的颜色和线宽进行区分。此外,如果检测到的圆的半径超过某个阈值(在这里是35),则会设置一个标志(buzz)。

实验全部过程视频:

OpenCv颜色追踪_程序手动调试HSV色彩空间_检测圆

完整实例代码贴出:

实时地从视频流中检测特定颜色范围内的圆形物体。

可以通过Trackbars调整HSV颜色阈值来指定要检测圆的颜色范围。

# -*- coding: utf-8 -*-
import cv2
import numpy as np
import time  kernel = np.ones((5,5),np.uint8)
# 从网络摄像头获取输入
cap = cv2.VideoCapture(0)time.sleep(0.5)# 将视频尺寸减小到320x240,这样rpi处理速度就会更快
cap.set(3,320)
cap.set(4,240)#第一个空回调函数
def nothing(x):pass# 创建一个供以后使用的窗口
cv2.namedWindow('HueComp')
cv2.namedWindow('SatComp')
cv2.namedWindow('ValComp')
cv2.namedWindow('closing')
cv2.namedWindow('tracking')# 创建跟踪条的最小和最大的色调,饱和度和价值
# 允许用户实时调整参数值HSV
cv2.createTrackbar('hmin', 'HueComp',12,179,nothing)
cv2.createTrackbar('hmax', 'HueComp',37,179,nothing)cv2.createTrackbar('smin', 'SatComp',96,255,nothing)
cv2.createTrackbar('smax', 'SatComp',255,255,nothing)cv2.createTrackbar('vmin', 'ValComp',186,255,nothing)
cv2.createTrackbar('vmax', 'ValComp',255,255,nothing)while(1):buzz = 0#读取帧并转换到HSV空间_, frame = cap.read()hsv = cv2.cvtColor(frame,cv2.COLOR_BGR2HSV)hue,sat,val = cv2.split(hsv)#获取Trackbar的当前值hmn = cv2.getTrackbarPos('hmin','HueComp')hmx = cv2.getTrackbarPos('hmax','HueComp')smn = cv2.getTrackbarPos('smin','SatComp')smx = cv2.getTrackbarPos('smax','SatComp')vmn = cv2.getTrackbarPos('vmin','ValComp')vmx = cv2.getTrackbarPos('vmax','ValComp')#应用HSV阈值hthresh = cv2.inRange(np.array(hue),np.array(hmn),np.array(hmx))sthresh = cv2.inRange(np.array(sat),np.array(smn),np.array(smx))vthresh = cv2.inRange(np.array(val),np.array(vmn),np.array(vmx))# 组合HSV阈值 使用按位与操作来组合三个HSV分量的阈值结果,从而得到颜色范围内所有像素的掩码。tracking = cv2.bitwise_and(hthresh,cv2.bitwise_and(sthresh,vthresh))#形态学操作#对掩码进行膨胀、闭操作和高斯模糊,以减少噪声并增强圆形物体的检测。dilation = cv2.dilate(tracking,kernel,iterations = 1)closing = cv2.morphologyEx(dilation, cv2.MORPH_CLOSE, kernel)closing = cv2.GaussianBlur(closing,(5,5),0)#使用霍夫圆变换来检测圆形。circles = cv2.HoughCircles(closing,cv2.HOUGH_GRADIENT,2,120,param1=120,param2=50,minRadius=10,maxRadius=0)#绘制检测到的圆形#如果检测到圆形,就在原始帧上绘制它们。根据圆形的半径大小,使用不同的颜色和线宽进行绘制。if circles is not None:x, y, r = circles[0][0]x_p = int(round(x))print (x_p)for i in circles[0,:]:if int(round(i[2])) < 30:cv2.circle(frame,(int(round(i[0])),int(round(i[1]))),int(round(i[2])),(0,255,0),5)cv2.circle(frame,(int(round(i[0])),int(round(i[1]))),2,(0,255,0),10)elif int(round(i[2])) > 35:cv2.circle(frame,(int(round(i[0])),int(round(i[1]))),int(round(i[2])),(0,0,255),5)cv2.circle(frame,(int(round(i[0])),int(round(i[1]))),2,(0,0,255),10)buzz = 1  cv2.imshow('HueComp',hthresh)cv2.imshow('SatComp',sthresh)cv2.imshow('ValComp',vthresh)cv2.imshow('closing',closing)cv2.imshow('tracking',frame)if cv2.waitKey(1) & 0xFF == ord('q'):cap.release()L_Motor.stop()R_Motor.stop()GPIO.cleanup()cv2.destroyAllWindows() breakcap.release()
cv2.destroyAllWindows() 

代码小结:

1、创建Trackbar

2、始化循环,读取帧并转换到HSV空间

3、获取Trackbar的当前值

4、应用HSV阈值

5、组合HSV阈值

6、形态学操作

7、检测圆形

8、绘制检测到的圆形

9、输出和判断

代码实验操作与测试结果图:

1、使用树莓派的USB摄像头拍摄一张球形物体的图片用于取色获取大致BGR色域范围:

我的颜色范围是:138   67   17

拍摄程序在这篇文章有提到:树莓派4B_OpenCv学习笔记4:测试摄像头_imread加载显示图像_imwrite保存图片_树莓派摄像头怎么保存照片-CSDN博客

2、运行程序将BGR颜色空间转换为HSV:

BGR_HSV转换程序在这篇文章有提到:

树莓派4B_OpenCv学习笔记6:OpenCv识别已知颜色_运用掩膜_树莓派 图像融合-CSDN博客

3、运行本次实验的程序,将TrackBar调整到差不多的HSV范围:

发现如果不进行调整直接运用第二步得到的颜色空间范围,那么将会检测到许多的“圆”:

然后根据HSV窗口展示轮廓,调整它们的最大值与最小值,使其掩膜中的目标圆球轮廓更清晰,而其余噪声点更小:

然后拿远点测试,以及将瓶盖侧放,看是否会误检测为圆:

应用HSV阈值函数 cv2.inRange()

    #应用HSV阈值
    hthresh = cv2.inRange(np.array(hue),np.array(hmn),np.array(hmx))
    sthresh = cv2.inRange(np.array(sat),np.array(smn),np.array(smx))
    vthresh = cv2.inRange(np.array(val),np.array(vmn),np.array(vmx))

  1. hthresh

    • np.array(hue): HSV图像中的色调通道(H)。
    • np.array(hmn): 色调通道的下限值。
    • np.array(hmx): 色调通道的上限值。
    • 输出: 一个二值图像,其中在hmnhmx之间的色调值被设置为白色,其他值被设置为黑色。
  2. sthresh

    • np.array(sat): HSV图像中的饱和度通道(S)。
    • np.array(smn): 饱和度通道的下限值。
    • np.array(smx): 饱和度通道的上限值。
    • 输出: 一个二值图像,其中在smnsmx之间的饱和度值被设置为白色,其他值被设置为黑色。
  3. vthresh

    • np.array(val): HSV图像中的亮度通道(V或I,取决于你如何称呼它)。
    • np.array(vmn): 亮度通道的下限值。
    • np.array(vmx): 亮度通道的上限值。
    • 输出: 一个二值图像,其中在vmnvmx之间的亮度值被设置为白色,其他值被设置为黑色。

Tip:之前的颜色追踪实验也用到了掩膜,inRange(),只不过指定的通道为HSV全部:

树莓派4B_OpenCv学习笔记12:OpenCv颜色追踪_画出轨迹-CSDN博客

组合HSV阈值 cv2.bitwise_and():

    # 组合HSV阈值 使用按位与操作来组合三个HSV分量的阈值结果,

        从而得到颜色范围内所有像素的掩码。
    tracking = cv2.bitwise_and(hthresh,cv2.bitwise_and(sthresh,vthresh))

函数作用

cv2.bitwise_and() 对两个数组进行按位与操作,通常用于组合或修改二值图像。

当想将多个二值图像(或掩码)组合在一起时,通常需要使用这个函数来确保只有在所有掩码中对应位置都为“真”(即白色或255)的像素才会在结果图像中保留为白色。

在给出的例子中,将三个HSV分量(色调、饱和度和亮度)的阈值结果组合成一个最终的掩码,以识别特定颜色范围内的所有像素。

在这个修正后的代码中:

  • hsv_thresh_hshthreshsthresh 的按位与结果,它只包含同时在色调和饱和度范围内的像素。
  • trackinghsv_thresh_hsvthresh 的按位与结果,它只包含同时在色调、饱和度和亮度范围内的像素,即您想要跟踪的颜色范围内的所有像素。

形态学操作函数:(膨胀/腐蚀/开运算/闭运算):

closing = cv2.morphologyEx(dilation, cv2.MORPH_CLOSE, kernel)

cv2.morphologyEx() 是 OpenCV 中用于形态学变换的函数,它可以执行各种形态学操作,如腐蚀(erosion)、膨胀(dilation)、开运算(opening)和闭运算(closing)等。

在给出的例子中,cv2.morphologyEx(dilation, cv2.MORPH_CLOSE, kernel) 是执行闭运算(closing operation)的调用。

函数作用闭运算首先执行膨胀操作,然后执行腐蚀操作。闭运算的主要目的是消除图像中的小孔(即黑色区域中的白色点),并连接相邻的对象。这在图像处理中用于平滑物体的轮廓,去除小的孔洞,以及连接断裂的轮廓。

传入参数:

src

输入图像,通常是二值图像。在给出的例子中,是 dilation,即已经过膨胀操作的图像。

  • 类型:可以是灰度图或二值图,其数据类型通常是 CV_8U, CV_16U, CV_16S, CV_32F, 或 CV_64F 之一。
  • 描述:源图像,即要进行形态学操作的图像。

operation

形态学操作的类型。在给出的例子中,是 cv2.MORPH_CLOSE,表示执行闭运算。

  • cv2.MORPH_ERODE:腐蚀操作
  • cv2.MORPH_DILATE:膨胀操作
  • cv2.MORPH_OPEN:开运算(先腐蚀后膨胀)
  • cv2.MORPH_CLOSE:闭运算(先膨胀后腐蚀)
  • cv2.MORPH_GRADIENT:形态学梯度
  • cv2.MORPH_TOPHAT:原图像减去膨胀的图像
  • cv2.MORPH_HITMISS:结构元素对应的点集比较
  • 注意:其他可能还有如 cv2.MORPH_BLACKHAT 等操作,具体请参考 OpenCV 官方文档。
kernel:结构元素(structuring element)。
  • 类型:数组,通常是 numpy 数组,形状如矩形、椭圆或交叉形等。
  • 描述:定义了形态学操作的局部形状和大小。可以使用cv2.getStructuringElement() 函数来创建结构元素。

dst (输出图像, 可选):

  • 类型:与 src 相同的数据类型
  • 描述:输出图像,如果未指定,则函数会创建一个新的输出图像。

anchor (锚点位置, 可选):

  • 类型:元组,指定了结构元素的锚点位置。
  • 描述:默认为结构元素的中心。如果指定了锚点,则形态学操作将围绕该点进行。

iterations (迭代次数, 可选):

  • 类型:整数
  • 描述:腐蚀与膨胀被应用的次数。默认为1。

borderType (边界类型, 可选):

  • 类型:整数
  • 描述:像素边界扩展类型,具体类型请参考 OpenCV 官方文档中的 BorderTypes

borderValue (边界值, 可选):

  • 类型:与 src 相同的数据类型
  • 描述:当 borderTypeBORDER_CONSTANT 时,用于填充边界的常量值。

高斯模糊cv2.GaussianBlur():

closing = cv2.GaussianBlur(closing,(5,5),0)

在 OpenCV 中用于对图像进行高斯模糊。高斯模糊是一种用于减少图像噪声和细节层次的图像滤波技术。它使用一个高斯函数来创建模糊滤波器,该滤波器在中心点的权重最高,然后随着距离的增加权重逐渐降低。

该函数对 closing 图像进行高斯模糊。这通常在图像处理流程中用于减少图像的细节和噪声,尤其是在特征检测或对象识别之前。

传入参数

  1. src (closing 在此例中):输入图像,即要进行高斯模糊的图像。
  2. ksize ((5,5) 在此例中):高斯核的大小。它必须是正奇数,并且可以是元组 (width, height),其中 widthheight 必须是正整数且都是奇数。如果 ksize 是一个整数,那么它会被视为 (ksize, ksize) 的正方形核。在此例中,(5,5) 表示一个 5x5 的核。
  3. sigmaX (0 在此例中):X 方向的标准差;决定了模糊的程度。如果 sigmaX 是 0,那么它会根据核大小来计算。如果 sigmaY 也是 0,那么 sigmaY 会与 sigmaX 相等。在此例中,因为 sigmaX 是 0,所以会根据 5x5 的核大小来计算标准差。

输出
输出是一个与输入图像 closing 大小和类型相同的新图像,其中包含了高斯模糊的结果。这个新的图像是原图像的模糊版本,细节层次被降低,噪声被减少。

 霍夫圆变换来检测圆形:

#使用霍夫圆变换来检测圆形。
circles = cv2.HoughCircles(closing,cv2.HOUGH_GRADIENT,2,120,param1=120,param2=50,minRadius=10,maxRadiu
s=0)

cv2.HoughCircles 函数用于在灰度图像中检测圆形。它使用霍夫变换的一个变种来检测图像中的圆形。

传入参数

  1. image:8位单通道灰度图像。
  2. method:检测方法,如 cv2.HOUGH_GRADIENTcv2.HOUGH_GRADIENT_ALT
  3. dp:检测器分辨率的倒数。如果设置为 1,则与图像分辨率相同。如果设置为 2,则分辨率是原始图像的一半。
  4. minDist:检测到的圆心之间的最小距离。
  5. param1:Canny 边缘检测中的高阈值。
  6. param2:在检测阶段,检测到的圆心的累加器阈值。这个值越小,检测到的圆就越多。
  7. minRadius:最小圆半径。
  8. maxRadius:最大圆半径。如果设置为 0,则使用最大可能的半径。

输出
返回一个 NumPy 数组,其中包含检测到的圆的 (x,y) 坐标和半径。数组的形状是 (num_circles, 3),其中每一行包含三个值:(x, y, radius)

网上查阅资料贴出:

[树莓派基础]8.树莓派OpenCV颜色追踪讲解_哔哩哔哩_bilibili

文心一言

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/35688.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

AI新热点:边云协同:大模型结合小模型(大小模型联合推理)

背景 AI模型规模不断剧增已是不争的事实。模型参数增长至百亿、千亿、万亿甚至十万亿&#xff0c;大模型在算力推动下演变为人工智能领域一场新的“军备竞赛”。 这种竞赛很大程度推动了人工智能的发展&#xff0c;但随之而来的能耗和端侧部署问题限制了大模型应用落地。2022…

4. ansible角色

ansible角色 一、ansible角色 role1、创建角色2、角色目录结构 二、部署zabbix-agent1、创建角色2、编写剧本3、执行角色中的操作 三、部署分布式zabbix1、zabbixproxy角色结构2、zabbixProxy task/main.yml3、zabbixAgentByProxy角色结构4、zabbixAgentByProxy tasks/main.yml…

非极大值抑制算法(Non-Maximum Suppression,NMS)

https://tcnull.github.io/nms/ https://blog.csdn.net/weicao1990/article/details/103857298 目标检测中检测出了许多的候选框&#xff0c;候选框之间是有重叠的&#xff0c;NMS作用重叠的候选框只保留一个 算法&#xff1a; 将所有候选框放入到集和B从B中选出分数S最大的b…

ubuntu安装QT

以QT5.15.14为例 下载地址&#xff1a;Index of /archive/qt 安装步骤&#xff1a; 解压qt-everywhere-src-5.15.14运行&#xff1a; cd qt-everywhere-src-5.15.14 mkdir build cd build ../configure -prefix /opt/qt5.15.14 -opensource -confirm-license make -j16 sudo…

keep-alive页面切回原滚动位置hook方法

keep-alive页面切回原滚动位置hook方法 原理hook使用 原理 如果使用了keep-alive组件&#xff0c;当前组件会额外增加两个生命周期。 activated&#xff1a;被 keep-alive 缓存的组件激活时调用 deactivated&#xff1a;被 keep-alive 缓存的组件失活时调用。 通过这两个声明周…

VBA技术资料MF168:移动工作表为单独工作簿

我给VBA的定义&#xff1a;VBA是个人小型自动化处理的有效工具。利用好了&#xff0c;可以大大提高自己的工作效率&#xff0c;而且可以提高数据的准确度。“VBA语言専攻”提供的教程一共九套&#xff0c;分为初级、中级、高级三大部分&#xff0c;教程是对VBA的系统讲解&#…

eventbus和vuex

EventBus和Vuex EventBus 工作原理 创建一个vue实例&#xff0c;然后通过空的vue实例作为组件之间的桥梁&#xff0c;进行通信&#xff0c;利用到的设计模式有发布订阅模式 Vuex 工作原理 维护了一个state树&#xff0c;是独立的状态树&#xff0c;有明显的层级关系。不论…

云计算-期末复习题-框架设计/选择/填空/简答(2)

目录 框架设计 1.负载分布架构 2.动态可扩展架构 3.弹性资源容量架构 4.服务负载均衡架构 5.云爆发结构 6.弹性磁盘供给结构 7.负载均衡的虚拟服务器实例架构 填空题/简答题 单选题 多选题 云计算期末复习部分练习题&#xff0c;包括最后的部分框架设计大题(只是部分…

vue3工程引用vue2模块文件时所做的修改

vue3工程引用vue2模块文件&#xff0c;如果代码没改的话&#xff0c;编译运行时可能会报错&#xff1a; SyntaxError: The requested module /fs/D:/HBuilderX.3.8.7.20230703/HBuilderX/plugins/uniapp-cli-vite/node_modules/dcloudio/uni-h5-vue/dist/vue.runtime.esm.js do…

SchedulerLock LockProvider参数配置表,列,大小写等 分布式锁 定时任务锁 学习总结

一、SchedulerLock 使用场景 如果是分布式任务&#xff0c;即多个相同的应用执行定时任务&#xff0c;那么为了防止重复执行可以使用其他分布式锁做内部判断或其他形式的锁机制来防止重复执行。 SchedulerLock 提供了现成的封装好的分布式锁机制来防止定时任务被重复执行 gi…

jQuery动画与特效

显示与隐藏动画 语法&#xff1a; $(obj).show(duration,fn);显示 $(obj).hide(duration,fn);隐藏 $(obj).toggle(); 功能&#xff1a; 1. show()方法能动态地改变当前元素的高度、宽度和不透明度&#xff0c;最终显示当前元素&#xff1b; 2. hide()方法会动态地改变当前元素…

AI办公自动化:多音频轨电影视频抽取出英语音频

很多电影视频是有中、英、粤语等多个音频轨的&#xff0c;如果直接转换成音频&#xff0c;很有可能不是自己想要的那种语音。 可以先查看音频流信息&#xff0c;确定属于哪个音频轨&#xff1a; Reading video file: E:\1-7\比得兔1.mp4 输出音频流信息 Available audio str…

利用viztracer进行性能分析和优化

上一篇文章&#xff0c;我们详细讲解了scalene这个性能分析和优化工具的使用流程&#xff1b;今天&#xff0c;我们将深入探讨另一个性能分析和优化工具——viztracer。 什么是viztracer&#xff1f; viztracer是一个非常强大的分析器&#xff0c;可以生成详细的性能报告和可…

设计师进阶指南:掌握这6条版式设计要点

布局设计是设计师的必修课。优秀的排版不是强制性的“东拼西凑”&#xff0c;而是通过设计师独特的排版获得的。这不是简单的信息列表&#xff0c;而是认真思考如何分层、有节奏地组织和安排元素。今天我将给你带来它 6 文章还附带了布局设计模板资源&#xff0c;设计师朋友一定…

《Windows API每日一练》6.1 鼠标基础知识

本节我们讲述鼠标的一些基础知识。 本节必须掌握的知识点&#xff1a; 鼠标 6.1.1 鼠标 鼠标是1964年由Douglas Engelbart发明的&#xff0c;用来取代由键盘输入的繁琐指令&#xff0c;简化电脑操作。早期的鼠标是单键鼠标&#xff0c;只有一个键&#xff0c;后来逐步改进为双…

EthernetIP IO从站设备数据 转opc ua项目案例

1 案例说明 设置网关采集EthernetIP IO设备数据把采集的数据转成opc ua协议转发给其他系统。 2 VFBOX网关工作原理 VFBOX网关是协议转换网关&#xff0c;是把一种协议转换成另外一种协议。网关可以采集西门子&#xff0c;欧姆龙&#xff0c;三菱&#xff0c;AB PLC&#xff0…

Element 页面滚动表头置顶

在开发后台管理系统时&#xff0c;表格是最常用的一个组件&#xff0c;为了看数据方便&#xff0c;时常需要固定表头。 如果页面基本只有一个表格区域&#xff0c;我们可以根据屏幕的高度动态的计算出一个值&#xff0c;给表格设定一个固定高度&#xff0c;这样表头就可以固定…

红酒达人教你秘技:选酒、存酒,一招一式皆学问

在繁忙的都市生活中&#xff0c;红酒不仅仅是一种饮品&#xff0c;更是一种生活态度&#xff0c;一种品味的象征。然而&#xff0c;面对琳琅满目的红酒品牌与种类&#xff0c;如何选择一瓶心仪的红酒&#xff0c;又如何妥善保存&#xff0c;使其保持很好口感&#xff0c;成为了…

python函数练习

1、编写函数&#xff0c;传入N&#xff0c;求123…N的和 def s_sum(num):i 1sum1 0while i < num:sum1 ii 1return sum1num int(input(请输入一个整数&#xff1a;)) print(和为:,s_sum(num))2、编写一个函数&#xff0c;定义一个列表&#xff0c;求列表中的最大值 d…

LabVIEW遇到无法控制国外设备时怎么办

当使用LabVIEW遇到无法控制国外产品的问题时&#xff0c;解决此类问题需要系统化的分析和处理方法。以下是详细的解决思路和具体办法&#xff0c;以及不同方法的分析和比较&#xff0c;包括寻求代理、国外技术支持、国内用过的人请教等内容。 1. 了解产品的通信接口和协议 思路…