Discussion:
osgShadow, node traversal, and node mask
Ben Discoe
2008-05-15 02:35:24 UTC
Permalink
There's something i'm not understanding about osgShadow, and it's probably a basic behavior of OSG.

So, the simple question first:
The default node mask for all nodes is 0xffffffff.
It i set the mask to 0, then the node (and its children) is not drawn.
If i set the mask to some other value, then it seems to be drawn also. So what is OSG testing for, mask!=0? The NodeVisitor code seem to deal with bit masks. So is there some specific bit (high bit, perhaps?) in the node mask which says "draw me"?

This relates to osgShadow's CastsShadowTraversalMask.
Let's say it's set to 1.
In the simple case (like example osgshadow) of a ShadowedScene with some children, it's clear how it will behave: nodes with the 0x1 bit set in their mask will cast shadows.
But, what if there is a large complex scene graph?
Nodes A and B are far apart in the graph. The ShadowedScene node is up at the top of the graph. If we want A to shadow B, then we need to set the appropriate bits in the node mask of A and B, and un-set them for everything else. But, will the node traversal (of the ShadowTechnique) ever reach A and B, to test if they have CastsShadowTraversalMask set? Or does every parent along the nodepath need the flag set also?

If that's true, then for this to be useful, we'd need some iteration code (NodeVisitors, presumably) to set up the scene graph, clearing the mask bits everywhere, and then starting with the ShadowCasting nodes, walking upwards setting the CastsShadowTraversalMask bits along the way, until it reaches ShadowedScene?

If anyone can answer these, i am happy to add an explanation the osgShadow wiki docs.

Thanks,
Ben
Gordon Tomlinson
2008-05-15 02:55:55 UTC
Permalink
Hi Ben

I can answer the Node Mask

See Loading Image...

Loading Image...

These were part of the Vega/Vega Prime course I used to teach, they explain
how masks work , the difference for Vega/Vega Prime/Performer is they had 3
masks for draw, cull and intersect for each node, while OSG sadly only has
one

So in this case the Camera will have a default mask of 0xfffffff so a
logical AND apart from 0x0 will produce true result, eg 0x00000010 &
0xffffffff results in 0x00000010 etc while 0xffffffff & 0x00000000 will
produce 0x00000000 false etc...


__________________________________________________________
Gordon Tomlinson

Email   : gordon-/RZN+***@public.gmane.org
YIM/AIM : gordon3dBrit
MSN IM  : gordon3dBrit-***@public.gmane.org
Website : www.vis-sim.com www.gordontomlinson.com
__________________________________________________________


-----Original Message-----
From: osg-users-bounces-***@public.gmane.org
[mailto:osg-users-bounces-***@public.gmane.org] On Behalf Of Ben Discoe
Sent: Wednesday, May 14, 2008 10:35 PM
To: 'OpenSceneGraph Users'
Subject: [osg-users] osgShadow, node traversal, and node mask

There's something i'm not understanding about osgShadow, and it's probably a
basic behavior of OSG.

So, the simple question first:
The default node mask for all nodes is 0xffffffff.
It i set the mask to 0, then the node (and its children) is not drawn.
If i set the mask to some other value, then it seems to be drawn also. So
what is OSG testing for, mask!=0? The NodeVisitor code seem to deal with
bit masks. So is there some specific bit (high bit, perhaps?) in the node
mask which says "draw me"?

This relates to osgShadow's CastsShadowTraversalMask.
Let's say it's set to 1.
In the simple case (like example osgshadow) of a ShadowedScene with some
children, it's clear how it will behave: nodes with the 0x1 bit set in their
mask will cast shadows.
But, what if there is a large complex scene graph?
Nodes A and B are far apart in the graph. The ShadowedScene node is up at
the top of the graph. If we want A to shadow B, then we need to set the
appropriate bits in the node mask of A and B, and un-set them for everything
else. But, will the node traversal (of the ShadowTechnique) ever reach A
and B, to test if they have CastsShadowTraversalMask set? Or does every
parent along the nodepath need the flag set also?

If that's true, then for this to be useful, we'd need some iteration code
(NodeVisitors, presumably) to set up the scene graph, clearing the mask bits
everywhere, and then starting with the ShadowCasting nodes, walking upwards
setting the CastsShadowTraversalMask bits along the way, until it reaches
ShadowedScene?

If anyone can answer these, i am happy to add an explanation the osgShadow
wiki docs.

