diff --git a/jme3-core/src/main/java/com/jme3/renderer/opengl/GLRenderer.java b/jme3-core/src/main/java/com/jme3/renderer/opengl/GLRenderer.java index 0aa0d693f..276453117 100644 --- a/jme3-core/src/main/java/com/jme3/renderer/opengl/GLRenderer.java +++ b/jme3-core/src/main/java/com/jme3/renderer/opengl/GLRenderer.java @@ -1459,25 +1459,44 @@ public class GLRenderer implements Renderer { rb.getId()); } } + + private void bindFrameBuffer(FrameBuffer fb) { + if (fb == null) { + if (context.boundFBO != 0) { + glfbo.glBindFramebufferEXT(GLFbo.GL_FRAMEBUFFER_EXT, 0); + statistics.onFrameBufferUse(null, true); + context.boundFBO = 0; + context.boundFB = null; + } + } else { + assert fb.getId() != -1 && fb.getId() != 0; + if (context.boundFBO != fb.getId()) { + glfbo.glBindFramebufferEXT(GLFbo.GL_FRAMEBUFFER_EXT, fb.getId()); + context.boundFBO = fb.getId(); + context.boundFB = fb; + statistics.onFrameBufferUse(fb, true); + } else { + statistics.onFrameBufferUse(fb, false); + } + } + } public void updateFrameBuffer(FrameBuffer fb) { + if (fb.getNumColorBuffers() == 0 && fb.getDepthBuffer() == null) { + throw new IllegalArgumentException("The framebuffer: " + fb + + "\nDoesn't have any color/depth buffers"); + } + int id = fb.getId(); if (id == -1) { - // create FBO glfbo.glGenFramebuffersEXT(intBuf1); id = intBuf1.get(0); fb.setId(id); objManager.registerObject(fb); - statistics.onNewFrameBuffer(); } - if (context.boundFBO != id) { - glfbo.glBindFramebufferEXT(GLFbo.GL_FRAMEBUFFER_EXT, id); - // binding an FBO automatically sets draw buf to GL_COLOR_ATTACHMENT0 - context.boundDrawBuf = 0; - context.boundFBO = id; - } + bindFrameBuffer(fb); FrameBuffer.RenderBuffer depthBuf = fb.getDepthBuffer(); if (depthBuf != null) { @@ -1488,7 +1507,8 @@ public class GLRenderer implements Renderer { FrameBuffer.RenderBuffer colorBuf = fb.getColorBuffer(i); updateFrameBufferAttachment(fb, colorBuf); } - + + setReadDrawBuffers(fb); checkFrameBufferError(); fb.clearUpdateNeeded(); @@ -1516,93 +1536,45 @@ public class GLRenderer implements Renderer { } public void setMainFrameBufferOverride(FrameBuffer fb) { + mainFbOverride = null; + if (context.boundFBO == 0) { + // Main FB is now set to fb, make sure its bound + setFrameBuffer(fb); + } mainFbOverride = fb; } - public void setFrameBuffer(FrameBuffer fb) { - if (fb == null && mainFbOverride != null) { - fb = mainFbOverride; - } - - if (context.boundFB == fb) { - if (fb == null || !fb.isUpdateNeeded()) { - return; - } - } - - if (!caps.contains(Caps.FrameBuffer)) { - throw new RendererException("Framebuffer objects are not supported" - + " by the video hardware"); - } - - // generate mipmaps for last FB if needed - if (context.boundFB != null) { - for (int i = 0; i < context.boundFB.getNumColorBuffers(); i++) { - RenderBuffer rb = context.boundFB.getColorBuffer(i); - Texture tex = rb.getTexture(); - if (tex != null - && tex.getMinFilter().usesMipMapLevels()) { - setTexture(0, rb.getTexture()); - - int textureType = convertTextureType(tex.getType(), tex.getImage().getMultiSamples(), rb.getFace()); - glfbo.glGenerateMipmapEXT(textureType); - } - } + public void setReadDrawBuffers(FrameBuffer fb) { + if (gl2 == null) { + return; } - + + final int NONE = -2; + final int INITIAL = -1; + final int MRT_OFF = 100; + if (fb == null) { - // unbind any fbos - if (context.boundFBO != 0) { - glfbo.glBindFramebufferEXT(GLFbo.GL_FRAMEBUFFER_EXT, 0); - statistics.onFrameBufferUse(null, true); - - context.boundFBO = 0; + // Set Read/Draw buffers to initial value. + if (context.boundDrawBuf != INITIAL) { + gl2.glDrawBuffer(context.initialDrawBuf); + context.boundDrawBuf = INITIAL; } - // select back buffer - if (gl2 != null) { - if (context.boundDrawBuf != -1) { - gl2.glDrawBuffer(context.initialDrawBuf); - context.boundDrawBuf = -1; - } - if (context.boundReadBuf != -1) { - gl2.glReadBuffer(context.initialReadBuf); - context.boundReadBuf = -1; - } + if (context.boundReadBuf != INITIAL) { + gl2.glReadBuffer(context.initialReadBuf); + context.boundReadBuf = INITIAL; } - - context.boundFB = null; } else { - if (fb.getNumColorBuffers() == 0 && fb.getDepthBuffer() == null) { - throw new IllegalArgumentException("The framebuffer: " + fb - + "\nDoesn't have any color/depth buffers"); - } - - if (fb.isUpdateNeeded()) { - updateFrameBuffer(fb); - } - - // update viewport to reflect framebuffer's resolution - setViewPort(0, 0, fb.getWidth(), fb.getHeight()); - - if (context.boundFBO != fb.getId()) { - glfbo.glBindFramebufferEXT(GLFbo.GL_FRAMEBUFFER_EXT, fb.getId()); - statistics.onFrameBufferUse(fb, true); - - context.boundFBO = fb.getId(); - } else { - statistics.onFrameBufferUse(fb, false); - } if (fb.getNumColorBuffers() == 0) { // make sure to select NONE as draw buf - // no color buffer attached. select NONE + // no color buffer attached. if (gl2 != null) { - if (context.boundDrawBuf != -2) { + if (context.boundDrawBuf != NONE) { gl2.glDrawBuffer(GL.GL_NONE); - context.boundDrawBuf = -2; + context.boundDrawBuf = NONE; } - if (context.boundReadBuf != -2) { + if (context.boundReadBuf != NONE) { gl2.glReadBuffer(GL.GL_NONE); - context.boundReadBuf = -2; + context.boundReadBuf = NONE; } } } else { @@ -1622,7 +1594,7 @@ public class GLRenderer implements Renderer { + " by the video hardware!"); } - if (context.boundDrawBuf != 100 + fb.getNumColorBuffers()) { + if (context.boundDrawBuf != MRT_OFF + fb.getNumColorBuffers()) { intBuf16.clear(); for (int i = 0; i < fb.getNumColorBuffers(); i++) { intBuf16.put(GLFbo.GL_COLOR_ATTACHMENT0_EXT + i); @@ -1630,7 +1602,7 @@ public class GLRenderer implements Renderer { intBuf16.flip(); glext.glDrawBuffers(intBuf16); - context.boundDrawBuf = 100 + fb.getNumColorBuffers(); + context.boundDrawBuf = MRT_OFF + fb.getNumColorBuffers(); } } else { RenderBuffer rb = fb.getColorBuffer(fb.getTargetIndex()); @@ -1643,8 +1615,56 @@ public class GLRenderer implements Renderer { } } } + } + + } + + public void setFrameBuffer(FrameBuffer fb) { + if (fb == null && mainFbOverride != null) { + fb = mainFbOverride; + } + + if (context.boundFB == fb) { + if (fb == null || !fb.isUpdateNeeded()) { + return; + } + } + + if (!caps.contains(Caps.FrameBuffer)) { + throw new RendererException("Framebuffer objects are not supported" + + " by the video hardware"); + } + + // generate mipmaps for last FB if needed + if (context.boundFB != null) { + for (int i = 0; i < context.boundFB.getNumColorBuffers(); i++) { + RenderBuffer rb = context.boundFB.getColorBuffer(i); + Texture tex = rb.getTexture(); + if (tex != null + && tex.getMinFilter().usesMipMapLevels()) { + setTexture(0, rb.getTexture()); + + int textureType = convertTextureType(tex.getType(), tex.getImage().getMultiSamples(), rb.getFace()); + glfbo.glGenerateMipmapEXT(textureType); + } + } + } + + if (fb == null) { + bindFrameBuffer(null); + setReadDrawBuffers(null); + } else { + if (fb.isUpdateNeeded()) { + updateFrameBuffer(fb); + } else { + bindFrameBuffer(fb); + setReadDrawBuffers(fb); + } + + // update viewport to reflect framebuffer's resolution + setViewPort(0, 0, fb.getWidth(), fb.getHeight()); - assert fb.getId() >= 0; + assert fb.getId() > 0; assert context.boundFBO == fb.getId(); context.boundFB = fb; diff --git a/jme3-core/src/main/java/com/jme3/renderer/opengl/GLTracer.java b/jme3-core/src/main/java/com/jme3/renderer/opengl/GLTracer.java index a2775ba0a..f252d22dc 100644 --- a/jme3-core/src/main/java/com/jme3/renderer/opengl/GLTracer.java +++ b/jme3-core/src/main/java/com/jme3/renderer/opengl/GLTracer.java @@ -336,6 +336,21 @@ public final class GLTracer implements InvocationHandler { print(")"); } + private void printArgsGetInteger(Object[] args) { + print("("); + int param = (Integer)args[0]; + IntBuffer ib = (IntBuffer) args[1]; + printEnum(param); + print(", "); + printOut(); + if (param == GL2.GL_DRAW_BUFFER || param == GL2.GL_READ_BUFFER) { + printEnum(ib.get(0)); + } else { + printInt(ib.get(0)); + } + print(")"); + } + private void printArgsTexParameter(Object[] args) { print("("); @@ -389,6 +404,9 @@ public final class GLTracer implements InvocationHandler { } else if (methodName.equals("glTexParameteri")) { printArgsTexParameter(args); return; + } else if (methodName.equals("glGetInteger")) { + printArgsGetInteger(args); + return; } if (args == null) {