A plasma effect in C

Save this code to your computer with an appropriate name (such as plasma.c) and download the plasma images to go with it. Compile it with something like:

gcc -o plasma plasma.c -lbr -lm

and enjoy!


#include <stdio.h>
#include <math.h>
#include <SDL/SDL.h>
#include <SDL/SDL_mixer.h>
#include <SDL/SDL_image.h>
#include <brick.h>


/* Compile with: gcc -g -o plasma plasma.c -lm -lbr */


/*
 * a few configuration options
 */
#define SCREEN_W 256
#define SCREEN_H 180

#define IMG_W 500
#define IMG_H 400

#define WAVE_W (IMG_W+40)
#define WAVE_H (IMG_H+40)

#define DIFF_W (IMG_W - SCREEN_W)
#define DIFF_H (IMG_H - SCREEN_H)

#define SPR_CT 6

#define SPR_P1 0
#define SPR_P2 1
#define SPR_P3 2
#define SPR_P4 3
#define SPR_W1 4
#define SPR_W2 5




int main() {

  int i,j;

  /* layer vars */
  int layer_id;

  /* the sprite variables and setup information */
  struct sprite *sprites[SPR_CT];

  /* the displacement waves */
  short waves1[WAVE_H][WAVE_W][2];
  short waves2[WAVE_H][WAVE_W][2];

  /* the sprite offsets */
  float angles[SPR_CT], adders[SPR_CT];

  /* a struct to contain inputs */
  struct input io;

  /* initialize brick and create the layer */
  init_brick();

  layer_id = layer_add();
  layer_set_sorting( layer_id, 1 );
  layer_set_camera( layer_id, DIFF_W/2, DIFF_H/2 );


  /* load the plasma sprites */
  for( i=0; i < SPR_CT; i++ ) {
    sprites[i] = sprite_create();
    list_add( layer_get_sprite_list(layer_id), sprites[i] );
  }

  sprite_add_frame(sprites[SPR_P1], frame_convert(frame_from_disk("p1.png", NULL), FRAME_LT, NULL));
  sprite_set_z_hint(sprites[SPR_P1], 10);

  sprite_add_frame(sprites[SPR_P2], frame_convert(frame_from_disk("p2.png", NULL), FRAME_LT, NULL));
  sprite_set_z_hint(sprites[SPR_P2], 10);

  sprite_add_frame(sprites[SPR_P3], frame_convert(frame_from_disk("p3.png", NULL), FRAME_LT, NULL));
  sprite_set_z_hint(sprites[SPR_P3], 20);

  sprite_add_frame(sprites[SPR_P4], frame_convert(frame_from_disk("p4.png", NULL), FRAME_LT, NULL));
  sprite_set_z_hint(sprites[SPR_P4], 20);


  /* create the wave data for the displacment sprite */
  for( i=0; i < WAVE_H; i++ )
    for( j=0; j < WAVE_W; j++ ) {
      waves1[i][j][0] = (int)(-20.0 * sin(i*6.28/IMG_H));
      waves1[i][j][1] = (int)(-20.0 * sin(j*6.28/IMG_W));
      waves2[i][j][0] = (int)(20.0 * sin(i*6.28/IMG_H));
      waves2[i][j][1] = (int)(20.0 * sin(j*6.28/IMG_W));
    }

  /* and load the wave sprite data */
  sprite_add_frame_data(sprites[SPR_W1], FRAME_DISPL, WAVE_W, WAVE_H, waves1, NULL);
  sprite_add_frame_data(sprites[SPR_W2], FRAME_DISPL, WAVE_W, WAVE_H, waves2, NULL);
  sprite_set_z_hint(sprites[SPR_W1], 15);
  sprite_set_z_hint(sprites[SPR_W2], 30);


  /* open graphics! */
  graphics_open(GRAPHICS_ACCEL, SCREEN_W, SCREEN_H, 0, 3);
  render_set_bg_color(0, 0, 0);
  render_set_overdraw(40, 40);


  /* initialize the sprite position setters and enter the main loop */
  for( i=0; i < SPR_CT; i++ )
    angles[i] = 0;

  adders[SPR_P1] = .01;
  adders[SPR_P2] = .03;
  adders[SPR_P3] = .02;
  adders[SPR_P4] = .02;
  adders[SPR_W1] = .04;
  adders[SPR_W2] = .04;

  for(;;) {

    /* update the plasma sprites */
    for( i=0; i<4; i++ ) {
      angles[i] += adders[i];
      sprite_set_position(sprites[i], (int)( (DIFF_W/2 - 40) * cos(angles[i]) ), (int)( (DIFF_H/2 - 40) * sin(angles[i]) ));
    }

    /* and update the distorting waves */
    angles[SPR_W1] += adders[SPR_W1];
    sprite_set_position(sprites[SPR_W1], (int)( -40 + (DIFF_W/2 - 40) * cos(angles[SPR_W1]) ), (int)( -40 + (DIFF_H/2 - 40) * sin(angles[SPR_W1]) ));

    angles[SPR_W2] += adders[SPR_W2];
    sprite_set_position(sprites[SPR_W2], (int)( -20 + (DIFF_W/2 - 20) * cos(angles[SPR_W2]) ), (int)( -20 + (DIFF_H/2 - 20) * sin(angles[SPR_W2]) ));


    /* display the frame and run the delay loop */
    render_display();
    delay(50);

    /* quit on escape keypress */
    io_fetch(0, &io);
    if( io.esc || io_has_quit() )
       {
	  quit_brick();
	  exit(0);
       }

  }

}

 
demos/plasma_in_c.txt · Last modified: 2010/05/09 12:13 by steve