gpt4 book ai didi

c - OpenGL/OpenCL 互操作,OpenCL 渲染到纹理问题

转载 作者:太空宇宙 更新时间:2023-11-03 23:31:44 27 4
gpt4 key购买 nike

我正在尝试将 OpenCL 渲染为 OpenGL 256x256 纹理。
全部编译正确,但只渲染黑屏:

如果关闭纹理,它通常呈现白色矩形。

// Setting up OpenCL

const char *source =
"__kernel void Main(__write_only image2d_t image)\n"
"{\n"
" int x = get_global_id(0);\n"
" int y = get_global_id(1);\n"
" write_imagef(image, (int2)(x, y), (float4)(x / 256.0f, y / 256.0f, 1.0f, 1.0f));\n"
"}\n";

cl_platform_id platform;
clGetPlatformIDs(1, &platform, NULL);

cl_device_id cdDeviceID;
clGetDeviceIDs(platform, CL_DEVICE_TYPE_GPU, 1, &cdDeviceID, NULL);

cl_context_properties props[] = {
CL_CONTEXT_PLATFORM,
(cl_context_properties)platform,
CL_GL_CONTEXT_KHR,
(cl_context_properties)wglGetCurrentContext,
CL_WGL_HDC_KHR,
(cl_context_properties)wglGetCurrentDC,
};

*context = clCreateContextFromType(props, CL_DEVICE_TYPE_GPU ,NULL, NULL, NULL);
*queue = clCreateCommandQueue(*context, cdDeviceID, 0, NULL);
*program = clCreateProgramWithSource(*context, 1, &source, NULL, NULL);
clBuildProgram(*program, 1, &cdDeviceID, NULL, NULL, NULL);
*kernel = clCreateKernel(*program, "Main", NULL);
...
// Setting up texture

glEnable(GL_TEXTURE_2D);

GLuint texture;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);

glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 256, 256, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);

cl_mem cl_screen;
cl_screen = clCreateFromGLTexture2D(context, CL_MEM_WRITE_ONLY, GL_TEXTURE_2D, 0, texture, 0);
...
// Rendering
clEnqueueAcquireGLObjects(queue, 1, &cl_screen, 0, NULL, NULL);
clSetKernelArg(kernel, 0, sizeof(cl_screen), cl_screen);
size_t work_size[] = { 256, 256 };
clEnqueueNDRangeKernel(queue, kernel, 2, 0, work_size, 0, 0, NULL, NULL);
clEnqueueReleaseGLObjects(queue, 1, &cl_screen, 0, NULL, NULL);
clFinish(queue);

glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
glClear(GL_COLOR_BUFFER_BIT);

glBindTexture(GL_TEXTURE_2D, texture);

glBegin(GL_QUADS);
glTexCoord2i(0, 1);
glVertex3f(-1.0f, 1.0f, 0.0f);
glTexCoord2i(1, 1);
glVertex3f( 1.0f, 1.0f, 0.0f);
glTexCoord2i(1, 0);
glVertex3f( 1.0f,-1.0f, 0.0f);
glTexCoord2i(0, 0);
glVertex3f(-1.0f,-1.0f, 0.0f);
glEnd();
glFinish();

SwapBuffers(hDC);
...

完整代码:

#include <windows.h>
#include <gl/gl.h>
#include <CL/cl.h>
#include <CL/cl_gl.h>

LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);
void EnableOpenGL(HWND hWnd, HDC * hDC, HGLRC * hRC);
void DisableOpenGL(HWND hWnd, HDC hDC, HGLRC hRC);
void EnableOpenCL(cl_kernel * kernel, cl_program * program, cl_context * context, cl_command_queue * queue);
void DisableOpenCL(cl_kernel * kernel, cl_program * program, cl_context * context, cl_command_queue * queue);

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int iCmdShow)
{
WNDCLASS wc;
HWND hWnd;
HDC hDC;
HGLRC hRC;
MSG msg;
BOOL quit = FALSE;

wc.style = CS_OWNDC;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = LoadIcon( NULL, IDI_APPLICATION );
wc.hCursor = LoadCursor( NULL, IDC_ARROW );
wc.hbrBackground = (HBRUSH)GetStockObject( BLACK_BRUSH );
wc.lpszMenuName = NULL;
wc.lpszClassName = "GLCLInterop";

RegisterClass(&wc);

hWnd = CreateWindow("GLCLInterop", "GLCLInterop", WS_CAPTION | WS_POPUPWINDOW | WS_VISIBLE, 0, 0, 640, 480, NULL, NULL, hInstance, NULL);

cl_kernel kernel;
cl_program program;
cl_context context;
cl_command_queue queue;

EnableOpenGL(hWnd, &hDC, &hRC);
EnableOpenCL(&kernel, &program, &context, &queue);

glEnable(GL_TEXTURE_2D);

GLuint texture;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);

glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 256, 256, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);

