Showing posts with label particle. Show all posts
Showing posts with label particle. Show all posts

Sunday, May 29, 2011

Particle System with Point Sprites–Part II

After struggle for a day (though it’s a simple logic), i got the desired particle effect…

Effect i was looking for is “Particles continuously flow from the centre”, this effect i could achieve without Shaders, but i wanted to do the same with Shaders.

code changes from the previous post are as below…

Changes in Draw function of ParticleManger class are highlighted below.

public void draw(int iPosition, int iMove, int iTimes, int iColor, int iLife, int iAge)
  {
    GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
  
    vertexBuffer.position(0);
    GLES20.glVertexAttribPointer(iPosition, 3, GLES20.GL_FLOAT, false, PARTICLE_SIZE * 4, vertexBuffer);
    GLES20.glEnableVertexAttribArray(iPosition);
  
    vertexBuffer.position(3);
    GLES20.glVertexAttribPointer(iColor, 3, GLES20.GL_FLOAT, false, PARTICLE_SIZE * 4, vertexBuffer);
    GLES20.glEnableVertexAttribArray(iColor);
  
    vertexBuffer.position(6);
    GLES20.glVertexAttribPointer(iMove, 3, GLES20.GL_FLOAT, false, PARTICLE_SIZE * 4, vertexBuffer);
    GLES20.glEnableVertexAttribArray(iMove);
  
    vertexBuffer.position(9);
    GLES20.glVertexAttribPointer(iLife, 1, GLES20.GL_FLOAT, false, PARTICLE_SIZE * 4, vertexBuffer);
    GLES20.glEnableVertexAttribArray(iLife);
  
    vertexBuffer.position(10);
    GLES20.glVertexAttribPointer(iAge, 1, GLES20.GL_FLOAT, false, PARTICLE_SIZE * 4, vertexBuffer);
    GLES20.glEnableVertexAttribArray(iAge);
  
    GLES20.glUniform1f(iTimes, nTimeCounter);
  
    GLES20.glDrawArrays(GLES20.GL_POINTS, 0, NUM_PARTICLES);
  }

I'm passing life and age attribute values for each particle to Vertex Shader.

Changes in Vertex Shader are highlighted below (need to optimize interms of operation steps though).

String strVShader =
            "precision mediump float;" +
            "attribute vec4 a_Position;" +
            "attribute vec4 a_move;" +
            "uniform float a_time;" +
            "attribute vec4 a_color;" +
            "varying vec4 v_color;" +
            "attribute float a_life;" +
            "attribute float a_age;" +
            "varying float alpha;" +
            "float time;" +
            "void main()" +
            "{" +
                "alpha = a_life - (a_time * 10.0 * a_age);" +
                "time = a_time;" +
                "if (alpha < 0.0)" +
                "{" +
                    "float td = a_life/a_age;" +
                    "td /= 10.0;" +
                    "float df = a_time/td;" +
                    "int div = int(df);" +
                    "df = float(div);" +
                    "td *= df;" +
                    "time = a_time - td;" +
                    "alpha = a_life - (time * 10.0 * a_age);" +
                "}" +
                "gl_PointSize = 5.0;" +
                "v_color = a_color;" +
                "gl_Position = a_Position;" +              
                "gl_Position += (time * a_move * 0.5);" +
                "gl_Position.w = 1.0;" +
            "}";

here calculation logic is as follows:

  1. if particle run out of life (i.e., alpha calculated is less than zero), then
  2. Calculate the time (td), when particle has possibly died.
  3. find the modulo of current time and the calculated time in above step. thats is stored in time variable.
  4. calculate the alpha value based on the new calculated time.
  5. use calculated time to set the vertex position.

Fragment Shader do not have any changes.

Code for this post can be found at Google Code


Saturday, May 28, 2011

Particle System with Point Sprites


It's been almost 10 days I stuck with particle system. Still I have few doubts/problems/queries. But still I'll post my progress
I have asked my question regarding particle system updation on stackoverflow, waiting for answers J

Creating particle system with point sprites is very exciting for me.
Here is the screen shot:

 

Let's dig in.
Code for this post can be found at Google Code
Particle Structure
First let's look at properties of a Particle.
My particle structure as [x,y,z,     r,g,b,      dx,dy,dz, life,age]
                                       Position    Color         displacement
ParticleManager class

Setup function, for initiating the particle system with the position, random colors and displacement.
Draw function, is for drawing the particles, we here pass the particle related information to shaders
Update function, is called by Update Thread
Rendering
Vertex Shader
String strVShader =

            "attribute vec4 a_Position;" +
            "attribute vec4 a_move;" +
            "uniform float a_time;" +
            "attribute vec3 a_color;" +
            "varying vec3 v_color;" +
            "void main()" +
            "{" +
                "v_color = a_color;" +
                "gl_PointSize = 10.0;" +
                "gl_Position = a_Position;" +               
                "gl_Position += (a_time * a_move * 0.5);" +
                "gl_Position.w = 1.0;" +
            "}";
 
a_position represents position of each particle, a_move represents displacement/movement
a_color represents color of a particle,
In this vertex shader, we are setting the position of each particle based on the time and the displacement values.
Fragment Shader
String strFShader =
            "precision mediump float;" +
            "uniform sampler2D u_texture;" +
            "varying vec3 v_color;" +
            "void main()" +
            "{" +               
                "vec4 tex = texture2D(u_texture, gl_PointCoord);" +
                "gl_FragColor = vec4(v_color,0.5) * tex;" +
            "}";

Fragment shader is not changed much, only I'm setting alpha to 0.5,
We have to take it from life and age value of particle, will do it later.
Drawing
Drawing part is very similar to previous posts. Not many changes here, you can have look in the code.

 

Todo:
  1. Add gravity and wind
  2. Change alpha value with particle life


Update::

More details in next post