D435+opencv识别色块

ops/2024/9/23 2:40:11/

在当前的机器视觉和机器人技术领域,实时图像处理是一项至关重要的技术。本文介绍了如何利用Python、OpenCV库以及Intel的Realsense摄像头来进行实时的颜色识别。这种技术可以广泛应用于自动化检测、机器人导航以及交互式媒体等领域。

一、 开发环境配置

首先,我们需要配置Python开发环境,确保安装了`pyrealsense2`和`numpy`、`opencv-python`(通常简称cv2)这些库。这些库允许我们操作Realsense摄像头并进行图像处理。

```bash

pip install pyrealsense2 numpy opencv-python

```

整体代码:
 

#!/usr/bin/env python3.8
# _*_ coding: utf-8 _*_
# 导入依赖
import pyrealsense2 as rs
import numpy as np
import cv2# 设置颜色字典
ball_color = 'red'
color_dist = {'red': {'Lower': np.array([0, 60, 60]), 'Upper': np.array([6, 255, 255])},'blue': {'Lower': np.array([100, 80, 46]), 'Upper': np.array([124, 255, 255])},'green': {'Lower': np.array([35, 43, 35]), 'Upper': np.array([90, 255, 255])},
}# 初始化realsense相机
pipeline = rs.pipeline()
config = rs.config()
config.enable_stream(rs.stream.depth, 640, 480, rs.format.z16, 30)
config.enable_stream(rs.stream.color, 640, 480, rs.format.bgr8, 30)
pipeline.start(config)# 创建opencv窗口
cv2.namedWindow('RealSense', cv2.WINDOW_AUTOSIZE)try:while True:# 等待一帧数据frames = pipeline.wait_for_frames()color_frame = frames.get_color_frame()if not color_frame:continue# 将图像转为numpy数组以便OpenCV处理color_image = np.asanyarray(color_frame.get_data())# 颜色识别流程gs_frame = cv2.GaussianBlur(color_image, (5, 5), 0)  # 高斯模糊hsv = cv2.cvtColor(gs_frame, cv2.COLOR_BGR2HSV)      # 转换到HSVerode_hsv = cv2.erode(hsv, None, iterations=2)      # 腐蚀处理inRange_hsv = cv2.inRange(erode_hsv, color_dist[ball_color]['Lower'], color_dist[ball_color]['Upper'])cnts = cv2.findContours(inRange_hsv.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)[-2]if len(cnts) > 0:c = max(cnts, key=cv2.contourArea)rect = cv2.minAreaRect(c)box = cv2.boxPoints(rect)cv2.drawContours(color_image, [np.int0(box)], -1, (0, 255, 255), 2)cv2.imshow('RealSense', color_image)if cv2.waitKey(1) & 0xFF == ord('q'):break
finally:# 停止流pipeline.stop()cv2.destroyAllWindows()

二、 设定颜色字典

在开始编写代码之前,首先设定一个颜色字典,用于定义我们想要识别的颜色范围。这里,我们定义了红色、蓝色和绿色三种颜色的HSV范围。HSV(色相、饱和度、亮度)是一种比RGB颜色空间更适合颜色识别的模型。

```python

color_dist = {

    'red': {'Lower': np.array([0, 60, 60]), 'Upper': np.array([6, 255, 255])},

    'blue': {'Lower': np.array([100, 80, 46]), 'Upper': np.array([124, 255, 255])},

    'green': {'Lower': np.array([35, 43, 35]), 'Upper': np.array([90, 255, 255])},

}

```

三、 初始化和配置Realsense摄像头

通过`pyrealsense2`库,我们可以轻松初始化Intel Realsense摄像头,并设置其流输出格式。本示例中,我们启用了640x480分辨率的深度流和颜色流。

```python

pipeline = rs.pipeline()

config = rs.config()

config.enable_stream(rs.stream.depth, 640, 480, rs.format.z16, 30)

config.enable_stream(rs.stream.color, 640, 480, rs.format.bgr8, 30)

pipeline.start(config)

```

四、 实时颜色识别

在获取到摄像头的实时视频流后,我们对每一帧图像进行如下处理:

1. 应用高斯模糊,以减少图像噪声。

2. 将图像从BGR转换到HSV颜色空间。

