- Home ›
- Forum ›
- Development ›
- User Code & Projects ›
- Procedural Infinite 3D Cave Generation

Hello,

I want to show my latest project ‘Procedural Infinite 3D Cave Generation’. The idea I got from NVidia’s article: Chapter 1. Generating Complex Procedural Terrains Using the GPU.

Video:

http://www.youtube.com/watch?v=KIEY3py5w1k

Cave scalar field is sum of 5 random 3D noises. Each of them is tri-linearly interpolated. Marching tetrahedrons algorithm is used for polygonization. Texture coordinates for tri-planar texture and bump mapping are calculated in shader program. Geometry is calculated in another thread in CPU, not in GPU like in the NVidia’s article.

Here is my first shader program: ‘Triplanar texture and bump mapping shader’. The shader samples two textures: diffuse and normal.

triplanaltexturing.frac

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
varying vec4 vertex; varying vec3 normal, vNormal, lightDir, eyeVec; varying float att; void main() { normal = normalize(gl_Normal); vertex = gl_Vertex; vNormal = gl_NormalMatrix * gl_Normal; vec3 vVertex = vec3(gl_ModelViewMatrix * gl_Vertex); lightDir = vec3(gl_LightSource[0].position.xyz – vVertex); eyeVec = -vVertex; float d = length(lightDir); att = 1.0 / ( gl_LightSource[0].constantAttenuation + (gl_LightSource[0].linearAttenuation * d) + (gl_LightSource[0].quadraticAttenuation * d * d)); gl_Position = ftransform(); } |

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 |
uniform sampler2D sampler; uniform sampler2D samplerBump; varying vec4 vertex; varying vec3 normal, vNormal, lightDir, eyeVec; varying float att; void main(void) { if(att > 0.01) { // tri-planar texture bending factor vec3 blending = (abs( normal ) – 0.2) * 7.0; blending = normalize(max(blending, 0)); // Force weights to sum to 1.0 (very important!) blending /= (blending.x + blending.y + blending.z ).xxx; //vec3 blending = abs( normal ); vec3 signedBlending = sign(normal) * blending; // texture coords vec4 coords = vertex * 0.05; vec4 col1 = texture2D( sampler, coords.yz ); vec4 col2 = texture2D( sampler, coords.zx ); vec4 col3 = texture2D( sampler, coords.xy ); vec3 nor1 = texture2D( samplerBump, coords.yz ).zxy – 0.5; vec3 nor2 = texture2D( samplerBump, coords.zx ).yzx – 0.5; vec3 nor3 = texture2D( samplerBump, coords.xy ).xyz – 0.5; // Finally, blend the results of the 3 planar projections. vec4 colBlended = col1 * blending.x + col2 * blending.y + col3 * blending.z; vec3 norBlended = nor1 * signedBlending.x + nor2 * signedBlending.y + nor3 * signedBlending.z; vec3 N = normalize(gl_NormalMatrix * norBlended); vec3 L = normalize(lightDir); float lambertTerm = max(0.2, dot(N,L)); colBlended = colBlended * lambertTerm * att; vec3 E = normalize(eyeVec); vec3 R = reflect(-L, N); float specular = 0.25 * pow( max(dot(R, E), 0.0), 32 ) * att; colBlended += specular * att; gl_FragColor = colBlended; } else { gl_FragColor = vec4(0,0,0,0); } } |

Wow, cool! So your are still working on this? Any chance to see some contribution growing out of this? It really looks great.

Cheers,

Normen

P.S.: I removed the “html link” around your youtube video link to it displays in the thread.

Gorgeous! This is like one of our coolest graphics showcases to date I might be out of time for today but I’m gonna take a snapshot of the HD video and add it to our showcase screenshots. If you could give me a screenshot if your own though, that’d be even better. Ideally you also include a description of the image (SEO stuff basically), though I do have enough to go on by what you’ve explained in this post. Lastly, I suppose I could include a link of your choice.

Great job man.

@erlend_sh, shouldn’t you be sure that @mazander did this in jME3? The GLSL could be for a number of graphics packages

Either way, it looks fantastic! Can’t wait to see more on this!

I see, sorry I jumped to conclusions. Too bad though, it won’t make the showcase then. If you do end up porting this to jME3 though, I guarantee you we’ll showcase it; it might very well be frontpage material ;)

I’m at a lost where to start, but how do I use this in JME3? :D

You can’t USE it. Mazender is just demonstrating his work.

It’s made for JME2, and the given shader code is just used to render the material of the cave.

Though it would need some adaptation to work with JME3.

But if you are eager to step into this, you would need to generate a procedural terrain first with JME3, which is far from trivial.

You can start by reading the article on GPU gem about this (if you didn’t yet).

But be aware that this is a very advanced topic.

I did read the article, and it did feel above my level at this point for sure. But definitely within my grasp with time. And I was referring to the article and the terrain generation described there, not Mazander’s. Sorry for confusion.

If someone wants use or just test this, the source code of the project is now hosted on Google.

https://code.google.com/p/cave3d/

I added one y-axis scaled noise which produced nice stalactites:

That’s a great contribution to the community! Kudos

I totally agree to what Skye said! Fantastic, that will make porting it to jme3 easier.. Anyone? :D

Cooool

Jme3:

A few issues to sort out still.

1. Texture stretching. I need to properly calculate the tex coords from the view projection. I’ve realized it has to do with trigonometry. Simply using pythagoras theorem on the “v” coord produces a radial shape in the texture.

2. Normal maps. Ran into some problems generating TangentBinormals. It seems no triangles are found/generated for the VertexData. I haven’t worked with that before so i’m not sure how to solve it.

The reason for this is it’s now using the Lighting material. Previously everything was handled by the shader (and i didn’t get that to work)

Now i need to get some fresh air. Hope to complete this later

Edit: issue clarification. If anyone has any pointers to give regarding the issues, feel free to mention them.

You must be logged in to reply to this topic.