Back to index

extremetuxracer  0.5beta
Functions
ui_snow.h File Reference
#include "ppgltk/ppgltk.h"
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

void init_ui_snow (void)
void update_ui_snow (double time_step, bool windy)
void push_ui_snow (pp::Vec2d pos)
void draw_ui_snow (void)
void make_ui_snow (pp::Vec2d pos)
void reset_ui_snow_cursor_pos (pp::Vec2d pos)

Function Documentation

void draw_ui_snow ( void  )

Definition at line 212 of file ui_snow.cpp.

{
    GLuint   texture_id;
    char *binding;
    pp::Vec2d *pt, *tex_min, *tex_max;
    double size;
    double xres, yres;
    int i;

    xres = getparam_x_resolution();
    yres = getparam_y_resolution();
    
    UIMgr.setupDisplay();

    binding = "ui_snow_particle";
    if (!get_texture_binding( "ui_snow_particle", &texture_id ) ) {
       print_warning( IMPORTANT_WARNING,
                     "Couldn't get texture for binding %s", 
                     binding );
       texture_id = 0;
    } 

    glTexEnvf( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );

    glBindTexture( GL_TEXTURE_2D, texture_id );

    glColor4f( particleColor[0], 
              particleColor[1], 
              particleColor[2],
              particleColor[3] );

    glPushMatrix();
    {
       for ( i=0; i<num_particles; i++) {
           pt = &particles[i].pt;
           size = particles[i].size;
           tex_min = &particles[i].tex_min;
           tex_max = &particles[i].tex_max;
           glPushMatrix();
           {
              glTranslatef( pt->x*xres, pt->y*yres, 0 );
              glBegin( GL_QUADS );
              {
                  glTexCoord2f( tex_min->x, tex_min->y );
                  glVertex2f( 0, 0 );
                  glTexCoord2f( tex_max->x, tex_min->y );
                  glVertex2f( size, 0 );
                  glTexCoord2f( tex_max->x, tex_max->y );
                  glVertex2f( size, size );
                  glTexCoord2f( tex_min->x, tex_max->y );
                  glVertex2f( 0, size );
              }
              glEnd();
           }
           glPopMatrix();
       } 
    }
    glPopMatrix();

} 

Here is the call graph for this function:

Here is the caller graph for this function:

void init_ui_snow ( void  )

Definition at line 102 of file ui_snow.cpp.

{
    int i;

    for( i=0; i<num_particles; i++) {
       make_particle( i, frand(), frand() );
    }
    push_position = pp::Vec2d( 0.0, 0.0 );
}

Here is the call graph for this function:

Here is the caller graph for this function:

void make_ui_snow ( pp::Vec2d  pos)

Definition at line 302 of file ui_snow.cpp.

                            {
    double xres, yres;

    xres = getparam_x_resolution();
    yres = getparam_y_resolution();

    if ( num_particles < MAX_NUM_PARTICLES ) {
       make_particle( num_particles, pos.x/xres, pos.y/yres );
       num_particles++;
    }
}

Here is the call graph for this function:

Here is the caller graph for this function:

void push_ui_snow ( pp::Vec2d  pos)

Definition at line 287 of file ui_snow.cpp.

{
    double xres, yres;

    xres = getparam_x_resolution();
    yres = getparam_y_resolution();
    push_position = pp::Vec2d( pos.x/(double)xres,
                              pos.y/(double)yres );
    if ( !push_position_initialized ) {
       last_push_position = push_position;
    }
    push_position_initialized = true;
}

Here is the caller graph for this function:

Definition at line 274 of file ui_snow.cpp.

{
    double xres, yres;

    xres = getparam_x_resolution();
    yres = getparam_y_resolution();
    push_position = pp::Vec2d( pos.x/(double)xres,
                              pos.y/(double)yres );
    last_push_position = push_position;
    push_position_initialized = true;
}

Here is the caller graph for this function:

void update_ui_snow ( double  time_step,
bool  windy 
)

Definition at line 112 of file ui_snow.cpp.

{
    pp::Vec2d *v, f;
    pp::Vec2d *pt;
    double size;
    double dist_from_push, p_dist;
    pp::Vec2d push_vector;
    int i;
    double push_timestep, time;

    time = getClockTime();

    push_vector.x = 0;
    push_vector.y = 0;
    push_timestep = 0;
       
    if ( push_position_initialized ) {
       push_vector.x = push_position.x - last_push_position.x;
       push_vector.y = push_position.y - last_push_position.y;
       push_timestep = time - last_update_time;
    }
    last_push_position = push_position;
    last_update_time = time;

    for ( i=0; i<num_particles; i++) {
       pt = &particles[i].pt;
       v = &particles[i].vel;
       size = particles[i].size;

       f.x = 0;
       f.y = 0;

       /* Mouse push and gravity */
       dist_from_push = (pow((pt->x - push_position.x), 2) +
                       pow((pt->y - push_position.y), 2));
       if ( push_timestep > 0 ) {
           f.x = PUSH_FACTOR * push_vector.x / push_timestep; 
           
           f.y = PUSH_FACTOR * push_vector.y / push_timestep; 

           f.x = min(MAX_PUSH_FORCE,f.x);
           f.x = max(-MAX_PUSH_FORCE,f.x);
           f.y = min(MAX_PUSH_FORCE,f.y);
           f.y = max(-MAX_PUSH_FORCE,f.y);

           f.x *= 1.0/(PUSH_DIST_DECAY*dist_from_push + 1) * 
              size/PARTICLE_SIZE_RANGE;
           f.y *= 1.0/(PUSH_DIST_DECAY*dist_from_push + 1) *
              size/PARTICLE_SIZE_RANGE;
       }

       /* Update velocity */
       v->x += ( f.x + ( windy ? WIND_FORCE : 0.0 ) - v->x * AIR_DRAG ) * 
           time_step;
       v->y += ( f.y - GRAVITY_FACTOR - v->y * AIR_DRAG ) * 
           time_step;

       /* Update position */
        pt->x += v->x * time_step * ( size / PARTICLE_SIZE_RANGE ); 
        pt->y += v->y * time_step * ( size / PARTICLE_SIZE_RANGE );

       if ( pt->x < 0 ) {
           pt->x = 1;
       } else if ( pt->x > 1 ) {
           pt->x = 0.0;
       }
    }

    /* Kill off & regenerate particles */
    for (i=0; i<num_particles; i++) {
       particle_t *p = &particles[i];

       if (p->pt.y < -0.05) {
           /* If we have an excess of particles, kill off with
              50% probability */
           if ( num_particles > BASE_NUM_PARTICLES && frand() > 0.5 ) {
              /* Delete the particle */
              *p = particles[num_particles-1];
              num_particles -= 1;
           } else {
              p->pt.x = frand();
              p->pt.y = 1+frand()*BASE_VELOCITY;
              p_dist = frand();
              p->size = PARTICLE_MIN_SIZE + 
                  ( 1.0 - p_dist ) * PARTICLE_SIZE_RANGE;
              p->vel.x = 0;
              p->vel.y = -BASE_VELOCITY-p_dist*VELOCITY_RANGE;
           }
       }
    }

    if ( time_step < PUSH_DECAY_TIME_CONSTANT ) {
       push_vector.x *= 1.0 - time_step/PUSH_DECAY_TIME_CONSTANT;
       push_vector.y *= 1.0 - time_step/PUSH_DECAY_TIME_CONSTANT;
    } else {
       push_vector.x = 0.0;
       push_vector.y = 0.0;
    }
} 

Here is the call graph for this function:

Here is the caller graph for this function: