else
{
level_free_gfx();
- level_free(¤t_level);
+ current_level.cleanup();
level_free_song();
unloadshared();
arrays_free();
save_hs(score);
}
level_free_gfx();
- level_free(¤t_level);
+ current_level.cleanup();
level_free_song();
unloadshared();
arrays_free();
tux.level_begin();
set_defaults();
- level_free(¤t_level);
+ current_level.cleanup();
if (st_gl_mode == ST_GL_LOAD_LEVEL_FILE)
{
}
else
{
- if(level_load(¤t_level,level_subset,level) != 0)
+ if(current_level.load(level_subset,level) != 0)
return 0;
}
}
else
{
- if(level_load(¤t_level, level_subset, level) != 0)
+ if(current_level.load(level_subset, level) != 0)
exit(1);
}
halt_music();
level_free_gfx();
- level_free(¤t_level);
+ current_level.cleanup();
level_free_song();
unloadshared();
arrays_free();
}
}
-
-/* What shape is at some position? */
-unsigned int shape(float x, float y)
-{
-
- int xx, yy;
- unsigned int c;
-
- yy = ((int)y / 32);
- xx = ((int)x / 32);
-
- if (yy >= 0 && yy < 15 && xx >= 0 && xx <= current_level.width)
- {
- c = current_level.ia_tiles[yy][xx];
- }
- else
- c = 0;
-
- return(c);
-}
-
-Tile* gettile(float x, float y)
-{
- return TileManager::instance()->get(shape(x, y));
-}
-
-bool issolid(float x, float y)
-{
- Tile* tile = TileManager::instance()->get
- (shape(x,y));
- if(tile)
- {
- if(tile->solid == true)
- return true;
- else
- return false;
- }
- else
- {
- return false;
- }
-}
-
-/* Is it a brick? */
-
-bool isbrick(float x, float y)
-{
- Tile* tile = TileManager::instance()->get
- (shape(x,y));
- if(tile)
- {
- if(tile->brick == true)
- return true;
- else
- return false;
- }
- else
- {
- return false;
- }
-}
-
-
-/* Is it ice? */
-
-bool isice(float x, float y)
-{
- Tile* tile = TileManager::instance()->get
- (shape(x,y));
- if(tile)
- {
- if(tile->ice == true)
- return true;
- else
- return false;
- }
- else
- {
- return false;
- }
-}
-
-/* Is it a full box? */
-
-bool isfullbox(float x, float y)
-{
- Tile* tile = TileManager::instance()->get
- (shape(x,y));
- if(tile)
- {
- if(tile->fullbox == true)
- return true;
- else
- return false;
- }
- else
- {
- return false;
- }
-}
-
-bool isdistro(float x, float y)
-{
- Tile* tile = TileManager::instance()->get(shape(x,y));
- return tile && tile->distro;
-}
-
/* Break a brick: */
void trybreakbrick(float x, float y, bool small)
{
(int)(y / 32) * 32);
play_sound(sounds[SND_BRICK], SOUND_CENTER_SPEAKER);
-
}
-
/* Empty a box: */
void tryemptybox(float x, float y, int col_side)
{
fread(&level,sizeof(int),1,fi);
set_defaults();
- level_free(¤t_level);
- if(level_load(¤t_level,level_subset,level) != 0)
+ current_level.cleanup();
+ if(current_level.load(level_subset,level) != 0)
exit(1);
arrays_free();
activate_bad_guys(¤t_level);
#define ST_GL_LOAD_GAME 2
#define ST_GL_LOAD_LEVEL_FILE 3
-extern int game_started;
+// FIXME: Make this local to the gamesession
extern st_level current_level;
+extern int game_started;
+
/* Function prototypes: */
class Tile;
-Tile* gettile(float x, float y);
-void activate_bad_guys(st_level* plevel);
-int gameloop(const char * subset, int levelnb, int mode);
-void savegame(int slot);
-void loadgame(int slot);
+void activate_bad_guys(st_level* plevel);
+int gameloop(const char * subset, int levelnb, int mode);
+void savegame(int slot);
+void loadgame(int slot);
std::string slotinfo(int slot);
-bool issolid(float x, float y);
-bool isbrick(float x, float y);
-bool isice(float x, float y);
-bool isfullbox(float x, float y);
-bool rectcollision(base_type* one, base_type* two);
-void drawshape(float x, float y, unsigned int c, Uint8 alpha = 255);
-unsigned int shape(float x, float y);
+
+bool rectcollision(base_type* one, base_type* two);
+void drawshape(float x, float y, unsigned int c, Uint8 alpha = 255);
void bumpbrick(float x, float y);
/** Try to grab the coin at the given coordinates */
#include "level.h"
#include "physic.h"
#include "scene.h"
+#include "tile.h"
#include "lispreader.h"
using namespace std;
new_subset.title = "Unknown Title";
new_subset.description = "No description so far.";
new_subset.save();
- level_default(&new_lev);
+ new_lev.init_defaults();
level_save(&new_lev,subset_name.c_str(),1);
}
levels = 0;
}
-void level_default(st_level* plevel)
+void
+st_level::init_defaults()
{
- int i,y;
- plevel->name = "UnNamed";
- plevel->theme = "antarctica";
- plevel->song_title = "Mortimers_chipdisko.mod";
- plevel->bkgd_image = "arctis.png";
- plevel->width = 21;
- plevel->time_left = 100;
- plevel->gravity = 10.;
- plevel->bkgd_red = 0;
- plevel->bkgd_green = 0;
- plevel->bkgd_blue = 0;
-
- for(i = 0; i < 15; ++i)
+ name = "UnNamed";
+ theme = "antarctica";
+ song_title = "Mortimers_chipdisko.mod";
+ bkgd_image = "arctis.png";
+ width = 21;
+ time_left = 100;
+ gravity = 10.;
+ bkgd_red = 0;
+ bkgd_green = 0;
+ bkgd_blue = 0;
+
+ for(int i = 0; i < 15; ++i)
{
- plevel->ia_tiles[i] = (unsigned int*) malloc((plevel->width+1)*sizeof(unsigned int));
- plevel->ia_tiles[i][plevel->width] = (unsigned int) '\0';
- for(y = 0; y < plevel->width; ++y)
- plevel->ia_tiles[i][y] = 0;
- plevel->ia_tiles[i][plevel->width] = (unsigned int) '\0';
-
- plevel->bg_tiles[i] = (unsigned int*) malloc((plevel->width+1)*sizeof(unsigned int));
- plevel->bg_tiles[i][plevel->width] = (unsigned int) '\0';
- for(y = 0; y < plevel->width; ++y)
- plevel->bg_tiles[i][y] = 0;
- plevel->bg_tiles[i][plevel->width] = (unsigned int) '\0';
-
- plevel->fg_tiles[i] = (unsigned int*) malloc((plevel->width+1)*sizeof(unsigned int));
- plevel->fg_tiles[i][plevel->width] = (unsigned int) '\0';
- for(y = 0; y < plevel->width; ++y)
- plevel->fg_tiles[i][y] = 0;
- plevel->fg_tiles[i][plevel->width] = (unsigned int) '\0';
+ ia_tiles[i] = (unsigned int*) malloc((width+1)*sizeof(unsigned int));
+ ia_tiles[i][width] = (unsigned int) '\0';
+ for(int y = 0; y < width; ++y)
+ ia_tiles[i][y] = 0;
+ ia_tiles[i][width] = (unsigned int) '\0';
+
+ bg_tiles[i] = (unsigned int*) malloc((width+1)*sizeof(unsigned int));
+ bg_tiles[i][width] = (unsigned int) '\0';
+ for(int y = 0; y < width; ++y)
+ bg_tiles[i][y] = 0;
+ bg_tiles[i][width] = (unsigned int) '\0';
+
+ fg_tiles[i] = (unsigned int*) malloc((width+1)*sizeof(unsigned int));
+ fg_tiles[i][width] = (unsigned int) '\0';
+ for(int y = 0; y < width; ++y)
+ fg_tiles[i][y] = 0;
+ fg_tiles[i][width] = (unsigned int) '\0';
}
}
/* Load data for this level: */
/* Returns -1, if the loading of the level failed. */
-int level_load(st_level* plevel, const char *subset, int level)
+int
+st_level::load(const char *subset, int level)
{
char filename[1024];
if(!faccessible(filename))
snprintf(filename, 1024, "%s/levels/%s/level%d.stl", datadir.c_str(), subset, level);
- return level_load(plevel, filename);
+ return level_load(this, filename);
}
int level_load(st_level* plevel, const char* filename)
/* Unload data for this level: */
-void level_free(st_level* plevel)
+void
+st_level::cleanup()
{
- int i;
- for(i=0; i < 15; ++i)
- free(plevel->bg_tiles[i]);
- for(i=0; i < 15; ++i)
- free(plevel->ia_tiles[i]);
- for(i=0; i < 15; ++i)
- free(plevel->fg_tiles[i]);
-
- plevel->name.clear();
- plevel->theme.clear();
- plevel->song_title.clear();
- plevel->bkgd_image.clear();
-
- plevel->badguy_data.clear();
+ for(int i=0; i < 15; ++i)
+ free(bg_tiles[i]);
+ for(int i=0; i < 15; ++i)
+ free(ia_tiles[i]);
+ for(int i=0; i < 15; ++i)
+ free(fg_tiles[i]);
+
+ name.clear();
+ theme.clear();
+ song_title.clear();
+ bkgd_image.clear();
+
+ badguy_data.clear();
}
/* Load graphics: */
free(song_subtitle);
free(song_path);
}
+
+
+unsigned int gettileid(float x, float y)
+{
+ int xx, yy;
+ unsigned int c;
+
+ yy = ((int)y / 32);
+ xx = ((int)x / 32);
+
+ if (yy >= 0 && yy < 15 && xx >= 0 && xx <= current_level.width)
+ c = current_level.ia_tiles[yy][xx];
+ else
+ c = 0;
+
+ return c;
+}
+
+Tile* gettile(float x, float y)
+{
+ return TileManager::instance()->get(gettileid(x, y));
+}
+
+bool issolid(float x, float y)
+{
+ Tile* tile = TileManager::instance()->get(gettileid(x,y));
+ return tile && tile->solid;
+}
+
+bool isbrick(float x, float y)
+{
+ Tile* tile = TileManager::instance()->get(gettileid(x,y));
+ return tile && tile->brick;
+}
+
+bool isice(float x, float y)
+{
+ Tile* tile = TileManager::instance()->get(gettileid(x,y));
+ return tile && tile->ice;
+}
+
+bool isfullbox(float x, float y)
+{
+ Tile* tile = TileManager::instance()->get(gettileid(x,y));
+ return tile && tile->fullbox;
+}
+
+bool isdistro(float x, float y)
+{
+ Tile* tile = TileManager::instance()->get(gettileid(x,y));
+ return tile && tile->distro;
+}
+
+/* EOF */
#include "badguy.h"
#include "lispreader.h"
-/* This type holds meta-information about a level-subset. */
-/* It could be extended to handle manipulation of subsets. */
+class Tile;
+
+/** This type holds meta-information about a level-subset.
+ It could be extended to handle manipulation of subsets. */
class st_subset
{
public:
std::vector<BadGuyData> badguy_data;
public:
+ /** Will the Level structure with default values */
+ void init_defaults();
+
+ /** Cleanup the level struct from allocated tile data and such */
+ void cleanup();
+
+ int load(const char * subset, int level);
};
-void level_default (st_level* plevel);
-int level_load (st_level* plevel, const char * subset, int level);
-void level_parse (st_level* plevel, lisp_object_t* cursor);
int level_load (st_level* plevel, const char* filename);
void level_save (st_level* plevel, const char * subset, int level);
-void level_free (st_level* plevel);
void level_load_gfx (st_level* plevel);
void level_change (st_level* plevel, float x, float y, int tm, unsigned int c);
void level_change_size (st_level* plevel, int new_width);
void level_load_image(texture_type* ptexture, std::string theme, const char * file, int use_alpha);
void level_free_song(void);
+/** Return the id of the tile at the given x/y coordinates */
+unsigned int gettileid(float x, float y);
+
+/** Return a pointer to the tile at the given x/y coordinates */
+Tile* gettile(float x, float y);
+
+// Some little helper function to check for tile properties
+bool issolid(float x, float y);
+bool isbrick(float x, float y);
+bool isice(float x, float y);
+bool isfullbox(float x, float y);
+
#endif /*SUPERTUX_LEVEL_H*/
arrays_free();
loadshared();
le_current_level = new st_level;
- if(level_load(le_current_level, le_level_subset.name.c_str(), le_level) != 0)
+ if(le_current_level->load(le_level_subset.name.c_str(), le_level) != 0)
{
le_quit();
return 1;
arrays_free();
loadshared();
le_current_level = new st_level;
- if(level_load(le_current_level, le_level_subset.name.c_str(), le_level) != 0)
+ if(le_current_level->load(le_level_subset.name.c_str(), le_level) != 0)
{
le_quit();
return 1;
{
arrays_free();
- level_free(le_current_level);
- if(level_load(le_current_level, le_level_subset.name.c_str(), levelnb) != 0)
+ le_current_level->cleanup();
+ if(le_current_level->load(le_level_subset.name.c_str(), levelnb) != 0)
{
- level_load(le_current_level, le_level_subset.name.c_str(), le_level);
+ le_current_level->load(le_level_subset.name.c_str(), le_level);
}
else
{
if(le_current_level != NULL)
{
level_free_gfx();
- level_free(le_current_level);
+ le_current_level->cleanup();
unloadshared();
arrays_free();
}
switch(event.key.keysym.sym)
{
case SDLK_y:
- level_default(&new_lev);
+ new_lev.init_defaults();
level_save(&new_lev,le_level_subset.name.c_str(),++le_level);
le_level_subset.levels = le_level;
le_goto_level(le_level);
}
else if (base.x> screen->w / 2 + scroll_x && scroll_x < ((current_level.width * 32) - screen->w))
{
- /* Scroll the screen in past center: */
+ // Scroll the screen in past center:
- scroll_x = base.x- screen->w / 2;
- /*base.x= 320 + scroll_x;*/
+ scroll_x = base.x - screen->w / 2;
if (scroll_x > ((current_level.width * 32) - screen->w))
scroll_x = ((current_level.width * 32) - screen->w);
void arrays_free(void)
{
-bad_guys.clear();
-bouncy_distros.clear();
-broken_bricks.clear();
-bouncy_bricks.clear();
-floating_scores.clear();
-upgrades.clear();
-bullets.clear();
-std::vector<ParticleSystem*>::iterator i;
-for(i = particle_systems.begin(); i != particle_systems.end(); ++i) {
- delete *i;
-}
-particle_systems.clear();
+ bad_guys.clear();
+ bouncy_distros.clear();
+ broken_bricks.clear();
+ bouncy_bricks.clear();
+ floating_scores.clear();
+ upgrades.clear();
+ bullets.clear();
+ std::vector<ParticleSystem*>::iterator i;
+ for(i = particle_systems.begin(); i != particle_systems.end(); ++i) {
+ delete *i;
+ }
+ particle_systems.clear();
}
void set_defaults(void)
{
- /* Set defaults: */
-
+ // Set defaults:
scroll_x = 0;
score_multiplier = 1;
// FIXME: Insert a real savegame struct/class here instead of
// doing string vodoo
std::string tmp = slotinfo(slot-1);
+
if (tmp.length() == strlen("Slot X - Free"))
- {
+ { // Slot is free, so start a new game
gameloop("default", 1, ST_GL_PLAY);
show_menu = true;
Menu::set_current(main_menu);
}
else
- {
+ { // Slot contains a level, so load it
if (game_started)
{
gameloop("default",slot - 1,ST_GL_LOAD_GAME);
(*p)->simulate(frame_ratio);
}
- /* Draw particle systems (background) */
+ // Draw particle systems (background)
for(p = particle_systems.begin(); p != particle_systems.end(); ++p)
{
(*p)->draw(scroll_x, 0, 0);
}
- /* Draw interactive tiles: */
-
+ // Draw interactive tiles:
for (int y = 0; y < 15; ++y)
{
for (int x = 0; x < 21; ++x)
void bouncy_distro_action(bouncy_distro_type* pbouncy_distro)
{
- pbouncy_distro->base.y = pbouncy_distro->base.y + pbouncy_distro->base.ym * frame_ratio;
+ pbouncy_distro->base.y = pbouncy_distro->base.y + pbouncy_distro->base.ym * frame_ratio;
- pbouncy_distro->base.ym += 0.1 * frame_ratio;
+ pbouncy_distro->base.ym += 0.1 * frame_ratio;
- if (pbouncy_distro->base.ym >= 0)
- bouncy_distros.erase(static_cast<std::vector<bouncy_distro_type>::iterator>(pbouncy_distro));
+ if (pbouncy_distro->base.ym >= 0)
+ bouncy_distros.erase(static_cast<std::vector<bouncy_distro_type>::iterator>(pbouncy_distro));
}
void bouncy_distro_draw(bouncy_distro_type* pbouncy_distro)
{
- texture_draw(&img_distro[0],
- pbouncy_distro->base.x - scroll_x,
- pbouncy_distro->base.y);
+ texture_draw(&img_distro[0],
+ pbouncy_distro->base.x - scroll_x,
+ pbouncy_distro->base.y);
}
void broken_brick_init(broken_brick_type* pbroken_brick, float x, float y, float xm, float ym)
void broken_brick_action(broken_brick_type* pbroken_brick)
{
- pbroken_brick->base.x = pbroken_brick->base.x + pbroken_brick->base.xm * frame_ratio;
- pbroken_brick->base.y = pbroken_brick->base.y + pbroken_brick->base.ym * frame_ratio;
+ pbroken_brick->base.x = pbroken_brick->base.x + pbroken_brick->base.xm * frame_ratio;
+ pbroken_brick->base.y = pbroken_brick->base.y + pbroken_brick->base.ym * frame_ratio;
- if (!timer_check(&pbroken_brick->timer))
- broken_bricks.erase(static_cast<std::vector<broken_brick_type>::iterator>(pbroken_brick));
+ if (!timer_check(&pbroken_brick->timer))
+ broken_bricks.erase(static_cast<std::vector<broken_brick_type>::iterator>(pbroken_brick));
}
void broken_brick_draw(broken_brick_type* pbroken_brick)
{
-SDL_Rect src, dest;
- src.x = rand() % 16;
- src.y = rand() % 16;
- src.w = 16;
- src.h = 16;
-
- dest.x = (int)(pbroken_brick->base.x - scroll_x);
- dest.y = (int)pbroken_brick->base.y;
- dest.w = 16;
- dest.h = 16;
-
- texture_draw_part(&img_brick[0],src.x,src.y,dest.x,dest.y,dest.w,dest.h);
+ SDL_Rect src, dest;
+ src.x = rand() % 16;
+ src.y = rand() % 16;
+ src.w = 16;
+ src.h = 16;
+
+ dest.x = (int)(pbroken_brick->base.x - scroll_x);
+ dest.y = (int)pbroken_brick->base.y;
+ dest.w = 16;
+ dest.h = 16;
+
+ texture_draw_part(&img_brick[0],src.x,src.y,dest.x,dest.y,dest.w,dest.h);
}
void bouncy_brick_init(bouncy_brick_type* pbouncy_brick, float x, float y)
pbouncy_brick->base.y = y;
pbouncy_brick->offset = 0;
pbouncy_brick->offset_m = -BOUNCY_BRICK_SPEED;
- pbouncy_brick->shape = shape(x, y);
+ pbouncy_brick->shape = gettileid(x, y);
}
void bouncy_brick_action(bouncy_brick_type* pbouncy_brick)
{
- pbouncy_brick->offset = (pbouncy_brick->offset +
- pbouncy_brick->offset_m * frame_ratio);
+ pbouncy_brick->offset = (pbouncy_brick->offset +
+ pbouncy_brick->offset_m * frame_ratio);
- /* Go back down? */
+ /* Go back down? */
- if (pbouncy_brick->offset < -BOUNCY_BRICK_MAX_OFFSET)
- pbouncy_brick->offset_m = BOUNCY_BRICK_SPEED;
+ if (pbouncy_brick->offset < -BOUNCY_BRICK_MAX_OFFSET)
+ pbouncy_brick->offset_m = BOUNCY_BRICK_SPEED;
- /* Stop bouncing? */
+ /* Stop bouncing? */
- if (pbouncy_brick->offset >= 0)
- bouncy_bricks.erase(static_cast<std::vector<bouncy_brick_type>::iterator>(pbouncy_brick));
+ if (pbouncy_brick->offset >= 0)
+ bouncy_bricks.erase(static_cast<std::vector<bouncy_brick_type>::iterator>(pbouncy_brick));
}
void bouncy_brick_draw(bouncy_brick_type* pbouncy_brick)
int s;
SDL_Rect dest;
- if (pbouncy_brick->base.x >= scroll_x - 32 &&
- pbouncy_brick->base.x <= scroll_x + screen->w)
+ if (pbouncy_brick->base.x >= scroll_x - 32 &&
+ pbouncy_brick->base.x <= scroll_x + screen->w)
+ {
+ dest.x = (int)(pbouncy_brick->base.x - scroll_x);
+ dest.y = (int)pbouncy_brick->base.y;
+ dest.w = 32;
+ dest.h = 32;
+
+ // FIXME: overdrawing hack to clean the tile from the screen to
+ // paint it later at on offseted position
+ if(current_level.bkgd_image[0] == '\0')
{
- dest.x = (int)(pbouncy_brick->base.x - scroll_x);
- dest.y = (int)pbouncy_brick->base.y;
- dest.w = 32;
- dest.h = 32;
-
- if(current_level.bkgd_image[0] == '\0')
- {
- fillrect(pbouncy_brick->base.x - scroll_x,pbouncy_brick->base.y,32,32,current_level.bkgd_red,current_level.bkgd_green,
- current_level.bkgd_blue,0);
- }
- else
- {
- s = (int)scroll_x / 30;
- texture_draw_part(&img_bkgd,dest.x + s,dest.y,dest.x,dest.y,dest.w,dest.h);
- }
-
- drawshape(pbouncy_brick->base.x - scroll_x,
- pbouncy_brick->base.y + pbouncy_brick->offset,
- pbouncy_brick->shape);
+ fillrect(pbouncy_brick->base.x - scroll_x, pbouncy_brick->base.y,
+ 32,32,current_level.bkgd_red,current_level.bkgd_green,
+ current_level.bkgd_blue,0);
}
+ else
+ {
+ s = (int)scroll_x / 30;
+ texture_draw_part(&img_bkgd,dest.x + s,dest.y,dest.x,dest.y,dest.w,dest.h);
+ }
+
+ drawshape(pbouncy_brick->base.x - scroll_x,
+ pbouncy_brick->base.y + pbouncy_brick->offset,
+ pbouncy_brick->shape);
+ }
}
void floating_score_init(floating_score_type* pfloating_score, float x, float y, int s)
void floating_score_action(floating_score_type* pfloating_score)
{
- pfloating_score->base.y = pfloating_score->base.y - 2 * frame_ratio;
+ pfloating_score->base.y = pfloating_score->base.y - 2 * frame_ratio;
- if(!timer_check(&pfloating_score->timer))
- floating_scores.erase(static_cast<std::vector<floating_score_type>::iterator>(pfloating_score));
+ if(!timer_check(&pfloating_score->timer))
+ floating_scores.erase(static_cast<std::vector<floating_score_type>::iterator>(pfloating_score));
}
void floating_score_draw(floating_score_type* pfloating_score)
{
- char str[10];
- sprintf(str, "%d", pfloating_score->value);
- text_draw(&gold_text, str, (int)pfloating_score->base.x + 16 - strlen(str) * 8, (int)pfloating_score->base.y, 1);
+ char str[10];
+ sprintf(str, "%d", pfloating_score->value);
+ text_draw(&gold_text, str, (int)pfloating_score->base.x + 16 - strlen(str) * 8, (int)pfloating_score->base.y, 1);
}
+/* EOF */
+