【发布时间】:2018-11-30 13:29:00
【问题描述】:
我有一个 OpenCV 垫子,我想用 OpenGL 进行渲染。所以我尝试通过我在网上找到的代码将 openCV mat 作为纹理加载并渲染到该纹理:
void BindCVMat2GLTexture(cv::Mat& image, GLuint& imageTexture)
{
if (image.empty()) {
std::cout << "image empty" << std::endl;
}
else {
glEnable(GL_TEXTURE_2D);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
//glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glGenTextures(1, &imageTexture);
glBindTexture(GL_TEXTURE_2D, imageTexture);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
// Set texture clamping method
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP);
cv::cvtColor(image, image, CV_RGB2BGR);
glTexImage2D(GL_TEXTURE_2D, // Type of texture
0, // Pyramid level (for mip-mapping) - 0 is the top level
GL_RGB, // Internal colour format to convert to
image.cols, // Image width i.e. 640 for Kinect in standard mode
image.rows, // Image height i.e. 480 for Kinect in standard mode
0, // Border width in pixels (can either be 1 or 0)
GL_RGB, // Input image format (i.e. GL_RGB, GL_RGBA, GL_BGR etc.)
GL_UNSIGNED_BYTE, // Image data type
image.ptr()); // The actual image data itself
//NULL);
}
}
然后我创建一个 FBO:
//init the texture
GLuint imageTexture;
BindCVMat2GLTexture(target, imageTexture);
//init the frame buffer
GLuint fbo = 0;
glGenFramebuffers(1, &fbo);
glBindFramebuffer(GL_FRAMEBUFFER, fbo);
// Set "renderedTexture" as our colour attachement #0
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, imageTexture, 0);
然后我打电话:
glViewport(0, 0, target.cols, target.rows);
MyDraw();
在这个调用之后,我使用另一个我发现的函数将纹理数据复制回 openCV mat:
cv::Mat GetOcvImgFromOglImg(GLuint ogl_texture_id)
{
glBindTexture(GL_TEXTURE_2D, ogl_texture_id);
GLenum gl_texture_width, gl_texture_height;
glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, (GLint*)&gl_texture_width);
glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, (GLint*)&gl_texture_height);
unsigned char* gl_texture_bytes = (unsigned char*)malloc(sizeof(unsigned char)*gl_texture_width*gl_texture_height * 3);
glGetTexImage(GL_TEXTURE_2D, 0 /* mipmap level */, GL_BGR, GL_UNSIGNED_BYTE, gl_texture_bytes);
return cv::Mat(gl_texture_height, gl_texture_width, CV_8UC3, gl_texture_bytes);
}
并通过以下方式调用它:
target = GetOcvImgFromOglImg(imageTexture);
我还创建了三角形顶点和一个简单地保持它们不变的顶点着色器和一个只显示红色的片段着色器。理论上,我只想要在这个纹理上绘制一个红色三角形作为第一步。但是它不起作用,因为我根本没有得到渲染图像。我是openGL的初学者,现在我自己找不到任何解决方案。任何想法我做错了什么?
【问题讨论】: