/// <summary> /// Initializes a new instance of the <see cref="RenderTargetCube"/> class. /// </summary> /// <param name="graphicsDevice">The graphics device.</param> /// <param name="size">The width and height of a texture cube face in pixels.</param> /// <param name="mipMap"> /// <see langword="true"/> to generate a full mipmap chain; otherwise <see langword="false"/>. /// </param> /// <param name="preferredFormat">The preferred format of the surface.</param> /// <param name="preferredDepthFormat">The preferred format of the depth-stencil buffer.</param> /// <param name="preferredMultiSampleCount">The preferred number of multisample locations.</param> /// <param name="usage">The usage mode of the render target.</param> public RenderTargetCube( GraphicsDevice graphicsDevice, int size, bool mipMap, SurfaceFormat preferredFormat, DepthFormat preferredDepthFormat, int preferredMultiSampleCount, RenderTargetUsage usage ) : base( graphicsDevice, size, mipMap, preferredFormat ) { DepthStencilFormat = preferredDepthFormat; MultiSampleCount = Math.Min( MathHelper.ClosestMSAAPower(preferredMultiSampleCount), graphicsDevice.GLDevice.MaxMultiSampleCount ); RenderTargetUsage = usage; // If we don't need a depth buffer then we're done. if (preferredDepthFormat == DepthFormat.None) { return; } glDepthStencilBuffer = graphicsDevice.GLDevice.GenRenderbuffer( size, size, preferredDepthFormat ); }
public void SetRenderTargets( RenderTargetBinding[] renderTargets, IGLRenderbuffer renderbuffer, DepthFormat depthFormat ) { ForceToMainThread(() => { GLDevice.SetRenderTargets( renderTargets, renderbuffer, depthFormat ); }); // End ForceToMainThread }
public RenderTarget2D( GraphicsDevice graphicsDevice, int width, int height, bool mipMap, SurfaceFormat preferredFormat, DepthFormat preferredDepthFormat, int preferredMultiSampleCount, RenderTargetUsage usage ) : base( graphicsDevice, width, height, mipMap, preferredFormat ) { DepthStencilFormat = preferredDepthFormat; MultiSampleCount = Math.Min( MathHelper.ClosestMSAAPower(preferredMultiSampleCount), graphicsDevice.GLDevice.MaxMultiSampleCount ); RenderTargetUsage = usage; if (MultiSampleCount > 0) { glColorBuffer = graphicsDevice.GLDevice.GenRenderbuffer( Width, Height, Format, MultiSampleCount, texture ); } // If we don't need a depth buffer then we're done. if (DepthStencilFormat == DepthFormat.None) { return; } glDepthStencilBuffer = graphicsDevice.GLDevice.GenRenderbuffer( Width, Height, DepthStencilFormat, MultiSampleCount ); }
public IGLRenderbuffer GenRenderbuffer( int width, int height, DepthFormat format, int multiSampleCount ) { IGLRenderbuffer result = null; ForceToMainThread(() => { result = GLDevice.GenRenderbuffer( width, height, format, multiSampleCount ); }); // End ForceToMainThread return(result); }
public void SetRenderTargets( RenderTargetBinding[] renderTargets, IGLRenderbuffer renderbuffer, DepthFormat depthFormat ) { // Bind the right framebuffer, if needed if (renderTargets == null) { BindFramebuffer( (Backbuffer is OpenGLBackbuffer) ? (Backbuffer as OpenGLBackbuffer).Handle : 0 ); flipViewport = 1; return; } else { BindFramebuffer(targetFramebuffer); flipViewport = -1; } int i; uint[] attachments = new uint[renderTargets.Length]; GLenum[] attachmentTypes = new GLenum[renderTargets.Length]; for (i = 0; i < renderTargets.Length; i += 1) { IGLRenderbuffer colorBuffer = (renderTargets[i].RenderTarget as IRenderTarget).ColorBuffer; if (colorBuffer != null) { attachments[i] = (colorBuffer as OpenGLRenderbuffer).Handle; attachmentTypes[i] = GLenum.GL_RENDERBUFFER; } else { attachments[i] = (renderTargets[i].RenderTarget.texture as OpenGLTexture).Handle; if (renderTargets[i].RenderTarget is RenderTarget2D) { attachmentTypes[i] = GLenum.GL_TEXTURE_2D; } else { attachmentTypes[i] = GLenum.GL_TEXTURE_CUBE_MAP_POSITIVE_X + (int) renderTargets[i].CubeMapFace; } } } // Update the color attachments, DrawBuffers state for (i = 0; i < attachments.Length; i += 1) { if (attachments[i] != currentAttachments[i]) { if (currentAttachments[i] != 0) { if ( attachmentTypes[i] != GLenum.GL_RENDERBUFFER && currentAttachmentTypes[i] == GLenum.GL_RENDERBUFFER ) { glFramebufferRenderbuffer( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, GLenum.GL_RENDERBUFFER, 0 ); } else if ( attachmentTypes[i] == GLenum.GL_RENDERBUFFER && currentAttachmentTypes[i] != GLenum.GL_RENDERBUFFER ) { glFramebufferTexture2D( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, currentAttachmentTypes[i], 0, 0 ); } } if (attachmentTypes[i] == GLenum.GL_RENDERBUFFER) { glFramebufferRenderbuffer( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, GLenum.GL_RENDERBUFFER, attachments[i] ); } else { glFramebufferTexture2D( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, attachmentTypes[i], attachments[i], 0 ); } currentAttachments[i] = attachments[i]; currentAttachmentTypes[i] = attachmentTypes[i]; } else if (attachmentTypes[i] != currentAttachmentTypes[i]) { // Texture cube face change! glFramebufferTexture2D( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, attachmentTypes[i], attachments[i], 0 ); currentAttachmentTypes[i] = attachmentTypes[i]; } } while (i < currentAttachments.Length) { if (currentAttachments[i] != 0) { if (currentAttachmentTypes[i] == GLenum.GL_RENDERBUFFER) { glFramebufferRenderbuffer( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, GLenum.GL_RENDERBUFFER, 0 ); } else { glFramebufferTexture2D( GLenum.GL_FRAMEBUFFER, GLenum.GL_COLOR_ATTACHMENT0 + i, currentAttachmentTypes[i], 0, 0 ); } currentAttachments[i] = 0; currentAttachmentTypes[i] = GLenum.GL_TEXTURE_2D; } i += 1; } if (attachments.Length != currentDrawBuffers) { glDrawBuffers(attachments.Length, drawBuffersArray); currentDrawBuffers = attachments.Length; } // Update the depth/stencil attachment /* FIXME: Notice that we do separate attach calls for the stencil. * We _should_ be able to do a single attach for depthstencil, but * some drivers (like Mesa) cannot into GL_DEPTH_STENCIL_ATTACHMENT. * Use XNAToGL.DepthStencilAttachment when this isn't a problem. * -flibit */ uint handle; if (renderbuffer == null) { handle = 0; } else { handle = (renderbuffer as OpenGLRenderbuffer).Handle; } if (handle != currentRenderbuffer) { if (currentDepthStencilFormat == DepthFormat.Depth24Stencil8) { glFramebufferRenderbuffer( GLenum.GL_FRAMEBUFFER, GLenum.GL_STENCIL_ATTACHMENT, GLenum.GL_RENDERBUFFER, 0 ); } currentDepthStencilFormat = depthFormat; glFramebufferRenderbuffer( GLenum.GL_FRAMEBUFFER, GLenum.GL_DEPTH_ATTACHMENT, GLenum.GL_RENDERBUFFER, handle ); if (currentDepthStencilFormat == DepthFormat.Depth24Stencil8) { glFramebufferRenderbuffer( GLenum.GL_FRAMEBUFFER, GLenum.GL_STENCIL_ATTACHMENT, GLenum.GL_RENDERBUFFER, handle ); } currentRenderbuffer = handle; } }
private void DeleteRenderbuffer(IGLRenderbuffer renderbuffer) { uint handle = (renderbuffer as OpenGLRenderbuffer).Handle; if (handle == currentRenderbuffer) { // Force a renderbuffer update, this no longer exists! currentRenderbuffer = uint.MaxValue; } glDeleteRenderbuffers(1, ref handle); }
public void AddDisposeRenderbuffer(IGLRenderbuffer renderbuffer) { if (IsOnMainThread()) { DeleteRenderbuffer(renderbuffer); } else { GCDepthBuffers.Enqueue(renderbuffer); } }
public void AddDisposeRenderbuffer(IGLRenderbuffer renderbuffer) { GCRenderbuffers.Enqueue(renderbuffer); }
public RenderTarget2D( GraphicsDevice graphicsDevice, int width, int height, bool mipMap, SurfaceFormat preferredFormat, DepthFormat preferredDepthFormat, int preferredMultiSampleCount, RenderTargetUsage usage ) : base( graphicsDevice, width, height, mipMap, preferredFormat ) { DepthStencilFormat = preferredDepthFormat; MultiSampleCount = Math.Min( MathHelper.ClosestMSAAPower(preferredMultiSampleCount), graphicsDevice.GLDevice.MaxMultiSampleCount ); RenderTargetUsage = usage; if (MultiSampleCount > 0) { glColorBuffer = graphicsDevice.GLDevice.GenRenderbuffer( width, height, Format, MultiSampleCount ); } // If we don't need a depth buffer then we're done. if (preferredDepthFormat == DepthFormat.None) { return; } glDepthStencilBuffer = graphicsDevice.GLDevice.GenRenderbuffer( width, height, preferredDepthFormat, MultiSampleCount ); }