在Windows11系统上配置interl Realsense D435i深度相机+Python

在Windows11系统上配置interl Realsense D435i深度相机+Python

一、产品介绍

Intel RealSense D435i是英特尔公司推出的一款消费级深度相机,它的主要构成如下图所示。

主要包含一个RGB相机、两个红外相机以及一个红外发射器,此外还有一个IMU单元(这也就是D435i和D435的区别,i就表示imu)。简单来说它的深度成像原理是主动立体红外成像,不是传统意义上理解的双目RGB相机成像,这点需要注意一下。 有了深度图(3D点云)和对应的RGB影像,因此也就很容易获得RGB-D点云了。因此从输出的角度而言,D435i可以看做是一个RGB-D传感器相机。后续可以搭配ORB-SLAM中RGB-D的模式进行使用。当然,也可以只用单目RGB影像,以单目SLAM模式运行,或者单目结合IMU,以Mono-Initial模式运行。唯一不能运行的是双目RGB模式(因为两个红外相机是单通道的)。当然我们可以获取双目的红外影像,以此作为输入,进行双目SLAM,结果也是类似的。因此可以看出,D435i是一个比较“全能”的传感器,从单目、单目+IMU、双目、双目+IMU、RGB-D都可以使用。

对于它的一些技术上的参数,这里也简单列举一下:

  • 深度技术:主动立体IR
  • 图像传感器技术:3μm×3μm像素大小,全局快门
  • 深度视场(H×V):86°×57°(±3°)
  • 深度分辨率&帧率:1280×720,90FPS(最高)
  • RGB传感器技术:卷帘快门
  • RGB传感器分辨率&帧率:1920×1080,30FPS(最高)
  • RGB传感器FOV(H×V):69°×42°(±1°)
  • 最小深度距离(Min-Z):0.105m
  • 最大范围:约10m
  • 尺寸(长宽高):90mm × 25mm × 25mm

从上面的参数中,也可以看出来它的一些特点。比如深度图和RGB影像的大小是不同的,换句话说RGB影像中只有和深度图重叠的那部分才有深度信息,否则是没有的。同时帧率也不相同,如果需要使用RGB-D信息,那么时间同步也可能是个需要处理的问题。第二点是RGB传感器采用的是卷帘快门,因此在一些高速运动的场景下,可能会出现果冻效应。最后由于采用主动红外测距技术,而红外传感器本身发射的信号强度有限,最大10m左右,因此并不能适用于室外很大的场景。

二、SDK下载

2.1 下载

进入网址:RealSense SDK 2.0
直接拉到网站最下端,在Asset下可以看到很多exe可执行软件,由于我的电脑是win11,所以选择第三个。

注:win11和win10的SDK通用的,均可使用。

装SDK会附带安装可视化界面Viewer、Examples和Depth Quality Tool。

2.2 安装与测试

首先,连接D435i到电脑上,然后在终端中输入<font>realsense-viewer</font>启动数据可视化界面,如下图所示。

点击左侧的Stereo Module可以开启深度图显示,RGB Module可以显示RGB影像,Motion Module会显示IMU相关数据,如下图所示。

如果可以正常显示上图中的画面,那么就说明RealSense的基本配置就成功了,可以向电脑传输数据了。

同样地,Stereo Module和RGB Camera可以分别设置参数(很重要,后面要用到)。这里简单说一下,Stereo Module的作用是用来设置深度信息的,而RGB Camera就是用来设置RGB颜色信息的!当然,主要用到的还是分辨率和FPS。

三、结合python配置相机

3.1 虚拟环境配置

  1. 首先在windows下安装anaconda和Vscode,然后配置open3d新环境。
  2. 创建一个新的环境,以下分别是python 版本是3.8和3.6的安装教程。
  3. 在conda终端下使用命令:
#创建python3.6环境 conda create -n Rd543i python=3.6#激活使用python3.6 conda activate Rd543i 
#创建python3.8环境 conda create -n Rd543i python=3.8#激活使用python3.8 conda activate Rd543i 
  1. 配置opencv环境,安装opencv。
