static void eatTakeDamage(Entity *other, int damage) { Entity *temp; if (!(self->flags & INVULNERABLE)) { setCustomAction(self, &flashWhite, 6, 0, 0); setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); self->mental--; enemyPain(); if (self->mental <= 0) { self->action = &eatExplode; } if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } } }
static void upTouch(Entity *other) { int bottomBefore; if (self->active == TRUE && !(other->flags & FLY)) { if (other->dirY > 0) { bottomBefore = other->y + other->h - other->dirY - 1; if (bottomBefore < self->y) { /* Place the player as close to the solid tile as possible */ other->y = self->y; other->y -= other->h; other->standingOn = self; other->dirY = 0; other->flags |= ON_GROUND; } else { setCustomAction(other, &antiGravity, 2, 0, 1); } } else { setCustomAction(other, &antiGravity, 2, 0, 1); } } }
static void takeDamage(Entity *other, int damage) { Entity *temp; if (!(self->flags & INVULNERABLE)) { if (strcmpignorecase(other->name, "weapon/wood_axe") == 0) { playSoundToMap("sound/item/chop", -1, self->x, self->y, 0); self->health -= damage; if (self->health > 0) { setCustomAction(self, &flashWhite, 6, 0, 0); } else { if (self->mental > 0) { self->health = self->maxHealth; self->mental--; } else { setInfoBoxMessage(60, 255, 255, 255, _("It's out of apples...")); } } } else { playSoundToMap("sound/common/dink", -1, self->x, self->y, 0); if (other->reactToBlock != NULL) { temp = self; self = other; self->reactToBlock(temp); self = temp; } damage = 0; if (other->type != PROJECTILE && prand() % 10 == 0) { setInfoBoxMessage(60, 255, 255, 255, _("This weapon is not having any effect...")); } } setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); } }
void iceBlockTakeDamage(Entity *other, int damage) { Entity *temp; if (self->flags & INVULNERABLE) { return; } if (strcmpignorecase(other->name, "weapon/pickaxe") == 0) { self->damage = 0; self->die(); } else if (damage != 0) { self->health -= damage; if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } if (self->health > 0) { setCustomAction(self, &flashWhite, 6, 0, 0); /* Don't make an enemy invulnerable from a projectile hit, allows multiple hits */ if (other->type != PROJECTILE) { setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); } if (self->pain != NULL) { self->pain(); } } else { self->damage = 0; self->die(); } } }
void entityTakeDamageNoFlinch(Entity *other, int damage) { Entity *temp; if (self->flags & INVULNERABLE) { return; } if (damage != 0) { self->health -= damage; if (self->health > 0) { setCustomAction(self, &flashWhite, 6, 0, 0); /* Don't make an enemy invulnerable from a projectile hit, allows multiple hits */ if (other->type != PROJECTILE) { setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); } if (self->pain != NULL) { self->pain(); } } else { self->damage = 0; if (other->type == WEAPON || other->type == PROJECTILE) { increaseKillCount(); } self->die(); } if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } } }
void entityTakeDamageFlinch(Entity *other, int damage) { Entity *temp; if (self->flags & INVULNERABLE) { return; } if (damage != 0) { self->health -= damage; if (self->health > 0) { setCustomAction(self, &helpless, 10, 0, 0); setCustomAction(self, &invulnerable, HIT_INVULNERABLE_TIME, 0, 0); if (self->pain != NULL) { self->pain(); } self->dirX = other->face == RIGHT ? 6 : -6; } else { self->damage = 0; if (other->type == WEAPON || other->type == PROJECTILE) { increaseKillCount(); } self->die(); } if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } } }
static void touch(Entity *other) { Entity *temp; if (!(self->flags & INVULNERABLE) && other->type == ITEM && strcmpignorecase(other->name, "item/repellent_spray") == 0) { self->mental++; if (self->mental == 50) { self->action = &shudder; self->targetX = self->x; self->thinkTime = 300; if (player.health > 0) { setInfoBoxMessage(180, 255, 255, 255, _("Now! Run while it's stunned!")); } self->health = 0; } else if (self->mental > 50) { self->thinkTime = 300; } setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); setCustomAction(self, &flashWhite, 6, 0, 0); } else if (other->type == PLAYER && self->action == &attack) { temp = self; self = other; freeEntityList(playerGib()); self = temp; } else { entityTouch(other); } }
static void riftWait() { self->thinkTime--; if (self->thinkTime <= 0) { stopSound(self->health); self->action = &riftClose; self->thinkTime = 20; } else { if (collision(self->x - self->mental, self->y - self->mental, self->mental * 2, self->mental * 2, player.x, player.y, player.w, player.h) == 1) { setCustomAction(&player, &attract, 5, 0, (player.x < (self->x + self->w / 2) ? 2 : -2)); } if (prand() % 3 == 0) { addRiftEnergy(self->x + self->w / 2, self->y + self->h / 2); } } }
static void extend() { setCustomAction(&player, &helpless, 2, 0, 0); if (self->dirX == 0) { self->dirX = self->face == LEFT ? self->speed : -self->speed; self->action = &retract; setEntityAnimation(self, "JUMP"); self->health = 2; } else { checkToMap(self); self->mental += fabs(self->dirX); if (self->mental >= 256) { self->dirX = 0; } } self->y = player.y + player.h / 2 - self->h / 2; }
static void webTouch(Entity *other) { if (other->type == PLAYER && !(other->flags & WRAPPED) && !(other->flags & INVULNERABLE) && other->health > 0) { if ((other->flags & BLOCKING) && ((self->dirX > 0 && player.face == LEFT) || (self->dirX < 0 && player.face == RIGHT))) { player.dirX = self->dirX < 0 ? -2 : 2; checkToMap(&player); setCustomAction(&player, &helpless, 2, 0, 0); if (playerShield.thinkTime <= 0) { playSoundToMap("sound/edgar/block", EDGAR_CHANNEL, player.x, player.y, 0); playerShield.thinkTime = 5; } } else { setPlayerWrapped(120); } self->inUse = FALSE; } }
static void dieWait() { self->flags |= NO_DRAW; self->thinkTime--; if (self->thinkTime <= 0) { self->mental = 0; self->flags |= FLY; self->flags &= ~NO_DRAW; self->dirX = 0; self->dirY = 0; self->y = self->startY; self->touch = &entityTouch; self->action = &entityWait; setCustomAction(self, &invulnerable, 180, 0, 0); } }
static void riftWait() { int x, y; self->thinkTime--; if (self->thinkTime <= 0 || self->head->health <= 0) { stopSound(self->health); self->action = &riftClose; self->thinkTime = 20; } else { x = self->x + self->w / 2; y = self->y + self->h / 2; if (collision(x - self->speed, y - self->speed, self->speed * 2, self->speed * 2, player.x, player.y, player.w, player.h) == 1) { setCustomAction(&player, &attract, 5, 0, (player.x < (self->x + self->w / 2) ? player.speed - 0.25 : -(player.speed - 0.25))); } if (prand() % 3 == 0) { addRiftEnergy(self->x + self->w / 2, self->y + self->h / 2); } } checkToMap(self); }
static void activate(int val) { if (self->head->active == FALSE) { runScript("rusted"); } else { self->head->action = &fire; setEntityAnimation(self->head, "WALK"); self->head->frameSpeed = 1; setCustomAction(&player, &invulnerableNoFlash, 60, 0, 0); setPlayerStunned(60); player.dirX = 12; player.dirY = -22; self->head->thinkTime = 120; } }
static void die() { int i; self->action = ¨ setCustomAction(self, &invulnerableNoFlash, 240, 0, 0); setEntityAnimation(self, "STUNNED"); self->flags &= ~FLY; self->dirX = 0; self->mental = self->x < getMapStartX() + SCREEN_WIDTH / 2 ? 0 : 1; checkToMap(self); if (self->flags & ON_GROUND) { for (i=0;i<20;i++) { addSmoke(self->x + prand() % self->w, self->y + self->h - prand() % 10, "decoration/dust"); } playSoundToMap("sound/common/crash", BOSS_CHANNEL, self->x, self->y, 0); self->thinkTime = 120; self->endY = 0; self->action = &dieFinish; } }
static void dieFinish() { if (self->thinkTime > 0) { self->thinkTime--; setCustomAction(self, &invulnerableNoFlash, 240, 0, 0); if (self->thinkTime <= 0) { fireTrigger(self->objectiveName); fireGlobalTrigger(self->objectiveName); } } if (self->endY == 1) { setEntityAnimation(self, "STAND"); self->thinkTime = 60; facePlayer(); self->action = &finalAttack; } checkToMap(self); }
static void takeDamage(Entity *other, int damage) { Entity *temp; setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); playSoundToMap("sound/common/dink", -1, self->x, self->y, 0); if (other->reactToBlock != NULL) { temp = self; self = other; self->reactToBlock(temp); self = temp; } if (other->type != PROJECTILE && prand() % 10 == 0) { setInfoBoxMessage(60, 255, 255, 255, _("This weapon is not having any effect...")); } damage = 0; }
void entityDieNoDrop() { self->damage = 0; self->health = 0; if (!(self->flags & INVULNERABLE)) { self->flags &= ~FLY; self->weight = fabs(self->originalWeight); self->flags |= DO_NOT_PERSIST; self->thinkTime = 60; setCustomAction(self, &invulnerable, 240, 0, 0); self->frameSpeed = 0; self->action = &noItemDie; fireTrigger(self->objectiveName); fireGlobalTrigger(self->objectiveName); } }
void entityDie() { self->damage = 0; self->health = 0; if (!(self->flags & INVULNERABLE)) { self->flags &= ~FLY; self->weight = fabs(self->originalWeight); self->flags |= DO_NOT_PERSIST; self->thinkTime = 60; setCustomAction(self, &invulnerable, 240, 0, 0); self->frameSpeed = 0; self->action = &standardDie; self->damage = 0; } }
static void segmentTakeDamage(Entity *other, int damage) { Entity *temp; if (self->flags & INVULNERABLE) { return; } if (damage != 0) { self->health -= damage; if (self->health > 0) { setCustomAction(self, &flashWhite, 6, 0, 0); /* Don't make an enemy invulnerable from a projectile hit, allows multiple hits */ if (other->type != PROJECTILE) { setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); } enemyPain(); } else { self->damage = 0; self->die(); } if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } } }
static void takeDamage(Entity *other, int damage) { Entity *temp; if (!(self->flags & INVULNERABLE)) { if (damage < self->health) { self->targetY = self->startY; setCustomAction(self, &flashWhite, 6, 0, 0); self->action = &retreat; setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); } else { self->flags &= ~FLY; self->dirY = ITEM_JUMP_HEIGHT; self->damage = 0; if (other->type == WEAPON || other->type == PROJECTILE) { increaseKillCount(); } self->die(); } if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } } }
static void die() { self->flags &= ~FLY; self->weight = 1; playSoundToMap("sound/boss/chaos/die", BOSS_CHANNEL, self->x, self->y, 0); setEntityAnimation(self, "DIE_1"); self->animationCallback = NULL; activateEntitiesWithObjectiveName("CHAOS_VINES", FALSE); self->x = self->startX; if (self->flags & GRABBING) { if (self->face == LEFT) { player.x = self->x + self->w - player.w - self->offsetX; } else { player.x = self->x + self->offsetX; } player.y = self->y + self->offsetY; setCustomAction(&player, &invulnerable, 60, 0, 0); setPlayerStunned(30); player.x -= player.dirX; player.y -= player.dirY; player.dirX = (10 + prand() % 3) * (self->face == LEFT ? -1 : 1); player.dirY = -3; self->touch = &entityTouch; } self->mental = 0; self->thinkTime = 420; self->damage = 0; self->takeDamage = NULL; self->action = &dieWait; fadeOutMusic(3000); checkToMap(self); }
static void stunned() { int i; long onGround = self->flags & ON_GROUND; Entity *e; setEntityAnimation(self, "PAIN"); checkToMap(self); if (self->flags & ON_GROUND) { self->dirX = 0; setCustomAction(self, &helpless, 300, 0, 0); if (onGround == 0) { addSmokeAlongBody(); } self->action = &attackFinished; for (i=0; i<2; i++) { e = getFreeEntity(); if (e == NULL) { showErrorAndExit("No free slots to add the Armour Boss's Star"); } loadProperties("boss/armour_boss_star", e); e->x = self->x; e->y = self->y; e->action = &starWait; e->draw = &drawLoopingAnimationToMap; e->thinkTime = 300; e->head = self; setEntityAnimation(e, "STAND"); e->currentFrame = (i == 0 ? 0 : 6); e->x = self->x + self->w / 2 - e->w / 2; e->y = self->y - e->h - 8; } } alignBodyToHead(); }
static void entityWait() { EntityList *el, *entities; entities = getEntities(); setEntityAnimation(self, self->active == FALSE ? "STAND" : "WALK"); if (self->active == TRUE) { if (self->health == -1) { self->health = playSoundToMap("sound/item/rift", -1, self->x, self->y, -1); } self->thinkTime--; if (self->thinkTime <= 0) { for (el=entities->next;el!=NULL;el=el->next) { if (el->entity->inUse == TRUE && el->entity->type == ENEMY && collision(self->x - self->mental, self->y, self->mental * 2, self->mental * 2, el->entity->x, el->entity->y, el->entity->w, el->entity->h) == 1) { setCustomAction(el->entity, &attract, self->maxThinkTime, 0, (el->entity->x < (self->x + self->w / 2) ? self->speed : -self->speed)); } } self->thinkTime = self->maxThinkTime; if (collision(self->x - self->mental, self->y, self->mental * 2, self->mental * 2, player.x, player.y, player.w, player.h) == 1) { setCustomAction(&player, &attract, self->maxThinkTime, 0, (player.x < (self->x + self->w / 2) ? self->speed : -self->speed)); } stopSound(self->health); } if (prand() % 3 == 0) { addRiftEnergy(self->x + self->w / 2, self->y + self->h / 2); } } }
static void stalagmiteTakeDamage(Entity *other, int damage) { Entity *temp; if (strcmpignorecase(self->requires, other->name) == 0) { self->health -= damage; setCustomAction(self, &flashWhite, 6, 0, 0); setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); if (self->health <= 0) { self->damage = 0; self->die(); } } else { setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); playSoundToMap("sound/common/dink", -1, self->x, self->y, 0); if (other->reactToBlock != NULL) { temp = self; self = other; self->reactToBlock(temp); self = temp; } if (other->type != PROJECTILE && prand() % 10 == 0) { setInfoBoxMessage(60, 255, 255, 255, _("This weapon is not having any effect...")); } damage = 0; } }
static void takeDamage(Entity *other, int damage) { int minHealth; Entity *temp; minHealth = self->maxHealth / 10; if (!(self->flags & INVULNERABLE)) { /* Take minimal damage from bombs */ if (other->type == EXPLOSION) { damage = 1; } self->health -= damage; if (self->health <= minHealth) { self->health = minHealth; } setCustomAction(self, &flashWhite, 6, 0, 0); setCustomAction(self, &invulnerableNoFlash, HIT_INVULNERABLE_TIME, 0, 0); enemyPain(); if (other->type == PROJECTILE) { temp = self; self = other; self->die(); self = temp; } } }
static void disintegrationTouch(Entity *other) { Entity *temp; if (other->type == PLAYER) { if ((other->flags & BLOCKING) && strcmpignorecase(playerShield.objectiveName, "Disintegration Shield") == 0) { if (self->mental != 3) { self->dirX = self->head->face == LEFT ? -1 : 1; temp = self; self = other; other->takeDamage(temp, 1); self = temp; self->mental = 3; self->thinkTime = 30; stopSound(BOSS_CHANNEL); } } else { if (self->mental != 2) { setPlayerLocked(TRUE); setPlayerLocked(FALSE); self->thinkTime = 180; other->dirX = 0; setCustomAction(other, &helpless, self->thinkTime, 0, 0); setEntityAnimation(other, "CUSTOM_1"); self->mental = 2; playSoundToMap("sound/boss/sorceror/electrocute", BOSS_CHANNEL, self->x, self->y, 0); } } } }
static void die() { int i; Entity *e; char name[MAX_VALUE_LENGTH]; playSoundToMap("sound/common/crumble", -1, self->x, self->y, 0); snprintf(name, sizeof(name), "%s_piece", self->name); fireTrigger(self->objectiveName); fireGlobalTrigger(self->objectiveName); for (i=0;i<9;i++) { e = addTemporaryItem(name, self->x, self->y, self->face, 0, 0); e->x += (self->w - e->w) / 2; e->y += (self->w - e->w) / 2; e->dirX = (prand() % 5) * (prand() % 2 == 0 ? -1 : 1); e->dirY = ITEM_JUMP_HEIGHT + (prand() % ITEM_JUMP_HEIGHT); setEntityAnimationByID(e, i); e->thinkTime = 60 + (prand() % 180); } self->damage = 0; if (!(self->flags & INVULNERABLE)) { self->touch = &entityTouch; self->flags &= ~FLY; self->flags |= (DO_NOT_PERSIST|NO_DRAW); self->thinkTime = 60; setCustomAction(self, &invulnerableNoFlash, 240, 0, 0); self->frameSpeed = 0; self->action = &standardDie; self->damage = 0; } }
static void breatheIn() { Entity *e; self->thinkTime--; if (self->thinkTime <= 0) { self->thinkTime = 30; self->action = &breatheFire; self->creditsAction = &breatheFire; } e = addSmoke(0, 0, "decoration/dust"); if (e != NULL) { if (self->face == LEFT) { e->x = self->x + self->w - e->w - self->offsetX; } else { e->x = self->x + self->offsetX; } e->y = self->y + self->offsetY; e->targetX = e->x; e->targetY = e->y; e->x += (128 + prand() % 128) * (self->face == LEFT ? -1 : 1); e->y += (prand() % 64) * (prand() % 2 == 0 ? -1 : 1); calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY); e->dirX *= 6; e->dirY *= 6; e->thinkTime = 30; } setCustomAction(&player, &attract, 2, 0, (player.x < (self->x + self->w / 2) ? (player.speed - 0.5) : -(player.speed - 0.5))); checkToMap(self); }
static void partGrab(Entity *other) { if (self->health <= 0) { return; } if (other->type == WEAPON && (other->flags & ATTACKING)) { if (self->takeDamage != NULL && !(self->flags & INVULNERABLE)) { self->takeDamage(other, other->damage); } } else if (other->type == PROJECTILE && other->parent != self) { if (self->takeDamage != NULL && !(self->flags & INVULNERABLE)) { self->takeDamage(other, other->damage); } other->inUse = FALSE; } else if (other->type == PLAYER && !(self->flags & GRABBING)) { self->startX = (prand() % (other->w / 2)) * (prand() % 2 == 0 ? 1 : -1); self->startY = prand() % (other->h - self->h); setCustomAction(other, &slowDown, 3, 1, 0); self->action = &stickToPlayerAndDrain; self->touch = NULL; self->flags |= GRABBING; self->layer = FOREGROUND_LAYER; other->flags |= GRABBED; self->thinkTime = 0; self->mental = 3 + (prand() % 3); } }
static void respawn() { self->thinkTime--; checkToMap(self); if (self->thinkTime <= 0) { self->x = self->startX; self->y = self->startY; setCustomAction(self, &invulnerable, 60, 0, 0); self->action = &entityWait; } }