Thanks,
Ben
Ben Discoe
2008-05-15 07:27:22 UTC
Permalink
Gordon, thanks, that clears up the first part, a default Camera mask of 0xffffffff explains why any non-zero node mask is rendered.

I fear that also means, in the second question below, that the CastsShadow bit _does_ need to be set for every parent along the nodepath. Otherwise, a "visitor" recursive descent of the scene graph will quit as soon as it encounters any node, like a Group or LOD, that does not have the CastsShadow bit set. Can anyone who understands osgShadow's NodeVisitors comment?

If it's true, then that's a very big consideration in how scene graphs must be constructed to use osgShadow, and i can document it.

-Ben
Post by Gordon Tomlinson
-----Original Message-----
From: Gordon Tomlinson
Sent: Wednesday, May 14, 2008 4:56 PM
I can answer the Node Mask
See http://www.vis-sim.com/imgdp/vp_rendermasks_01.jpg
http://www.vis-sim.com/imgdp/vp_rendermasks_01a.jpg
So in this case the Camera will have a default mask of 0xfffffff so a
logical AND apart from 0x0 will produce true result, eg 0x00000010 &
0xffffffff results in 0x00000010 etc while 0xffffffff & 0x00000000 will
produce 0x00000000 false etc...
__________________________________________________________
-----Original Message-----
From: Ben Discoe
Sent: Wednesday, May 14, 2008 10:35 PM
There's something i'm not understanding about osgShadow, and it's probably
a basic behavior of OSG.
The default node mask for all nodes is 0xffffffff.
It i set the mask to 0, then the node (and its children) is not drawn.
If i set the mask to some other value, then it seems to be drawn also. So
what is OSG testing for, mask!=0? The NodeVisitor code seem to deal with
bit masks. So is there some specific bit (high bit, perhaps?) in the node
mask which says "draw me"?
This relates to osgShadow's CastsShadowTraversalMask.
Let's say it's set to 1.
In the simple case (like example osgshadow) of a ShadowedScene with some
children, it's clear how it will behave: nodes with the 0x1 bit set in
their mask will cast shadows.
But, what if there is a large complex scene graph?
Nodes A and B are far apart in the graph. The ShadowedScene node is up at
the top of the graph. If we want A to shadow B, then we need to set the
appropriate bits in the node mask of A and B, and un-set them for
everything else. But, will the node traversal (of the ShadowTechnique)
ever reach A and B, to test if they have CastsShadowTraversalMask set?
Or does every parent along the nodepath need the flag set also?
If that's true, then for this to be useful, we'd need some iteration code
(NodeVisitors, presumably) to set up the scene graph, clearing the mask
bits everywhere, and then starting with the ShadowCasting nodes, walking
upwards setting the CastsShadowTraversalMask bits along the way, until
it reaches ShadowedScene?
If anyone can answer these, i am happy to add an explanation the osgShadow wiki docs.
Thanks,
Ben
Wojciech Lewandowski
2008-05-15 08:29:21 UTC
Permalink
Hi Ben,
Post by Ben Discoe
I fear that also means, in the second question below, that the CastsShadow
bit _does_ need to be set for every parent along the nodepath. Otherwise,
a "visitor" recursive descent of the scene graph will quit as soon as it
encounters any node, like a Group or LOD, that does not have the
CastsShadow bit set. Can anyone who understands osgShadow's NodeVisitors
comment?
If it's true, then that's a very big consideration in how scene graphs
must be constructed to use osgShadow, and i can document it.
Yes its true, but defaults for Node mask are 0xffffffff and NodeVisitor
mask is also 0xffffffff. If one changes masks, he does it with deliberate
intention to limit traversals to some portions of the scene.

For most typical scenario where all parts of the graph cast shadow and can
receive shadow, Cast and /Receive masks should be left at default 0xffffffff
setting. Scenarios where some portion of the scene graph does not cast or
receive shadows are unusual and indeed may require careful selection of node
masks .

If one does not want some portion of the scene to cast or receive shadows he
may also choose to not attach them to ShadowedScene node. ShadowedScene does
not have to be root node so its possible to create graph hierarchy where all
non shadowing / non shadowed objects are put under one branch and those
using and casting shadows are put under ShadowedScene in other branch of
the scene graph.

Wojtek
Alejandro Segovia
2008-05-15 18:19:42 UTC
Permalink
Hello,

I'm having a problem somewhat related to node masks and shadows.