## python3.6的版本必须装这个版本,此处必须按照指定版本安装 pip install -i https://mirrors.aliyun.com/pypi/simple/ opencv-python==4.3.0.38 pip install opencv-contrib-python==4.4.0.46
pip install opencv-python pip install opencv-contrib-python 
  1. 接着安装open3d和pyrealsense2,open3d需要等很长时间。
pip install pywinpty==1.1.4 pip install open3d==0.15.1 pip install pyrealsense2==2.48.0.3891
pip install open3d pip install pyrealsense2 

3.2 可视化

可视化脚本:

import pyrealsense2 as rs import numpy as np import cv2 if __name__ =="__main__":# Configure depth and color streams 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)# Start streaming pipeline.start(config)try:whileTrue:# Wait for a coherent pair of frames: depth and color frames = pipeline.wait_for_frames() depth_frame = frames.get_depth_frame() color_frame = frames.get_color_frame()ifnot depth_frame ornot color_frame:continue# Convert images to numpy arrays depth_image = np.asanyarray(depth_frame.get_data()) color_image = np.asanyarray(color_frame.get_data())# Apply colormap on depth image (image must be converted to 8-bit per pixel first) depth_colormap = cv2.applyColorMap(cv2.convertScaleAbs(depth_image, alpha=0.03), cv2.COLORMAP_JET)# Stack both images horizontally images = np.hstack((color_image, depth_colormap))# Show images cv2.namedWindow('RealSense', cv2.WINDOW_AUTOSIZE) cv2.imshow('RealSense', images) key = cv2.waitKey(1)# Press esc or 'q' to close the image windowif key &0xFF==ord('q')or key ==27: cv2.destroyAllWindows()breakfinally:# Stop streaming pipeline.stop()

运行脚本结果如下图所示:

四、结合python+Vscode实现数据采集

4.1 实现RGB数据采集

脚本:

import os import cv2 import numpy as np import pyrealsense2 as rs import time # 初始化 RealSense pipeline = rs.pipeline() config = rs.config() config.enable_stream(rs.stream.color,1920,1080, rs.format.bgr8,15) profile = pipeline.start(config) cv2.namedWindow('RGB Image', cv2.WINDOW_AUTOSIZE)# 设置保存目录 save_dir ='E:/my_images/' os.makedirs(save_dir, exist_ok=True) counter =0try:whileTrue: frames = pipeline.wait_for_frames() color_frame = frames.get_color_frame()ifnot color_frame:continue# 获取 RGB 图像数据 color_image = np.asanyarray(color_frame.get_data()) cv2.imshow('RGB Image', color_image)# 按 't' 键保存 RGB 图像 key = cv2.waitKey(1)if key ==ord('t'): rgb_file = os.path.join(save_dir,f'rgb_{counter:04d}.png') cv2.imwrite(rgb_file, color_image)print(f'Saved: {rgb_file}') counter +=1# 按 'q' 或 ESC 退出if key in[27,ord('q')]: cv2.destroyAllWindows()breakfinally: pipeline.stop()

五、一些其他扩展玩法

5.1 YOLOv8结合相机

具体脚本如下:

