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);
}
}
}