Core components
Core engine
Scene graph & rendering abstraction
25 min
overview the scene graph & rendering abstraction system is responsible for organizing and visualizing 3d objects in the ir engine it provides a structured approach to defining spatial relationships between objects, their visual appearance, and how they are rendered on screen by separating the logical structure of a scene from the rendering process, the system enables flexible, efficient, and visually compelling 3d environments this chapter explores the concepts, structure, and implementation of the scene graph & rendering abstraction within the ir engine scene graph the scene graph is a hierarchical organization of entities in 3d space, defining parent child relationships that determine how objects are positioned relative to one another transform component at the core of the scene graph is the transformcomponent , which defines an entity's position, rotation, and scale // simplified concept of transformcomponent const transformcomponent = definecomponent({ name 'transformcomponent', schema s object({ position s object({ x s number({ default 0 }), y s number({ default 0 }), z s number({ default 0 }) }), rotation s object({ x s number({ default 0 }), y s number({ default 0 }), z s number({ default 0 }) }), scale s object({ x s number({ default 1 }), y s number({ default 1 }), z s number({ default 1 }) }) }) }); the transformcomponent has several key characteristics it defines an entity's position, rotation, and scale in 3d space for root entities (those without parents), these values are in world space for child entities, these values are relative to their parent's space changes to a parent's transform cascade to all its children parent child relationships entities can form hierarchical relationships, creating a tree like structure // example of creating a parent child relationship const parententity = createentity(); const childentity = createentity(); // set up the parent's transform setcomponent(parententity, transformcomponent, { position { x 10, y 0, z 0 } }); // set up the child's transform (relative to parent) setcomponent(childentity, transformcomponent, { position { x 0, y 5, z 0 } }); // establish the parent child relationship setcomponent(childentity, parentcomponent, { parent parententity }); in this example the parent entity is at position (10, 0, 0) in world space the child entity is at position (0, 5, 0) relative to its parent the child's actual world position is (10, 5, 0) if the parent moves to (20, 0, 0), the child automatically moves to (20, 5, 0) this hierarchical structure is powerful for creating complex objects with multiple parts animating articulated structures (like characters) organizing scenes logically efficiently transforming groups of objects rendering components while the scene graph defines spatial relationships, rendering components determine how entities appear visually mesh component the meshcomponent defines an entity's visual appearance // simplified concept of meshcomponent const meshcomponent = definecomponent({ name 'meshcomponent', schema s object({ geometrytype s string(), // e g , 'box', 'sphere', 'custom' geometryparameters s object({}), // parameters specific to the geometry type materialtype s string(), // e g , 'standard', 'basic', 'phong' materialprops s object({}) // material properties like color, roughness, etc }) }); the meshcomponent specifies the shape (geometry) of the object defines how the surface looks (material) can reference simple built in shapes or complex custom geometries can use basic colors or detailed textures and material properties gltf component for complex models, the gltfcomponent provides a powerful way to load and display pre built 3d assets // simplified concept of gltfcomponent const gltfcomponent = definecomponent({ name 'gltfcomponent', schema s object({ src s string(), // path to the glb or gltf file visible s bool({ default true }), castshadow s bool({ default true }), receiveshadow s bool({ default true }) }) }); the gltfcomponent references a gltf/glb file containing a 3d model uses the asset management system to load the model automatically creates child entities for each part of the model sets up appropriate transformcomponent and meshcomponent instances maintains the hierarchical structure defined in the gltf file object component the objectcomponent serves as a bridge between the ecs architecture and the underlying rendering system // simplified concept of objectcomponent const objectcomponent = definecomponent({ name 'objectcomponent', schema s object({ object s any(), // reference to the actual 3d object in the renderer visible s bool({ default true }) }) }); the objectcomponent is typically added automatically by systems like sceneobjectsystem holds a reference to the actual 3d object in the rendering engine allows systems to directly manipulate the renderer's objects serves as a cache to avoid recreating objects unnecessarily environment components beyond individual objects, the scene's overall environment significantly impacts visual quality and mood skybox component the skyboxcomponent defines the background of the entire scene // simplified concept of skyboxcomponent const skyboxcomponent = definecomponent({ name 'skyboxcomponent', schema s object({ backgroundtype s enum({ none 0, color 1, equirectangular 2, cubemap 3 }), backgroundcolor s object({ / rgb color / }), equirectangularpath s string(), cubemappaths s object({ / paths for 6 sides / }) }) }); the skyboxcomponent creates the background environment for the entire scene can use a simple color, a 360° panoramic image, or a cubemap provides a sense of place and atmosphere often serves as a source of ambient lighting environment map component the envmapcomponent controls how objects reflect their surroundings // simplified concept of envmapcomponent const envmapcomponent = definecomponent({ name 'envmapcomponent', schema s object({ type s enum({ / types of environment maps / }), path s string(), intensity s number({ default 1 0 }) }) }); the envmapcomponent defines how reflective surfaces appear makes materials like metal and glass look realistic can use the skybox or a separate environment map affects the overall lighting quality of the scene shadow component the shadowcomponent controls shadow casting and receiving // simplified concept of shadowcomponent const shadowcomponent = definecomponent({ name 'shadowcomponent', schema s object({ cast s bool({ default true }), receive s bool({ default true }) }) }); the shadowcomponent determines if an object casts shadows onto other objects controls if an object receives shadows from other objects significantly enhances visual realism and depth perception can be applied to individual objects or entire hierarchies rendering systems several systems work together to process these components and render the scene scene object system the sceneobjectsystem is responsible for managing renderable objects // simplified concept of sceneobjectsystem const sceneobjectsystem = definesystem({ uuid 'ir engine sceneobjectsystem', execute () => { // find all entities with meshcomponent or gltfcomponent const renderableentities = renderablequery(); for (const entity of renderableentities) { // get or create an objectcomponent for this entity const objectcomp = getorcreateobjectcomponent(entity); // update the object's transform updateobjecttransform(entity, objectcomp); // update visibility, shadows, etc updateobjectproperties(entity, objectcomp); } } }); the sceneobjectsystem processes entities with visual components creates and updates objectcomponent instances calculates world transforms by traversing the scene graph updates visibility and other rendering properties bridges between the ecs and the rendering engine environment system the environmentsystem manages scene wide visual settings // simplified concept of environmentsystem const environmentsystem = definesystem({ uuid 'ir engine environmentsystem', execute () => { // find entities with environment components const skyboxentities = skyboxquery(); const envmapentities = envmapquery(); // apply skybox settings for (const entity of skyboxentities) { const skybox = getcomponent(entity, skyboxcomponent); applyskyboxtorenderer(skybox); } // apply environment map settings for (const entity of envmapentities) { const envmap = getcomponent(entity, envmapcomponent); applyenvmaptorenderer(envmap); } } }); the environmentsystem processes entities with environment components configures the renderer's global settings sets up skyboxes, environment maps, and lighting ensures consistent environment across the scene practical example let's create a simple space scene with a spaceship, a planet, and a starry background // create the main scene entity const sceneentity = createentity(); // set up the starry background setcomponent(sceneentity, skyboxcomponent, { backgroundtype skytypeenum equirectangular, equirectangularpath "textures/starry sky ktx2" }); // create the spaceship entity const spaceshipentity = createentity(); // position the spaceship setcomponent(spaceshipentity, transformcomponent, { position { x 0, y 50, z 100 }, rotation { x 0, y math pi / 4, z 0 }, scale { x 1, y 1, z 1 } }); // load the spaceship model setcomponent(spaceshipentity, gltfcomponent, { src "models/spaceship glb", castshadow true, receiveshadow true }); // create the planet entity const planetentity = createentity(); // position the planet setcomponent(planetentity, transformcomponent, { position { x 200, y 0, z 500 }, scale { x 100, y 100, z 100 } }); // give the planet a visual appearance setcomponent(planetentity, meshcomponent, { geometrytype 'sphere', materialprops { color 'blue', roughness 0 7, metalness 0 2 } }); // make the planet cast and receive shadows setcomponent(planetentity, shadowcomponent, { cast true, receive true }); // add a light source const lightentity = createentity(); setcomponent(lightentity, transformcomponent, { position { x 500, y 300, z 0 } }); setcomponent(lightentity, lightcomponent, { type 'directional', intensity 1 5, castshadow true }); this example demonstrates setting up a skybox for the background creating a spaceship using a gltf model creating a planet using a basic sphere geometry adding shadows for realism including a light source to illuminate the scene when the engine runs, the systems will load the necessary assets (starry sky texture, spaceship model) process the scene graph to determine object positions set up the rendering environment (skybox, lighting) render the scene from the perspective of a camera rendering pipeline the rendering process follows a specific sequence sequencediagram participant developer participant ecs as ecs components participant scenesys as scene systems participant renderer as rendering engine participant gpu as graphics hardware participant screen developer >>ecs define entities with transform, mesh, gltf components loop each frame scenesys >>ecs query for renderable entities scenesys >>scenesys process scene graph hierarchy scenesys >>scenesys calculate world transforms scenesys >>scenesys determine visibility scenesys >>ecs query for environment settings scenesys >>scenesys process skybox, lighting, shadows scenesys >>renderer update scene objects and settings renderer >>renderer sort objects by material/depth renderer >>renderer apply culling and optimizations renderer >>gpu send draw commands and data gpu >>screen render final image end this pipeline starts with the ecs components that define the scene processes the scene graph to determine spatial relationships updates the renderer with the current scene state optimizes the rendering process sends commands to the gpu displays the final image on screen benefits of the scene graph & rendering abstraction the scene graph & rendering abstraction system provides several key benefits hierarchical organization the scene graph enables intuitive organization of complex scenes relative positioning parent child relationships simplify positioning and animation separation of concerns the ecs architecture separates spatial data from rendering logic rendering abstraction the system hides the complexity of the underlying rendering engine efficient updates only changed components trigger updates to the rendering state flexible environment skyboxes, lighting, and shadows create visually rich environments these benefits make the scene graph & rendering abstraction a powerful system for creating and visualizing 3d worlds in the ir engine next steps with an understanding of how objects are organized and rendered in the scene, the next chapter explores how characters and avatars are represented and animated next avatar system docid\ mphr4hy5nlfxvelwzu yo