forked from tas/major_tom
Distance-based sound effects with stereo panning for explosions, impacts, and pickups. Spacecraft entity with full state machine (fly-in, land, take off, fly-out), engine/synth sound loops, thruster particles, and PNG spritesheet. Moon level intro defers player spawn until ship lands. Also untrack build/ objects that were committed by mistake.
119 lines
5.1 KiB
C
119 lines
5.1 KiB
C
#include "game/entity_registry.h"
|
|
#include "game/player.h"
|
|
#include "game/enemy.h"
|
|
#include "game/projectile.h"
|
|
#include "game/hazards.h"
|
|
#include "game/powerup.h"
|
|
#include "game/drone.h"
|
|
#include "game/spacecraft.h"
|
|
#include <string.h>
|
|
#include <stdio.h>
|
|
|
|
EntityRegistry g_entity_registry = {0};
|
|
|
|
/* ── Wrapper spawn functions ──────────────────────
|
|
* Some spawn functions need extra args beyond (em, pos).
|
|
* We wrap them to match the EntitySpawnFn signature.
|
|
* ──────────────────────────────────────────────────── */
|
|
|
|
static Entity *spawn_platform_v(EntityManager *em, Vec2 pos) {
|
|
return mplat_spawn_dir(em, pos, vec2(0.0f, 1.0f));
|
|
}
|
|
|
|
static Entity *spawn_powerup_health(EntityManager *em, Vec2 pos) {
|
|
return powerup_spawn_health(em, pos);
|
|
}
|
|
|
|
static Entity *spawn_powerup_jetpack(EntityManager *em, Vec2 pos) {
|
|
return powerup_spawn_jetpack(em, pos);
|
|
}
|
|
|
|
static Entity *spawn_powerup_drone(EntityManager *em, Vec2 pos) {
|
|
return powerup_spawn_drone(em, pos);
|
|
}
|
|
|
|
static Entity *spawn_powerup_gun(EntityManager *em, Vec2 pos) {
|
|
return powerup_spawn_gun(em, pos);
|
|
}
|
|
|
|
/* ── Registry population ─────────────────────────── */
|
|
|
|
static void reg_add(const char *name, const char *display,
|
|
EntitySpawnFn fn, SDL_Color color, int w, int h) {
|
|
EntityRegistry *r = &g_entity_registry;
|
|
if (r->count >= MAX_REGISTRY_ENTRIES) return;
|
|
r->entries[r->count++] = (EntityRegEntry){
|
|
.name = name,
|
|
.display = display,
|
|
.spawn_fn = fn,
|
|
.color = color,
|
|
.width = w,
|
|
.height = h,
|
|
};
|
|
}
|
|
|
|
void entity_registry_init(EntityManager *em) {
|
|
g_entity_registry.count = 0;
|
|
|
|
/* Register all entity behaviors with the entity manager */
|
|
player_register(em);
|
|
player_set_entity_manager(em);
|
|
grunt_register(em);
|
|
flyer_register(em);
|
|
projectile_register(em);
|
|
turret_register(em);
|
|
mplat_register(em);
|
|
flame_vent_register(em);
|
|
force_field_register(em);
|
|
powerup_register(em);
|
|
drone_register(em);
|
|
asteroid_register(em);
|
|
spacecraft_register(em);
|
|
|
|
/* ════════════════════════════════════════════
|
|
* REGISTRY TABLE
|
|
*
|
|
* To add a new entity type to the game:
|
|
* 1. Create its .h/.c files
|
|
* 2. Register its behaviors above
|
|
* 3. Add one reg_add() line below
|
|
*
|
|
* The editor will pick it up automatically.
|
|
* ════════════════════════════════════════════ */
|
|
|
|
/* .lvl name display name spawn fn color (editor) w h */
|
|
reg_add("grunt", "Grunt", grunt_spawn, (SDL_Color){200, 60, 60, 255}, GRUNT_WIDTH, GRUNT_HEIGHT);
|
|
reg_add("flyer", "Flyer", flyer_spawn, (SDL_Color){140, 80, 200, 255}, FLYER_WIDTH, FLYER_HEIGHT);
|
|
reg_add("turret", "Turret", turret_spawn, (SDL_Color){160, 160, 160, 255}, TURRET_WIDTH, TURRET_HEIGHT);
|
|
reg_add("platform", "Platform (H)", mplat_spawn, (SDL_Color){80, 180, 80, 255}, MPLAT_WIDTH, MPLAT_HEIGHT);
|
|
reg_add("platform_v", "Platform (V)", spawn_platform_v, (SDL_Color){80, 160, 100, 255}, MPLAT_WIDTH, MPLAT_HEIGHT);
|
|
reg_add("flame_vent", "Flame Vent", flame_vent_spawn, (SDL_Color){255, 120, 40, 255}, FLAME_WIDTH, FLAME_HEIGHT);
|
|
reg_add("force_field", "Force Field", force_field_spawn, (SDL_Color){60, 140, 255, 255}, FFIELD_WIDTH, FFIELD_HEIGHT);
|
|
reg_add("powerup_hp", "Health Pickup", spawn_powerup_health, (SDL_Color){255, 80, 80, 255}, 12, 12);
|
|
reg_add("powerup_jet", "Jetpack Refill", spawn_powerup_jetpack,(SDL_Color){255, 200, 50, 255}, 12, 12);
|
|
reg_add("powerup_drone", "Drone Pickup", spawn_powerup_drone, (SDL_Color){80, 200, 255, 255}, 12, 12);
|
|
reg_add("powerup_gun", "Gun Pickup", spawn_powerup_gun, (SDL_Color){200, 200, 220, 255}, 12, 12);
|
|
reg_add("asteroid", "Asteroid", asteroid_spawn, (SDL_Color){140, 110, 80, 255}, ASTEROID_WIDTH, ASTEROID_HEIGHT);
|
|
reg_add("spacecraft", "Spacecraft", spacecraft_spawn, (SDL_Color){187, 187, 187, 255}, SPACECRAFT_WIDTH, SPACECRAFT_HEIGHT);
|
|
|
|
printf("Entity registry: %d types registered\n", g_entity_registry.count);
|
|
}
|
|
|
|
const EntityRegEntry *entity_registry_find(const char *name) {
|
|
for (int i = 0; i < g_entity_registry.count; i++) {
|
|
if (strcmp(g_entity_registry.entries[i].name, name) == 0) {
|
|
return &g_entity_registry.entries[i];
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
Entity *entity_registry_spawn(EntityManager *em, const char *name, Vec2 pos) {
|
|
const EntityRegEntry *entry = entity_registry_find(name);
|
|
if (!entry) {
|
|
fprintf(stderr, "entity_registry_spawn: unknown type '%s'\n", name);
|
|
return NULL;
|
|
}
|
|
return entry->spawn_fn(em, pos);
|
|
}
|