The area of the shadow that one 3d model creates over other 3d models

Hi,

I want to make an app to calculate the area of the shadow that one 3d model creates over other 3d models.

Do you think is possible with OGL?

Yes, you can use occlusion query to find out how many pixels were rendered. So you can enable texture queries during some additional rendering pass that renders “invisible” pixels on top of shadowed area of your object and discards unshadowed pixels. You can use that in either eye space or during rendering to shadowmap.

You could also count number of pixels used to render your model in ambient pass and then subtract number of pixels rendered during lighting pass (assuming you discard all shadowed pixels during lighting pass) - this one will work in eye space only.

that’s not the area though is it?
that’s calculating the number of pixels.
a large-area surface at an oblique angle to the viewer could be totally in shadow but only contribute a small number of pixels.

One (very, very poor) method would be to test each screen pixel for shadowed-ness, and if so, create 4 world-space points and calculate the world-space “area” of that pixel.

that’s calculating the number of pixels.
a large-area surface at an oblique angle to the viewer could be totally in shadow but only contribute a small number of pixels.
You’re right, but perhaps that’s what he needs (an approximation or a relation between number of shadowed and unshadowed pixels), so it’s a starting point. If he needs something more accurate he will surely tell us.

occlusion query wont work cause u will often get multiple hits for a single pixel eg a 10x10 sized area may return 200!

(off the top of my head)
one method would be to render both objs from the lights position

A/ clear stencil 0x00
B/ draw the far objects with stencil 0x01
then draw the shadow caster object + anytime the fragment passes z test check to see if the stencil == 0x01 and if so set to say 0xff
C/ at the end read back number of pixels whose stencil values are 0xff
should give accurate results (but quite slow maybe 0.05secs a good sized frame)

occlusion query wont work cause u will often get multiple hits for a single pixel

C/ at the end read back number of pixels whose stencil values are 0xff
Does it mean: don’t use hardware pixel counter - implement your own in software mode? :slight_smile:

You can avoid multiple hits very easily using glDepthFunc(GL_EQUAL):

  1. Render object to shadowmap
  2. Render object again with occlusion query and glDepthFunc(GL_EQUAL);
  3. Render other shadow casters
  4. Render object again with occlusion query and glDepthFunc(GL_EQUAL);

Occlusion query results from #2 and #4 give approximate precentage of object area covered by shadow.

thanks for your interest, i didnt explain it well :slight_smile:

Here it goes again:

Imagine i have a 10x10x10 cube on a plane, simulating a building on the ground.

If we put a light simulating the sun, that cube will create a shadow on the plane. Independtly the position where im looking at the scene or I render it, i want to know the area of that shadow.

If you put your finger above your table, it will give the same shadow independtly from where you are looking at it…

Is it possible?

Originally posted by k_szczech:
[b] [quote]occlusion query wont work cause u will often get multiple hits for a single pixel

  1. Render object to shadowmap
  2. Render object again with occlusion query and glDepthFunc(GL_EQUAL);
  3. Render other shadow casters
  4. Render object again with occlusion query and glDepthFunc(GL_EQUAL);

Occlusion query results from #2 and #4 give approximate precentage of object area covered by shadow. [/b][/QUOTE]To be more precise, that would calculate the percentage of shadowed object area that is visible from the light source.
In general, I believe the shadow area depends very much on the viewpoint position, if it is to be calculated using the “pixel count”.

I believe the shadow area depends very much on the viewpoint position
Agreed. That’s what I had in mind when I wrote:

You can use that in either eye space or during rendering to shadowmap
Ok, back to tirengarfio’s post:

Independtly the position where im looking at the scene or I render it, i want to know the area of that shadow.
That would be more less these 4 steps I described. If you do occlusion query during rendering to shadowmap it will be dependent on light source position and not on camera position. Of source you don’t need to use shadow mapping - you just need to render scene from light source’s point of view (just like in shadowmapping), but since this step needs to be done anyway, then there is no reason to use any other shadow casting method at this point.