3. 对HSV图像进行腐蚀处理,以过滤小的颜色斑点。

4. 使用`cv2.inRange`函数根据颜色字典中的阈值检测特定颜色。

通过以上步骤,我们可以将图像中的特定颜色区域提取出来。如果找到相应颜色的轮廓,我们计算其最小覆盖矩形,并在原图上绘制该矩形,从而实现实时的颜色跟踪。

```python

color_image = np.asanyarray(color_frame.get_data())

gs_frame = cv2.GaussianBlur(color_image, (5, 5), 0)

hsv = cv2.cvtColor(gs_frame, cv2.COLOR_BGR2HSV)

erode_hsv = cv2.erode(hsv, None, iterations=2)

inRange_hsv = cv2.inRange(erode_hsv, color_dist[ball_color]['Lower'], color_dist[ball_color]['Upper'])

```

在我们的实时颜色识别程序中,一段关键的代码负责识别和高亮显示特定颜色的对象。这部分代码如下:

```python

cnts = cv2.findContours(inRange_hsv.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)[-2]

if len(cnts) > 0:

    c = max(cnts, key=cv2.contourArea)

    rect = cv2.minAreaRect(c)

    box = cv2.boxPoints(rect)

    cv2.drawContours(color_image, [np.int0(box)], -1, (0, 255, 255), 2)

```

五、 识别显示

1. 轮廓查找:

   - `cv2.findContours()` 函数用于在二值图像中查找轮廓,这里的图像是已经通过颜色阈值处理后的 `inRange_hsv`。

   - `cv2.RETR_EXTERNAL` 参数表示仅检索最外层轮廓,适合我们的需求,因为我们关心的是物体的外围轮廓。

   - `cv2.CHAIN_APPROX_SIMPLE` 是一个轮廓近似方法,它压缩水平、垂直和对角线段,只留下它们的端点。这种方法有效减少存储空间,并去除不必要的信息。

2. 选择最大轮廓:

   - 从所有检测到的轮廓中,我们选择面积最大的一个,认为这是我们要追踪的主要对象。`max(cnts, key=cv2.contourArea)` 实现了这一点。

3. 计算最小矩形并绘制:

   - `cv2.minAreaRect()` 函数计算轮廓的最小外接矩形,无论对象的角度如何。

   - `cv2.boxPoints()` 函数根据 `minAreaRect` 的输出,生成矩形的四个角点。

   - 使用 `cv2.drawContours()` 在原始彩色图像上绘制这个矩形,用以高亮显示检测到的对象。

4. 显示图像与退出:

   - `cv2.imshow()` 用于在窗口中显示实时视频流中的帧。

   - `cv2.waitKey(1)` 检测按键操作。如果检测到按键 `q`,则退出循环,这是程序结束录像和关闭窗口的信号。

通过这一系列步骤,我们能够在视频流中实时检测并标记特定颜色的对象,为进一步的图像处理或机器人视觉任务提供基础。

六、 识别优化:

为了优化实时颜色识别的精确度和效率,我们可以在原有代码的基础上调整图像预处理和轮廓筛选的参数。这将有助于提高算法的性能和适应不同的应用场景。下面将详细说明如何实现这些调整:

 1. 图像预处理调整

图像预处理主要包括应用高斯模糊以及腐蚀操作,来减少噪点和改善图像质量。在代码中,这可以通过调整 `cv2.GaussianBlur` 和 `cv2.erode` 的参数实现。

2. 高斯模糊

高斯模糊有助于减少图像噪声和细节,使颜色块更加连贯。可以通过调整核的大小和标准差来控制模糊程度。

```python

# 调整高斯模糊的核大小和标准差

kernel_size = (5, 5)  # 可增大核尺寸例如(9, 9)

sigma = 0             # 标准差,0表示由函数自动计算

gs_frame = cv2.GaussianBlur(color_image, kernel_size, sigma)

```

3. 腐蚀操作

腐蚀可以帮助移除小的颜色斑点,增强图像中主要颜色区域的连续性。可以通过调整腐蚀的核大小和迭代次数来改变其效果。

```python

# 调整腐蚀的核大小和迭代次数

erode_size = (3, 3)  # 核的大小

iterations = 2       # 迭代次数,可以增加以增强效果

erode_kernel = np.ones(erode_size, np.uint8)

erode_hsv = cv2.erode(hsv, erode_kernel, iterations=iterations)

```

