public override bool Bind() { Debug.Assert(!isDisposed); Upload(); if (textureId <= 0) { return(false); } if (IsTransparent) { return(false); } OsuGlControl.BindTexture(textureId); if (internalWrapMode != WrapMode) { updateWrapMode(); } return(true); }
internal void Unbind() { if (!bound) { return; } if (OsuGlControl.CanUseFBO) { currentFrameBuffer = lastFrameBuffer; GL.BindFramebuffer(FramebufferTarget.Framebuffer, lastFrameBuffer); } else { //Copy from backbuffer OsuGlControl.BindTexture(Texture.TextureId); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMinFilter, (int)All.Linear); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMagFilter, (int)All.Linear); GL.CopyTexSubImage2D(All.Texture2D, 0, (int)copyDstPosition.X, (int)copyDstPosition.Y, copySrcRectangle.X, copySrcRectangle.Y, copySrcRectangle.Width, copySrcRectangle.Height); } if (OsuGlControl.Viewport != prevViewport) { OsuGlControl.ResetViewport(prevViewport); OsuGlControl.ResetOrtho(prevOrtho); } bound = false; }
internal void Bind() { if (bound) { return; } prevViewport = OsuGlControl.Viewport; prevOrtho = OsuGlControl.Ortho; if (OsuGlControl.CanUseFBO) { lastFrameBuffer = currentFrameBuffer; currentFrameBuffer = frameBuffer; GL.BindFramebuffer(FramebufferTarget.Framebuffer, frameBuffer); } GL.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit); //For now we have this conditional here to reduce GL calls //This will be removed in peppy/more_gl_stuff (among a whole slew of other things) if (viewport != prevViewport) { OsuGlControl.ResetViewport(viewport); OsuGlControl.ResetOrtho(viewport); } bound = true; }
internal RenderTarget2D(TextureGlSingle texture, RenderbufferInternalFormat?renderBufferType = null) { Texture = texture; this.renderBufferType = renderBufferType; viewport = new Rectangle(0, 0, Width, Height); // Make sure the texture is generated and allocated to the proper size. Texture.SetData(new byte[0]); Texture.Upload(); if (OsuGlControl.CanUseFBO) { lastFrameBuffer = currentFrameBuffer; currentFrameBuffer = frameBuffer = GL.GenFramebuffer(); GL.BindFramebuffer(FramebufferTarget.Framebuffer, frameBuffer); GL.FramebufferTexture2D(FramebufferTarget.Framebuffer, All.ColorAttachment0, TextureTarget2d.Texture2D, Texture.TextureId, 0); OsuGlControl.BindTexture(0); if (renderBufferType != null) { renderBuffer = GL.GenRenderbuffer(); GL.BindRenderbuffer(RenderbufferTarget.Renderbuffer, renderBuffer); GL.RenderbufferStorage(RenderbufferTarget.Renderbuffer, RenderbufferInternalFormat.DepthComponent16, Width, Height); GL.FramebufferRenderbuffer(FramebufferTarget.Framebuffer, All.DepthAttachment, RenderbufferTarget.Renderbuffer, renderBuffer); TotalRenderBuffers++; } currentFrameBuffer = lastFrameBuffer; GL.BindFramebuffer(FramebufferTarget.Framebuffer, lastFrameBuffer); TotalFrameBuffers++; } SetCopyRectangle(); }
public override bool Upload() { if (ConfigManager.dDisableTextureUploads) { return(false); } // We should never run raw OGL calls on another thread than the main thread due to race conditions. Debug.Assert(GameBase.MainThread == Thread.CurrentThread); if (isDisposed) { return(false); } lock (this) { if (dataToBeUploaded == null) { return(false); } IntPtr dataPointer; GCHandle?h0; if (dataToBeUploaded.Length == 0) { h0 = null; dataPointer = IntPtr.Zero; } else { h0 = GCHandle.Alloc(dataToBeUploaded, GCHandleType.Pinned); dataPointer = h0.Value.AddrOfPinnedObject(); } try { if (levelToBeUploaded > 0) { return(false); } // Do we need to generate a new texture? if (textureId <= 0 || internalWidth < width || internalHeight < height) { GameBase.PerformanceMonitor.ReportCount(CounterType.TextureGen); internalWidth = width; internalHeight = height; potWidth = TextureGl.GetPotDimension(width); potHeight = TextureGl.GetPotDimension(height); // We only need to generate a new texture if we don't have one already. Otherwise just re-use the current one. if (textureId <= 0) { #if DEBUG ++GameBase.AmountTextures; #endif int[] textures = new int[1]; GL.GenTextures(1, textures); textureId = textures[0]; OsuGlControl.BindTexture(textureId); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMinFilter, (int)All.Linear); GL.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMagFilter, (int)All.Linear); updateWrapMode(); } else { OsuGlControl.BindTexture(textureId); } if (potWidth == boundsToBeUploaded.Width && potHeight == boundsToBeUploaded.Height || dataPointer == IntPtr.Zero) { GL.TexImage2D(TextureTarget2d.Texture2D, levelToBeUploaded, TextureComponentCount.Rgba, potWidth, potHeight, 0, formatToBeUploaded, PixelType.UnsignedByte, dataPointer); } else { if (transparentBlack.Length < potWidth * potHeight * 4) { transparentBlack = new byte[potWidth * potHeight * 4]; // Default value is 0, exactly what we need. } GCHandle h1 = GCHandle.Alloc(transparentBlack, GCHandleType.Pinned); GL.TexImage2D(TextureTarget2d.Texture2D, levelToBeUploaded, TextureComponentCount.Rgba, potWidth, potHeight, 0, formatToBeUploaded, PixelType.UnsignedByte, h1.AddrOfPinnedObject()); h1.Free(); GL.TexSubImage2D(TextureTarget2d.Texture2D, levelToBeUploaded, boundsToBeUploaded.X, boundsToBeUploaded.Y, boundsToBeUploaded.Width, boundsToBeUploaded.Height, formatToBeUploaded, PixelType.UnsignedByte, dataPointer); } } // Just update content of the current texture else if (dataPointer != IntPtr.Zero) { GameBase.PerformanceMonitor.ReportCount(CounterType.TextureUpload); OsuGlControl.BindTexture(textureId); GL.TexSubImage2D(TextureTarget2d.Texture2D, levelToBeUploaded, boundsToBeUploaded.X, boundsToBeUploaded.Y, boundsToBeUploaded.Width, boundsToBeUploaded.Height, formatToBeUploaded, PixelType.UnsignedByte, dataPointer); } return(true); } finally { if (h0.HasValue) { h0.Value.Free(); } if (dataToBeUploaded != null) { FreeBuffer(dataToBeUploaded); } dataToBeUploaded = null; } } }