Ale*_*DET 2 framebuffer glsl game-engine libgdx
我在我的LevelScreen渲染方法中使用FBO渲染多遍模糊着色器.我想要实现的是制作一个MenuScreen,在背景上渲染LevelScreen,在其上应用另一个模糊效果.
这是伪代码
protected void render(float delta) {
// render the scene to the FBO
fbo.begin();
levelScreen.render(delta);
fbo.end();
// retrieve texture and flip Y
Sprite background = new Sprite(fbo.getColorBufferTexture());
background.flip(false, true);
// apply the blurX shader and
// render the sprite
batch.setShader(blurH);
batch.begin();
background.draw(batch);
batch.end();
}
Run Code Online (Sandbox Code Playgroud)
问题是该levelScreen.render()函数已经包含a fbo.begin() fbo.end()并且场景直接在屏幕上呈现.
有没有办法处理正确嵌套的fbo?
你可以手工处理的事情,使用自定义的类来处理帧缓冲区,可能通过支持堆叠,以类似的方法startRender(FrameBuffer)和endRender()界河会妥善管理的东西,喜欢接近老帧缓冲,并打开新的话,等
另外,尽量避免在render方法中创建新对象.
Sprite background = new Sprite(fbo.getColorBufferTexture());
Run Code Online (Sandbox Code Playgroud)
如果这是一个字段,这应该工作得很好.
编辑:
如果我理解正确,您当前的问题如下所示:
FrameBuffer fb1 = ..., fb2 = ...;
fb1.begin();
// draw something on fb1
fb2.begin();
// draw something on fb2
fb2.end();
// draw something on fb1 again
fb1.end();
Run Code Online (Sandbox Code Playgroud)
但是你不能同时打开多个FrameBuffers,对吧?因此,创建一个基于堆栈的类来为您管理FrameBuffers,简单的事情可以做:
class FrameBufferManager {
private Stack<FrameBuffer> stack = new Stack<FrameBuffer>();
public void begin(FrameBuffer buffer) {
if (!stack.isEmpty()) {
stack.peek().end();
}
stack.push(buffer).begin();
}
public void end() {
stack.pop().end();
if (!stack.isEmpty()) {
stack.peek().begin();
}
}
}
Run Code Online (Sandbox Code Playgroud)
然后你像这样使用它:
FrameBuffer fb1 = ..., fb2 = ...;
FrameBufferManager manager = ...;
manager.begin(fb1);
// draw something on fb1
manager.begin(fb2);
// draw something on fb2
manager.end();
// draw something on fb1 again
manager.end();
Run Code Online (Sandbox Code Playgroud)
但是,无论有没有经理,我都没有尝试过,但它应该解决你的问题.我不确定每次更改FrameBuffer时我是否需要重新打开渲染器和批处理(我通常这样做).