是否可以将OpenCV GpuMat绑定为OpenGL纹理?

时间:2013-08-06 17:19:07

标签: opengl opencv cuda textures gpgpu

除了:

之外,我找不到任何参考

http://answers.opencv.org/question/9512/how-to-bind-gpumat-to-texture/

讨论了CUDA方法。

理想情况下,我想用cv::gpu::GpuMat的内容更新OpenGL纹理而不复制回CPU,而不直接使用CUDA(尽管我认为在添加此功能之前可能需要这样做)。 / p>

2 个答案:

答案 0 :(得分:12)

OpenCV支持OpenGL。请参阅opencv2/core/opengl_interop.hpp头文件。您可以将GpuMat的内容复制到Texture:

cv::gpu::GpuMat d_mat(768, 1024, CV_8UC3);
cv::ogl::Texture2D tex;
tex.copyFrom(d_mat);
tex.bind();
// draw something

您也可以使用cv::ogl::Buffer课程。它是OpenGL缓冲区内存的包装器。此内存可以映射到CUDA内存而无需内存复制:

cv::ogl::Buffer ogl_buf(1, 1000, CV_32FC3);
cv::gpu::GpuMat d_mat = ogl_buf.mapDevice();
// fill d_mat with CUDA
ogl_buf.unmapDevice();
// use ogl_buf in OpenGL
ogl_buf.bind(cv::ogl::Buffer::ARRAY_BUFFER);
glDrawArray(...);

答案 1 :(得分:4)

这是我的理解,也许不是100%正确,并为我的非母语朗英语道歉。

GpuMat使用全局记忆。然而,OpenGL纹理位于纹理存储器中,这是专门为GPU的纹理硬件(而不是CUDA核心)设计的。纹理mem不像通常的线性2D / 3D阵列那样组织,它可以使用某些Space Filling Curve来组织其内容以优化纹理缓存率。因此,您无法获得指向Texture的设备指针。您只能通过Texture Fetch(只读)或Surface R / W直接在CUDA中访问Texture Mem。

目前的OpenCV实现似乎没有使用cuda纹理/表面特征。您必须从纹理复制到全局内存以将它们绑定为GpuMat。好吧,不是一个“绑定”的解决方案。

This thread描述了一种写入OpenGL纹理的CUDA方法。

要么等待OpenCV实现新功能,要么等待NVIDIA的新GPU架构统一纹理内存和全局内存,或等待有人发明一个特殊的EMP设备来破解这些内存...... XD