feat(ecs): wire ECS components into render scene and light pipeline - #656
Merged
Conversation
Add ECS::Systems::SyncECSToRenderScene — iterates all entities with both TransformComponent and MeshComponent each frame, interpolates position using the fixed-timestep alpha (PreviousPosition→Position), builds a Mat4f via ComposeTransformMatrix, and calls RenderScene::SetInstanceTransform for every registered instance. Called from Engine::MainThreadRun after the fixed-step loop and before PrepareScene, so the render thread always sees up-to-date transforms. Closes #642
Add ECS::Systems::SyncECSToLights — iterates all entities with LightComponent + TransformComponent each frame. Directional lights extract their forward direction from the rotation matrix (column 2, YXZ Euler order). Point lights use the entity's world position. Writes the assembled LightArrayUBO into RenderScene::PendingLights. AppRenderPipeline::RenderScene uploads PendingLights to the GPU LightBuffer each frame, replacing the hardcoded directional light. Closes #643
New scenes no longer open dark after the hardcoded sun was removed. EditorScene::Initialize spawns a directional light actor (intensity 3, white, -60 pitch / 30 yaw) so geometry is visible without the user manually adding a light first.
Add BuiltinMeshes.h/.cpp with CreateDirectionalLightMesh — generates a 12-gon disc + 8 diamond rays in the local XY plane (the source face) and a cross-section arrow along local +Z (light travel direction) for 360-degree visibility without a billboard shader. EditorScene::Initialize ingests the mesh via AssetManager and gives the default DirectionalLight actor a MeshComponent so the icon appears in the viewport and rotates with the entity transform.
…zmo jitter
SyncECSToRenderScene ran after g_app->Update (where the gizmo fires),
overwriting the exact gizmo-set transform with an interpolated position
between PreviousPosition and Position — causing visible jitter whenever
an object was moved.
Two fixes:
- TransformSyncSystem uses Position directly; alpha interpolation is
deferred until fixed-timestep physics systems are active.
- HierarchyViewUIComponent gizmo sets PreviousPosition = new_pos
(not old_pos) so there is no divergence for SnapshotTransforms
to amplify on subsequent frames.
Replace the one-off CreateDirectionalLightMesh free function with a
scalable table-driven system:
- BuiltinMeshID enum (editor icons + future primitive shapes)
- kBuiltinMeshTable: one entry per ID holds mesh UUID, material UUID,
BuildMesh fn, and BuildMaterial fn
- static_assert enforces table size == BuiltinMeshID::COUNT
- RegisterBuiltinMeshes ingests all materials then all meshes in one call
- BuiltinMeshUUIDParsed / BuiltinMaterialUUIDParsed for call-site lookup
UUID collision guarantee: third group '0000' is structurally impossible
for v4 random UUIDs (importers always emit third group starting with '4').
DirectionalLightIcon gains a yellow emissive material (ff000000-0001)
instead of borrowing whatever sits at slot 0.
EditorScene::Initialize simplified to two lines:
RegisterBuiltinMeshes(&LocalArena)
BuiltinMeshUUIDParsed(BuiltinMeshID::DirectionalLightIcon)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Three commits — ECS → rendering bridge for issues #642, #643, and a follow-on default light.
TransformComponent → RenderScene (#642)
ECS::Systems::SyncECSToRenderScene(Scene&, float alpha, RenderScene&)— iteratesTransformComponent+MeshComponent, interpolates position with fixed-timestep alpha, buildsMat4fviaComposeTransformMatrix, callsSetInstanceTransformEngine::MainThreadRunafter the fixed-step loop, beforePrepareSceneLightComponent → LightArrayUBO (#643)
ECS::Systems::SyncECSToLights(Scene&, RenderScene&)— iteratesLightComponent+TransformComponentLightArrayUBOintoRenderScene::PendingLightsAppRenderPipeline::RenderSceneuploadsPendingLightsto GPU — replaces the hardcoded directional lightDefault directional light
EditorScene::Initializespawns a defaultDirectionalLightactor (white, intensity 3, -60° pitch / 30° yaw) so new scenes open litTest plan
Closes #642
Closes #643