为了提高渲染质量,我正在使用OpenCL 1.1中的多功能可分离缩减器进行编写。
基本图像(仅覆盖最终图像的一小部分)被渲染成一个非常大的帧缓冲区。然后,它的颜色附加纹理被下采样并通过OpenCL放入另一个纹理中。最后,渲染屏幕对齐的四边形以显示结果。
到目前为止的想法。我们有什么:
运行kernel_instance_1( <otherParams>, inputTexture, tempTexture )
会产生所需的结果,但仅限于第一帧 - 不知何故动画中发生的更改根本不会显示。因为我没有错误(见下文)我假设内核每帧运行,但源纹理内容保持不变(它没有,我也有该纹理的实时输出)。
Question:
每次帧缓冲的内容发生变化时,是否必须调用clCreateFromGLTexture2D()?
编辑我刚刚意识到:inputTexture仍然附加到帧缓冲对象的GL_COLOR_ATTACHMENT0
- 这可能是个问题吗?的 EndEdit中
即使在两个内核调用之间排队的屏障,运行kernel_instance_2( <otherParams>, tempTexture, outputTexture )
也不会产生任何可见结果。即outputTexture保持为空。
Question:
我是否需要在两个内核调用之间释放并重新获取纹理对象tempTexture
,以便OpenCL看到这些更改?
只是看看OpenCL调用了什么,产生了以下输出:
clCreateKernel( separable_X )
clRetainMemObject( separable_X::convolution )
clCreateKernel( separable_Y )
clRetainMemObject( separable_Y::convolution )
clCreateFromGLTexture2D( separable_X::dst + separable_y::src, texID=24, usage=temporary (source and target) )
clCreateFromGLTexture2D( separable_Y::dst, texID=18, usage=target )
clCreateFromGLTexture2D( separable_X::src, texID=22, usage=source )
clRetainMemObject( separable_X::dst )
clRetainMemObject( separable_Y::src )
clRetainMemObject( separable_Y::dst )
clRetainMemObject( clearEmpty::dst )
clEnqueueAcquireGLObjects( count=3 )
clEnqueueBarrier()
clSetKernelArg( separable_X::convert )
clSetKernelArg( separable_X::offset )
clSetKernelArg( separable_X::convolution )
clSetKernelArg( separable_X::dst )
clSetKernelArg( separable_X::src )
clEnqueueNDRangeKernel( separable_X, (1440, 1080, 0), waiting4 0 events )
clSetKernelArg( separable_Y::convert )
clSetKernelArg( separable_Y::offset )
clEnqueueBarrier()
clSetKernelArg( separable_Y::convolution )
clSetKernelArg( separable_Y::dst )
clSetKernelArg( separable_Y::src )
clEnqueueNDRangeKernel( separable_Y, (540, 1440, 0), waiting4 0 events )
clEnqueueBarrier()
clEnqueueReleaseGLObjects( count=3 )
如果任何调用产生了错误,那么它就会在输出中。
我遇到很多次的另一种情况是clEnqueueReleaseGLObjects()
返回错误代码-9999,有人将其称为“NVidia:非法读取或写入缓冲区”。
Question:
如果任何组件超过1.0f且存储格式为RGBA8,那么write_imagef()
是否会阻止颜色值?所以这实际上意味着必须写write_imagef( texture, (int2)coord, clamp( color, 0.f, 1.f ) );
...
提前多多感谢 - 这让我在近一周的时间里敲打了我的脑袋......
修改 还有一些可能值得一提的信息:
我如何区分这两个实例?
在程序源中有两个不同的__kernel
函数,它们具有不同的名称(separable_X
和separable_Y
),它们都具有调用separable()
- 函数的相同主体。
如何在GL和CL之间进行同步?
- 在致电glFinish()
之前,负责获取GL对象的函数会发出clEnqueueAcquireGLObjects()
- 我等待使用cl_events完成clEnqueueReleaseGLObjects()
(将来可能会改变)