import cv2 import pyrealsense2 as rs import time import numpy as np import math from ultralytics import YOLO # 加载 YOLOv8 模型 model = YOLO("runs/detect/train/weights/best.pt")# # 获取摄像头内容,参数 0 表示使用默认的摄像头# cap = cv2.VideoCapture(1)# 配置 RealSense pipeline = rs.pipeline() config = rs.config() config.enable_stream(rs.stream.depth,848,480, rs.format.z16,30) config.enable_stream(rs.stream.color,848,480, rs.format.bgr8,30)# 启动相机流 pipeline.start(config) align_to = rs.stream.color # 与color流对齐 align = rs.align(align_to)defget_aligned_images(): frames = pipeline.wait_for_frames()# 等待获取图像帧 aligned_frames = align.process(frames)# 获取对齐帧 aligned_depth_frame = aligned_frames.get_depth_frame()# 获取对齐帧中的depth帧 color_frame = aligned_frames.get_color_frame()# 获取对齐帧中的color帧# 相机参数的获取 intr = color_frame.profile.as_video_stream_profile().intrinsics # 获取相机内参 depth_intrin = aligned_depth_frame.profile.as_video_stream_profile().intrinsics # 获取深度参数(像素坐标系转相机坐标系会用到)'''camera_parameters = {'fx': intr.fx, 'fy': intr.fy, 'ppx': intr.ppx, 'ppy': intr.ppy, 'height': intr.height, 'width': intr.width, 'depth_scale': profile.get_device().first_depth_sensor().get_depth_scale() }'''# 保存内参到本地# with open('./intrinsics.json', 'w') as fp:# json.dump(camera_parameters, fp)####################################################### depth_image = np.asanyarray(aligned_depth_frame.get_data())# 深度图(默认16位) depth_image_8bit = cv2.convertScaleAbs(depth_image, alpha=0.03)# 深度图(8位) depth_image_3d = np.dstack((depth_image_8bit, depth_image_8bit, depth_image_8bit))# 3通道深度图 color_image = np.asanyarray(color_frame.get_data())# RGB图# 返回相机内参、深度参数、彩色图、深度图、齐帧中的depth帧return intr, depth_intrin, color_image, depth_image, aligned_depth_frame defget_3d_camera_coordinate(depth_pixel, aligned_depth_frame, depth_intrin): x = depth_pixel[0] y = depth_pixel[1] dis = aligned_depth_frame.get_distance(x, y)# 获取该像素点对应的深度# print ('depth: ',dis) # 深度单位是m camera_coordinate = rs.rs2_deproject_pixel_to_point(depth_intrin, depth_pixel, dis)# print ('camera_coordinate: ',camera_coordinate)return dis, camera_coordinate # 初始化 FPS 计算 fps =0 frame_count =0 start_time = time.time()try:whileTrue:# 等待获取一对连续的帧:深度和颜色 intr, depth_intrin, color_image, depth_image, aligned_depth_frame = get_aligned_images()ifnot depth_image.any()ornot color_image.any():continue# 获取当前时间 time1 = time.time()# 将图像转为numpy数组 depth_colormap = cv2.applyColorMap(cv2.convertScaleAbs( depth_image, alpha=0.03), cv2.COLORMAP_JET) images = np.hstack((color_image, depth_colormap))# 使用 YOLOv8 进行目标检测 results = model.predict(color_image, conf=0.5) annotated_frame = results[0].plot() detected_boxes = results[0].boxes.xyxy # 获取边界框坐标# print('方框坐标', detected_boxes)for i, box inenumerate(detected_boxes): x1, y1, x2, y2 =map(int, box)# 获取边界框坐标# 计算步长xrange=max(1, math.ceil(abs((x1 - x2)/30))) yrange =max(1, math.ceil(abs((y1 - y2)/30)))# xrange = 1# yrange = 1 point_cloud_data =[]# 获取范围内点的三维坐标for x_position inrange(x1, x2,xrange):for y_position inrange(y1, y2, yrange): depth_pixel =[x_position, y_position] dis, camera_coordinate = get_3d_camera_coordinate(depth_pixel, aligned_depth_frame, depth_intrin)# 获取对应像素点的三维坐标 point_cloud_data.append(f"{camera_coordinate} ")# 一次性写入所有数据withopen("point_cloud_data.txt","a")asfile:file.write(f"\nTime: {time.time()}\n")file.write(" ".join(point_cloud_data))# 显示中心点坐标 ux =int((x1 + x2)/2) uy =int((y1 + y2)/2) dis, camera_coordinate = get_3d_camera_coordinate([ux, uy], aligned_depth_frame, depth_intrin)# 获取对应像素点的三维坐标 formatted_camera_coordinate =f"({camera_coordinate[0]:.2f}, {camera_coordinate[1]:.2f}, {camera_coordinate[2]:.2f})" cv2.circle(annotated_frame,(ux, uy),4,(255,255,255),5)# 标出中心点 cv2.putText(annotated_frame, formatted_camera_coordinate,(ux +20, uy +10),0,1,[225,255,255], thickness=1, lineType=cv2.LINE_AA)# 标出坐标# 计算 FPS frame_count +=1 time2 = time.time() fps =int(1/(time2 - time1))# 显示 FPS cv2.putText(annotated_frame,f'FPS: {fps:.2f}',(10,30), cv2.FONT_HERSHEY_SIMPLEX,1,(0,255,0),2, cv2.LINE_AA)# 显示结果 cv2.imshow('YOLOv8 RealSense', annotated_frame)if cv2.waitKey(1)&0xFF==ord('q'):breakfinally:# 停止流 pipeline.stop()

