Hi Viggo, One thing I have considered in the path is to have an osg::Layer node which is a group that has a StateSet per child, this does sound kinda similar to what you are after. You can implement this without any custom nodes just be arranging Group/Switch and StateSet's as required - its just a bit more wordy w.r.t lines of code.
Robert. On Wed, Nov 19, 2008 at 1:32 PM, Viggo Løvli <[EMAIL PROTECTED]> wrote: > Solution suggestion: StateSetSwitchNode > > Motivation: > - I need to render with different shader-programs and state-sets, on the > same geometry, during one tick. > - Example of when I need this is explained in the EXAMPLE section below. > > I hope from this e-mail to get feedback: > - Is this solution ok? > - Can it be improved? > - Can I submit it to OSG? And supported in the .ive file format? > > Solution: > ========== > I use Group instances to hold the StateSets. > Need to store Group pointers in an array: > > class StateSetSwitchNode : public Group > { > ... > private: > std::vector<Group*> _nodeArray; > }; > > Need to override the accept function: > > void StateSetSwitchNode::accept( osg::NodeVisitor& nv ) > { > if( nv.validNodeMask( *this )) > { > if( osg::Group* group = _nodeArray[ INDEX ] ) > { > // Apply the Group holding the StateSet instead of 'this' > pointer > nv.pushOntoNodePath( group ); > nv.apply( *group ); > nv.popFromNodePath(); > } > } > } > > I will explain the INDEX and array size later in this e-mail. > > Each Group pointer in the _nodeArray: > - must be set up with the same children as the StateSetSwitchNode > instance has. > - will not have any parents (unless the element point to the > StateSetSwithNode instance). > - will by default point to the StateSetSwitchNode instance. > > The StateSetSwitchNode's own StateSet is the default StateSet. > > I am conserned about how smart it is to have nodes that is not tied to a > parent, but that links to multiple children in the node-tree. It will not > affect performance when traversing children, but any parent traversal will > go into all of the extra nodes stored in the _nodeArray. They do not have > parents, so it is not a large performance penalty. > The class will also need function overrides for adding/removing/replacing > children as we would need to ensure that each element in the array point to > the same children as the StateSetSwitchNode. > > We do not need to do any code changes to OSG (except for supporting the > class in file formats, and to add the class to OSG). > Cull-traveresal does not suffer a performance-hit, unless you actually use > the StateSetSwitchNode. > Using the StateSetSwitchNode comes with a minimal performance-hit for > StateSet switching (bitvise and operation + an array lookup). > > > INDEX (and the array size): > ============================ > We need some way to select what array index we want to use. My need is to > have multiple camera's render the scene in different ways (by using > different state-sets and shader-programs). > I decided to do it in a way that need no new code, except for the indexing > inside my new class. So I use the traversal-mask which automatically makes > it possible for my camera's to decide what StateSets to render the scene > with. I allocate some of the least significant bits in the node-mask to be > StateSet selectors. So if I use 4 bits for this, then I get a total of 16 > different StateSet possibilities in each StateSetSwitchNode. > We do not want to check array size during cull-traverse, the size of the > array should be in the power of two so that we can bitvise and the index > before we read the array. All elements in the array thus need to point to an > instance. > Any not used elements will point to the default instance (which is the > StateSetSwitchNode instance itself). This must be enforced in the > StateSetSwitchNode constructor. > > INDEX (in the above code) is thus replaced by this: > (nv.getTraversalMask() & (_arraySize-1)) > > > EXAMPLE: > ========= > Currently we render our scene three times each tick: > - One pre-render camera that render the scene and generate a water-surface > reflection image. > - One pre-render camera that render the scene and generate a sub-sea > refraction image. > - One camera that render the scene and use the two textures above to > display a good looking sea surface. > > The pre-render cameras renders only parts of the scene (those nodes that > actually need to be in the reflective image and those that is underneath > water). > > Our terrain use four different shaders: > - High detail shader on the lod's that are close to camera. > - Low detail shader on distant lods. > - Lower detail shader on the reflection surface both for close and distant > lods. > - Special fog shader and lower detail both for close and distant lods when > under water. > > The same goes for vegetation and buildings (which has different shaders than > then terrain). > > We can optionally switch to even simpler shaders when the water-surface > start to have higher waves. So dynamically we will be able to speed up > reflection and underwater rendering based on wave-height. This would be a > matter of changing the cull-mask on the pre-render cameras and writing even > simpler shaders. > > We use the StateSetSwitchNode to select which shaders to render with, and > this is controlled by setting the lower bits in the camera's cull-mask. > We use bit 0,1 and 2 to select shader. > We use bit 3,4 and 5 to select scene (normal, reflection and underwater). > Doing this has proven to be a performance boost for our scene. We can write > as simple as possible shaders to use at need. The reflection and underwater > does not need high detail. In the future we will also use this to render the > shadow-caster scene with super-simple shaders too. > > Regards, > Viggo > > > ________________________________ > Windows Live SkyDrive. På tide å glemme minnepinnen. > _______________________________________________ > osg-users mailing list > osg-users@lists.openscenegraph.org > http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org > > _______________________________________________ osg-users mailing list osg-users@lists.openscenegraph.org http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org