From 4d3c5fc31688d2e7da6d662b09c3e48af1a30cea Mon Sep 17 00:00:00 2001 From: cosmonaut Date: Tue, 8 Dec 2020 02:49:18 -0800 Subject: [PATCH] more shadow decoupling + change world instance to position instance --- EffectInterfaces/IHasTranslation.cs | 9 ++ EffectInterfaces/IHasWorldMatrix.cs | 2 +- Effects/FXB/DeferredPBR_GBufferEffect.fxb | 4 +- Effects/FXB/SimpleDepthEffect.fxb | 4 +- Effects/FXB/SimpleDepthEffectInstanced.fxb | 3 + Effects/HLSL/DeferredPBR_GBufferEffect.fx | 21 +-- Effects/HLSL/SimpleDepthEffect.fx | 12 +- Effects/HLSL/SimpleDepthEffectInstanced.fx | 45 ++++++ Effects/SimpleDepthEffect.cs | 28 ---- Effects/SimpleDepthEffectInstanced.cs | 56 +++++++ Geometry/Interfaces/IHasVertexPositions.cs | 9 ++ Geometry/MeshPart.cs | 2 +- Kav.Core.csproj | 3 + Kav.Framework.csproj | 3 + Renderer.cs | 151 ++++++++++++++---- Resources.cs | 13 ++ VertexDeclarations.cs | 7 +- ...nceVertex.cs => PositionInstanceVertex.cs} | 12 +- 18 files changed, 296 insertions(+), 88 deletions(-) create mode 100644 EffectInterfaces/IHasTranslation.cs create mode 100644 Effects/FXB/SimpleDepthEffectInstanced.fxb create mode 100644 Effects/HLSL/SimpleDepthEffectInstanced.fx create mode 100644 Effects/SimpleDepthEffectInstanced.cs create mode 100644 Geometry/Interfaces/IHasVertexPositions.cs rename Vertices/{GBufferInstanceVertex.cs => PositionInstanceVertex.cs} (57%) diff --git a/EffectInterfaces/IHasTranslation.cs b/EffectInterfaces/IHasTranslation.cs new file mode 100644 index 0000000..969cfdb --- /dev/null +++ b/EffectInterfaces/IHasTranslation.cs @@ -0,0 +1,9 @@ +using Microsoft.Xna.Framework; + +namespace Kav +{ + public interface IHasTranslation + { + Vector3 Translation { get; set; } + } +} diff --git a/EffectInterfaces/IHasWorldMatrix.cs b/EffectInterfaces/IHasWorldMatrix.cs index 7f87b42..e7d2bae 100644 --- a/EffectInterfaces/IHasWorldMatrix.cs +++ b/EffectInterfaces/IHasWorldMatrix.cs @@ -1,4 +1,4 @@ -using Microsoft.Xna.Framework; +using Microsoft.Xna.Framework; namespace Kav { diff --git a/Effects/FXB/DeferredPBR_GBufferEffect.fxb b/Effects/FXB/DeferredPBR_GBufferEffect.fxb index 4ad7c73..2012ecb 100644 --- a/Effects/FXB/DeferredPBR_GBufferEffect.fxb +++ b/Effects/FXB/DeferredPBR_GBufferEffect.fxb @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:7c70594ec60f6f791f6d836d0ca1736284e8158f11ce439a18ad120fc440ad10 -size 9148 +oid sha256:240a1d0911f6bba0da34d5a158c5868e52f6612dc055cdc42d8cef2a5f3febaa +size 8908 diff --git a/Effects/FXB/SimpleDepthEffect.fxb b/Effects/FXB/SimpleDepthEffect.fxb index 8281157..fee70bc 100644 --- a/Effects/FXB/SimpleDepthEffect.fxb +++ b/Effects/FXB/SimpleDepthEffect.fxb @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:e0984ae92245afe3e2bda5fab0135293b5121c3ee7b5f146e7d4ddd1684ee74b -size 848 +oid sha256:41083a1789c08363517ab1279e80e985e8fcfc3439411d13df4a5ea4667491e9 +size 1340 diff --git a/Effects/FXB/SimpleDepthEffectInstanced.fxb b/Effects/FXB/SimpleDepthEffectInstanced.fxb new file mode 100644 index 0000000..9c19b29 --- /dev/null +++ b/Effects/FXB/SimpleDepthEffectInstanced.fxb @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:6f5eb937af7db2fd9a149ae06981af2a33043abaa5fbb72c8382b4b72097f98f +size 1008 diff --git a/Effects/HLSL/DeferredPBR_GBufferEffect.fx b/Effects/HLSL/DeferredPBR_GBufferEffect.fx index 13c48c2..52f911c 100644 --- a/Effects/HLSL/DeferredPBR_GBufferEffect.fx +++ b/Effects/HLSL/DeferredPBR_GBufferEffect.fx @@ -24,11 +24,6 @@ struct VertexInput float2 TexCoord : TEXCOORD; }; -struct InstanceInput -{ - float4x4 World : TEXCOORD2; -}; - struct PixelInput { float4 Position : SV_POSITION; @@ -61,15 +56,23 @@ PixelInput main_vs(VertexInput input) return output; } -PixelInput instanced_vs(VertexInput input, InstanceInput instanceInput) +PixelInput instanced_vs(VertexInput input, float3 Translation : TEXCOORD2) { PixelInput output; - output.PositionWorld = mul(input.Position, instanceInput.World).xyz; - output.NormalWorld = normalize(mul(input.Normal, instanceInput.World)); + float4x4 world = float4x4( + float4(1, 0, 0, 0), + float4(0, 1, 0, 0), + float4(0, 0, 1, 0), + float4(Translation.x, Translation.y, Translation.z, 1) + ); + + float4x4 worldViewProjection = mul(world, ViewProjection); + + output.PositionWorld = mul(input.Position, world); + output.NormalWorld = mul(input.Normal, world); output.TexCoord = input.TexCoord; - float4x4 worldViewProjection = mul(instanceInput.World, ViewProjection); output.Position = mul(input.Position, worldViewProjection); return output; diff --git a/Effects/HLSL/SimpleDepthEffect.fx b/Effects/HLSL/SimpleDepthEffect.fx index f813bd7..a4c3bbc 100644 --- a/Effects/HLSL/SimpleDepthEffect.fx +++ b/Effects/HLSL/SimpleDepthEffect.fx @@ -2,10 +2,11 @@ BEGIN_CONSTANTS - float4x4 ModelViewProjection _vs(c0) _cb(c0); - MATRIX_CONSTANTS + float4x4 World _vs(c0) _cb(c0); + float4x4 ViewProjection _vs(c4) _cb(c4); + END_CONSTANTS struct VertexShaderInput @@ -15,15 +16,16 @@ struct VertexShaderInput struct VertexShaderOutput { - float4 Position : SV_Position; - float Depth : TEXCOORD0; + float4 Position : SV_POSITION; + float Depth : DEPTH; }; VertexShaderOutput main_vs(VertexShaderInput input) { VertexShaderOutput output; - output.Position = mul(input.Position, ModelViewProjection); + float4x4 worldViewProjection = mul(World, ViewProjection); + output.Position = mul(input.Position, worldViewProjection); output.Depth = output.Position.z / output.Position.w; return output; diff --git a/Effects/HLSL/SimpleDepthEffectInstanced.fx b/Effects/HLSL/SimpleDepthEffectInstanced.fx new file mode 100644 index 0000000..f35471e --- /dev/null +++ b/Effects/HLSL/SimpleDepthEffectInstanced.fx @@ -0,0 +1,45 @@ +float4x4 ViewProjection; + +struct VertexShaderInput +{ + float4 Position : POSITION; +}; + +struct VertexShaderOutput +{ + float4 Position : POSITION0; + float4 ProjectedPosition : TEXCOORD0; +}; + +VertexShaderOutput instanced_vs(VertexShaderInput input, float3 Translation : TEXCOORD2) +{ + VertexShaderOutput output; + + float4x4 world = float4x4( + float4(1, 0, 0, 0), + float4(0, 1, 0, 0), + float4(0, 0, 1, 0), + float4(Translation.x, Translation.y, Translation.z, 1) + ); + + float4x4 worldViewProjection = mul(world, ViewProjection); + + output.Position = mul(input.Position, worldViewProjection); + output.ProjectedPosition = output.Position; + + return output; +} + +float4 main_ps(VertexShaderOutput input) : COLOR0 +{ + return float4(input.ProjectedPosition.z / input.ProjectedPosition.w, 0.0, 0.0, 0.0); +} + +Technique SimpleDepth +{ + Pass + { + VertexShader = compile vs_3_0 instanced_vs(); + PixelShader = compile ps_3_0 main_ps(); + } +} diff --git a/Effects/SimpleDepthEffect.cs b/Effects/SimpleDepthEffect.cs index 200d743..2020c11 100644 --- a/Effects/SimpleDepthEffect.cs +++ b/Effects/SimpleDepthEffect.cs @@ -7,12 +7,10 @@ namespace Kav { EffectParameter worldParam; EffectParameter viewProjectionParam; - EffectParameter vertexShaderIndexParam; Matrix world; Matrix view; Matrix projection; - bool hardwareInstancingEnabled = false; EffectDirtyFlags dirtyFlags = EffectDirtyFlags.All; @@ -46,19 +44,6 @@ namespace Kav } } - public bool HardwareInstancingEnabled - { - get { return hardwareInstancingEnabled; } - set - { - if (value != hardwareInstancingEnabled) - { - hardwareInstancingEnabled = value; - dirtyFlags |= EffectDirtyFlags.VertexShaderIndex; - } - } - } - public SimpleDepthEffect(GraphicsDevice graphicsDevice) : base(graphicsDevice, Resources.SimpleDepthEffect) { CacheEffectParameters(); @@ -80,25 +65,12 @@ namespace Kav dirtyFlags &= ~EffectDirtyFlags.ViewProj; } - - if ((dirtyFlags & EffectDirtyFlags.VertexShaderIndex) != 0) - { - int vertexShaderIndex = 0; - - if (hardwareInstancingEnabled) - { - vertexShaderIndex = 1; - } - - vertexShaderIndexParam.SetValue(vertexShaderIndex); - } } private void CacheEffectParameters() { worldParam = Parameters["World"]; viewProjectionParam = Parameters["ViewProjection"]; - vertexShaderIndexParam = Parameters["VertexShaderIndex"]; } } } diff --git a/Effects/SimpleDepthEffectInstanced.cs b/Effects/SimpleDepthEffectInstanced.cs new file mode 100644 index 0000000..52fc597 --- /dev/null +++ b/Effects/SimpleDepthEffectInstanced.cs @@ -0,0 +1,56 @@ +using Microsoft.Xna.Framework; +using Microsoft.Xna.Framework.Graphics; + +namespace Kav +{ + public class SimpleDepthEffectInstanced : Effect + { + EffectParameter viewProjectionParam; + + Matrix view; + Matrix projection; + + EffectDirtyFlags dirtyFlags = EffectDirtyFlags.All; + + public Matrix View + { + get { return view; } + set + { + view = value; + dirtyFlags |= EffectDirtyFlags.ViewProj; + } + } + + public Matrix Projection + { + get { return projection; } + set + { + projection = value; + dirtyFlags |= EffectDirtyFlags.ViewProj; + } + } + + public SimpleDepthEffectInstanced(GraphicsDevice graphicsDevice) : base(graphicsDevice, Resources.SimpleDepthEffectInstanced) + { + CacheEffectParameters(); + } + + protected override void OnApply() + { + if ((dirtyFlags & EffectDirtyFlags.ViewProj) != 0) + { + Matrix.Multiply(ref view, ref projection, out Matrix viewProjection); + viewProjectionParam.SetValue(viewProjection); + + dirtyFlags &= ~EffectDirtyFlags.ViewProj; + } + } + + private void CacheEffectParameters() + { + viewProjectionParam = Parameters["ViewProjection"]; + } + } +} diff --git a/Geometry/Interfaces/IHasVertexPositions.cs b/Geometry/Interfaces/IHasVertexPositions.cs new file mode 100644 index 0000000..e39483b --- /dev/null +++ b/Geometry/Interfaces/IHasVertexPositions.cs @@ -0,0 +1,9 @@ +using Microsoft.Xna.Framework; + +namespace Kav +{ + public interface IHasVertexPositions + { + Vector3[] Positions { get; } + } +} diff --git a/Geometry/MeshPart.cs b/Geometry/MeshPart.cs index c8d033b..80f52de 100644 --- a/Geometry/MeshPart.cs +++ b/Geometry/MeshPart.cs @@ -3,7 +3,7 @@ using Microsoft.Xna.Framework.Graphics; namespace Kav { - public class MeshPart : IIndexDrawable, IGBufferDrawable, ICullable + public class MeshPart : IIndexDrawable, IGBufferDrawable, ICullable, IHasVertexPositions { public IndexBuffer IndexBuffer { get; } public VertexBuffer VertexBuffer { get; } diff --git a/Kav.Core.csproj b/Kav.Core.csproj index 9cb9564..6077186 100644 --- a/Kav.Core.csproj +++ b/Kav.Core.csproj @@ -43,6 +43,9 @@ Kav.Resources.SimpleDepthEffect.fxb + + Kav.Resources.SimpleDepthEffectInstanced.fxb + Kav.Resources.LinearDepthEffect.fxb diff --git a/Kav.Framework.csproj b/Kav.Framework.csproj index d5c6c57..60a7849 100644 --- a/Kav.Framework.csproj +++ b/Kav.Framework.csproj @@ -43,6 +43,9 @@ Kav.Resources.SimpleDepthEffect.fxb + + Kav.Resources.SimpleDepthEffectInstanced.fxb + Kav.Resources.LinearDepthEffect.fxb diff --git a/Renderer.cs b/Renderer.cs index fb153dc..a3cb74a 100644 --- a/Renderer.cs +++ b/Renderer.cs @@ -9,7 +9,6 @@ namespace Kav public class Renderer { private const int MAX_INSTANCE_VERTEX_COUNT = 1000000; - private const int MAX_SHADOW_CASCADES = 4; private GraphicsDevice GraphicsDevice { get; } @@ -23,6 +22,7 @@ namespace Kav private DeferredPBR_DirectionalLightEffect DeferredDirectionalLightEffect { get; } private Deferred_ToonEffect Deferred_ToonEffect { get; } private SimpleDepthEffect SimpleDepthEffect { get; } + private SimpleDepthEffectInstanced SimpleDepthEffectInstanced { get; } private LinearDepthEffect LinearDepthEffect { get; } private Effect ToneMapEffect { get; } private SkyboxEffect SkyboxEffect { get; } @@ -30,10 +30,8 @@ namespace Kav private Kav.Model UnitCube { get; } - private SpriteBatch SpriteBatch { get; } - - private DynamicVertexBuffer GBufferInstanceVertexBuffer { get; } - private readonly GBufferInstanceVertex[] GBufferInstanceVertices = new GBufferInstanceVertex[MAX_INSTANCE_VERTEX_COUNT]; + private DynamicVertexBuffer PositionInstanceVertexBuffer { get; } + private readonly PositionInstanceVertex[] GBufferInstanceVertices = new PositionInstanceVertex[MAX_INSTANCE_VERTEX_COUNT]; public Renderer( GraphicsDevice graphicsDevice @@ -41,6 +39,7 @@ namespace Kav GraphicsDevice = graphicsDevice; SimpleDepthEffect = new SimpleDepthEffect(GraphicsDevice); + SimpleDepthEffectInstanced = new SimpleDepthEffectInstanced(GraphicsDevice); LinearDepthEffect = new LinearDepthEffect(GraphicsDevice); DeferredPBREffect = new DeferredPBREffect(GraphicsDevice); @@ -65,11 +64,9 @@ namespace Kav Smuggler.Importer.ImportGLB(GraphicsDevice, new MemoryStream(Resources.UnitCubeModel)) ); - SpriteBatch = new SpriteBatch(graphicsDevice); - - GBufferInstanceVertexBuffer = new DynamicVertexBuffer( + PositionInstanceVertexBuffer = new DynamicVertexBuffer( GraphicsDevice, - VertexDeclarations.GBufferInstanceDeclaration, + VertexDeclarations.PositionInstanceDeclaration, MAX_INSTANCE_VERTEX_COUNT, BufferUsage.WriteOnly ); @@ -203,13 +200,11 @@ namespace Kav // Effect must be pre-configured!! public static void CullAndRenderIndexed( GraphicsDevice graphicsDevice, - PerspectiveCamera camera, + BoundingFrustum boundingFrustum, IEnumerable<(T, Matrix)> drawableTransformPairs, U effect ) where T : IIndexDrawable, ICullable where U : Effect, IHasWorldMatrix { - var boundingFrustum = new BoundingFrustum(camera.View * camera.Projection); - foreach (var (drawable, transform) in FrustumCull(boundingFrustum, drawableTransformPairs)) { effect.World = transform; @@ -253,14 +248,14 @@ namespace Kav IEnumerable transforms, V[] vertexData, DynamicVertexBuffer dynamicVertexBuffer - ) where T : ICullable, IIndexDrawable where V : struct, IVertexType, IHasWorldMatrix + ) where T : ICullable, IIndexDrawable where V : struct, IVertexType, IHasTranslation { var boundingFrustum = new BoundingFrustum(camera.View * camera.Projection); int numInstances = 0; foreach (var transform in FrustumCull(boundingFrustum, drawable, transforms)) { - vertexData[numInstances].World = transform; + vertexData[numInstances].Translation = transform.Translation; numInstances += 1; } @@ -331,7 +326,7 @@ namespace Kav CullAndRenderIndexed( GraphicsDevice, - camera, + new BoundingFrustum(camera.View * camera.Projection), drawableTransforms, SimpleDepthEffect ); @@ -396,7 +391,7 @@ namespace Kav drawable, transforms, GBufferInstanceVertices, - GBufferInstanceVertexBuffer + PositionInstanceVertexBuffer ); RenderInstanced( @@ -407,12 +402,15 @@ namespace Kav ); // re-render to get depth - GraphicsDevice.SetRenderTarget(depthBuffer); + GraphicsDevice.SetRenderTargets(depthBuffer); + + SimpleDepthEffectInstanced.View = camera.View; + SimpleDepthEffectInstanced.Projection = camera.Projection; RenderInstanced( GraphicsDevice, drawable, - Deferred_GBufferEffect, + SimpleDepthEffectInstanced, numInstances ); } @@ -498,17 +496,16 @@ namespace Kav RenderFullscreenEffect(DeferredPointLightEffect); } - public void RenderDirectionalLight( + public void RenderDirectionalLight( RenderTarget2D renderTarget, Texture2D gPosition, Texture2D gAlbedo, Texture2D gNormal, Texture2D gMetallicRoughness, + DirectionalShadowMapData shadowMapData, PerspectiveCamera camera, - IEnumerable<(T, Matrix)> modelTransforms, - DirectionalLight directionalLight, - DirectionalShadowMapData shadowMapData - ) where T : ICullable, IIndexDrawable { + DirectionalLight directionalLight + ) { GraphicsDevice.SetRenderTarget(renderTarget); GraphicsDevice.DepthStencilState = DepthStencilState.DepthRead; GraphicsDevice.BlendState = BlendState.Additive; @@ -522,21 +519,25 @@ namespace Kav DeferredDirectionalLightEffect.ShadowMapOne = shadowMapData.ShadowMaps[0]; DeferredDirectionalLightEffect.LightSpaceMatrixOne = shadowMapData.LightSpaceMatrixOne; + DeferredDirectionalLightEffect.CascadeFarPlanes[0] = shadowMapData.CascadeFarPlanes[0]; if (shadowMapData.NumShadowCascades > 1) { DeferredDirectionalLightEffect.ShadowMapTwo = shadowMapData.ShadowMaps[1]; DeferredDirectionalLightEffect.LightSpaceMatrixTwo = shadowMapData.LightSpaceMatrixTwo; + DeferredDirectionalLightEffect.CascadeFarPlanes[1] = shadowMapData.CascadeFarPlanes[1]; } if (shadowMapData.NumShadowCascades > 2) { DeferredDirectionalLightEffect.ShadowMapThree = shadowMapData.ShadowMaps[2]; DeferredDirectionalLightEffect.LightSpaceMatrixThree = shadowMapData.LightSpaceMatrixThree; + DeferredDirectionalLightEffect.CascadeFarPlanes[2] = shadowMapData.CascadeFarPlanes[2]; } if (shadowMapData.NumShadowCascades > 3) { DeferredDirectionalLightEffect.ShadowMapFour = shadowMapData.ShadowMaps[3]; DeferredDirectionalLightEffect.LightSpaceMatrixFour = shadowMapData.LightSpaceMatrixFour; + DeferredDirectionalLightEffect.CascadeFarPlanes[3] = shadowMapData.CascadeFarPlanes[3]; } DeferredDirectionalLightEffect.DirectionalLightDirection = directionalLight.Direction; @@ -549,7 +550,7 @@ namespace Kav RenderFullscreenEffect(DeferredDirectionalLightEffect); } - public void RenderDirectionalLightToon( + public void RenderDirectionalLightToon( RenderTarget2D renderTarget, Texture2D gPosition, Texture2D gAlbedo, @@ -557,10 +558,9 @@ namespace Kav Texture2D gMetallicRoughness, DirectionalShadowMapData shadowMapData, PerspectiveCamera camera, - IEnumerable<(T, Matrix)> modelTransforms, DirectionalLight directionalLight, bool ditheredShadows - ) where T : ICullable, IIndexDrawable { + ) { GraphicsDevice.SetRenderTarget(renderTarget); GraphicsDevice.DepthStencilState = DepthStencilState.DepthRead; GraphicsDevice.BlendState = BlendState.Additive; @@ -697,10 +697,15 @@ namespace Kav shadowMapData.LightSpaceMatrixFour = lightSpaceMatrix; } - CullAndRenderIndexed(GraphicsDevice, camera, drawableTransforms, SimpleDepthEffect); + CullAndRenderIndexed( + GraphicsDevice, + new BoundingFrustum(lightSpaceMatrix), + drawableTransforms, + SimpleDepthEffect + ); } - public void RenderPointShadowsIndexed( + public void RenderPointShadowMapIndexed( RenderTargetCube pointShadowCubeMap, PerspectiveCamera camera, IEnumerable<(T, Matrix)> modelTransforms, @@ -770,13 +775,101 @@ namespace Kav CullAndRenderIndexed( GraphicsDevice, - camera, + new BoundingFrustum(LinearDepthEffect.View * LinearDepthEffect.Projection), modelTransforms, LinearDepthEffect ); } } + public void RenderPointShadowMapInstanced( + RenderTargetCube pointShadowCubeMap, + PerspectiveCamera camera, + T drawable, + IEnumerable modelTransforms, + PointLight pointLight + ) where T : ICullable, IIndexDrawable + { + GraphicsDevice.DepthStencilState = DepthStencilState.Default; + GraphicsDevice.BlendState = BlendState.Opaque; + + foreach (CubeMapFace face in Enum.GetValues(typeof(CubeMapFace))) + { + GraphicsDevice.SetRenderTarget(pointShadowCubeMap, face); + + Vector3 targetDirection; + Vector3 targetUpDirection; + switch(face) + { + case CubeMapFace.PositiveX: + targetDirection = Vector3.Right; + targetUpDirection = Vector3.Up; + break; + + case CubeMapFace.NegativeX: + targetDirection = Vector3.Left; + targetUpDirection = Vector3.Up; + break; + + case CubeMapFace.PositiveY: + targetDirection = Vector3.Up; + targetUpDirection = Vector3.Forward; + break; + + case CubeMapFace.NegativeY: + targetDirection = Vector3.Down; + targetUpDirection = Vector3.Backward; + break; + + case CubeMapFace.PositiveZ: + targetDirection = Vector3.Backward; + targetUpDirection = Vector3.Up; + break; + + case CubeMapFace.NegativeZ: + targetDirection = Vector3.Forward; + targetUpDirection = Vector3.Up; + break; + + default: + targetDirection = Vector3.Right; + targetUpDirection = Vector3.Up; + break; + } + + LinearDepthEffect.View = Matrix.CreateLookAt( + pointLight.Position, + pointLight.Position + targetDirection, + targetUpDirection + ); + LinearDepthEffect.Projection = Matrix.CreatePerspectiveFieldOfView( + MathHelper.PiOver2, + 1, + 0.1f, + 25f // FIXME: magic value + ); + LinearDepthEffect.FarPlane = 25f; + + LinearDepthEffect.LightPosition = pointLight.Position; + + // TODO: set up instancing + // var numInstances = FillAndSetBuffersForInstancing( + // GraphicsDevice, + // camera, + // drawable, + // transforms, + // VertexPos + // ); + + // RenderInstanced( + // GraphicsDevice, + // camera, + // modelTransforms, + // LinearDepthEffect + // ); + } + } + private static IEnumerable<(T, Matrix)> FrustumCull( BoundingFrustum boundingFrustum, IEnumerable<(T, Matrix)> cullableTransforms diff --git a/Resources.cs b/Resources.cs index 44c28f7..2924998 100644 --- a/Resources.cs +++ b/Resources.cs @@ -111,6 +111,18 @@ namespace Kav } } + public static byte[] SimpleDepthEffectInstanced + { + get + { + if (simpleDepthEffectInstanced == null) + { + simpleDepthEffectInstanced = GetResource("SimpleDepthEffectInstanced.fxb"); + } + return simpleDepthEffectInstanced; + } + } + public static byte[] LinearDepthEffect { get @@ -168,6 +180,7 @@ namespace Kav private static byte[] deferredPBREffect; private static byte[] pbrEffect; private static byte[] simpleDepthEffect; + private static byte[] simpleDepthEffectInstanced; private static byte[] linearDepthEffect; private static byte[] skyboxEffect; private static byte[] diffuseLitSpriteEffect; diff --git a/VertexDeclarations.cs b/VertexDeclarations.cs index d77327b..f8b073f 100644 --- a/VertexDeclarations.cs +++ b/VertexDeclarations.cs @@ -4,12 +4,9 @@ namespace Kav { public static class VertexDeclarations { - public static VertexDeclaration GBufferInstanceDeclaration = new VertexDeclaration + public static VertexDeclaration PositionInstanceDeclaration = new VertexDeclaration ( - new VertexElement(0, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 2), - new VertexElement(16, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 3), - new VertexElement(32, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 4), - new VertexElement(48, VertexElementFormat.Vector4, VertexElementUsage.TextureCoordinate, 5) + new VertexElement(0, VertexElementFormat.Vector3, VertexElementUsage.TextureCoordinate, 2) ); } } diff --git a/Vertices/GBufferInstanceVertex.cs b/Vertices/PositionInstanceVertex.cs similarity index 57% rename from Vertices/GBufferInstanceVertex.cs rename to Vertices/PositionInstanceVertex.cs index 32ae321..f173cef 100644 --- a/Vertices/GBufferInstanceVertex.cs +++ b/Vertices/PositionInstanceVertex.cs @@ -5,24 +5,24 @@ using Microsoft.Xna.Framework.Graphics; namespace Kav { [StructLayout(LayoutKind.Sequential, Pack = 1)] - public struct GBufferInstanceVertex : IVertexType, IHasWorldMatrix + public struct PositionInstanceVertex : IVertexType, IHasTranslation { VertexDeclaration IVertexType.VertexDeclaration { get { - return VertexDeclarations.GBufferInstanceDeclaration; + return VertexDeclarations.PositionInstanceDeclaration; } } - public Matrix World { get; set; } + public Vector3 Translation { get; set; } public static readonly VertexDeclaration VertexDeclaration; - public GBufferInstanceVertex( - Matrix world + public PositionInstanceVertex( + Vector3 translation ) { - World = world; + Translation = translation; } } }