5.2 关键点识别结合相机

脚本思路:

1、获取相机对齐图像帧与相机参数

 frames = pipeline.wait_for_frames()# 等待获取图像帧,获取颜色和深度的框架集 aligned_frames = align.process(frames)# 获取对齐帧,将深度框与颜色框对齐 aligned_depth_frame = aligned_frames.get_depth_frame()# 获取对齐帧中的的depth帧 aligned_color_frame = aligned_frames.get_color_frame()# 获取对齐帧中的的color帧#### 获取相机参数 #### depth_intrin = aligned_depth_frame.profile.as_video_stream_profile().intrinsics # 获取深度参数(像素坐标系转相机坐标系会用到) color_intrin = aligned_color_frame.profile.as_video_stream_profile().intrinsics # 获取相机内参#### 将images转为numpy arrays #### img_color = np.asanyarray(aligned_color_frame.get_data())# RGB图 img_depth = np.asanyarray(aligned_depth_frame.get_data())# 深度图(默认16位)

2、检测

# 检测 result =list(model(image, conf=0.3, stream=True))[0]# inference boxes = result.boxes # Boxes object for bbox outputs boxes = boxes.cpu().numpy()# convert to numpy array

3、遍历所有的Keypoints

# 遍历keypoints keypoints = result.keypoints # Keypoints object for pose outputs keypoints = keypoints.cpu().numpy()# convert to numpy array

4、获得所有关键点二维坐标

 point1 =(int(x0),int(y0)) point2 =(int(x1),int(y1))

5、计算所有点的深度值

point1_dis = depth_frame.get_distance(x0, y0)# 获取第一个点的深度值 point2_dis = depth_frame.get_distance(x1, y1)# 获取第二个点的深度值

6、计算所有点的三维坐标

point1_dis = depth_frame.get_distance(x0, y0)# 获取第一个点的深度值 point2_dis = depth_frame.get_distance(x1, y1)# 获取第二个点的深度值

Read more

【OpenClaw从入门到精通】第10篇:OpenClaw生产环境部署全攻略:性能优化+安全加固+监控运维(2026实测版)

【OpenClaw从入门到精通】第10篇:OpenClaw生产环境部署全攻略:性能优化+安全加固+监控运维(2026实测版)

摘要:本文聚焦OpenClaw从测试环境走向生产环境的核心痛点,围绕“性能优化、安全加固、监控运维”三大维度展开实操讲解。先明确生产环境硬件/系统选型标准,再通过硬件层资源管控、模型调度策略、缓存优化等手段提升响应速度(实测响应效率提升50%+);接着从网络、权限、数据三层构建安全防护体系,集成火山引擎安全方案拦截高危操作;最后落地TenacitOS可视化监控与Prometheus告警体系,配套完整故障排查清单和虚拟实战案例。全文所有配置、代码均经实测验证,兼顾新手入门实操性和进阶读者的生产级部署需求,帮助开发者真正实现OpenClaw从“能用”到“放心用”的跨越。 优质专栏欢迎订阅! 【DeepSeek深度应用】【Python高阶开发:AI自动化与数据工程实战】【YOLOv11工业级实战】 【机器视觉:C# + HALCON】【大模型微调实战:平民级微调技术全解】 【人工智能之深度学习】【AI 赋能:Python 人工智能应用实战】【数字孪生与仿真技术实战指南】 【AI工程化落地与YOLOv8/v9实战】【C#工业上位机高级应用:高并发通信+性能优化】 【Java生产级避坑指南:

