OpenGL 帧缓冲区 + LibGDX
OpenGL frame buffer + LibGDX
我有一个关于 openGL 帧缓冲区的问题。
我想达到:
- 绑定FBO1。将 image1 绘制到 FBO1。解绑FBO1.
- 绑定FBO2。绘制 FBO1 到 FBO2。解绑FBO2.
- 绑定FBO1。将 image2 绘制到 FBO1。解绑FBO1.
- 将 FBO2 绘制到屏幕上
我希望看到的:
我希望在屏幕上只看到 image1,因为它是在第一个 FBO 中绘制的,然后第一个 FBO 被绘制到第二个 FBO
问题是什么:
我在绘制时同时看到 image1 和 image2,这应该是不可能的,因为当 FBO1 在 FBO2 中绘制时,只有第一张图像在 FBO1 中绘制,而我只在屏幕上绘制 FBO2。
这是重现问题的代码:
// --- in show() method
this.img = new Texture(Gdx.files.internal("shaders/image.jpg"));
this.img2 = new Texture(Gdx.files.internal("shaders/image2.jpg"));
this.fbo = new FrameBuffer(Format.RGBA8888, Gdx.graphics.getWidth(), Gdx.graphics.getHeight(), false);
this.fbo2 = new FrameBuffer(Format.RGBA8888, Gdx.graphics.getWidth(), Gdx.graphics.getHeight(), false);
// --- in render() method
// start frame buffer 1 and draw image 1
this.fbo.begin();
{
this.batch.begin();
this.batch.draw(this.img, 0, 0, 400, 400, 0, 0, this.img.getWidth(), this.img.getHeight(), false, true);
this.batch.end();
}
this.fbo.end();
// start frame buffer 2 and frame buffer 1 output
this.fbo2.begin();
{
this.batch.begin();
this.batch.draw(this.fbo.getColorBufferTexture(), 500, 0, this.fbo.getColorBufferTexture().getWidth(), this.fbo.getColorBufferTexture().getHeight(), 0, 0, this.fbo.getColorBufferTexture()
.getWidth(), this.fbo.getColorBufferTexture().getHeight(), false, true);
this.batch.end();
}
this.fbo2.end();
// start frame buffer 1 again and draw image 2
this.fbo.begin();
{
this.batch.begin();
this.batch.draw(this.img2, 150, 150, 400, 400, 0, 0, this.img2.getWidth(), this.img2.getHeight(), false, true);
this.batch.end();
}
this.fbo.end();
// draw frame buffer 2 to the batch
this.batch.begin();
this.batch.draw(this.fbo2.getColorBufferTexture(), 0, 0);
this.batch.end();
draw() 方法有点长,因为我想传递 flipY = true,因为 OpenGL 会颠倒绘制帧缓冲区。
我使用的draw()方法的参数是:
Texture texture, float x, float y, float width, float height, int srcX, int srcY, int srcWidth, int srcHeight, boolean flipX, boolean flipY
我错过了什么?为什么会这样?
每次开始在另一个 FrameBuffer 上绘图时,如果您不想要旧内容,则需要清除它。
frameBuffer.begin();
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
//...
如果您不想要上次调用 render()
的内容,您还需要在 render()
开始时清除屏幕。
此外,如果您用图像覆盖整个背景,您最好禁用 SpriteBatch 上的混合。
我有一个关于 openGL 帧缓冲区的问题。 我想达到:
- 绑定FBO1。将 image1 绘制到 FBO1。解绑FBO1.
- 绑定FBO2。绘制 FBO1 到 FBO2。解绑FBO2.
- 绑定FBO1。将 image2 绘制到 FBO1。解绑FBO1.
- 将 FBO2 绘制到屏幕上
我希望看到的: 我希望在屏幕上只看到 image1,因为它是在第一个 FBO 中绘制的,然后第一个 FBO 被绘制到第二个 FBO
问题是什么: 我在绘制时同时看到 image1 和 image2,这应该是不可能的,因为当 FBO1 在 FBO2 中绘制时,只有第一张图像在 FBO1 中绘制,而我只在屏幕上绘制 FBO2。
这是重现问题的代码:
// --- in show() method
this.img = new Texture(Gdx.files.internal("shaders/image.jpg"));
this.img2 = new Texture(Gdx.files.internal("shaders/image2.jpg"));
this.fbo = new FrameBuffer(Format.RGBA8888, Gdx.graphics.getWidth(), Gdx.graphics.getHeight(), false);
this.fbo2 = new FrameBuffer(Format.RGBA8888, Gdx.graphics.getWidth(), Gdx.graphics.getHeight(), false);
// --- in render() method
// start frame buffer 1 and draw image 1
this.fbo.begin();
{
this.batch.begin();
this.batch.draw(this.img, 0, 0, 400, 400, 0, 0, this.img.getWidth(), this.img.getHeight(), false, true);
this.batch.end();
}
this.fbo.end();
// start frame buffer 2 and frame buffer 1 output
this.fbo2.begin();
{
this.batch.begin();
this.batch.draw(this.fbo.getColorBufferTexture(), 500, 0, this.fbo.getColorBufferTexture().getWidth(), this.fbo.getColorBufferTexture().getHeight(), 0, 0, this.fbo.getColorBufferTexture()
.getWidth(), this.fbo.getColorBufferTexture().getHeight(), false, true);
this.batch.end();
}
this.fbo2.end();
// start frame buffer 1 again and draw image 2
this.fbo.begin();
{
this.batch.begin();
this.batch.draw(this.img2, 150, 150, 400, 400, 0, 0, this.img2.getWidth(), this.img2.getHeight(), false, true);
this.batch.end();
}
this.fbo.end();
// draw frame buffer 2 to the batch
this.batch.begin();
this.batch.draw(this.fbo2.getColorBufferTexture(), 0, 0);
this.batch.end();
draw() 方法有点长,因为我想传递 flipY = true,因为 OpenGL 会颠倒绘制帧缓冲区。
我使用的draw()方法的参数是:
Texture texture, float x, float y, float width, float height, int srcX, int srcY, int srcWidth, int srcHeight, boolean flipX, boolean flipY
我错过了什么?为什么会这样?
每次开始在另一个 FrameBuffer 上绘图时,如果您不想要旧内容,则需要清除它。
frameBuffer.begin();
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
//...
如果您不想要上次调用 render()
的内容,您还需要在 render()
开始时清除屏幕。
此外,如果您用图像覆盖整个背景,您最好禁用 SpriteBatch 上的混合。