The question is if you want accurate result or approximated. If you need accurate result then it will be a bit complex.

I guess what you need to do is making a shadow projection matrix (just as plane stencil shadow – not shadow volume), and project the shadow on each triangle that might receive it and do some uggly maths calculations to know what area it covers.
Of course my guess doesn’t request GL…

Originally posted by k_szczech:
The question is if you want accurate result or approximated. If you need accurate result then it will be a bit complex. [/QB]
I would like to have accurate results as possible. Even perfect :slight_smile:

Can you explain me some about the relation accuracy-complexity in this case?

Originally posted by tirengarfio:
[b] thanks for your interest, i didnt explain it well :slight_smile:

Here it goes again:

Imagine i have a 10x10x10 cube on a plane, simulating a building on the ground.

If we put a light simulating the sun, that cube will create a shadow on the plane. Independtly the position where im looking at the scene or I render it, i want to know the area of that shadow.

If you put your finger above your table, it will give the same shadow independtly from where you are looking at it…

Is it possible? [/b]
If you just want the precise area of the projection of an object onto a plane, that’s pretty easy math and doesn’t involve OpenGL.

  • Create a projection matrix (light->plane)
  • Multiply vertices with projection matrix, perform perspective divide by w
  • per triangle, check whether it’s facing the light (winding), and if so, calculate its area and accumulate
  • alternatively: don’t check winding, calculate area anyway. Accumulate, then divide by two

If you want the area of projection onto any kind of geometry, it gets complicated. You’d have to calculate the intersection of the shadow volume with the light-facing polygons in the scene.

You can do a coarse approximation using OpenGL, by rendering the scene twice from the light POV. First render the scene without the shadow caster, only write eye space Z and the angle between surface normal and view direction into a float texture rendertarget. In the second pass, disable depth buffering and draw only the shadow caster. Read the texture at the fragment position and determine the area of a quad at the given depth and angle that would result in a pixel-sized projection. Write the result to a float rendertarget.
Finally, accumulate the values in the float rendertarget.

Originally posted by Xmas:
If you just want the precise area of the projection of an object onto a plane, that’s pretty easy math and doesn’t involve OpenGL.
[/QB]
But i would like to have a 3d representation of the objects.

Xmas, I agree with you but when the shadow does not fully fill in the triangle, then it’s harder to know how much area it covers. That’s why I talked about uggly maths.

tirengarfio, I don’t understand what you meant… maybe you need more understanding about 3D… or maybe I need more understanding about what you try to mean.

I want to add also my thoughts :slight_smile: :

in the case i have only a cube on a plane, knowing the window coordinates of the corners of the shadow, and finding their object coordinates, with 1 or 2 easy area equations for trapezoids or triangles its easy to find the area of the shadow.

The complexer is the geometry of the shadow, the harder it will be to divide it in trapezoids or triangles to find the areas of each of them.

This can help maybe someone who doesnt need too much accuracy in the calculations.

If you need accurate area then you have to do all maths by yourself and that ain’t gonna be pretty.

First of all, with complex geometry polygons can overlap when viewed from light source’s position. You can forget just adding shadow areas - you’ll need an algorithm that finds overlapping polygons and cuts occluded fragment from polygon further away from light. It means that 100 polygons can dynamically turn into 300 or worse.

Then you need shadow test. Normally you do that per pixel and draw or discard it. This time you want accuracy, so you don’t limit yourself to 1 pixel precision, but perform per-polygon shadow test and clip these parts of shadow receiver that do not receive shadow.
Now you have some 3d object that represent shadowed fragments of shadow receiver. Get rid of overlapping polygon fragments and finally compute field of final shape.

So that means a lot of clipping and cutting. But not clipping to a single plane but to other polygons. That’s a task for advanced programmers at least.