4.轮廓筛选标准

轮廓筛选是颜色识别后处理的重要部分,通过选择适当的轮廓可以排除不必要的小区域和误识别,提高识别的准确性。

5. 轮廓面积过滤

在检测到的轮廓中,我们通常只关心较大的对象。设置一个面积阈值,只考虑面积超过此阈值的轮廓。

```python

min_area = 100  # 设置最小面积阈值

cnts = cv2.findContours(inRange_hsv.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)[-2]

filtered_cnts = [c for c in cnts if cv2.contourArea(c) > min_area]  # 过滤小面积轮廓

if len(filtered_cnts) > 0:

    c = max(filtered_cnts, key=cv2.contourArea)  # 选择最大的轮廓

    # ...之后的代码处理选中的轮廓

```

这些调整可以显著提高颜色识别的精度和鲁棒性,特别是在复杂环境中。通过试验不同的参数设置,可以找到最适合具体应用场景的配置。在实际部署前,建议在不同的光照和背景条件下进行充分测试,以确保系统的可靠性和效果。


http://www.ppmy.cn/ops/24943.html

相关文章

JAVA 每日面试题(一)

Java 高级面试问题及答案 以下是几个常见的Java高级面试问题,以及对应的答案。 1. 解释Java中的强引用、软引用、弱引用和虚引用的区别? 答案: 强引用(Strong Reference):如果一个对象具有强引用&#…

Redis缓存介绍以及常见缓存问题:穿透、雪崩和击穿

概念 缓存就是数据交换的缓冲区(Cache),是存贮数据的临时地方,一般读写性能较高。 作用: 降低后端负载 提高读写效率,降低相应时间 成本: 数据一致性成本 代码维护成本 运维成本 缓存更…

手搓数组栈(C语言)

stack.h #pragma once#include <stdio.h> #include <stdlib.h> #include <assert.h> #include <stdbool.h> // 支持动态增长的栈 typedef int STDataType; typedef struct Stack {STDataType* a;int top; // 栈顶int capacity; // 容量 }Stack; //…

spring-security 学习笔记一 --- 基于默认配置

1.前言 本文主要讲解 spring-security 在不做任何配置情况下&#xff0c;它的启动流程和认证过程。 1. 准备工作 这里是基于springboot 2.2.5版本对应 spring-security 5.2.2版本演示的 &#xff08;按我下面导入即可&#xff0c;版本是它自己匹配的&#xff09; 引入依赖 &…

国内各种免费AI聊天机器人(ChatGPT)推荐(上)

作者主页&#xff1a;点击&#xff01; 国内免费AI推荐专栏&#xff1a;点击&#xff01; 创作时间&#xff1a;2024年4月27日11点25分 欢迎来到AI聊天机器人推荐系列的第一篇文章&#xff01; 在这个系列中&#xff0c;我将引领您探索国内各种AI聊天机器人的精彩世界。 从…

PyTorch库中item()函数的作用(python)

在Python的PyTorch库中&#xff0c;.item() 函数用于从包含单个元素的张量中提取其值&#xff0c;并将该值转换为一个标准的Python数值。这个函数是特别用于处理单个数据点的情况&#xff0c;使得从张量对象中获取数值变得简洁而高效。 作用和功能 提取数值&#xff1a; 当你有…

力扣练习4.29-30

86. 分隔链表 解题思路&#xff1a;设置两个链表&#xff0c;分别装小于x和>x的节点&#xff0c;最后将两个链表拼接。 步骤&#xff1a; 1.初始化两个新链表的头结点和指针节点&#xff0c;初始化链表的指针节点 2.遍历变量&#xff0c;如果是小于x&#xff0c;就将第一个…

【动态规划】Leetcode 416. 分割等和子集【中等】

分割等和子集 给你一个 只包含正整数 的 非空 数组 nums 。请你判断是否可以将这个数组分割成两个子集&#xff0c;使得两个子集的元素和相等。 示例 1&#xff1a; 输入&#xff1a;nums [1,5,11,5] 输出&#xff1a;true 解释&#xff1a;数组可以分割成 [1, 5, 5] 和 [1…