2011-05-15 173 views
1

我试图一个OpenGL创建场景保存为TBitmap。我遇到的问题是glReadPixels将返回所有空数据(全0)。为什么会发生这种想法?我试图捕获当前的OpenGL上下文。 (在屏幕上显示的都是正常工作)。这是在Windows下的Delphi 7。保存OpenGL场景到TBitmap - glReadPixels返回空闲数据?

var 
    pbuf: pointer; 
    y: integer; 
    bmp: TBitmap; 
    p1, p2: pointer; 
begin 
    GetMem(pbuf, pnScene.Width * pnScene.Height * 4); 
    glReadPixels(0, 0, pnScene.Width, pnScene.Height, GL_RGBA, GL_UNSIGNED_BYTE, pbuf); 
    //<------ pbuf now contains all 0's ----------> 

    bmp := TBitmap.Create; 
    bmp.PixelFormat := pf32bit; 
    bmp.Width := pnScene.Width; 
    bmp.Height := pnScene.height; 

    for y := 0 to (pnScene.Height -1) do 
    begin 
     p1 := bmp.ScanLine[y]; 
     p2 := pointer(integer(pbuf)+ (y * bmp.Width * 4)); 
     CopyMemory(p1, p2, bmp.Width * 4); 
    end; 

    bmp.SaveToFile('c:\test\temp.bmp'); 
    bmp.Free; 
    FreeMem(pbuf); 
end; 

非常欢迎您的建议/想法!

附录:

最终的计划是放置glReadPixels()调用渲染要求录制视频的目的之后。当我这样做的时候,它运作良好,所以这最终成为一个没有问题的东西。

+0

您是否检查错误? glGetError – Bart 2011-05-15 08:26:31

+0

是的,对不起,我应该提到 - 没有错误glReadPixels() – GrandmasterB 2011-05-15 17:33:21

回答

4

请确保您从创建GL上下文的同一线程执行此操作。如果这是你提供给第三方库的回调函数,然后它可能没有你甚至没有意识到它在另一个线程中执行。这发生在我身上一次,我所得到的只有零和你一样。

+0

这不是问题所在,但它确实导致我试图将glReadPixels()嵌入到最终会反正出现的位置(我的上面的代码只是一个测试函数) - 并且工作正常。 – GrandmasterB 2011-05-17 05:16:29

3

我假设你想取回已被交换到一个双缓冲窗口的前缓冲器中的图片。然后尝试在glReadPixels(...)之前glReadPixels(...)

+0

我实际上已经尝试过,但它似乎没有区别。尽管我可以看到那些可能应该在那里的东西,以防后来的代码改变这个设置。 – GrandmasterB 2011-05-17 05:40:37

0

for循环必须更改声明:

p1 := bmp.ScanLine[y]; 

p1 := bmp.ScanLine[OpenGlPanel.Height -1 -y]; 

否则,复制的位图将是颠倒。