From 4cd0bff91d83b59e98fddf2376b5b6fc9fe8b83b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Simon=20L=C3=BCbe=C3=9F?= Date: Wed, 18 May 2022 14:12:26 +0200 Subject: [PATCH] Fixed editorcamera stuttering, Added editor icons --- .../content/Textures/EditorIcons.dds | Bin 0 -> 32896 bytes .../content/Textures/EditorIcons.psd | Bin 0 -> 9434 bytes GlitchyEditor/src/EditorLayer.bf | 121 ++++++++++----- GlitchyEngine/src/Core/RefCounter.bf | 5 + GlitchyEngine/src/Math/MathHelper.bf | 6 + GlitchyEngine/src/Renderer/DebugRenderer.bf | 140 ++++++++++++++++++ GlitchyEngine/src/Renderer/Renderer.bf | 29 +++- GlitchyEngine/src/Renderer/Renderer2D.bf | 2 +- GlitchyEngine/src/World/EditorCamera.bf | 7 +- GlitchyEngine/src/World/Scene.bf | 14 +- 10 files changed, 273 insertions(+), 51 deletions(-) create mode 100644 GlitchyEditor/content/Textures/EditorIcons.dds create mode 100644 GlitchyEditor/content/Textures/EditorIcons.psd diff --git a/GlitchyEditor/content/Textures/EditorIcons.dds b/GlitchyEditor/content/Textures/EditorIcons.dds new file mode 100644 index 0000000000000000000000000000000000000000..25dc22d60d41b57f642e8c47ce8c0f369576efda GIT binary patch literal 32896 zcmeHF+ie^{47<32xCECH1MVR0A@B{QgCt`jcw;&nq?V-@So7Ht_lN+r!Q6V&(?;+w(bd z_C0I;2Kc-4x!%$3VCDw+yYo47_C0I;2Kc-4x!zIS0eiIxY*$17Y^=HiJ z%piAT)z(alC*LfMk#Eui)!nnMs*k?U?%LkYIQXt{Fgq53JRt!+La9HIXm1WgWpu zo~$Dph@E+tp1GbmUz^1~I--Ht*>~xi>)9T79?zF2zjdE- z2G%?a`|?g0dB@tT!MK$tdZ+trKeIh(^CCUkPXw=FXYbgWC;eGCe3Lw_M!a>Gd<)n0 zCg(+JIX}XaSgEl~P5wMyWR6Jf)%M^zFcI$(D`(4oq?Q_2sU!I;>`r+tpW2(|UBg*D zO=I_-l_&GIQ(mus%X5c@rN8pcn=Oi4nMs>{F=J9GQn|Yo5efIPI;%)$}U8ikAwv;&~J|l1E~x_Ik?ly!ugG)=!of^*0kw znY{BbfA;R3Hwu^ajl5C*cGboF+575zS>MQ8on!WV%wM_B_RjMvo{`I%|I3N_EB949 zt9VB4stl{DZ2zn0Rd#j6 zot5cmex*Ol`z~`TyRx{W^I5YiZ=-$hreE3B8Fy6Hv$>V`QJ#0zt?bIf?au9)S;2Js z-CeJ;D=)We2i|!VT$k6Y=u~#aT*}I|b!K;BY4V%b1LKd*tjC>rl+EksXb;}Loa5yX zPV%%ms}0PadJGJ~H)_d19z1(hGrx#7@YQ3ZV zYB`RuR=-Qfnh|~L@}%ipt!M2HvshT|4f%A}aFHHsMmQRlb>ykxte)gvwYKu{8)xIY z=VXpNJv<8|wWzkRo;TFXXlfc)>3Md7({2U78coMqgLBNAh{GT5d1bgF}4}$BRL2x>vZG-cCJlwg?XMMYta9&id$W=euXu z8H~)F;h%A&KGkRV%)6XXP()UIJm=|yrCELy7G?Ru6oBEUNy(UVY=(0lu{@Jx@eiCi$Yokl4Tb)VVD@^2h3z!nwRJU zv~Q4i$bKlHi-8WLo@6riwXd(Qf5yM+cciN;UE2d)&7#N`9UUF%N=HXJ(sz&VZ*DzC z3Ff!P>|3T^aRb+k2*2Im{Qie)EnT{WpP85VWVzI>eWL63q((aW7+a{IihUg7bNqI}IVoF} zUy8Q-2emy`%WunM!0m_C+V<1K>cM_xcjHlY=h-13ZFisVSJ~!MrrT7$iW;`@l+&u> zfYYmBmlJx#(hi}}U7{^++v zj0YTTkE7R^msqyXI{fD*%o)ZvWHPFnw*ES{k5WOZDzh5v3iV+)wT zzt8hqd;uQ>R1i=B@sq<`SA+@-(lqo#n8%m-`}Ia)&z6a!S3Q@$(ZhtOaH7tM8;8W0 zLt?=pQQMR$BF0RK;ZkBk$BmE>-z7wdBaHb;F=ol+BAF2XO(-$>YRU3jwnsOLFXCB+*TlGn0)G(lIgg5z+OObVl8eIL8sGoSm;O zc}%TsY2GqDnBJskJB}IE*TZOLv@{wM`}r#xRyp5uVU;tFUggIk3%(qDIh@#6e_~4@ zNQN$lh^ff(G@YES2c`g#v&al-vr7rdtXLnvhNBwLJu#;h~rjGvESYVt> zB~E2yf^mk$1gSZk+FrnAk&X@~)LJ5ktqhx4j27vLp+sV$r5cGwNGy@M6p&uTsD+6w zHgXM8FUI&j*S71$8qacRgE7aGeD+O#Wt`*|iWr0ZJGWwsvB*TkIg5nrlh!VOR+HcJ?fjA1aK%1eUY6w#uKUC!7>kR4y4hBk^h zr&LhivQ)6+au0$f?I^DboM_sH$X0POx0bGToXkAZGOh|1)$XW1rGkG|VHfsu%lkWapjSq| zqwLNe=v9+(tOpD;iSv|!UTxo_dU_{_4<75?vFwe;OJ5-P>zKR8u5$3#;IF}7C8iPX gS3xP^epMP-g!?rqAl7id20U#3%MW(); - - Vector3 position = transformCmp.Position; - - if (Input.IsKeyPressed(Key.A)) - { - position.X -= gameTime.DeltaTime; - } - if (Input.IsKeyPressed(Key.D)) - { - position.X += gameTime.DeltaTime; - } - if (Input.IsKeyPressed(Key.W)) - { - position.Y += gameTime.DeltaTime; - } - if (Input.IsKeyPressed(Key.S)) - { - position.Y -= gameTime.DeltaTime; - } - - transformCmp.Position = position; - } - - protected override void OnDestroy() - { - Log.EngineLogger.Trace("Cam controller destroyed!"); - } - } + Texture2D _editorIcons ~ _.ReleaseRef(); + SubTexture2D _iconDirectionalLight ~ _.ReleaseRef(); + SubTexture2D _iconCamera ~ _.ReleaseRef(); public this() : base("Example") { @@ -125,6 +91,11 @@ namespace GlitchyEditor _viewportTarget = new RenderTarget2D(RenderTarget2DDescription(.R8G8B8A8_UNorm, 100, 100)); _viewportTarget.SamplerState = SamplerStateManager.LinearClamp; + + _editorIcons = new Texture2D("Textures/EditorIcons.dds"); + _editorIcons.SamplerState = SamplerStateManager.AnisotropicClamp; + _iconDirectionalLight = .CreateFromGrid(_editorIcons, .(0, 0), .(64, 64)); + _iconCamera = .CreateFromGrid(_editorIcons, .(1, 0), .(64, 64)); } private void InitEditor() @@ -151,7 +122,7 @@ namespace GlitchyEditor RenderCommand.SetBlendState(_alphaBlendState); RenderCommand.SetDepthStencilState(_depthStencilState); - _scene.UpdateEditor(gameTime, _camera, _viewportTarget); + _scene.UpdateEditor(gameTime, _camera, _viewportTarget, scope => DebugDraw3D, scope => DebugDraw2D); RenderCommand.UnbindRenderTargets(); RenderCommand.SetRenderTarget(null, 0, true); @@ -160,6 +131,63 @@ namespace GlitchyEditor RenderCommand.SetViewport(_context.SwapChain.BackbufferViewport); } + private void DebugDraw3D() + { + /*for (var (entity, transform, camera) in _scene.[Friend]_ecsWorld.Enumerate()) + { + if (_editor.EntityHierarchyWindow.SelectedEntities.Contains(.(entity, _scene))) + { + DebugRenderer.DrawViewFrustum(transform.WorldTransform, camera.Camera.Projection); + } + }*/ + } + + private void DebugDraw2D() + { + RenderCommand.SetBlendState(_alphaBlendState); + + Matrix billboard = _camera.View.Invert(); + billboard.Translation = .Zero; + + Matrix Billboard(Matrix transform) + { + Vector3 worldPos = transform.Translation; + + return Matrix.Translation(worldPos) * billboard; + } + + for (var (entity, transform, camera) in _scene.[Friend]_ecsWorld.Enumerate()) + { + if (_editor.EntityHierarchyWindow.SelectedEntities.Contains(.(entity, _scene))) + { + DebugRenderer.DrawViewFrustum(transform.WorldTransform, camera.Camera.Projection, _camera.Projection * _camera.View); + } + + Matrix world = Billboard(transform.WorldTransform); + + Renderer2D.DrawQuad(world, _iconCamera); + } + + for (var (entity, transform, light) in _scene.[Friend]_ecsWorld.Enumerate()) + { + if (_editor.EntityHierarchyWindow.SelectedEntities.Contains(.(entity, _scene))) + { + Renderer.DrawRay(.Zero, .(0, 0, 20), ColorRGBA(light.SceneLight.Color, 1.0f), transform.WorldTransform); + + for (float angle = 0; angle < MathHelper.TwoPi; angle += MathHelper.TwoPi / 5.0f) + { + Vector2 pos = MathHelper.CirclePoint(angle, 0.5f); + + Renderer.DrawRay(.(pos, 0), .(pos, 20), .White, transform.WorldTransform); + } + } + + Matrix world = Billboard(transform.WorldTransform); + + Renderer2D.DrawQuad(world, _iconDirectionalLight, ColorRGBA(light.SceneLight.Color, 1.0f)); + } + } + public override void OnEvent(Event event) { EventDispatcher dispatcher = EventDispatcher(event); @@ -176,7 +204,7 @@ namespace GlitchyEditor private bool OnImGuiRender(ImGuiRenderEvent event) { - viewer.ViewTexture(_cameraTarget); + //viewer.ViewTexture(Renderer.[Friend]_gBuffer.Albedo); ImGui.Viewport* viewport = ImGui.GetMainViewport(); ImGui.DockSpaceOverViewport(viewport); @@ -217,6 +245,17 @@ namespace GlitchyEditor light.SceneLight.Color = .(1.0f, 0.95f, 0.8f); } + { + var cameraNtt = _scene.CreateEntity("My Camera"); + let transform = cameraNtt.GetComponent(); + transform.Position = .(5, 5, -5); + transform.RotationEuler = .(MathHelper.ToRadians(45), MathHelper.ToRadians(-45), 0); + + let camera = cameraNtt.AddComponent(); + camera.Primary = true; + camera.Camera.SetPerspective(MathHelper.ToRadians(45), 0.1f, 10.0f); + } + var fxLib = Application.Get().EffectLibrary; using (Effect myEffect = fxLib.Load("content/Shaders/myEffect.hlsl")) @@ -459,7 +498,7 @@ namespace GlitchyEditor bool control = Input.IsKeyPressed(Key.Control); bool shift = Input.IsKeyPressed(Key.Shift); - if (control) + if (!_camera.[Friend]BindMouse && control) { switch (e.KeyCode) { diff --git a/GlitchyEngine/src/Core/RefCounter.bf b/GlitchyEngine/src/Core/RefCounter.bf index 0d24eef..392644a 100644 --- a/GlitchyEngine/src/Core/RefCounter.bf +++ b/GlitchyEngine/src/Core/RefCounter.bf @@ -9,6 +9,11 @@ namespace GlitchyEngine.Core */ public class RefCounter : System.RefCounted, IDisposable { + protected ~this() + { + + } + public void Dispose() { ReleaseRef(); diff --git a/GlitchyEngine/src/Math/MathHelper.bf b/GlitchyEngine/src/Math/MathHelper.bf index 3a7ad5a..9b31db3 100644 --- a/GlitchyEngine/src/Math/MathHelper.bf +++ b/GlitchyEngine/src/Math/MathHelper.bf @@ -77,5 +77,11 @@ namespace GlitchyEngine.Math { return Math.Abs(value) < epsilon; } + + /// Returns the point that lies on the unit circle at the specified angle. + public static Vector2 CirclePoint(float angle, float radius = 1.0f) + { + return .(Math.Cos(angle), Math.Sin(angle)) * radius; + } } } diff --git a/GlitchyEngine/src/Renderer/DebugRenderer.bf b/GlitchyEngine/src/Renderer/DebugRenderer.bf index 32966cc..d7de1da 100644 --- a/GlitchyEngine/src/Renderer/DebugRenderer.bf +++ b/GlitchyEngine/src/Renderer/DebugRenderer.bf @@ -1,5 +1,6 @@ using GlitchyEngine.Math; using GlitchyEngine.World; +using System; namespace GlitchyEngine.Renderer { @@ -47,6 +48,145 @@ namespace GlitchyEngine.Renderer Renderer.DrawLine(.Zero, .Up, .Lime, transform); Renderer.DrawLine(.Zero, .Forward, .Blue, transform); } + + //static GeometryBinding _frustumGeometry; + //static VertexBuffer _frustumVertices; + + /** + * Draws the view frustum for the given camera transform and projection. + * @param worldTransform The cameras transform matrix. + * @param projection The cameras projection matrix. + * @param observerVP The view projection of the rendering camera. + * @param color The color of the frustum. + */ + public static void DrawViewFrustum(Matrix worldTransform, Matrix projection, Matrix observerVP, ColorRGBA color = .Red) + { + /*if (_frustumGeometry == null) + { + _frustumGeometry = new GeometryBinding(); + _frustumGeometry.SetPrimitiveTopology(.LineList); + + _frustumVertices = new VertexBuffer(typeof(Vector4), 8, .Dynamic, .Write); + _frustumGeometry.SetVertexBufferSlot(_frustumVertices, 0); + + using (IndexBuffer indexBuffer = new IndexBuffer(24, .Immutable)) + { + uint16[24] indices = .( + 0, 1, + 1, 2, + 2, 3, + 3, 0, + + 4, 5, + 5, 6, + 6, 7, + 7, 4, + + 0, 4, + 1, 5, + 2, 6, + 3, 7); + + indexBuffer.SetData(indices); + + _frustumGeometry.SetIndexBuffer(indexBuffer); + } + }*/ + + uint16[24] indices = .( + 0, 1, + 1, 2, + 2, 3, + 3, 0, + + 4, 5, + 5, 6, + 6, 7, + 7, 4, + + 0, 4, + 1, 5, + 2, 6, + 3, 7); + + Vector4[8] corners; + // Perspective + if(projection.V._43 != 0.0f) + { + // near plane for perspective projection, far plane if reversed + float d1 = -projection.V._34 / projection.V._33; + + float d2 = projection.V._34 / (1.0f - projection.V._33); + + float gOverS = projection.V._11; + float g = projection.V._22; + + //var corners = //(Vector4*)&_vbFrustum.Data; + + if(Math.Abs(d1) >= 10000) + { + d1 = 10.0f; + corners[0] = .( d1 / gOverS, d1 / g , d1, 0.0f); + corners[1] = .( corners[0].X, -corners[0].Y, d1, 0.0f); + corners[2] = .(-corners[0].X, -corners[0].Y, d1, 0.0f); + corners[3] = .(-corners[0].X, corners[0].Y, d1, 0.0f); + } + else + { + corners[0] = .( d1 / gOverS, d1 / g , d1, 1.0f); + corners[1] = .( corners[0].X, -corners[0].Y, d1, 1.0f); + corners[2] = .(-corners[0].X, -corners[0].Y, d1, 1.0f); + corners[3] = .(-corners[0].X, corners[0].Y, d1, 1.0f); + } + + if(Math.Abs(d2) >= 10000) + { + d2 = 10.0f; + + corners[4] = .( d2 / gOverS, d2 / g , d2, 0.0f); + corners[5] = .( corners[4].X, -corners[4].Y, d2, 0.0f); + corners[6] = .(-corners[4].X, -corners[4].Y, d2, 0.0f); + corners[7] = .(-corners[4].X, corners[4].Y, d2, 0.0f); + } + else + { + corners[4] = .( d2 / gOverS, d2 / g , d2, 1.0f); + corners[5] = .( corners[4].X, -corners[4].Y, d2, 1.0f); + corners[6] = .(-corners[4].X, -corners[4].Y, d2, 1.0f); + corners[7] = .(-corners[4].X, corners[4].Y, d2, 1.0f); + } + } + else + { + float l = -(projection.V._14 + 1.0f) / projection.V._11; + float r = (1.0f - projection.V._14) / projection.V._11; + + float t = -(projection.V._24 + 1.0f) / projection.V._22; + float b = (1.0f - projection.V._24) / projection.V._22; + + float n = -projection.V._34 / projection.V._33; + float f = (1 - projection.V._34) / projection.V._33; + + //var corners = (Vector4*)&_vbFrustum.Data; + corners[0] = .(r, t, n, 1.0f); + corners[1] = .(r, b, n, 1.0f); + corners[2] = .(l, b, n, 1.0f); + corners[3] = .(l, t, n, 1.0f); + + corners[4] = .(r, t, f, 1.0f); + corners[5] = .(r, b, f, 1.0f); + corners[6] = .(l, b, f, 1.0f); + corners[7] = .(l, t, f, 1.0f); + } + + for (int i = 0; i < indices.Count; i += 2) + { + uint16 index0 = indices[i]; + uint16 index1 = indices[i + 1]; + + Renderer.DrawLine(corners[index0], corners[index1], color, worldTransform, observerVP); + } + } public static void Render(EcsWorld world) { diff --git a/GlitchyEngine/src/Renderer/Renderer.bf b/GlitchyEngine/src/Renderer/Renderer.bf index e434028..ac5cdd9 100644 --- a/GlitchyEngine/src/Renderer/Renderer.bf +++ b/GlitchyEngine/src/Renderer/Renderer.bf @@ -527,7 +527,7 @@ namespace GlitchyEngine.Renderer * @param color The color of the line. * @param transform A transform matrix transforming the line. */ - public static void DrawLine(Vector3 start, Vector3 end, Color color, Matrix transform) + public static void DrawLine(Vector3 start, Vector3 end, ColorRGBA color, Matrix transform) { DrawLine(Vector4(start, 1.0f), Vector4(end, 1.0f), color, transform); } @@ -537,7 +537,7 @@ namespace GlitchyEngine.Renderer * @param direction The direction of the ray. * @param color The color of the ray. */ - public static void DrawRay(Vector3 start, Vector3 direction, Color color) + public static void DrawRay(Vector3 start, Vector3 direction, ColorRGBA color) { DrawLine(Vector4(start, 1.0f), Vector4(direction, 0.0f), color, .Identity); } @@ -548,7 +548,7 @@ namespace GlitchyEngine.Renderer * @param color The color of the ray. * @param transform A transform matrix transforming the ray. */ - public static void DrawRay(Vector3 start, Vector3 direction, Color color, Matrix transform) + public static void DrawRay(Vector3 start, Vector3 direction, ColorRGBA color, Matrix transform) { DrawLine(Vector4(start, 1.0f), Vector4(direction, 0.0f), color, transform); } @@ -559,7 +559,7 @@ namespace GlitchyEngine.Renderer * @param color The color of the line. * @param transform A transform matrix transforming the line. */ - public static void DrawLine(Vector4 start, Vector4 end, Color color, Matrix transform) + public static void DrawLine(Vector4 start, Vector4 end, ColorRGBA color, Matrix transform) { Debug.Profiler.ProfileRendererFunction!(); @@ -572,5 +572,26 @@ namespace GlitchyEngine.Renderer LineGeometry.Bind(); RenderCommand.DrawIndexed(LineGeometry); } + + /** @brief Draws a line. + * @param start The start point of the line. + * @param end The end point of the line. + * @param color The color of the line. + * @param transform A transform matrix transforming the line. + * @param viewProjection The observing cameras viewprojection + */ + public static void DrawLine(Vector4 start, Vector4 end, ColorRGBA color, Matrix transform, Matrix viewProjection) + { + Debug.Profiler.ProfileRendererFunction!(); + + LineVertices.SetData(Vector4[2](start, end), 0, .WriteDiscard); + LineEffect.Variables["ViewProjection"].SetData(viewProjection * transform); + LineEffect.Variables["Color"].SetData(color); + + LineEffect.Bind(_context); + + LineGeometry.Bind(); + RenderCommand.DrawIndexed(LineGeometry); + } } } diff --git a/GlitchyEngine/src/Renderer/Renderer2D.bf b/GlitchyEngine/src/Renderer/Renderer2D.bf index 837d7a0..1fccfc6 100644 --- a/GlitchyEngine/src/Renderer/Renderer2D.bf +++ b/GlitchyEngine/src/Renderer/Renderer2D.bf @@ -781,7 +781,7 @@ namespace GlitchyEngine.Renderer public static void DrawQuad(Matrix transform, SubTexture2D texture, ColorRGBA color = .White) { - DrawQuad(transform, texture.Texture, .White, texture.TexCoords); + DrawQuad(transform, texture.Texture, color, texture.TexCoords); } // Subtex + Texcoords diff --git a/GlitchyEngine/src/World/EditorCamera.bf b/GlitchyEngine/src/World/EditorCamera.bf index b6f7626..5386477 100644 --- a/GlitchyEngine/src/World/EditorCamera.bf +++ b/GlitchyEngine/src/World/EditorCamera.bf @@ -219,8 +219,8 @@ namespace GlitchyEngine.World float rotY = mouseDelta.X * _cameraRotationSpeedX; float rotX = mouseDelta.Y * _cameraRotationSpeedY; - - if (MouseCooldown == 0 && rotY != 0 && rotX != 0) + + if (MouseCooldown == 0) { Vector3 rotationEuler = RotationEuler + Vector3(rotX, rotY, 0); _rotation = Quaternion.FromEulerAngles(rotationEuler.Y, rotationEuler.X, rotationEuler.Z); @@ -298,7 +298,8 @@ namespace GlitchyEngine.World private void UpdateProjection() mut { - _projection = Matrix.InfinitePerspectiveProjection(_fovY, _aspectRatio, _nearPlane); + //_projection = Matrix.InfinitePerspectiveProjection(_fovY, _aspectRatio, _nearPlane); + _projection = Matrix.PerspectiveProjection(_fovY, _aspectRatio, _nearPlane, 10000); } public void OnViewportResize(uint32 sizeX, uint32 sizeY) mut diff --git a/GlitchyEngine/src/World/Scene.bf b/GlitchyEngine/src/World/Scene.bf index 960769c..f0136fd 100644 --- a/GlitchyEngine/src/World/Scene.bf +++ b/GlitchyEngine/src/World/Scene.bf @@ -111,7 +111,7 @@ namespace GlitchyEngine.World } } - public void UpdateEditor(GameTime gameTime, EditorCamera camera, RenderTarget2D viewportTarget) + public void UpdateEditor(GameTime gameTime, EditorCamera camera, RenderTarget2D viewportTarget, delegate void() DebugDraw3D, delegate void() DrawDebug2D) { Debug.Profiler.ProfileRendererFunction!(); @@ -132,16 +132,26 @@ namespace GlitchyEngine.World Renderer.Submit(light.SceneLight, transform.WorldTransform); } + DebugDraw3D(); + Renderer.EndScene(); + // TODO: alphablending + // Sprite renderer - Renderer2D.BeginScene(camera); + Renderer2D.BeginScene(camera, .BackToFront); for (var (entity, transform, sprite) in _ecsWorld.Enumerate()) { Renderer2D.DrawQuad(transform.WorldTransform, sprite.Sprite, sprite.Color); } + Renderer2D.EndScene(); + + Renderer2D.BeginScene(camera, .BackToFront); + + DrawDebug2D(); + Renderer2D.EndScene(); viewportTarget.ReleaseRef();