2012-02-01 118 views
0

我想在GLUT中执行屏幕捕获,我遇到了一些问题。 glReadPixels()似乎崩溃我的程序与GLUT屏幕捕获在C

Access violoation writing location 0x00000000 

这是奇怪的是项目的根目录中创建的文件,显然是空的东西。我快速设置了一些printf命令,看起来代码在glReadPixels()方法中每次崩溃。

我觉得这个问题可能是变量'像素'。我很难找出正确的方法来定义这个RGB值写入它。

任何提示将不胜感激。

void savePPM(char ppmFileName[]){ 
    int width = glutGet(GLUT_WINDOW_WIDTH); 
    int height = glutGet(GLUT_WINDOW_HEIGHT); 
    char *pixels = NULL; 

    glReadPixels(0,0, width, height, GL_RGB, GL_UNSIGNED_BYTE ,pixels); 

    ppmFile = fopen(ppmFileName, "wb"); 

    fprintf(ppmFile, "P6\n"); 
    fprintf(ppmFile, "%d %d\n", width, height); 
    fprintf(ppmFile, "255\n"); 
    fwrite(pixels, 1, width*height*3, ppmFile); 

    fclose(ppmFile); 
    free(pixels); 
} 

回答

3

glReadPixels不为你分配内存,它只是存储在你给它最后一个参数缓冲器中的像素数据。你给它一个NULL指针,所以它试图将数据存储在地址0,这显然会导致访问冲突。

您需要先分配内存,然后将其传递给glReadPixels,然后将其解除分配。您还需要确保调用glPixelStorei以确保像素数据返回打包,没有任何填充(或者,您可以单独编写每条扫描线,但这需要一点额外的努力)。

例如:

// Error checking omitted for expository purposes 
char *pixels = malloc(width * height * 3); // Assuming GL_RGB 
glPixelStorei(GL_PACK_ALIGNMENT, 1); 
glReadPixels(..., pixels); 
... 
fwrite(pixels, ...); 
... 
free(pixels); 
+0

与'3'在通话中的乘法'malloc'取决于像素格式。 '3'是24位像素。另外,为了不使用'malloc',为什么不声明像GLubyte pixels [PIXELSIZE];(其中'PIXELSIZE'是每个像素的字节数)的数组。 – 2012-02-01 07:10:37

+0

在这种情况下,你必须小心设置'glPixelStorei(GL_PACK_ALIGNMENT,1);',OpenGL默认是考虑每行对齐的倍数为4. – rotoglup 2012-02-01 08:22:19

+0

@Joachim:是的,乘以3取决于像素格式,但我们在这里用'GL_RGB'和'GL_UNSIGNED_BYTE'明确要求24位。声明'GLubyte像素[PIXELSIZE]'只为一个像素分配足够的内存,而不是为整个图像分配足够的内存 - 您需要动态分配带有malloc(或其亲属之一)的数组或者使用大型静态分配数组并且希望它足够大。 – 2012-02-02 00:00:51