首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >使用clCreateFromGLTexture的opencl/opengl互操作无法绘制到纹理(纹理黑色)

使用clCreateFromGLTexture的opencl/opengl互操作无法绘制到纹理(纹理黑色)
EN

Stack Overflow用户
提问于 2014-04-08 06:00:24
回答 3查看 2.5K关注 0票数 1

设置有点复杂,所以我将尽我最大的努力来详细说明它。

首先,我尝试使用openCL/openGL互操作。当没有使用interop cl::ImageGL时,代码就可以工作了,所以基本知识就在那里了。该项目使用了3个主openGL上下文(需要很长时间才能打开openCL上下文)。我在上下文中使用QGLWidgets。首先创建了一个隐藏的QGLWidget,另外两个共享隐藏的上下文。这两个QGLWidgets中的每一个都在各自的线程中运行。隐藏的QGLWidget被传输到创建openCL上下文的线程。

代码语言:javascript
运行
复制
QGLFormat qglFormat;
qglFormat.setVersion(3, 3); 
qglFormat.setProfile(QGLFormat::CoreProfile);

m_hiddenGl=new GLHiddenWidget(qglFormat);
m_hiddenGl->setVisible(false);

m_view1=new GLWidget(qglFormat, m_hiddenGl);
m_view2=new GLWidget(qglFormat, m_hiddenGl);
 ...
 QThread *processThread=m_process.qThread();

m_hiddenGl->doneCurrent();
m_hiddenGl->context()->moveToThread(processThread);

GLWidget是一个自定义类,它启动自己的线程并移动上下文,GLHiddenWidget再次使用自定义类,但基本上只是重写了防止主线程调用makeCurrent所需的所有函数。

启动时的进程线程内部有以下内容

代码语言:javascript
运行
复制
m_hiddenGl->makeCurrent();
hdc=wglGetCurrentDC();
glHandle=wglGetCurrentContext();

cl_context_properties clContextProps[]={ 
    CL_CONTEXT_PLATFORM, (cl_context_properties)m_openCLPlatform(),
    CL_WGL_HDC_KHR, (intptr_t) hdc,
    CL_GL_CONTEXT_KHR, (intptr_t) glHandle, 0
};

m_openCLContext=cl::Context(m_openCLDevice, clContextProps, NULL, NULL, &error);

这一切都是一次尝试。从这一点开始,将对输入的数据(即图像)依次执行几个内核。所有内核都成功了(没有错误),但是一个使用openGL纹理写入数据的内核没有写任何东西。当使用openCL cl::Image2d时,它可以正常工作(生成正确的输出),即使openCL上下文是作为互操作创建的。

openGL纹理是在创建所有openGL上下文之后和创建openCL上下文之后创建的(也是在与openCL上下文相同的线程中)。在processThread的开头,纹理由带有glGenTextures的隐藏QGLWidget生成。然后,所有内核都与其他openCL缓冲区和映像一起创建。在执行内核之前,将执行以下操作。

代码语言:javascript
运行
复制
if(initBuffer) //runs only if buffer size is changed, allways runs first time
{
    m_hiddenGl->makeCurrent();

    glBindTexture(GL_TEXTURE_2D, m_texture);

    //I have attempted to put data in, result is always black from kernel
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); 
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
    glBindTexture(GL_TEXTURE_2D, 0);

    glFinish();

    //m_flags is CL_MEM_READ_WRITE
    m_imageGL=cl::ImageGL(m_openCLContext, m_flags, GL_TEXTURE_2D, 0, m_texture, &error);
}

和一个简化的内核。

代码语言:javascript
运行
复制
__kernel void kernel1(__read_only image2d_t src1, __read_only image2d_t src2, __write_only image2d_t dst)
{
    int2 coord=(int2)(get_global_id(0), get_global_id(1));
    uint4 value=255;

    write_imageui(dst, coord, convert_uint4(value));
}

即使我没有显示纹理,图像仍然是黑色的。当使用cl::Image2d或cl::ImageGL时,映像将从openCL读取并保存到硬盘。对于cl::Image2d,它对cl::ImageGL是正确的,它是黑色的。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2014-05-01 23:06:00

如前所述,在我的评论中,我发现我的问题与openGL纹理的定义有关。由于我在write_imageui内核中使用了openCL,所以openGL纹理必须定义如下:

代码语言:javascript
运行
复制
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8UI, width, height, 0, GL_RGBA_INTEGER, GL_UNSIGNED_BYTE, NULL);

从那以后,我做了一些工作,并创建了一个使用openGL/openCL互操作和线程化QGLWidgets的示例程序。您可以在这里阅读我的评论,http://www.krazer.com/?p=109和/或您可以从github.com获得源代码

票数 0
EN

Stack Overflow用户

发布于 2016-04-10 01:57:31

我也遇到了同样的问题,使用write_imagef() (不要忘记将RGBA值除以255.0!),而不是OpenCL内核中的write_imageui()解决了它,而不改变OpenGL纹理的像素格式(您可能没有机会这样做,特别是如果它是在大型应用程序中创建的现有纹理的话)。

票数 1
EN

Stack Overflow用户

发布于 2014-04-09 04:43:15

您必须为我们发布更多的代码才能找到错误。

无论如何,我已经写了一个例子程序,它做了一些非常相似的事情。它使用OpenCL计算曼德尔布罗特分形,然后用OpenGL在QGLWidget中绘制它。消息来源在这里:https://github.com/kylelutz/compute/blob/master/example/mandelbrot.cpp

希望这能有所帮助。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/22928704

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档