I'm using the ShadowTexture technique on a Software project I'm working on,
and I've set the CastsShadowTraversalMask to 0x1, the
ReceivesShadowTraversalMask to 0x2, and have set the node masks for my nodes
to be 0x3 (0x1|0x2), meaning they cast and receive shadows at the same time,
however when I run the application, shadow casting nodes never get other
nodes' shadows casted upon.

If I just set the node mask to be 0x2 (the receive mask), they receive
shadows just fine, but when I set that to be 0x3, they stop receiving them.

Am I doing something wrong?

I'm under Linux with an nVIDIA graphics card.

Thanks in advance,
Alejandro.-
On Thu, May 15, 2008 at 5:29 AM, Wojciech Lewandowski <
Post by Wojciech Lewandowski
Hi Ben,
I fear that also means, in the second question below, that the
Post by Ben Discoe
CastsShadow bit _does_ need to be set for every parent along the nodepath.
Otherwise, a "visitor" recursive descent of the scene graph will quit as
soon as it encounters any node, like a Group or LOD, that does not have the
CastsShadow bit set. Can anyone who understands osgShadow's NodeVisitors
comment?
If it's true, then that's a very big consideration in how scene graphs
must be constructed to use osgShadow, and i can document it.
Yes its true, but defaults for Node mask are 0xffffffff and NodeVisitor
mask is also 0xffffffff. If one changes masks, he does it with deliberate
intention to limit traversals to some portions of the scene.
For most typical scenario where all parts of the graph cast shadow and can
receive shadow, Cast and /Receive masks should be left at default 0xffffffff
setting. Scenarios where some portion of the scene graph does not cast or
receive shadows are unusual and indeed may require careful selection of node
masks .
If one does not want some portion of the scene to cast or receive shadows
he may also choose to not attach them to ShadowedScene node. ShadowedScene
does not have to be root node so its possible to create graph hierarchy
where all non shadowing / non shadowed objects are put under one branch and
those using and casting shadows are put under ShadowedScene in other branch
of the scene graph.
Wojtek
_______________________________________________
osg-users mailing list
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org
--
http://varrojo.linuxuruguay.org
--
***@Linux
http://varrojo.linuxuruguay.org
Ben Discoe
2008-05-20 08:29:09 UTC
Permalink
Alejandro,

I suspect the most likely explanation is this:

1. You are using ShadowTexture, which AFAIK doesn't support self-shadowing.
2. ShadowTexture is ignoring your ReceivesShadow bit, however:
3. When you turn on CastsShadow for a node, it is then implicitly preventing it from receiving a shadow, because the algorithm can't do both.

Try replacing your ShadowTexture with a ShadowMap and see if the behavior changes; ShadowMap does support self-shadowing.

-Ben
-----
Sent: Thursday, May 15, 2008 8:20 AM
I'm using the ShadowTexture technique on a Software project I'm working on,
and I've set the CastsShadowTraversalMask to 0x1, the
ReceivesShadowTraversalMask to 0x2, and have set the node masks for my
nodes to be 0x3 (0x1|0x2), meaning they cast and receive shadows at the
same time, however when I run the application, shadow casting nodes never
get other nodes' shadows casted upon.
If I just set the node mask to be 0x2 (the receive mask), they receive
shadows just fine, but when I set that to be 0x3, they stop receiving them.
Am I doing something wrong?
I'm under Linux with an nVIDIA graphics card.
Alejandro Segovia
2008-05-20 14:05:16 UTC
Permalink
Hello Ben, thanks for your answer,
Post by Ben Discoe
Alejandro,
1. You are using ShadowTexture, which AFAIK doesn't support self-shadowing.
3. When you turn on CastsShadow for a node, it is then implicitly
preventing it from receiving a shadow, because the algorithm can't do both.
Try replacing your ShadowTexture with a ShadowMap and see if the behavior
changes; ShadowMap does support self-shadowing.
You're absolutely right: I am using ShadowTexture. I've tried different
shadow techniques, but for some reason ShadowTexture is the only one that
works in my application.

I bet this is a problem with the shadow's shaders in my application because
right now I'm trying to get PSSM to work and after setting the
OSG_NOTIFY_LEVEL to DEBUG, I noticed the shader never gets compiled, and
thus the app segfaults in the cull() call.

Do you know of any way to force the shader to get compiled? I've opened
another thread for this problem ("PSSM segfaulting in the cull() call").

