前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >OpenNi2 USB协议命令解码+Python读取码流

OpenNi2 USB协议命令解码+Python读取码流

作者头像
云深无际
发布2021-12-08 19:57:32
1.2K0
发布2021-12-08 19:57:32
举报
文章被收录于专栏:云深之无迹

奥比中光的相机是通过Type-C连接的,目前直接获得码流的SDK是OpenNi2,但是哇,这个SDK是13年就不维护了。年久失修吗?不,宝刀未老!各家的RGBD相机都适配了这个SDK,上层的接口给开发人员使用,下层的驱动层给厂家适配。但是哇,我就是怕C++,我不是不会,就是讨厌样板代码,那我肯定想办法搞个Python的接口~但是时间紧,任务重,从头写来不及,我只能改装啦!

首先安装:

代码语言:javascript
复制
pip install primesense

安装这个就好啦。

上面是编译过后的py脚本,下面是未编译前

我们就使用这个库的openni2的的接口。

里面包装了很多的C++方法

我们就看一个方法就好,大概就知道实现方法啦!

接下来就是更换我们的驱动了,方法有了,接口也有了,缺最终的引擎。

建立一个这样的文件夹

把我们OrbbecViewer的dll文件放成我上面的样子

代码语言:javascript
复制
import numpy as np
import cv2
from primesense import openni2
from primesense import _openni2 as c_api
openni2.initialize("./Redist")
if (openni2.is_initialized()):
    print("openNI2 initialized")
else:
    print("openNI2 not initialized")

写个初始化的代码。

成功

代码语言:javascript
复制
from primesense import openni2
from primesense import _openni2 as c_api
import numpy as np
import cv2
openni2.initialize("./Redist")
dev = openni2.Device.open_any()
print(dev.get_device_info())
depth_stream = dev.create_depth_stream()
depth_stream.start()

while True:
    # 显示深度图
    frame = depth_stream.read_frame()
    dframe_data = np.array(frame.get_buffer_as_triplet()
                           ).reshape([480, 640, 2])
    dpt1 = np.asarray(dframe_data[:, :, 0], dtype='float32')
    dpt2 = np.asarray(dframe_data[:, :, 1], dtype='float32')
    dpt2 *= 255
    dpt = dpt1 + dpt2
    cv2.imshow('dpt', dpt)

    # 按下q键退出循环
    key = cv2.waitKey(10)
    if int(key) == 113:
        break

# 人走带门,关闭设备
depth_stream.stop()
dev.close()

输出深度流

代码语言:javascript
复制
OniDeviceInfo(uri = b'\\\\?\\usb#
vid_2bc5
&
pid_0614#6&5dea7dd&0&2#
{c3b5f022-5a42-1980-1909-ea72095601b1}', 
vendor = b'Orbbec', 
name = b'Astra', 
usbVendorId = 11205, 
usbProductId = 1556)

输出的信息,可以看到输的正确

输出了

接口就是这样的

上面的输出信息来看这个地方(我写的)

在设备管理器也可以看到,深度相机

rgb是UVC实现

调用rgb相机

出流

接下来的是来着与论坛的硬货。

1.OpenNI协议命令是基于USB控制传输,使用默认的控制端点0;而图像数据传输是基于USB实现的批量传输,而后者根据取决于数据类型。图像传输端点:

2.OpenNI协议命令

使用默认的控制端点HOST使用USB默认端点0发送请求,协议包含一个头部信息,结构如下:

代码语言:javascript
复制
typedef struct{
uint16_t nMagic;
uint16_t nSize;
uint16_t nOpcode;
uint16_t nId;
                }ProtocolHeader;

其中,Request: nMagic=0x4252, Response: nMagic=0x4d47, nSize表示数据长度,nOpcode表示命令类型,如获取版本号、设置参数等,nId表示包号,设备应答时就使用接收到Request中的nId;

数据部分限制最大长度为512字节。具体实现在protocol.c中,命令类型定义在protocol.h中。

3.OpenNI图像传输

OpenNI支持IR/DEPTH/RGB传输,协议与UVC类似,OpenNI 12字节头部信息定义:

其中PACKAGE TYPE定义:

根据USB工作模式,在USB3.0下,每帧最大长度为1024字节,USB2.0则为512字节。

这里需要注意的是:

1) 大小端,package_id 是小端,而package_size和TimeStamp是大端;

2) 帧包与包号:package_id表示包号,每个传输完一个包加1;TimeStamp表示帧号,每传输完一帧加1,但每帧的第一个包,TimeStamp=0;

3) 包长度,SOF和Normal均为0xC00,而最后一包取决于实际所剩长度last_size,则pakage_size=last_size+12.

代码语言:javascript
复制
https://developer.orbbec.com.cn/forum_plate_module_details.html?id=1266
本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-12-03,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 云深之无迹 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档