protected Texture2D SaveScreenShot(ref string filename, Action draw, Action drawOverlay) { filename = filename ?? "Default"; filename = filename + "-" + Guid.NewGuid().ToString("B").ToUpper() + ".png"; var backBuffer = new RenderTarget2D(GraphicsDevice, GraphicsDevice.Viewport.Width, GraphicsDevice.Viewport.Height); backBuffer.Begin(); GraphicsDevice.Clear(Color.Black); draw(); backBuffer.End(); var frontBuffer = new RenderTarget2D(GraphicsDevice, GraphicsDevice.Viewport.Width, GraphicsDevice.Viewport.Height); frontBuffer.Begin(); GraphicsDevice.Clear(Color.Black); GraphicsDevice.DrawFullscreenQuad(backBuffer, null, null, Color.White, null); GraphicsDevice.Textures[0] = null; drawOverlay(); frontBuffer.End(); using (var output = new FileStream(filename, FileMode.Create)) { frontBuffer.SaveAsPng(output, frontBuffer.Width, frontBuffer.Height); } frontBuffer.Dispose(); return(backBuffer); }
/// <summary> /// Begins the rendering of all the lights in the scene. /// </summary> private void BeginLights(DrawingContext3D context) { if (hasLightBegin || hasSceneBegin) { throw new InvalidOperationException("Begin cannot be called until End has been successfully called."); } hasLightBegin = true; CreateLightBuffer(); lightBuffer.Begin(); // Setup render states for light rendering // Clear specular intensity to 0 GraphicsDevice.Clear(new Color(context.ambientLightColor.X, context.ambientLightColor.Y, context.ambientLightColor.Z, 0)); // Set render state for lights GraphicsDevice.BlendState = lightBlendState; GraphicsDevice.DepthStencilState = DepthStencilState.None; // Set up textures and sampler states GraphicsDevice.Textures[0] = depthBuffer; GraphicsDevice.Textures[1] = normalBuffer; GraphicsDevice.SamplerStates[0] = GraphicsDevice.SamplerStates[1] = SamplerState.PointClamp; }
private void DrawWithCombineMaterial(DrawingContext context, IList <IDrawableObject> drawables) { RenderTargetPool.Lock(InputTexture as RenderTarget2D); int i, p; for (p = 0; p < passes.Count; p++) { passes[p].GetActivePasses(workingPasses); RenderTarget2D intermediate = InputTexture as RenderTarget2D; for (i = 0; i < workingPasses.Count; ++i) { var workingPass = (PostEffect)workingPasses[i]; RenderTarget2D previous = intermediate; RenderTargetPool.Lock(previous); intermediate = workingPass.PrepareRenderTarget(context.graphics, intermediate, null); intermediate.Begin(); workingPass.InputTexture = previous; workingPass.Draw(context, drawables); intermediate.End(); RenderTargetPool.Unlock(previous); } passResults.Add(intermediate); workingPasses.Clear(); } RenderTargetPool.Unlock(InputTexture as RenderTarget2D); if (fullScreenQuad == null) { fullScreenQuad = new FullScreenQuad(context.graphics); } context.graphics.BlendState = BlendState.Opaque; Material.texture = InputTexture; for (i = 0, p = 0; p < passes.Count; p++) { if (passes[p].Enabled) { Material.SetTexture(passes[p].TextureUsage, passResults[i]); i++; } } fullScreenQuad.Draw(context, Material); lastEffects.Clear(); passResults.Clear(); }
public override void Draw(DrawingContext context, IList <IDrawableObject> drawables) { if (Material == null) { Material = adoptionMaterial = new AdaptionMaterial(context.graphics); } else if (Material != adoptionMaterial) { throw new InvalidOperationException(); } bool needLocalTexture = false; if (needLocalTexture = (currentFrame == null)) { PrepareRenderTarget(context.graphics, InputTexture, null); currentFrame.Begin(); } // Disable the adoption effect when we don't have a valid last frame texture // or when the adoption effect has been suspended for several frames. #if SILVERLIGHT if (lastFrame == null || lastFrame.IsDisposed) #else if (lastFrame == null || lastFrame.IsDisposed || lastFrame.IsContentLost) #endif { CopyToScreen(context, drawables); } else { var graphics = context.graphics; graphics.Textures[0] = adoptionMaterial.texture; graphics.Textures[1] = lastFrame; graphics.SamplerStates[0] = graphics.SamplerStates[1] = SamplerState.PointClamp; adoptionMaterial.effect.Delta.SetValue((1 - (float)Math.Pow(0.98f, 30 * context.elapsedTime)) * Speed); base.Draw(context, drawables); graphics.SamplerStates[1] = context.SamplerState; } if (needLocalTexture) { currentFrame.End(); InputTexture = currentFrame; CopyToScreen(context, drawables); } RenderTargetPool.Unlock(lastFrame); lastFrame = currentFrame; currentFrame = null; }
/// <summary> /// Begins the shadowmap generation process and clears the shadowmap to white. /// </summary> private void Begin() { if (hasBegin) { throw new InvalidOperationException("Begin cannot be called until End has been successfully called."); } hasBegin = true; if (renderTarget == null || renderTarget.IsDisposed || #if !SILVERLIGHT renderTarget.IsContentLost || #endif renderTarget.Format != SurfaceFormat || renderTarget.Width != Size) { if (renderTarget != null) { renderTarget.Dispose(); } renderTarget = new RenderTarget2D(graphics, Size, Size, false, SurfaceFormat, graphics.PresentationParameters.DepthStencilFormat); } renderTarget.Begin(); graphics.Clear(Color.White); }
protected Texture2D SaveScreenShot(string filename, Action draw) { filename = filename ?? "Default"; var backBuffer = new RenderTarget2D(GraphicsDevice, GraphicsDevice.Viewport.Width, GraphicsDevice.Viewport.Height); backBuffer.Begin(); GraphicsDevice.Clear(Color.Black); draw(); backBuffer.End(); using (var output = new FileStream(filename + "-" + Guid.NewGuid().ToString("B").ToUpper() + ".png", FileMode.Create)) { backBuffer.SaveAsPng(output, backBuffer.Width, backBuffer.Height); } return(backBuffer); }
/// <summary> /// Ends the shadowmap generation process and returns the result shadowmap texture. /// </summary> private Texture2D End(DrawingContext context) { if (!hasBegin) { throw new InvalidOperationException("Begin must be called successfully before End can be called."); } hasBegin = false; Texture2D map = renderTarget.End(); if (BlurEnabled) { if (depthBlur == null || depthBlur.IsDisposed || #if !SILVERLIGHT depthBlur.IsContentLost || #endif depthBlur.Format != SurfaceFormat || depthBlur.Width != Size) { if (depthBlur != null) { depthBlur.Dispose(); } depthBlur = new RenderTarget2D(graphics, Size, Size, false, SurfaceFormat, graphics.PresentationParameters.DepthStencilFormat); } // Blur H depthBlur.Begin(); blur.texture = map; blur.Direction = 0; fullScreenQuad.Draw(context, blur); map = depthBlur.End(); // Blur V renderTarget.Begin(); blur.texture = map; blur.Direction = MathHelper.PiOver2; fullScreenQuad.Draw(context, blur); map = renderTarget.End(); } context.textures[TextureUsage.ShadowMap] = map; return(Texture = map); }
/// <summary> /// Draws this pass using the specified drawing context. /// </summary> public override void Draw(DrawingContext context, IList <IDrawableObject> drawables) { var passes = context.Passes; for (int i = 0; i < passes.Count; ++i) { if (passes[i].Enabled && passes[i] is LightPrePass) { return; } } var graphics = context.graphics; if (depthMaterial == null) { depthMaterial = new DepthMaterial(graphics); } var surfaceFormat = SurfaceFormat.Single; if (depthBuffer == null || depthBuffer.IsDisposed || depthBuffer.IsContentLost) { if (depthBuffer != null) { depthBuffer.Dispose(); } depthBuffer = new RenderTarget2D(graphics, graphics.Viewport.Width, graphics.Viewport.Height, false, surfaceFormat, DepthFormat.Depth24Stencil8, 0, RenderTargetUsage.DiscardContents); } if (drawingPass == null) { drawingPass = new DrawingPass(); drawingPass.MaterialUsage = MaterialUsage.Depth; } depthBuffer.Begin(); graphics.Clear(Color.White); drawingPass.Draw(context, drawables); depthBuffer.End(); context.textures[TextureUsage.DepthBuffer] = depthBuffer; }
/// <summary> /// Draws the specified scene. /// </summary> public void Draw(float elapsedTime, Matrix view, Matrix projection) { if (isDrawing) { throw new InvalidOperationException("Cannot trigger another drawing of the scene while it's still been drawn"); } this.matrices.View = view; this.matrices.Projection = projection; this.isDrawing = true; this.VertexOffset = 0; this.VertexBuffer = null; this.PreviousMaterial = null; this.elapsedTime = elapsedTime; this.totalTime += TimeSpan.FromSeconds(elapsedTime); this.totalSeconds = (float)totalTime.TotalSeconds; this.boundingBoxNeedsUpdate = true; if (rootPass == null) { return; } graphics.SetVertexBuffer(null); graphics.Textures[0] = null; UpdateDefaultSamplerStates(); AddDrawablesToView(matrices.ViewFrustum); UpdatePassGraph(); UpdateActivePasses(); RenderTarget2D lastRenderTarget = null; RenderTarget2D intermediate = null; bool overrideViewFrustumLastPass = false; for (int i = 0; i < activePasses.Count; ++i) { var pass = activePasses[i]; var overrideViewFrustum = false; // Query the drawables in the current view frustum only when the view frustum changed // or the pass overrides the frustum. Matrix passView, passProjection; if (pass.TryGetViewFrustum(out passView, out passProjection)) { matrices.View = passView; matrices.Projection = passProjection; overrideViewFrustum = true; } if (overrideViewFrustum || overrideViewFrustumLastPass) { AddDrawablesToView(matrices.ViewFrustum); overrideViewFrustumLastPass = overrideViewFrustum; } if ((pass.PassOperation & PassOperation.EndRenderTarget) != 0) { intermediate.End(); lastRenderTarget = intermediate; } if ((pass.PassOperation & PassOperation.BeginRenderTarget) != 0) { intermediate = pass.PrepareRenderTarget(graphics, intermediate, pass.PassFormat); intermediate.Begin(); RenderTargetPool.Lock(intermediate); } var postEffect = pass as IPostEffect; if (postEffect != null) { postEffect.InputTexture = lastRenderTarget; pass.Draw(this, drawablesInViewFrustum); RenderTargetPool.Unlock(lastRenderTarget); } else { pass.Draw(this, drawablesInViewFrustum); } } currentFrame++; isDrawing = false; }
private void DrawWithoutCombineMaterial(DrawingContext context, IList <IDrawableObject> drawables) { RenderTargetPool.Lock(InputTexture as RenderTarget2D); int i, p; for (p = 0; p < passes.Count; p++) { passes[p].GetActivePasses(workingPasses); RenderTarget2D intermediate = InputTexture as RenderTarget2D; for (i = 0; i < workingPasses.Count - 1; ++i) { var workingPass = (PostEffect)workingPasses[i]; RenderTarget2D previous = intermediate; RenderTargetPool.Lock(previous); intermediate = workingPass.PrepareRenderTarget(context.graphics, intermediate, null); intermediate.Begin(); workingPass.InputTexture = previous; workingPass.Draw(context, drawables); intermediate.End(); RenderTargetPool.Unlock(previous); } PostEffect lastEffect; RenderTargetPool.Lock(intermediate); if (workingPasses.Count > 0) { lastEffect = (PostEffect)workingPasses[workingPasses.Count - 1]; } else { if (basicPostEffect == null) { basicPostEffect = new PostEffect(); basicPostEffect.Material = new TextureMaterial(context.graphics); } lastEffect = basicPostEffect; } lastEffects.Add(lastEffect); passResults.Add(intermediate); workingPasses.Clear(); } RenderTargetPool.Unlock(InputTexture as RenderTarget2D); for (i = 0, p = 0; p < passes.Count; p++) { if (passes[p].Enabled) { lastEffects[i].BlendState = passes[p].BlendState; lastEffects[i].InputTexture = passResults[i]; lastEffects[i].Draw(context, drawables); RenderTargetPool.Unlock(passResults[i]); i++; } } lastEffects.Clear(); passResults.Clear(); }
void CaptureScreen() { if (screenCapture != null) { screenCapture.Dispose(); } using (var graphics = glControl.CreateGraphics()) { var cameraZoom = camera.Zoom; var cameraPos = camera.Position; ResetCamera(); if (frameBufferObjects) { using (var renderTarget = new RenderTarget2D(textureWidth, textureHeight)) { var pixelsPerMeter = spriteBatch.PixelsPerMeter; spriteBatch.SetDimensions(textureWidth, textureHeight); spriteBatch.PixelsPerMeter = project.PixelsPerMillimeter; renderTarget.Begin(); RenderModel(new RectangleF(-backgroundWidth / 2, -backgroundHeight / 2, backgroundWidth, backgroundHeight), CaptureMarkerSize, 2); renderTarget.End(); screenCapture = renderTarget.Texture.ToBitmap(); if (textureWidth != backgroundWidth || textureHeight != backgroundHeight) { using (var rawCapture = screenCapture) { screenCapture = rawCapture.Clone(new Rectangle( (textureWidth - backgroundWidth) / 2, (textureHeight - backgroundHeight) / 2, backgroundWidth, backgroundHeight), screenCapture.PixelFormat); } } screenCapture.SetResolution(project.PixelsPerMillimeter * MillimetersPerInch, project.PixelsPerMillimeter * MillimetersPerInch); spriteBatch.PixelsPerMeter = pixelsPerMeter; spriteBatch.SetDimensions(glControl.Width, glControl.Height); } } else { screenCapture = new Bitmap(backgroundWidth, backgroundHeight); var blockColumns = backgroundWidth / glControl.Width; var blockRows = backgroundHeight / glControl.Height; var remainderWidth = backgroundWidth % glControl.Width; var remainderHeight = backgroundHeight % glControl.Height; var pixelsPerMeter = spriteBatch.PixelsPerMeter; spriteBatch.PixelsPerMeter = project.PixelsPerMillimeter; var viewWidthInMillimeters = glControl.Width / project.PixelsPerMillimeter; var viewHeightInMillimeters = glControl.Height / project.PixelsPerMillimeter; var widthInMillimeters = backgroundWidth / project.PixelsPerMillimeter; var heightInMillimeters = backgroundHeight / project.PixelsPerMillimeter; var offsetX = -widthInMillimeters / 2 + viewWidthInMillimeters / 2; var offsetY = -heightInMillimeters / 2 + viewHeightInMillimeters / 2; for (int i = 0; i <= blockRows; i++) { for (int j = 0; j <= blockColumns; j++) { if (j == blockColumns && remainderWidth == 0) { continue; } if (i == blockRows && remainderHeight == 0) { continue; } var captureWidth = j == blockColumns ? remainderWidth : glControl.Width; var captureHeight = i == blockRows ? remainderHeight : glControl.Height; var bitmapData = screenCapture.LockBits(new System.Drawing.Rectangle(j * glControl.Width, i * glControl.Height, captureWidth, captureHeight), System.Drawing.Imaging.ImageLockMode.WriteOnly, System.Drawing.Imaging.PixelFormat.Format24bppRgb); camera.Position = new Vector2(offsetX + j * viewWidthInMillimeters, offsetY + i * viewHeightInMillimeters); RenderModel(new RectangleF(-backgroundWidth / 2, -backgroundHeight / 2, backgroundWidth, backgroundHeight), DefaultMarkerSize, 2); glControl.SwapBuffers(); GL.ReadPixels(0, 0, bitmapData.Width, bitmapData.Height, PixelFormat.Bgr, PixelType.UnsignedByte, bitmapData.Scan0); screenCapture.UnlockBits(bitmapData); } } screenCapture.RotateFlip(RotateFlipType.RotateNoneFlipY); screenCapture.SetResolution(project.PixelsPerMillimeter * MillimetersPerInch, project.PixelsPerMillimeter * MillimetersPerInch); spriteBatch.PixelsPerMeter = pixelsPerMeter; } camera.Zoom = cameraZoom; camera.Position = cameraPos; deviceDpiX = graphics.DpiX; } }