Curved Relief Mapping with correct silhouettes

Hi… just created a new relief mapping shader supporting correct silhouettes and would like to share some images of the first test.

I use the surface curvature information passed in at vertices to perform a correct ray intersection in fragment shader that allows the relief to be visible at the object silhouette.

Compare the results from the previous tangent space version that considered the surface always flat to the new one that supports curvature information.

Old shader screenshot

New shader screenshot

Shun-SHENG duh gao-WAHN…

Hmm, the second sphere looks smaller. Are you using discard in there to kill some fragments at the edges?

Can you make a demo with a single quad?

Oh, man, this is simply stunning, when can we have a demo?

The picture is awesome!
I wonder on what card you have rendered it/on what cards it is possible/what is the performance?

I have read once an interesting discussion about ray-tracing vs rasterization. Someone said that none of these will win, but they will be replaced with their combination. It’s great to see this happen…

And I think I’ll add yet another request for a demo (and/or avi for those (me) with old junk). I’m dying to see how these bumps change with view direction!
See you!

Impressive! I imagine you use a fairly high-resolution normal and displacement map?

Does the map tile? If so, how do you tell the cases where you want to kill pixels from the cases where you don’t?

Awesome! That does look so much better.

-SirKnight

Ok, here we go…

Originally posted by MikeC:
Shun-SHENG duh gao-WAHN…
What does that mean!!! English please…
Looking over the web I found a reference in FireFly (scifi series) and translates to ‘holy testicle tuesday’?!?!? Should I take it as a complement???

Originally posted by V-man:
Hmm, the second sphere looks smaller. Are you using discard in there to kill some fragments at the edges?
Can you make a demo with a single quad?

Yes I use discard to define the silhouette. Yes it is possible to render planar objects too. Actulay a planar surface is just a special case in the new more generic curved surface shader (where curvature is infinite or just a too large value to make up a plane).

Originally posted by 991060:
Oh, man, this is simply stunning, when can we have a demo?
Soon… but next week I will be out of Brazil for some work meetings. I will try to get it done before the holidays. I still have to organize the demo inteface options now and do a few modifications to the curvature mesh offline preprocess (passed in 4th component of tangent space vectors using a floar4 for tangent vectors).

Originally posted by Lurker_pas:
[b]The picture is awesome!
I wonder on what card you have rendered it/on what cards it is possible/what is the performance?

I have read once an interesting discussion about ray-tracing vs rasterization. Someone said that none of these will win, but they will be replaced with their combination. It’s great to see this happen…

And I think I’ll add yet another request for a demo (and/or avi for those (me) with old junk). I’m dying to see how these bumps change with view direction!
See you![/b]
I use GeForce6800 GT (only one that runs this shader I think… maybe 3dlabs one can also do it). It works with Cg profile ARBFP1 and in D3D with pixel shader 2b.

Good point on the ray tracing thing… this is kind of mixed triangle rasterization and ray tracing. Cool!

I will place a video today so… and will make the demo available asap when I get it somehow complete with all options I want it to include.

Originally posted by jwatte:
Impressive! I imagine you use a fairly high-resolution normal and displacement map?
Does the map tile? If so, how do you tell the cases where you want to kill pixels from the cases where you don’t?

I’m using 512x512 normal and texture maps but 256x256 would also look ok. And yes, texture can tile as much as you want and mipmapping works fine in large tile cases.

The killed pixels are the ones where the ray-depthmap intersection does not hit the displaced surface.

See you…
FPO

Looking over the web I found a reference in FireFly (scifi series) and translates to ‘holy testicle tuesday’?!?!?

lol!

Should I take it as a complement???

Yes. That basically means “OMG HOLY CRAP THAT LOOKS AWESOME!!!” :smiley:

-SirKnight

Originally posted by fpo:
[b]

[quote]Shun-SHENG duh gao-WAHN…
Looking over the web I found a reference in FireFly (scifi series) and translates to ‘holy testicle tuesday’?!?!? Should I take it as a complement???
[/b][/QUOTE]Very much so; in its original context, it’s an exclamation of impressed awe. (Terribly offtopic, btw, but if anyone hasn’t seen Firefly yet they’re missing out. Partly because it has some interestingly novel and very effective “amateur” CGI aesthetics, with shaky camera and bad focus, but mostly because it’s just flat-out the coolest TV ever made.)

Does this fragment-kill approach look good on sharp corner silhouettes, as well as curves? Assuming the relief textures match up on each side, I’d think it would.

I do wonder how much you’d need to tweak your geometry for this approach… it’s going to be a while before anyone can assume hardware good enough to run this. If you had, say, a relief-mapped sphere resting on a flat surface, and it didn’t have any “bumps” on the underside, it’d appear to be floating in mid-air. I suppose this is just another example of “fake” geometry and physics not really mixing.

Still damned impressive, though.

For the extra data needed on models, I need 4 extra floats per vertex for the new effect. Two for curvature at each tangent direction and two for texture mapping scale at each tangent direction. This can all be calculated offline once and stored with the model vertices in the geometry file.

Actually, I wasn’t thinking about the extra data. I was thinking about the case where you have a big bunch of geometry art assets and want to switch between a bleeding-edge GL2.x renderer (with “fpo relief mapping”) or a fallback renderer (with cruder or no bump mapping) at runtime depending on the hardware/driver available. Because the fragment-kill approach to silhouettes has the side-effect of “shrinking” geometry, a model that looks good in one renderer might not look good, or even correct, in the other.

Video looks amazing. There’s a pale greenish fringe along the left-hand edge of the silhouette; it’s very obvious in the last frame. Is this an artifact of the movie encoding? There was no sign of it in the JPG you posted.

Also, does your shadowing still work?

Some other screenshots using the other maps (brickbump, brickwall, and rockwall).

new relief rock bump
new relief rock wall
new relief brick wall

This rocks!

Can you give a rough outline on the shader complexity? Instruction counts vertex/fragment? Number of dependency levels?

Originally posted by zeckensack:
This rocks!
Can you give a rough outline on the shader complexity? Instruction counts vertex/fragment? Number of dependency levels?

Compiled fragment shader assembler instruction count is at 248 now but can be optimized (too long shader but it is just the first test and can be optimized specialy in the search loops). I’m sure pro_optimizer can make it much smaller. Vertex shader is only 22 instructions.

It uses the same approach as the previous shader (linear search followed by a binary serach). For the linear search 16 steps are fine (16 texture reads) and for the the binary search about 6 dependent texture reads are enougth. Then two reads for color and normal textures.
(total 24 texure reads with 6 dependent ones)

looks nice. too bad it won’t run on my 9600pro…

Brilliant.
How does it work with shadow volumes? :slight_smile:

Originally posted by knackered:
Brilliant.
How does it work with shadow volumes? :slight_smile:

“Shadow volume reconstruction from depth maps” maybe?

-SirKnight

Who don’t have GF76800 can download relief
mapping shader(for Render Monkey 1.5) from here:
Shader

It uses pultipass rendering.

Would there be a way to avoid all heavy raytracing computation in the middle of the mesh and keep it only for the silhouettes ? This way you could switch to a cheaper approach for the “inside”.

In a more general case, is there a way to make it adaptative, say depending on a value stored by vertex, or even in a texture ?

SeskaPeel.