Draw jumpgate portal in jumpgate.c. Use systemPower instead of ALIVE_SLEEPING to determine status.
This commit is contained in:
parent
5267b7b559
commit
7118c10648
|
@ -94,13 +94,13 @@ void doCapitalShip(void)
|
|||
if (self->side == SIDE_ALLIES)
|
||||
{
|
||||
battle.stats[STAT_CAPITAL_SHIPS_LOST]++;
|
||||
|
||||
|
||||
runScriptFunction("CAPITAL_SHIPS_LOST %d", battle.stats[STAT_CAPITAL_SHIPS_LOST]);
|
||||
}
|
||||
else
|
||||
{
|
||||
battle.stats[STAT_CAPITAL_SHIPS_DESTROYED]++;
|
||||
|
||||
|
||||
runScriptFunction("CAPITAL_SHIPS_DESTROYED %d", battle.stats[STAT_CAPITAL_SHIPS_DESTROYED]);
|
||||
}
|
||||
}
|
||||
|
@ -356,7 +356,7 @@ static void loadCapitalShipDef(char *filename)
|
|||
|
||||
e->type = ET_CAPITAL_SHIP;
|
||||
e->active = 1;
|
||||
|
||||
|
||||
STRNCPY(e->name, cJSON_GetObjectItem(root, "name")->valuestring, MAX_NAME_LENGTH);
|
||||
STRNCPY(e->defName, e->name, MAX_NAME_LENGTH);
|
||||
e->shield = e->maxShield = cJSON_GetObjectItem(root, "shield")->valueint;
|
||||
|
@ -379,7 +379,7 @@ static void loadCapitalShipDef(char *filename)
|
|||
|
||||
cJSON_Delete(root);
|
||||
}
|
||||
|
||||
|
||||
free(text);
|
||||
}
|
||||
|
||||
|
@ -421,7 +421,7 @@ static void loadComponents(Entity *parent, cJSON *components)
|
|||
e->aiFlags = flagsToLong(cJSON_GetObjectItem(component, "aiFlags")->valuestring, NULL);
|
||||
}
|
||||
|
||||
e->systemPower = 100;
|
||||
e->systemPower = MAX_SYSTEM_POWER;
|
||||
|
||||
e->die = componentDie;
|
||||
|
||||
|
@ -475,7 +475,7 @@ static void loadGuns(Entity *parent, cJSON *guns)
|
|||
|
||||
SDL_QueryTexture(e->texture, NULL, NULL, &e->w, &e->h);
|
||||
|
||||
e->systemPower = 100;
|
||||
e->systemPower = MAX_SYSTEM_POWER;
|
||||
|
||||
e->action = gunThink;
|
||||
e->die = gunDie;
|
||||
|
@ -518,7 +518,7 @@ static void loadEngines(Entity *parent, cJSON *engines)
|
|||
|
||||
SDL_QueryTexture(e->texture, NULL, NULL, &e->w, &e->h);
|
||||
|
||||
e->systemPower = 100;
|
||||
e->systemPower = MAX_SYSTEM_POWER;
|
||||
|
||||
e->action = engineThink;
|
||||
e->die = engineDie;
|
||||
|
|
|
@ -31,8 +31,6 @@ static int drawComparator(const void *a, const void *b);
|
|||
static void notifyNewArrivals(void);
|
||||
static int isCapitalShipComponent(Entity *e);
|
||||
|
||||
static SDL_Texture *jumpPortal;
|
||||
static float jumpPortAngle;
|
||||
static Entity deadHead;
|
||||
static Entity *deadTail;
|
||||
static int disabledGlow;
|
||||
|
@ -41,14 +39,11 @@ static int disabledGlowDir;
|
|||
void initEntities(void)
|
||||
{
|
||||
memset(&deadHead, 0, sizeof(Entity));
|
||||
|
||||
|
||||
deadTail = &deadHead;
|
||||
|
||||
|
||||
disabledGlow = DISABLED_GLOW_MAX;
|
||||
disabledGlowDir = -DISABLED_GLOW_SPEED;
|
||||
|
||||
jumpPortal = getTexture("gfx/entities/portal.png");
|
||||
jumpPortAngle = 0;
|
||||
}
|
||||
|
||||
Entity *spawnEntity(void)
|
||||
|
@ -57,10 +52,10 @@ Entity *spawnEntity(void)
|
|||
memset(e, 0, sizeof(Entity));
|
||||
e->id = battle.entId++;
|
||||
e->active = 1;
|
||||
|
||||
|
||||
battle.entityTail->next = e;
|
||||
battle.entityTail = e;
|
||||
|
||||
|
||||
return e;
|
||||
}
|
||||
|
||||
|
@ -69,33 +64,33 @@ void doEntities(void)
|
|||
int numAllies, numEnemies;
|
||||
int numActiveAllies, numActiveEnemies;
|
||||
Entity *e, *prev;
|
||||
|
||||
|
||||
prev = &battle.entityHead;
|
||||
|
||||
|
||||
numAllies = numEnemies = numActiveAllies = numActiveEnemies = 0;
|
||||
|
||||
|
||||
if (dev.playerImmortal)
|
||||
{
|
||||
player->health = player->maxHealth;
|
||||
player->shield = player->maxShield;
|
||||
}
|
||||
|
||||
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
{
|
||||
removeFromQuadtree(e, &battle.quadtree);
|
||||
|
||||
|
||||
if (dev.allImmortal)
|
||||
{
|
||||
e->health = e->maxHealth;
|
||||
e->shield = e->maxShield;
|
||||
}
|
||||
|
||||
|
||||
if (e->active)
|
||||
{
|
||||
self = e;
|
||||
|
||||
|
||||
e->reload = MAX(e->reload - 1, 0);
|
||||
|
||||
|
||||
if (e->shieldRechargeRate)
|
||||
{
|
||||
if (e->shield >= 0)
|
||||
|
@ -103,7 +98,7 @@ void doEntities(void)
|
|||
if (--e->shieldRecharge <= 0)
|
||||
{
|
||||
e->shield = MIN(e->shield + 1, e->maxShield);
|
||||
|
||||
|
||||
e->shieldRecharge = e->shieldRechargeRate;
|
||||
}
|
||||
}
|
||||
|
@ -112,34 +107,34 @@ void doEntities(void)
|
|||
e->shield++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
e->armourHit = MAX(e->armourHit - 25, 0);
|
||||
e->shieldHit = MAX(e->shieldHit - 5, 0);
|
||||
e->systemHit = MAX(e->systemHit - 25, 0);
|
||||
|
||||
|
||||
e->aiDamageTimer = MAX(e->aiDamageTimer - 1, 0);
|
||||
if (!e->aiDamageTimer)
|
||||
{
|
||||
e->aiDamagePerSec = 0;
|
||||
e->aiFlags &= ~AIF_EVADE;
|
||||
}
|
||||
|
||||
|
||||
switch (e->type)
|
||||
{
|
||||
case ET_FIGHTER:
|
||||
doFighter();
|
||||
break;
|
||||
|
||||
|
||||
case ET_CAPITAL_SHIP:
|
||||
doCapitalShip();
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
doEntity();
|
||||
break;
|
||||
}
|
||||
|
||||
if (e->alive == ALIVE_ALIVE || e->alive == ALIVE_DYING || e->alive == ALIVE_SLEEPING)
|
||||
|
||||
if (e->alive == ALIVE_ALIVE || e->alive == ALIVE_DYING)
|
||||
{
|
||||
if (e->action != NULL)
|
||||
{
|
||||
|
@ -147,26 +142,26 @@ void doEntities(void)
|
|||
{
|
||||
e->thinkTime = 2;
|
||||
}
|
||||
|
||||
|
||||
if (--e->thinkTime <= 0)
|
||||
{
|
||||
e->thinkTime = 0;
|
||||
e->action();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
doRope(e);
|
||||
|
||||
|
||||
restrictToBattleArea(e);
|
||||
|
||||
|
||||
if (!e->speed)
|
||||
{
|
||||
e->dx = e->dy = 0;
|
||||
}
|
||||
|
||||
|
||||
e->x += e->dx;
|
||||
e->y += e->dy;
|
||||
|
||||
|
||||
if (!isCapitalShipComponent(e))
|
||||
{
|
||||
addToQuadtree(e, &battle.quadtree);
|
||||
|
@ -178,38 +173,38 @@ void doEntities(void)
|
|||
{
|
||||
battle.entityTail = prev;
|
||||
}
|
||||
|
||||
|
||||
if (e == battle.missionTarget)
|
||||
{
|
||||
battle.missionTarget = NULL;
|
||||
}
|
||||
|
||||
|
||||
if (e == player)
|
||||
{
|
||||
player = NULL;
|
||||
|
||||
|
||||
battle.playerSelect = battle.isEpic;
|
||||
}
|
||||
|
||||
|
||||
cutRope(e);
|
||||
|
||||
|
||||
prev->next = e->next;
|
||||
|
||||
|
||||
/* move to dead list */
|
||||
e->next = NULL;
|
||||
deadTail->next = e;
|
||||
deadTail = e;
|
||||
|
||||
|
||||
e = prev;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (e->type == ET_FIGHTER || e->type == ET_CAPITAL_SHIP)
|
||||
{
|
||||
if (e->side == SIDE_ALLIES)
|
||||
{
|
||||
numAllies++;
|
||||
|
||||
|
||||
if (e->health > 0 && e->active)
|
||||
{
|
||||
numActiveAllies++;
|
||||
|
@ -218,37 +213,37 @@ void doEntities(void)
|
|||
else
|
||||
{
|
||||
numEnemies++;
|
||||
|
||||
|
||||
if (e->health > 0 && e->active)
|
||||
{
|
||||
numActiveEnemies++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
prev = e;
|
||||
}
|
||||
|
||||
|
||||
battle.numAllies = (battle.isEpic) ? numAllies : numActiveAllies;
|
||||
battle.numEnemies = (battle.isEpic) ? numEnemies : numActiveEnemies;
|
||||
|
||||
|
||||
if (battle.isEpic && battle.stats[STAT_TIME] % FPS == 0)
|
||||
{
|
||||
if (numAllies > battle.epicFighterLimit)
|
||||
{
|
||||
activateEpicFighters(battle.epicFighterLimit - numActiveAllies, SIDE_ALLIES);
|
||||
}
|
||||
|
||||
|
||||
if (numEnemies > battle.epicFighterLimit)
|
||||
{
|
||||
activateEpicFighters(battle.epicFighterLimit - numActiveEnemies, SIDE_NONE);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
alignComponents();
|
||||
|
||||
|
||||
disabledGlow = MAX(DISABLED_GLOW_MIN, MIN(disabledGlow + disabledGlowDir, DISABLED_GLOW_MAX));
|
||||
|
||||
|
||||
if (disabledGlow <= DISABLED_GLOW_MIN)
|
||||
{
|
||||
disabledGlowDir = DISABLED_GLOW_SPEED;
|
||||
|
@ -257,39 +252,33 @@ void doEntities(void)
|
|||
{
|
||||
disabledGlowDir = -DISABLED_GLOW_SPEED;
|
||||
}
|
||||
|
||||
jumpPortAngle += 0.5;
|
||||
if (jumpPortAngle >= 360)
|
||||
{
|
||||
jumpPortAngle -= 360;
|
||||
}
|
||||
}
|
||||
|
||||
static void restrictToBattleArea(Entity *e)
|
||||
{
|
||||
float force;
|
||||
|
||||
|
||||
if (e->x <= BATTLE_AREA_EDGE)
|
||||
{
|
||||
force = BATTLE_AREA_EDGE - e->x;
|
||||
e->dx += force * 0.001;
|
||||
e->dx *= 0.95;
|
||||
}
|
||||
|
||||
|
||||
if (e->y <= BATTLE_AREA_EDGE)
|
||||
{
|
||||
force = BATTLE_AREA_EDGE - e->y;
|
||||
e->dy += force * 0.001;
|
||||
e->dy *= 0.95;
|
||||
}
|
||||
|
||||
|
||||
if (e->x >= BATTLE_AREA_WIDTH - BATTLE_AREA_EDGE)
|
||||
{
|
||||
force = e->x - (BATTLE_AREA_WIDTH - BATTLE_AREA_EDGE);
|
||||
e->dx -= force * 0.001;
|
||||
e->dx *= 0.95;
|
||||
}
|
||||
|
||||
|
||||
if (e->y >= BATTLE_AREA_HEIGHT - BATTLE_AREA_EDGE)
|
||||
{
|
||||
force = e->y - (BATTLE_AREA_HEIGHT - BATTLE_AREA_EDGE);
|
||||
|
@ -307,7 +296,7 @@ static void doEntity(void)
|
|||
self->health = 0;
|
||||
self->alive = ALIVE_DYING;
|
||||
self->die();
|
||||
|
||||
|
||||
if (self == battle.missionTarget)
|
||||
{
|
||||
battle.missionTarget = NULL;
|
||||
|
@ -332,28 +321,28 @@ static void alignComponents(void)
|
|||
Entity *e;
|
||||
float x, y;
|
||||
float c, s;
|
||||
|
||||
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
{
|
||||
if (isCapitalShipComponent(e))
|
||||
{
|
||||
s = sin(TO_RAIDANS(e->owner->angle));
|
||||
c = cos(TO_RAIDANS(e->owner->angle));
|
||||
|
||||
|
||||
x = (e->offsetX * c) - (e->offsetY * s);
|
||||
y = (e->offsetX * s) + (e->offsetY * c);
|
||||
|
||||
|
||||
x += e->owner->x;
|
||||
y += e->owner->y;
|
||||
|
||||
|
||||
e->x = x;
|
||||
e->y = y;
|
||||
|
||||
|
||||
if (e->flags & EF_STATIC)
|
||||
{
|
||||
e->angle = e->owner->angle;
|
||||
}
|
||||
|
||||
|
||||
addToQuadtree(e, &battle.quadtree);
|
||||
}
|
||||
}
|
||||
|
@ -368,85 +357,86 @@ void drawEntities(void)
|
|||
{
|
||||
Entity *e, **candidates;
|
||||
int i;
|
||||
|
||||
|
||||
candidates = getAllEntsWithin(battle.camera.x, battle.camera.y, SCREEN_WIDTH, SCREEN_HEIGHT, NULL);
|
||||
|
||||
|
||||
/* count number of candidates for use with qsort */
|
||||
for (i = 0, e = candidates[i] ; e != NULL ; e = candidates[++i]) {}
|
||||
|
||||
|
||||
qsort(candidates, i, sizeof(Entity*), drawComparator);
|
||||
|
||||
|
||||
for (i = 0, e = candidates[i] ; e != NULL ; e = candidates[++i])
|
||||
{
|
||||
if (e->active)
|
||||
self = e;
|
||||
|
||||
if (e->draw)
|
||||
{
|
||||
e->draw();
|
||||
}
|
||||
else
|
||||
{
|
||||
drawEntity(e);
|
||||
}
|
||||
|
||||
|
||||
drawTargetRects(e);
|
||||
|
||||
|
||||
drawRope(e);
|
||||
}
|
||||
}
|
||||
|
||||
static void drawEntity(Entity *e)
|
||||
{
|
||||
if (e->type == ET_JUMPGATE && e->alive == ALIVE_ALIVE)
|
||||
{
|
||||
blitRotated(jumpPortal, e->x - battle.camera.x, e->y - battle.camera.y, jumpPortAngle);
|
||||
}
|
||||
|
||||
SDL_SetTextureColorMod(e->texture, 255, 255, 255);
|
||||
|
||||
|
||||
if (e->armourHit > 0)
|
||||
{
|
||||
SDL_SetTextureColorMod(e->texture, 255, 255 - e->armourHit, 255 - e->armourHit);
|
||||
}
|
||||
|
||||
|
||||
if (e->systemHit > 0)
|
||||
{
|
||||
SDL_SetTextureColorMod(e->texture, 255 - e->systemHit, 255, 255);
|
||||
}
|
||||
|
||||
|
||||
if (e->flags & EF_DISABLED)
|
||||
{
|
||||
SDL_SetTextureColorMod(e->texture, disabledGlow, disabledGlow, 255);
|
||||
}
|
||||
|
||||
|
||||
blitRotated(e->texture, e->x - battle.camera.x, e->y - battle.camera.y, e->angle);
|
||||
|
||||
|
||||
if (e->shieldHit > 0)
|
||||
{
|
||||
drawShieldHitEffect(e);
|
||||
}
|
||||
|
||||
|
||||
SDL_SetTextureColorMod(e->texture, 255, 255, 255);
|
||||
}
|
||||
|
||||
static void drawTargetRects(Entity *e)
|
||||
{
|
||||
SDL_Rect r;
|
||||
|
||||
|
||||
int size = MAX(e->w, e->h) + 16;
|
||||
|
||||
|
||||
if (player != NULL && e == player->target)
|
||||
{
|
||||
r.x = e->x - (size / 2) - battle.camera.x;
|
||||
r.y = e->y - (size / 2) - battle.camera.y;
|
||||
r.w = size;
|
||||
r.h = size;
|
||||
|
||||
|
||||
SDL_SetRenderDrawColor(app.renderer, 255, 0, 0, 255);
|
||||
SDL_RenderDrawRect(app.renderer, &r);
|
||||
}
|
||||
|
||||
|
||||
if ((e == battle.missionTarget || e->flags & EF_MISSION_TARGET) && (e->flags & EF_NO_MT_BOX) == 0)
|
||||
{
|
||||
r.x = e->x - (size / 2) - battle.camera.x - 4;
|
||||
r.y = e->y - (size / 2) - battle.camera.y - 4;
|
||||
r.w = size + 8;
|
||||
r.h = size + 8;
|
||||
|
||||
|
||||
SDL_SetRenderDrawColor(app.renderer, 0, 255, 0, 255);
|
||||
SDL_RenderDrawRect(app.renderer, &r);
|
||||
}
|
||||
|
@ -456,9 +446,9 @@ void activateEntities(char *names)
|
|||
{
|
||||
Entity *e;
|
||||
char *name;
|
||||
|
||||
|
||||
name = strtok(names, ";");
|
||||
|
||||
|
||||
while (name)
|
||||
{
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
|
@ -466,17 +456,17 @@ void activateEntities(char *names)
|
|||
if (strcmp(e->name, name) == 0)
|
||||
{
|
||||
e->active = 1;
|
||||
|
||||
|
||||
if (e->type == ET_CAPITAL_SHIP)
|
||||
{
|
||||
updateCapitalShipComponentProperties(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
name = strtok(NULL, ";");
|
||||
}
|
||||
|
||||
|
||||
notifyNewArrivals();
|
||||
}
|
||||
|
||||
|
@ -484,9 +474,9 @@ void activateEntityGroups(char *groupNames)
|
|||
{
|
||||
Entity *e;
|
||||
char *groupName;
|
||||
|
||||
|
||||
groupName = strtok(groupNames, ";");
|
||||
|
||||
|
||||
while (groupName)
|
||||
{
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
|
@ -494,23 +484,28 @@ void activateEntityGroups(char *groupNames)
|
|||
if (strcmp(e->groupName, groupName) == 0)
|
||||
{
|
||||
e->active = 1;
|
||||
|
||||
if (e->type == ET_CAPITAL_SHIP)
|
||||
{
|
||||
updateCapitalShipComponentProperties(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
groupName = strtok(NULL, ";");
|
||||
}
|
||||
|
||||
|
||||
notifyNewArrivals();
|
||||
}
|
||||
|
||||
/*
|
||||
* Some craft, such as capital ships, might be performing a long action and won't notice new craft arrive for well over 30 seconds.
|
||||
* Some craft, such as capital ships, might be performing a long action and won't notice new craft arrive for well over 30 seconds.
|
||||
* We'll knock the times down to a max of 1 second, so they can react faster.
|
||||
*/
|
||||
static void notifyNewArrivals(void)
|
||||
{
|
||||
Entity *e;
|
||||
|
||||
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
{
|
||||
if (e->active && (e->type == ET_FIGHTER || e->type == ET_CAPITAL_SHIP))
|
||||
|
@ -523,7 +518,7 @@ static void notifyNewArrivals(void)
|
|||
static void activateEpicFighters(int n, int side)
|
||||
{
|
||||
Entity *e;
|
||||
|
||||
|
||||
if (n > 0)
|
||||
{
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
|
@ -531,7 +526,7 @@ static void activateEpicFighters(int n, int side)
|
|||
if (!e->active && e->type == ET_FIGHTER && !(e->flags & EF_NO_EPIC) && ((side == SIDE_ALLIES && e->side == SIDE_ALLIES) || (side != SIDE_ALLIES && e->side != SIDE_ALLIES)))
|
||||
{
|
||||
e->active = 1;
|
||||
|
||||
|
||||
if (--n <= 0)
|
||||
{
|
||||
return;
|
||||
|
@ -544,7 +539,7 @@ static void activateEpicFighters(int n, int side)
|
|||
void countNumEnemies(void)
|
||||
{
|
||||
Entity *e;
|
||||
|
||||
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
{
|
||||
if (e->side != SIDE_ALLIES && e->type == ET_FIGHTER)
|
||||
|
@ -552,14 +547,14 @@ void countNumEnemies(void)
|
|||
battle.numInitialEnemies++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, "battle.numInitialEnemies=%d", battle.numInitialEnemies);
|
||||
}
|
||||
|
||||
void addAllEntsToQuadtree(void)
|
||||
{
|
||||
Entity *e;
|
||||
|
||||
|
||||
for (e = battle.entityHead.next ; e != NULL ; e = e->next)
|
||||
{
|
||||
addToQuadtree(e, &battle.quadtree);
|
||||
|
@ -570,20 +565,20 @@ static int drawComparator(const void *a, const void *b)
|
|||
{
|
||||
Entity *e1 = *((Entity**)a);
|
||||
Entity *e2 = *((Entity**)b);
|
||||
|
||||
|
||||
return e2->type - e1->type;
|
||||
}
|
||||
|
||||
void destroyEntities(void)
|
||||
{
|
||||
Entity *e;
|
||||
|
||||
|
||||
while (deadHead.next)
|
||||
{
|
||||
e = deadHead.next;
|
||||
deadHead.next = e->next;
|
||||
free(e);
|
||||
}
|
||||
|
||||
|
||||
deadTail = &deadHead;
|
||||
}
|
||||
|
|
|
@ -660,7 +660,7 @@ static void loadFighterDef(char *filename)
|
|||
|
||||
e->type = ET_FIGHTER;
|
||||
e->active = 1;
|
||||
|
||||
|
||||
STRNCPY(e->name, cJSON_GetObjectItem(root, "name")->valuestring, MAX_NAME_LENGTH);
|
||||
STRNCPY(e->defName, e->name, MAX_NAME_LENGTH);
|
||||
e->health = e->maxHealth = cJSON_GetObjectItem(root, "health")->valueint;
|
||||
|
@ -715,12 +715,11 @@ static void loadFighterDef(char *filename)
|
|||
|
||||
e->separationRadius = MAX(e->w, e->h) * 3;
|
||||
|
||||
/* all craft default to 100 system power */
|
||||
e->systemPower = 100;
|
||||
e->systemPower = MAX_SYSTEM_POWER;
|
||||
|
||||
cJSON_Delete(root);
|
||||
}
|
||||
|
||||
|
||||
free(text);
|
||||
}
|
||||
|
||||
|
|
|
@ -21,55 +21,75 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|||
#include "jumpgate.h"
|
||||
|
||||
static void think(void);
|
||||
static void draw(void);
|
||||
static void handleFleeingEntities(void);
|
||||
static void addEscapeEffect(Entity *ent);
|
||||
|
||||
static SDL_Texture *portal;
|
||||
static float portalAngle;
|
||||
|
||||
Entity *spawnJumpgate(void)
|
||||
{
|
||||
Entity *jumpgate = spawnEntity();
|
||||
|
||||
|
||||
jumpgate->type = ET_JUMPGATE;
|
||||
jumpgate->health = jumpgate->maxHealth = FPS;
|
||||
jumpgate->texture = getTexture("gfx/entities/jumpgate.png");
|
||||
jumpgate->action = think;
|
||||
jumpgate->draw = draw;
|
||||
jumpgate->flags |= EF_NO_MT_BOX;
|
||||
|
||||
|
||||
portal = getTexture("gfx/entities/portal.png");
|
||||
portalAngle = 0;
|
||||
|
||||
return jumpgate;
|
||||
}
|
||||
|
||||
static void think(void)
|
||||
{
|
||||
self->thinkTime = 4;
|
||||
|
||||
|
||||
self->angle += 0.1;
|
||||
if (self->angle >= 360)
|
||||
{
|
||||
self->angle -= 360;
|
||||
}
|
||||
|
||||
if (self->alive == ALIVE_ALIVE)
|
||||
|
||||
if (self->systemPower)
|
||||
{
|
||||
handleFleeingEntities();
|
||||
}
|
||||
|
||||
battle.jumpgate = self;
|
||||
|
||||
if (!battle.jumpgate)
|
||||
{
|
||||
battle.jumpgate = self;
|
||||
}
|
||||
|
||||
if (battle.jumpgate == self)
|
||||
{
|
||||
portalAngle += 0.5;
|
||||
if (portalAngle >= 360)
|
||||
{
|
||||
portalAngle -= 360;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void handleFleeingEntities(void)
|
||||
{
|
||||
Entity *e, **candidates;
|
||||
int i;
|
||||
|
||||
|
||||
candidates = getAllEntsWithin(self->x - (self->w / 2), self->y - (self->h / 2), self->w, self->h, self);
|
||||
|
||||
|
||||
for (i = 0, e = candidates[i] ; e != NULL ; e = candidates[++i])
|
||||
{
|
||||
if (e->health > 0 && e->flags & EF_RETREATING && getDistance(self->x, self->y, e->x, e->y) <= 255)
|
||||
{
|
||||
e->alive = ALIVE_ESCAPED;
|
||||
|
||||
|
||||
addEscapeEffect(e);
|
||||
|
||||
|
||||
playBattleSound(SND_JUMP, e->x, e->y);
|
||||
}
|
||||
}
|
||||
|
@ -79,29 +99,39 @@ static void addEscapeEffect(Entity *ent)
|
|||
{
|
||||
Effect *e;
|
||||
int i, n, speed;
|
||||
|
||||
|
||||
n = ent->w * ent->h;
|
||||
|
||||
|
||||
for (i = 0 ; i < n ; i++)
|
||||
{
|
||||
e = malloc(sizeof(Effect));
|
||||
memset(e, 0, sizeof(Effect));
|
||||
battle.effectTail->next = e;
|
||||
battle.effectTail = e;
|
||||
|
||||
|
||||
speed = 50 + rand() % 50;
|
||||
|
||||
|
||||
e->type = EFFECT_POINT;
|
||||
e->x = ent->x + (rand() % ent->w) - (rand() % ent->w);
|
||||
e->y = ent->y + (rand() % ent->h) - (rand() % ent->w);
|
||||
|
||||
|
||||
e->dx = self->x - e->x;
|
||||
e->dx /= speed;
|
||||
|
||||
|
||||
e->dy = self->y - e->y;
|
||||
e->dy /= speed;
|
||||
|
||||
|
||||
e->r = e->g = e->b = e->a = (rand() % 255);
|
||||
e->health = speed;
|
||||
}
|
||||
}
|
||||
|
||||
static void draw(void)
|
||||
{
|
||||
if (self->systemPower)
|
||||
{
|
||||
blitRotated(portal, self->x - battle.camera.x, self->y - battle.camera.y, portalAngle);
|
||||
}
|
||||
|
||||
blitRotated(self->texture, self->x - battle.camera.x, self->y - battle.camera.y, self->angle);
|
||||
}
|
||||
|
|
|
@ -25,6 +25,7 @@ extern Entity *spawnEntity(void);
|
|||
extern Entity **getAllEntsWithin(int x, int y, int w, int h, Entity *ignore);
|
||||
extern int getDistance(int x1, int y1, int x2, int y2);
|
||||
extern void playBattleSound(int id, int x, int y);
|
||||
extern void blitRotated(SDL_Texture *texture, int x, int y, float angle);
|
||||
|
||||
extern Battle battle;
|
||||
extern Entity *self;
|
||||
|
|
|
@ -30,42 +30,42 @@ void initScript(cJSON *scriptNode)
|
|||
{
|
||||
memset(&head, 0, sizeof(ScriptRunner));
|
||||
tail = &head;
|
||||
|
||||
|
||||
scriptJSON = scriptNode;
|
||||
}
|
||||
|
||||
void doScript(void)
|
||||
{
|
||||
ScriptRunner *runner, *prev;
|
||||
|
||||
|
||||
prev = &head;
|
||||
|
||||
|
||||
for (runner = head.next ; runner != NULL ; runner = runner->next)
|
||||
{
|
||||
runner->delay = MAX(0, runner->delay - 1);
|
||||
|
||||
|
||||
if (runner->waitForMessageBox)
|
||||
{
|
||||
runner->waitForMessageBox = showingMessageBoxes();
|
||||
}
|
||||
|
||||
|
||||
if (!runner->delay && !runner->waitForMessageBox)
|
||||
{
|
||||
executeNextLine(runner);
|
||||
|
||||
|
||||
if (!runner->line)
|
||||
{
|
||||
if (runner == tail)
|
||||
{
|
||||
tail = prev;
|
||||
}
|
||||
|
||||
|
||||
prev->next = runner->next;
|
||||
free(runner);
|
||||
runner = prev;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
prev = runner;
|
||||
}
|
||||
}
|
||||
|
@ -85,26 +85,26 @@ void runScriptFunction(const char *format, ...)
|
|||
va_start(args, format);
|
||||
vsprintf(funcNameBuffer, format, args);
|
||||
va_end(args);
|
||||
|
||||
|
||||
function = scriptJSON->child;
|
||||
|
||||
|
||||
while (function)
|
||||
{
|
||||
functionName = cJSON_GetObjectItem(function, "function")->valuestring;
|
||||
|
||||
|
||||
if (strcmp(functionName, funcNameBuffer) == 0)
|
||||
{
|
||||
scriptRunner = malloc(sizeof(ScriptRunner));
|
||||
memset(scriptRunner, 0, sizeof(ScriptRunner));
|
||||
|
||||
|
||||
scriptRunner->line = cJSON_GetObjectItem(function, "lines")->child;
|
||||
|
||||
|
||||
tail->next = scriptRunner;
|
||||
tail = scriptRunner;
|
||||
|
||||
|
||||
SDL_LogMessage(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO, "Running script '%s'", funcNameBuffer);
|
||||
}
|
||||
|
||||
|
||||
function = function->next;
|
||||
}
|
||||
}
|
||||
|
@ -118,7 +118,7 @@ static void executeNextLine(ScriptRunner *runner)
|
|||
int intParam[2];
|
||||
|
||||
line = runner->line->valuestring;
|
||||
|
||||
|
||||
sscanf(line, "%s", command);
|
||||
|
||||
if (strcmp(command, "ACTIVATE_ENTITIES") == 0)
|
||||
|
@ -143,7 +143,7 @@ static void executeNextLine(ScriptRunner *runner)
|
|||
}
|
||||
else if (strcmp(command, "ACTIVATE_JUMPGATE") == 0)
|
||||
{
|
||||
battle.jumpgate->alive = ALIVE_ALIVE;
|
||||
battle.jumpgate->systemPower = MAX_SYSTEM_POWER;
|
||||
}
|
||||
else if (strcmp(command, "MSG_BOX") == 0)
|
||||
{
|
||||
|
@ -196,13 +196,13 @@ static void executeNextLine(ScriptRunner *runner)
|
|||
void destroyScript(void)
|
||||
{
|
||||
ScriptRunner *scriptRunner;
|
||||
|
||||
|
||||
while (head.next)
|
||||
{
|
||||
scriptRunner = head.next;
|
||||
head.next = scriptRunner->next;
|
||||
free(scriptRunner);
|
||||
}
|
||||
|
||||
|
||||
tail = &head;
|
||||
}
|
||||
|
|
|
@ -66,6 +66,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|||
|
||||
#define MAX_FIGHTER_GUNS 12
|
||||
#define MAX_TARGET_RANGE 65536
|
||||
#define MAX_SYSTEM_POWER 100
|
||||
|
||||
#define BATTLE_AREA_CELLS 50
|
||||
#define BATTLE_AREA_WIDTH (640 * BATTLE_AREA_CELLS)
|
||||
|
@ -165,8 +166,7 @@ enum
|
|||
ALIVE_ALIVE,
|
||||
ALIVE_DYING,
|
||||
ALIVE_DEAD,
|
||||
ALIVE_ESCAPED,
|
||||
ALIVE_SLEEPING /* used by jumpgate */
|
||||
ALIVE_ESCAPED
|
||||
};
|
||||
|
||||
enum
|
||||
|
|
|
@ -47,7 +47,7 @@ Mission *loadMissionMeta(char *filename)
|
|||
text = readFile(filename);
|
||||
|
||||
root = cJSON_Parse(text);
|
||||
|
||||
|
||||
mission = NULL;
|
||||
|
||||
if (root)
|
||||
|
@ -80,14 +80,14 @@ Mission *loadMissionMeta(char *filename)
|
|||
if (node)
|
||||
{
|
||||
mission->challengeData.isChallenge = 1;
|
||||
|
||||
|
||||
/* limits */
|
||||
mission->challengeData.timeLimit = getJSONValue(node, "timeLimit", 0) * FPS;
|
||||
mission->challengeData.killLimit = getJSONValue(node, "killLimit", 0);
|
||||
mission->challengeData.escapeLimit = getJSONValue(node, "escapeLimit", 0);
|
||||
mission->challengeData.waypointLimit = getJSONValue(node, "waypointLimit", 0);
|
||||
mission->challengeData.itemLimit = getJSONValue(node, "itemLimit", 0);
|
||||
|
||||
|
||||
/* restrictions */
|
||||
mission->challengeData.noMissiles = getJSONValue(node, "noMissiles", 0);
|
||||
mission->challengeData.noECM = getJSONValue(node, "noECM", 0);
|
||||
|
@ -121,7 +121,7 @@ Mission *loadMissionMeta(char *filename)
|
|||
|
||||
cJSON_Delete(root);
|
||||
}
|
||||
|
||||
|
||||
free(text);
|
||||
|
||||
return mission;
|
||||
|
@ -223,7 +223,7 @@ void loadMission(char *filename)
|
|||
initPlayer();
|
||||
|
||||
initMissionInfo();
|
||||
|
||||
|
||||
addAllEntsToQuadtree();
|
||||
|
||||
playMusic(music);
|
||||
|
@ -567,7 +567,7 @@ static void loadEntities(cJSON *node)
|
|||
{
|
||||
Entity *e;
|
||||
char *name, *groupName;
|
||||
int i, type, scatter, number, active, sleeping;
|
||||
int i, type, scatter, number, active, systemPower;
|
||||
float x, y;
|
||||
|
||||
if (node)
|
||||
|
@ -588,7 +588,7 @@ static void loadEntities(cJSON *node)
|
|||
number = getJSONValue(node, "number", 1);
|
||||
active = getJSONValue(node, "active", 1);
|
||||
scatter = getJSONValue(node, "scatter", 1);
|
||||
sleeping = getJSONValue(node, "sleeping", 0);
|
||||
systemPower = getJSONValue(node, "systemPower", MAX_SYSTEM_POWER);
|
||||
|
||||
for (i = 0 ; i < number ; i++)
|
||||
{
|
||||
|
@ -628,11 +628,8 @@ static void loadEntities(cJSON *node)
|
|||
}
|
||||
|
||||
e->active = active;
|
||||
|
||||
if (sleeping)
|
||||
{
|
||||
e->alive = ALIVE_SLEEPING;
|
||||
}
|
||||
|
||||
e->systemPower = systemPower;
|
||||
|
||||
SDL_QueryTexture(e->texture, NULL, NULL, &e->w, &e->h);
|
||||
}
|
||||
|
|
|
@ -145,6 +145,7 @@ struct Entity {
|
|||
Entity *leader;
|
||||
Entity *owner;
|
||||
void (*action)(void);
|
||||
void (*draw)(void);
|
||||
void (*die)(void);
|
||||
SDL_Texture *texture;
|
||||
Entity *next;
|
||||
|
|
Loading…
Reference in New Issue