cl_mem cl_screen;
cl_screen = clCreateFromGLTexture2D(context, CL_MEM_WRITE_ONLY, GL_TEXTURE_2D, 0, texture, 0);

while (!quit)
{
if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{
if (msg.message == WM_QUIT)
quit = TRUE;
else
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
else
{
clEnqueueAcquireGLObjects(queue, 1, &cl_screen, 0, NULL, NULL);
clSetKernelArg(kernel, 0, sizeof(cl_screen), cl_screen);
size_t work_size[] = { 256, 256 };
clEnqueueNDRangeKernel(queue, kernel, 2, 0, work_size, 0, 0, NULL, NULL);
clEnqueueReleaseGLObjects(queue, 1, &cl_screen, 0, NULL, NULL);
clFinish(queue);

glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
glClear(GL_COLOR_BUFFER_BIT);

glBindTexture(GL_TEXTURE_2D, texture);

glBegin(GL_QUADS);
glTexCoord2i(0, 1);
glVertex3f(-1.0f, 1.0f, 0.0f);
glTexCoord2i(1, 1);
glVertex3f( 1.0f, 1.0f, 0.0f);
glTexCoord2i(1, 0);
glVertex3f( 1.0f,-1.0f, 0.0f);
glTexCoord2i(0, 0);
glVertex3f(-1.0f,-1.0f, 0.0f);
glEnd();
glFinish();

SwapBuffers(hDC);
}
}

DisableOpenGL(hWnd, hDC, hRC);
DisableOpenCL(&kernel, &program, &context, &queue);
DestroyWindow(hWnd);

return msg.wParam;
}

LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{

switch (message)
{
case WM_CREATE:
return 0;

case WM_CLOSE:
PostQuitMessage(0);
return 0;

case WM_DESTROY:
return 0;

case WM_KEYDOWN:
switch (wParam)
{

case VK_ESCAPE:
PostQuitMessage(0);
return 0;

}
return 0;

default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
}

void EnableOpenGL(HWND hWnd, HDC * hDC, HGLRC * hRC)
{
PIXELFORMATDESCRIPTOR pfd;
int format;

*hDC = GetDC(hWnd);

ZeroMemory(&pfd, sizeof(pfd));

pfd.nSize = sizeof(pfd);
pfd.nVersion = 1;
pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
pfd.iPixelType = PFD_TYPE_RGBA;
pfd.cColorBits = 24;
pfd.cDepthBits = 16;
pfd.iLayerType = PFD_MAIN_PLANE;
format = ChoosePixelFormat(*hDC, &pfd);

SetPixelFormat(*hDC, format, &pfd);

*hRC = wglCreateContext(*hDC);
wglMakeCurrent(*hDC, *hRC);
}

void DisableOpenGL(HWND hWnd, HDC hDC, HGLRC hRC)
{
wglMakeCurrent(NULL, NULL);
wglDeleteContext(hRC);
ReleaseDC(hWnd, hDC);
}

void EnableOpenCL(cl_kernel * kernel, cl_program * program, cl_context * context, cl_command_queue * queue)
{
const char *source =
"__kernel void Main(__write_only image2d_t image)\n"
"{\n"
" int x = get_global_id(0);\n"
" int y = get_global_id(1);\n"
" write_imagef(image, (int2)(x, y), (float4)(x / 256.0f, y / 256.0f, 1.0f, 1.0f));\n"
"}\n";

cl_platform_id platform;
clGetPlatformIDs(1, &platform, NULL);

cl_device_id cdDeviceID;
clGetDeviceIDs(platform, CL_DEVICE_TYPE_GPU, 1, &cdDeviceID, NULL);

cl_context_properties props[] = {
CL_CONTEXT_PLATFORM,
(cl_context_properties)platform,
CL_GL_CONTEXT_KHR,
(cl_context_properties)wglGetCurrentContext,
CL_WGL_HDC_KHR,
(cl_context_properties)wglGetCurrentDC,
};

*context = clCreateContextFromType(props, CL_DEVICE_TYPE_GPU ,NULL, NULL, NULL);

*queue = clCreateCommandQueue(*context, cdDeviceID, 0, NULL);

*program = clCreateProgramWithSource(*context, 1, &source, NULL, NULL);
clBuildProgram(*program, 1, &cdDeviceID, NULL, NULL, NULL);

*kernel = clCreateKernel(*program, "Main", NULL);
}

void DisableOpenCL(cl_kernel * kernel, cl_program * program, cl_context * context, cl_command_queue * queue)
{
clReleaseKernel(*kernel);
clReleaseProgram(*program);
clReleaseContext(*context);
clReleaseCommandQueue(*queue);
}

这是怎么回事?

最佳答案

您的图像是 GL_UNSIGNED_BYTE,但您使用的是 write_imagef。切换到 GL_FLOAT 或 write_imageui。

关于c - OpenGL/OpenCL 互操作,OpenCL 渲染到纹理问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13891981/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com