public static void End() { Push(); #if DEBUG PixHelper.EndEvent(); #endif }
private static void Lighting(ref Camera camera) { PixHelper.BeginEvent(Color.Zero, "Lighting"); { Context.ClearRenderTargetView(camera.BackBuffer, Color.Zero); Context.OutputMerger.SetTargets((DepthStencilView)null, camera.BackBuffer); Context.PixelShader.SetShaderResources(0, camera.Buffer0, camera.Buffer1, camera.Buffer2, camera.Buffer3, camera.DepthStencilBuffer, Game.Lighting.Skybox?.IrradianceMap?.Texture, Game.Lighting.Skybox?.RadianceMap?.Texture); Context.PixelShader.SetConstantBuffers(0, camera.Constants, Services.Lighting.LightingConstantBuffer); LightingPass.Use(ref Context); Context.Draw(4, 0); Context.CopyResource(camera.BackBuffer.NativeTexture, camera.Buffer0.NativeTexture); Context.PixelShader.SetShaderResources(0, null, null, null, null, null, null, null, null); } PixHelper.EndEvent(); }
private static void DrawScreenGuis(Camera camera) { PixHelper.BeginEvent(Color.Zero, "ScreenGuis"); { if (camera.RenderTarget2D == null) { return; } var starterGui = Game.StarterGui; lock (camera.Locker) { var collectors = camera.LayerCollectors; var count = collectors.Count; for (var i = 0; i < count; i++) { var gui = collectors[i]; if ((RunService.SimulationState != SimulationState.Stopped) && (gui.Parent == starterGui)) { continue; } gui.Render(); } } } PixHelper.EndEvent(); }
/// <summary> /// Ends the current section of profiling (must match with a begin). /// </summary> public void End() { if (!Enabled) { return; } #if !W8CORE PixHelper.EndEvent(); #endif // TODO Add code for Direct3D11.1 annotation API }
public void Reduce(DeviceContext context, ShaderResourceView from) { PixHelper.BeginEvent(Color.Green, "MinMax {0}x{0}", 1 << ReduceFactor); context.InputAssembler.InputLayout = layout; context.InputAssembler.PrimitiveTopology = PrimitiveTopology.TriangleStrip; context.InputAssembler.SetVertexBuffers(0, new VertexBufferBinding(vertices, sizeof(float) * 2, 0)); context.VertexShader.Set(vertexShader); var viewport = new Viewport(0, 0, Size.Width, Size.Height); int maxLevels = texture2DMinMaxResourceView.Length; int lastSampleLevel = maxLevels % ReduceFactor; int levels = maxLevels / ReduceFactor; passCount = levels + (lastSampleLevel > 0 ? 1 : 0); for (int i = 0; i < passCount; i++) { int shaderIndex = ReduceFactor; int levelIndex = (i + 1) * ReduceFactor - 1; viewport.Width = Math.Max(((int)Size.Width) / (1 << (levelIndex + 1)), 1); viewport.Height = Math.Max(((int)Size.Height) / (1 << (levelIndex + 1)), 1); PixHelper.BeginEvent(Color.GreenYellow, "MinMax Level {0} Size: ({1},{2})", levelIndex, viewport.Width, viewport.Height); // Special case when last level is different from ReduceFactor size if (i == levels) { levelIndex = maxLevels - 1; shaderIndex = lastSampleLevel; viewport.Width = 1; viewport.Height = 1; } context.PixelShader.Set(i == 0 ? pixelShaderMinMaxBegin[shaderIndex - 1] : pixelShaderMinMax[shaderIndex - 1]); context.PixelShader.SetSampler(0, sampler); context.PixelShader.SetShaderResource(0, from); context.Rasterizer.SetViewport(viewport); //context.ClearRenderTargetView(texture2DMinMaxRenderView[levelIndex], Colors.Black); context.OutputMerger.SetTargets(texture2DMinMaxRenderView[levelIndex]); context.Draw(4, 0); context.PixelShader.SetShaderResource(0, null); context.OutputMerger.ResetTargets(); from = texture2DMinMaxResourceView[levelIndex]; PixHelper.EndEvent(); } PixHelper.EndEvent(); }
public static void Render() { int count; PrepareConstant(); //***************************** #if DEBUG PixHelper.BeginEvent(Color.Orange, "SM : Solid Rendering"); #endif Pass = RenderPass.Solid; count = Renderable_Solids.Length; for (int i = 0; i < count; i++) { Renderable_Solids[i].Render(); } #if DEBUG PixHelper.EndEvent(); #endif //***************************** #if DEBUG PixHelper.BeginEvent(Color.Orange, "SM : Transparent Rendering"); #endif Pass = RenderPass.Transparent; count = Renderable_Transparents.Length; for (int i = 0; i < count; i++) { Renderable_Transparents[i].Render(); } #if DEBUG PixHelper.EndEvent(); #endif //***************************** Display.context.ResolveSubresource(Display.backBuffer, 0, Display.backBufferCopy, 0, Format.R8G8B8A8_UNorm); #if DEBUG PixHelper.BeginEvent(Color.Orange, "SM : Special Rendering"); #endif Pass = RenderPass.Post; count = Renderable_Posts.Length; for (int i = 0; i < count; i++) { Renderable_Posts[i].Render(); } #if DEBUG PixHelper.EndEvent(); #endif }
private static void PostProcess(ref Camera camera) { PixHelper.BeginEvent(Color.Zero, "Post Processing"); { var postEffects = camera.PostEffects; lock (camera.PostEffectsLocker) { for (var i = 0; i < postEffects.Count; i++) { camera.PostEffects[i].Render(ref Context); } } } PixHelper.EndEvent(); }
private static void Draw3DGuis(Camera camera) { //if (camera != Game.FocusedCamera) return; PixHelper.BeginEvent(Color.Zero, "3D Guis"); lock (camera.Locker) { var guis = camera.Gui3Ds; var count = guis.Count; for (var i = 0; i < count; i++) { guis[i].Draw(ref Context, ref camera); } } PixHelper.EndEvent(); }
internal void Draw(ref DeviceContext context) { PixHelper.BeginEvent(Color.Zero, "Terrain"); if (_terrainPass == null) { _terrainShader = Shaders.Get("Terrain"); _terrainPass = _terrainShader.GetPass("Main"); } lock (Renderer.Context) { _terrainPass.Use(ref context); foreach (var chunk in _chunks) { chunk.Value.Draw(ref context); } } PixHelper.EndEvent(); }
/// <summary> /// Draws instances to the current render target. /// </summary> public void Draw(ref DeviceContext context, ref Camera camera, bool pix = true) { if (!IsBuilt) { Build(); } if (_bufferDirty) { Update(ref context); } if (InstanceCount == 0) { return; } if (pix) { PixHelper.BeginEvent(Color.Red, Name); } var newTopology = Geometry.PrimitiveTopology; if (newTopology != context.InputAssembler.PrimitiveTopology) { context.InputAssembler.PrimitiveTopology = Geometry.PrimitiveTopology; } context.InputAssembler.SetVertexBuffers(0, Bindings); context.InputAssembler.SetIndexBuffer(Geometry.IndexBuffer, Format.R32_UInt, 0); context.DrawIndexedInstanced(Geometry.IndexCount, InstanceCount, 0, 0, 0); if (pix) { PixHelper.EndEvent(); } }
internal override void Draw(ref DeviceContext context, ref Camera camera) { var adornee = Adornee; if (adornee == null || Visible == false) { return; } PixHelper.BeginEvent(Color.Zero, "ArcHandles"); Renderer.AdornSelfLitPass.Use(ref context); var adorneeCF = adornee.CFrame; var adorneeSize = adornee.Size; GetDistanceToNormals(10, 0.6f, ref adorneeCF, ref adorneeSize, ref _scales); var radius = adorneeSize.max() * 0.75f; for (int i = 0; i < 6; i++) { var sphere = _spheres[i]; var normalId = (NormalId)i; sphere.CFrame = adorneeCF + (Vector3.FromNormalId(normalId) * radius); sphere.Size = new Vector3(_scales[i]); sphere.UpdateRenderData(); sphere.Draw(ref context, ref camera); } for (int i = 0; i < 3; i++) { CFrame angle; if (i == 0) { angle = CFrame.Identity; } else if (i == 1) { angle = CFrame.Angles(0, Mathf.Pi / 2, 0); } else { angle = CFrame.Identity; } for (int j = 0; j < _segments; j++) { var cylinder = _cylinders[i * j]; cylinder.Size = _cylinderSize * (radius / 256); var sine = Mathf.Sin((360 / _segments + 360 / _segments * j) / (180 / Mathf.Pi)); var cosine = Mathf.Cos((360 / _segments + 360 / _segments * j) / (180 / Mathf.Pi)); var cframe = (adorneeCF) + new Vector3(radius * sine, 0, radius * cosine); cylinder.CFrame = cframe * CFrame.Angles(0, (360 / _segments + 360 / _segments * j) / (180 / Mathf.Pi), Mathf.Pi / 2); cylinder.UpdateRenderData(); cylinder.Draw(ref context, ref camera); } } PixHelper.EndEvent(); }
/// <summary> /// Draws the scene from the perspective of the given camera to its <see cref="Camera.BackBuffer" /> /// </summary> internal static void Render(IWorld world, PassType passes) { if (!world.IsRenderable) { return; } var camera = world.CurrentCamera; if (camera == null) { return; } lock (Locker) { if (camera.NeedsResize && (camera.SwapChain != null)) { camera.Resize(Device); return; } if (!camera.CanRender) { return; } if (passes.HasFlag(PassType.Shadow)) { Shadows.RenderShadowMap(ref Context, ref world, ref camera); } if (passes.HasFlag(PassType.Scene)) { PixHelper.BeginEvent(Color.Zero, "Geometry"); { Context.Rasterizer.SetViewport(camera.Viewport); Context.ClearDepthStencilView(camera.DepthStencilBuffer, DepthStencilClearFlags.Depth | DepthStencilClearFlags.Stencil, 1, 0); Context.ClearRenderTargetView(camera.Buffer0, Color.Zero); Context.ClearRenderTargetView(camera.Buffer1, Color.Zero); Context.ClearRenderTargetView(camera.Buffer2, Color.Zero); Context.ClearRenderTargetView(camera.Buffer3, Color.Zero); camera.UpdateConstants(ref Context); Context.OutputMerger.SetRenderTargets(camera.DepthStencilBuffer, camera.Buffer0, camera.Buffer1, camera.Buffer2, camera.Buffer3); CurrentPassType = PassType.Scene; #pragma warning disable CS0728 // Possibly incorrect assignment to local which is the argument to a using or lock statement world.RenderObjectProvider.Draw(ref Context, ref camera, false); if (ReferenceEquals(world, Game.Workspace)) { Game.Workspace.Terrain.Draw(ref Context); } #pragma warning restore CS0728 // Possibly incorrect assignment to local which is the argument to a using or lock statement } PixHelper.EndEvent(); if (passes.HasFlag(PassType.PhysicsDebug)) { PixHelper.BeginEvent(Color.Zero, "Physics Debug"); world.Physics?.DrawWorld(ref Context, ref camera); PixHelper.EndEvent(); } } else if (passes.HasFlag(PassType.Reflection)) { } if (passes.HasFlag(PassType.Lighting)) { Atmosphere.Atmosphere.Update(); Lighting(ref camera); // rt is set to camera's backbuffer here. } if (passes.HasFlag(PassType.PostProcess)) { CurrentPassType = PassType.PostProcess; PostProcess(ref camera); // uses camera's back buffer } if (passes.HasFlag(PassType.GUI)) { CurrentPassType = PassType.GUI; // uses camera's back buffer Draw3DGuis(camera); DrawSurfaceGuis(); DrawBillboardGuis(camera); DrawScreenGuis(camera); } if (camera.RenderHandle == IntPtr.Zero) { Context.Flush(); } else { camera.SwapChain.Present(1, 0); } } }
public static void RenderShadowMap(ref DeviceContext context, ref IWorld world, ref Camera camera) { PixHelper.BeginEvent(default(RawColorBGRA), "Shadow Rendering"); { if (ShadowMapsNeedRemade) CreateShadowMaps(); var shadowMapSize = ShadowMap.Width; if (AreSplitsDirty || camera != _lastCamera) ComputeSplits(ref camera); _lastCamera = camera; MakeGlobalShadowMatrix(ref camera, out ReceiverConstants.Data.ShadowMatrix); context.Rasterizer.SetViewport(_viewport); for (int cascadeIndex = 0; cascadeIndex < CascadeCount; ++cascadeIndex) { PixHelper.BeginEvent(default(RawColorBGRA), "Cascade"); { ResetFrustumCorners(ref _frustumCorners); var prevSplitDist = cascadeIndex == 0 ? MinCascadeDistance : _cascadeSplits[cascadeIndex - 1]; var splitDist = _cascadeSplits[cascadeIndex]; for (int i = 0; i < 8; i++) DxVector3.TransformCoordinate(ref _frustumCorners[i], ref camera.Constants.Data.InverseViewProjection, out _frustumCorners[i]); for (int i = 0; i < 4; i++) { DxVector3 cornerRay; DxVector3 nearCornerRay; DxVector3 farCornerRay; DxVector3.Subtract(ref _frustumCorners[i + 4], ref _frustumCorners[i], out cornerRay); DxVector3.Multiply(ref cornerRay, prevSplitDist, out nearCornerRay); DxVector3.Multiply(ref cornerRay, splitDist, out farCornerRay); DxVector3.Add(ref _frustumCorners[i], ref farCornerRay, out _frustumCorners[i + 4]); DxVector3.Add(ref _frustumCorners[i], ref nearCornerRay, out _frustumCorners[i]); } var frustumCenter = DxVector3.Zero; for (int i = 0; i < 8; i++) DxVector3.Add(ref frustumCenter, ref _frustumCorners[i], out frustumCenter); DxVector3.Multiply(ref frustumCenter, 0.125F, out frustumCenter); var upDir = DxVector3.Up; float sphereRadius = 0.0f; for (int i = 0; i < 8; ++i) { DxVector3 sum; DxVector3.Subtract(ref _frustumCorners[i], ref frustumCenter, out sum); sphereRadius = Math.Max(sphereRadius, sum.Length()); } sphereRadius = (float)Math.Ceiling(sphereRadius * 16.0f) / 16.0f; var maxExtents = new DxVector3(sphereRadius, sphereRadius, sphereRadius); DxVector3 minExtents; DxVector3.Negate(ref maxExtents, out minExtents); DxVector3 cascadeExtents; DxVector3.Subtract(ref maxExtents, ref minExtents, out cascadeExtents); // TODO: optimize var shadowCameraPos = frustumCenter + Direction * -minExtents.Z; Matrix viewMatrix; Matrix projectionMatrix; Matrix viewProjMatrix; Matrix.LookAtLH(ref shadowCameraPos, ref frustumCenter, ref upDir, out viewMatrix); Matrix.OrthoOffCenterLH(minExtents.X, maxExtents.X, minExtents.Y, maxExtents.Y, 0.0f, cascadeExtents.Z, out projectionMatrix); Matrix.Multiply(ref viewMatrix, ref projectionMatrix, out viewProjMatrix); var shadowOrigin = DxVector4.UnitW; DxVector4.Transform(ref shadowOrigin, ref viewProjMatrix, out shadowOrigin); DxVector4.Multiply(ref shadowOrigin, shadowMapSize / 2.0f, out shadowOrigin); var roundedOrigin = new DxVector4(Mathf.Round(shadowOrigin.X), Mathf.Round(shadowOrigin.Y), Mathf.Round(shadowOrigin.Z), Mathf.Round(shadowOrigin.W)); DxVector4 roundOffset; DxVector4.Subtract(ref roundedOrigin, ref shadowOrigin, out roundOffset); DxVector4.Multiply(ref roundOffset, 2.0f / shadowMapSize, out roundOffset); roundOffset.Z = 0.0f; roundOffset.W = 0.0f; projectionMatrix.Row4 += roundOffset; // R[3] Matrix.Multiply(ref viewMatrix, ref projectionMatrix, out viewProjMatrix); // RenderDepthCPU SetupRenderDepthState(ref context, ref viewProjMatrix, cascadeIndex); world.RenderObjectProvider.Draw(ref context, ref camera, true); var texScaleBias = new Matrix { Row1 = new SharpDX.Vector4(0.5f, 0.0f, 0.0f, 0.0f), Row2 = new SharpDX.Vector4(0.0f, -0.5f, 0.0f, 0.0f), Row3 = new SharpDX.Vector4(0.0f, 0.0f, 1.0f, 0.0f), Row4 = new SharpDX.Vector4(0.5f, 0.5f, 0.0f, 1.0f) }; Matrix.Multiply(ref viewProjMatrix, ref texScaleBias, out viewProjMatrix); var clipNear = camera.ClipNear; var clipFar = camera.ClipFar; var clipDist = clipFar - clipNear; ReceiverConstants.Data.CascadeSplits[cascadeIndex] = clipNear + splitDist * clipDist; Matrix invCascadeMatrix; Matrix.Invert(ref viewProjMatrix, out invCascadeMatrix); var zero = DxVector3.Zero; DxVector3 cascadeCorner; DxVector3.TransformCoordinate(ref zero, ref invCascadeMatrix, out cascadeCorner); DxVector3.TransformCoordinate(ref cascadeCorner, ref ReceiverConstants.Data.ShadowMatrix, out cascadeCorner); var one = DxVector3.One; DxVector3 otherCorner; DxVector3.TransformCoordinate(ref one, ref invCascadeMatrix, out otherCorner); DxVector3.TransformCoordinate(ref otherCorner, ref ReceiverConstants.Data.ShadowMatrix, out otherCorner); var cascadeScale = DxVector3.One / (otherCorner - cascadeCorner); ReceiverConstants.Data.CascadeOffsets[cascadeIndex] = new DxVector4(-cascadeCorner, 0.0f); ReceiverConstants.Data.CascadeScales[cascadeIndex] = new DxVector4(cascadeScale, 1.0f); if (RenderSettings.UseFilterableShadows) ConvertToVsm(ref context, cascadeIndex, ref ReceiverConstants.Data.CascadeSplits[cascadeIndex], ref ReceiverConstants.Data.CascadeScales[0]); } PixHelper.EndEvent(); } } PixHelper.EndEvent(); DataStream stream; context.MapSubresource(ReceiverConstants.Buffer, MapMode.WriteDiscard, MapFlags.None, out stream); stream.Write(ReceiverConstants.Data.ShadowMatrix); stream.WriteRange(ReceiverConstants.Data.CascadeSplits, 0, 4); stream.WriteRange(ReceiverConstants.Data.CascadeOffsets, 0, 4); stream.WriteRange(ReceiverConstants.Data.CascadeScales, 0, 4); stream.Write(ReceiverConstants.Data.ShadowDepthBias); stream.Write(ReceiverConstants.Data.ShadowOffsetScale); stream.Write(ReceiverConstants.Data.VisualizeCascades); context.UnmapSubresource(ReceiverConstants.Buffer, 0); //ReceiverConstants.Update(ref context); }