By Ne0inhk
ARM Linux 驱动开发篇--- Linux 并发与竞争实验(互斥体实现 LED 设备互斥访问)--- Ubuntu20.04互斥体实验

ARM Linux 驱动开发篇--- Linux 并发与竞争实验(互斥体实现 LED 设备互斥访问)--- Ubuntu20.04互斥体实验

🎬 渡水无言:个人主页渡水无言 ❄专栏传送门: 《linux专栏》《嵌入式linux驱动开发》《linux系统移植专栏》 ❄专栏传送门: 《freertos专栏》《STM32 HAL库专栏》 ⭐️流水不争先,争的是滔滔不绝  📚博主简介:第二十届中国研究生电子设计竞赛全国二等奖 |国家奖学金 | 省级三好学生 | 省级优秀毕业生获得者 | ZEEKLOG新星杯TOP18 | 半导纵横专栏博主 | 211在读研究生 在这里主要分享自己学习的linux嵌入式领域知识;有分享错误或者不足的地方欢迎大佬指导,也欢迎各位大佬互相三连 目录 前言  一、实验基础说明 1.1、互斥体简介 1.2 本次实验设计思路 二、硬件原理分析(看过之前博客的可以忽略) 三、实验程序编写 3.1 互斥体 LED 驱动代码(mutex.c) 3.2.1、设备结构体定义(28-39

By Ne0inhk
Flutter for OpenHarmony:swagger_dart_code_generator 接口代码自动化生成的救星(OpenAPI/Swagger) 深度解析与鸿蒙适配指南

Flutter for OpenHarmony:swagger_dart_code_generator 接口代码自动化生成的救星(OpenAPI/Swagger) 深度解析与鸿蒙适配指南

欢迎加入开源鸿蒙跨平台社区:https://openharmonycrossplatform.ZEEKLOG.net 前言 后端工程师扔给你一个 Swagger (OpenAPI) 文档地址,你会怎么做? 1. 对着文档,手写 Dart Model 类(容易写错字段类型)。 2. 手写 Retrofit/Dio 的 API 接口定义(容易拼错 URL)。 3. 当后端修改了字段名,你对着报错修半天。 这是重复劳动的地狱。 swagger_dart_code_generator 可以将 Swagger (JSON/YAML) 文件直接转换为高质量的 Dart 代码,包括: * Model 类:支持 json_serializable,带 fromJson/

By Ne0inhk
Linux 开发别再卡壳!makefile/git/gdb 全流程实操 + 作业解析,新手看完直接用----《Hello Linux!》(5)

Linux 开发别再卡壳!makefile/git/gdb 全流程实操 + 作业解析,新手看完直接用----《Hello Linux!》(5)

文章目录 * 前言 * make/makefile * 文件的三个时间 * Linux第一个小程序-进度条 * 回车和换行 * 缓冲区 * 程序的代码展示 * git指令 * 关于gitee * Linux调试器-gdb使用 * 作业部分 前言 做 Linux 开发时,你是不是也遇到过这些 “卡脖子” 时刻?写 makefile 时,明明语法没错却报错,最后发现是依赖方法行没加 Tab;想提交代码到 gitee,记不清 git add/commit/push 的 “三板斧”,还得反复搜教程;用 gdb 调试程序,输了命令没反应,才想起编译时没加-g生成 debug 版本;甚至连写个进度条,都搞不懂\r和\n的区别,导致进度条乱跳…… 其实这些问题,

By Ne0inhk