1 Million particles using geometry shader

Not really happy with the number of object the Blender game engine can handle, especially for effects such as particles, I decided to try using the graphics card to emit particles. So far, using Moguri’s GSOC branch I got the geometry shader to emit 1million textured particles at interactive framerate.

Of course, there is still tons of work to be done in order to have particle dynamics and collision, but it’s getting there…

http://blog.mikepan.com/wp-content/uploads/IMG_3301-560x373.jpg
http://blog.mikepan.com/wp-content/uploads/1Mb-560x350.jpg

My aging Geforce 8800GT is really pathetically slow when it comes to geometry amplications, since it’s the first generation of Geforce to support geometry shaders. If anyone here has a Radeon 5xxx or 6xxx series, and have 30 minutes of free time, it would be great if you can test this scene out for me. :yes:

Download
Blender build: soc-2010-moguri-2, latest SVN, you’ll have to compile it yourself :s
Blender file: soon :slight_smile:

opencl particles? i have a 8800gs but i want to try it anyways. where can I find a build? couldn’t find on GA:org

nice result
AFAIK it’s openGL (tessellation anyone?)

Oh boy.
Neither OpenCL nor tesselation.

It´s openGL using geometry shaders, just like his post says.

The G82 was the first chip with vertex, pixel AND geometry shaders and on top of that with unified shaders where you can choose what a shader should be according to your need. He uses the geometry shaders - the best thing since 1999 when shaders replaced HW T&L
And tesselation is a DX11/OpenGL3 feature which was introduced with the GF100 (and I know already the HD2000 had HW-tesselation, but is was and still is puny)

Where is the scene???

got a GTS 250, very willing to try out too :slight_smile:

Tessellation is completely different from Geometry Shader from my understanding, the graphic pipeline (DX11) works like this:
Vertex Shader > Tessellation > Geometry Shader > Fragment Shader > Output.

I am curious if I can brute force my way on the GPU by using the geometry shader to generate large number of vertices on modern hardware (Geforce 5xx class or Radeon 69xx class card with their huge geometry output capability), this particle approach should still be faster than CPU based particles.

This approach I am using is also different from using OpenCL or CUDA. I have no experience with GPGPU, so I can’t say what’s better…

ok folks I just tought tessellation is achieved via geometry shaders, my bad :slight_smile:

That’s what I thought at first too, and in theory it could. But apparently tessellation works better when it’s a separate stage in the pipeline. The D3D11 pipeline is getting annoyingly confusing! :s

I would be up for testing this, though i would have to find a complied build first :confused:

I have a Radeon 5870 and I’d be happy to test this. However, by the time I figured out how to compile a build the information would be useless. :frowning:

Still experimenting…

#version 120
#vertex shader

in vec4 vertex;
uniform float timer;

void main() {
vec4 v = vertex;
v.z = sin(timer+v.y+v.x)0.5+v.z;
v.x = sin(timer
10.0+v.y+v.y)*0.2+v.x;
gl_Position = gl_ModelViewProjectionMatrix * v;
}

#==========================

#version 330
#geometry shader

layout(triangles) in;
layout(triangle_strip) out;
out vec2 texCoord;

#define radius 0.01
#define layer 1

void main() {
//for(int i = 0; i < gl_in.length(); i++) { // avoid duplicate draw

for (int j=0; j vec4 p = gl_in[0].gl_Position;

texCoord = vec2(1.0,1.0);
gl_Position = vec4(p.r+radius, p.g+radius+j*0.05, p.b, p.a);
EmitVertex();

texCoord = vec2(0.0,1.0);
gl_Position = vec4(p.r-radius, p.g+radius+j*0.05, p.b, p.a);
EmitVertex();

texCoord = vec2(1.0,0.0);
gl_Position = vec4(p.r+radius, p.g-radius+j*0.05, p.b, p.a);
EmitVertex();

texCoord = vec2(0.0,0.0);
gl_Position = vec4(p.r-radius, p.g-radius+j*0.05, p.b, p.a);
EmitVertex();

EndPrimitive();
}
//}
}

#========================================

#version 330
#fragment shader
in vec2 texCoord;
out vec4 outColor;

uniform sampler2D col;
uniform float emit, alpha;

void main(void) {

// load color texture
vec4 color;
color = texture2D(col, texCoord);

// apply material panel values
color.rgb *= emit;
color.a *= alpha;

outColor = color;
}

I was waiting till someone pulled out a geometry shader. Very impressive mpan3! That looks very promising too! What else can be done with geometry shaders? (knowing me you might already be reading my mind: ‘sorry, no terrain for you out of geometry shader’… oh well, it’s OK…sigh…)

Geometry shader is useful for screenspace polygon manipulation. Billboard from point cloud expansion is definitely one of them. Silhouette displacement mapping is also very cool (it subdivides faces that is facing away from the camera so that the viewer see true displacement). There is also a lot of work can be done with edge detection, shadow volumes extrusion and onepass cubemap.