Thanks in advance,
Alejandro.-
--
***@Linux
http://varrojo.linuxuruguay.org
Ben Discoe
2008-05-20 08:42:05 UTC
Permalink
-----
Sent: Wednesday, May 14, 2008 10:29 PM
Hi Ben,
Post by Ben Discoe
CastsShadow bit _does_ need to be set for every parent along
the nodepath.
If it's true, then that's a very big consideration in how scene
graphs must be constructed to use osgShadow, and i can document it.
Yes its true, but defaults for Node mask are 0xffffffff and NodeVisitor
mask is also 0xffffffff. If one changes masks, he does it with deliberate
intention to limit traversals to some portions of the scene.
For most typical scenario where all parts of the graph cast shadow
and can receive shadow, Cast and /Receive masks should be left at
default 0xffffffff setting.
I fear this is not typical. Due to the scale limitations of osgShadow, i suspect that 'most' scenarios involve enabling shadow only for certain nodes.
Scenarios where some portion of the scene graph does not cast or
receive shadows are unusual and indeed may require careful
selection of node masks.
I think they are not 'unusual', rather, the case where the shadow flags should be set for every node might only exist in a tiny example like osgshadow.

This means that integrating a single shadow-casting node into an existing OSG application involves the entire application changing its node masks, with code throughout. It's unfortunate, but it is at least possible.
If one does not want some portion of the scene to cast or receive shadows
he may also choose to not attach them to ShadowedScene node.
Many (most) nontrivial 3D applications have scene graphs which are already quite structured for reasons such as LOD; moving nodes around to put them under ShadowedScene would break things completely. The only solution seems to be to put ShadowedScene high up in the graph, and change the code all over the place to carefully disable shadows.

This is a lot of grief that could be spared if the shadow mask logic was opposite; a bit set to NOT cast a shadow. Then, adding shadow code to an application would involve only small localized code changes. <shrug> But that's the design, and it can be documented, and i can work with it.

-Ben
Wojciech Lewandowski
2008-05-20 14:13:24 UTC
Permalink
Hi Ben,
Post by Ben Discoe
Post by Wojciech Lewandowski
For most typical scenario where all parts of the graph cast shadow
and can receive shadow, Cast and /Receive masks should be left at
default 0xffffffff setting.
I fear this is not typical. Due to the scale limitations of osgShadow, i
suspect that 'most' scenarios involve enabling shadow only for certain
nodes.
Scale limitations ? You mean when scene is so huge that ShadowMap texture
looses too much detail so its basically useless ? I agree. I would not use
ShadowMap or SoftShadowMap in its current form for any vizualization
involving large databases. Its good for small scenes and as an example code
showing shadow map algorithm implementation.

We use LispPSM for our flight sims. But IMHO its not shadowing algoritm
thats important but method of shadow camera culling the scene to find
smallest visible scene portion requiring shadows. Before shadow map
rendering we do some convex hull math finding intersection of main cam
frustum with light frustum and visible scene objects. Such intersected
convex hull is then used to optimize frustum for camera rendering shadow
map...
I believe other more appropriate algorithm for large databases could be
PSSM which also improves precision by limiting shadowed portion of the scene
with shortened camera frustum.
Post by Ben Discoe
Post by Wojciech Lewandowski
Scenarios where some portion of the scene graph does not cast or
receive shadows are unusual and indeed may require careful
selection of node masks.
I think they are not 'unusual', rather, the case where the shadow flags
should be set for every node might only exist in a tiny example like
osgshadow.
This means that integrating a single shadow-casting node into an existing
OSG application involves the entire application changing its node masks,
with code throughout. It's unfortunate, but it is at least possible.
Post by Wojciech Lewandowski
If one does not want some portion of the scene to cast or receive shadows
he may also choose to not attach them to ShadowedScene node.
Many (most) nontrivial 3D applications have scene graphs which are already
quite structured for reasons such as LOD; moving nodes around to put them
under ShadowedScene would break things completely. The only solution
seems to be to put ShadowedScene high up in the graph, and change the code
all over the place to carefully disable shadows.
I did not mean moving nodes in the hierarchy in the runtime. I simply meant
that some pieces of 3D database are usually either illuminated and shadowed
or not illuminated and not shadowed. For example our terrain, buildings,
moving objects are attached to ShadowedScene but sky and ephemeris node,
clouds and some special effect nodes are attached under separate nonshadowed
group.

I don't also say that dynamic node mask manipulation is needed for our
shadowing either. We do large terrain simulation using paged terrain
database with LOD with number of detailed objects and we are able to handle
shadows without changing node masks on the fly. Its just a matter of shadow
scene management and culling approach I believe. But I ceratinly understand
that others may tackle the problem in different way.

Cheers,
Wojtek

Loading...