• When developing big projects, lots of data have to be managed • It quickly becomes a big mess ! • A robust and extensible data structure is required Introduction to Scene Graphs Scene Graph

Kévin Boulanger November 2006 • Hierarchical data structure • EbildEasy to build • Easy to extend • Allows work by many developers at the same time

Some examples Definition

• Objects, items in a 3D scene are rarely independent: • Scene graph is a commonly used data structure (web, video games) • physical connection • interaction • Examples: • influence (light) • OpenSceneGraph (www..org) • requirement (data) • OpenSG (www .opensg . org) • nVSG (developer.nvidia.com/object/nvsg_home.html) A scene graph is a hierarchical data structure, based on a graph: • Java3D (java.sun.com/products/java-media/3D) • the leaf nodes represent objects to render, • VRML, (3d)(www.x3d.org) • the in terna l no des are groups, trans formati ons, properti es • SGI Open Inventor (oss.sgi.com/projects/inventor) • OpenMASK (www.irisa.fr/siames/OpenMASK) • Two types: •etc. • • DAG (Directed Acyclic Graph) • Many scene graph designs exist, each adapted to its respective use Tree DAG ((y)Directed Acyclic Graph)

A tree contains no loop and each node has a single parent node A DAG contains no loop and each node can have several parent nodes

car car

paint translation translation translation translation paint tire material

body tire material tire material tire material tire material body translation translation translation translation

wheel wheel wheel wheel wheel

Comparison Rendering

• Tree (one parent, several children per node): • Rendering consists of traversing the graph: • very simple to build and manage, • a geometry node has to be rendered (primitives , meshes), • simple to traverse, •a transform node has to modify the transformation matrices, • however, duplication of data •a state node has to change a render state (color, material, shader, …) iiidin memory is required • Depth-first traversal: • simple for a tree, • DAG (several parents, several children per node): • for a DAG, do as if it is a tree, nodes will be traversed several times if • more complicated to build, necessary •sliggyhtly more com plicated to traverse, • great advantage: no duplication of data in memory, sharing of resources  instancing Traversal of the gg(raph (example 1) Transform node

Execution equivalent to the depth-first traversal

void RenderCar() { setMaterial(paint); renderBody(); car setMaterial(tire); 1. Save the current modelview : glPushMatrix() // Wheel 1 glPushMatrix(); paitint tire ma teri a l glTranslatefv(transWheel1); renderWheel(); 2. Appl y the transf ormati on: glTranslatef(), glRotatef(), glPopMatrix();

// Wheel 2 glMultMatrixf() body translation translation translation translation glPushMatrix(); glTranslatefv(transWheel2); renderWheel(); glPopMatrix(); 3. Render every children wheel // Wheel 3 glPushMatrix(); glTranslatefv(transWheel3); 4. Restore the modelview matrix: ggplPopMatrix () renderWheel(); glPopMatrix();

// Wheel 4 glPushMatrix(); glTranslatefv(transWheel4); renderWheel(); glPopMatrix(); }

Second example Traversal of the gg(raph (example 2)

Execution equivalent to HdHand-coddfded func tion robot claw the depth-first traversal

glPushMatrix(); glPushMatrix(); glRotatef(-angle1); origin point glRotatef(-angle1); transArm render(arm1); rotation rotation render(arm1); Left Right glPushMatrix(); arm arm -angle1 angle1 glTranslatef(transArm); angle1 glTranslatef(transArm); glRotatef(-angle2); glPushMatrix(); render(arm2); glRotatef(-angle2); angle2 glPopMatrix(); render(arm2); translation translation glPushMatrix(); arm1 glPopMatrix(); glRotatef(angle1); transArm transArm glPopMatrix(); glPopMatrix(); render(arm1); glPushMatrix(); glTranslatef(transArm); rotation rotation glRotatef(angle1); glRotatef(angle2); Direct traversal of the graph will -angle2 angle2 render(arm1); render(arm2); render the same object but not glPushMatrix(); glPopMatrix(); optimally glTranslatef(transArm);

glPushMatrix(); arm2 glRotatef(angle2); render(arm2);

glPopMatrix(); glPopMatrix(); glPopMatrix(); Comparison Optimization

Hand-coded function Graph traversal • Direct traversal of the graph for rendering is not optimal when there are glPushMatrix(); glPushMatrix(); many transform and render state nodes: glRotatef(-angle1); glRotatef(-angle1); • useless glPushMatrix() and glPopMatrix() calls, render(arm1); render(arm1);

glTranslatef(transArm); glPushMatrix(); • useless changes of render states (two times the same color) glRotatef(-angle2); glTranslatef(transArm);

render(arm2); glPushMatrix(); glRotatef(-angle2); • Usage of a structure in parallel, dedicated to rendering: glPopMatrix(); render(arm2); • the scene graph is traversed, glPushMatrix(); glRotatef(angle1); glPopMatrix(); glPopMatrix(); • each encountered node is stored in a queue or a tree, render(arm1); glPopMatrix(); • sorting is done to group render state changes, glTranslatef(transArm); glPushMatrix(); glRotatef(angle2); glRotatef(angle1); • if possible, matrix modifications are reduced, render(arm2); render(arm1); • finally, the queue or tree is traversed for rendering

glPopMatrix(); glPushMatrix(); glTranslatef(transArm);

glPushMatrix(); • Sometimes quite difficult to do the sorting because of constraints, as for glRotatef(angle2); transparency (polygons have to be rendered from back to front) render(arm2);

glPopMatrix(); glPopMatrix(); glPopMatrix();

Culling

• Culling consists in rendering parts of the 3D scene for optimization purposes • Scene graphs are well adapted to collision detection • frustum culling allows to render only what is in the viewer field-of- view, •Approach similar to cullin g: • space partitioni ng meth od s miiinim ize the s ize o fthf the spaces to manage (BSP trees, octrees, etc.), • intersection points of rays with the scene have to be computed, • Scene graphs allow efficient culling by removing full branches when • if a ray does not collide the bounding volume of a node, there is no traversing. If a node is considered out of view, it is not rendered, neither the need to test the intersection with the children, a whole branch of the children graph is eliminated • Bounding boxes or spheres are commonly associated with the nodes • if a ray collides the bounding volume of a node, the intersection has • the leaf nodes have associated bounding volumes to be found by testing the child nodes • the internal node bounding volumes enclose every bounding volume of the children • the closer to the root node, the bigger are the bounding volumes Base node: group Base node: transform

group transform transform

• Connects a parent to several children • Transform the child or every children • Used in ggpraphs where ever y nodes have a sin gle child ((pj)translation, rotation, scale, projection)

• When traversing for rendering, • Must save the current transformation matrix before rendering the children simply traverse every children for rendering and restore it after

Base node: render state Base node: switch

render state render state switch

• Does a selection by rendering only the desired child • Change one of the current render states • Often used for levels-of-detail management ((ggpy)color, material, lighting, transparency, shader, etc.) (selection of the mesh quality depending on the distance from the • Implemented different ways depending on the graph design camera for example)

• Must save the current render state before rendering the children and restore it after Scene gggraph design

• There are at least many different scene graph design approaches as the number of existing libraries

• Common examples: • usage of nodes for everything, with only one child (group nodes have to be used) • usage of nodes for everything, with several children per node • usage of only transform nodes (several children) and geometry nodes (leaves). Additional data are associated with each node.