Beispiel #1
0
static void disintegrationSpellInit()
{
	Entity *e = addPixelDecoration(self->x, self->y);

	if (e != NULL)
	{
		e->x = self->x + (prand() % 32) * (prand() % 2 == 0 ? -1 : 1) + self->w / 2;
		e->y = self->y + (prand() % 32) * (prand() % 2 == 0 ? -1 : 1) + self->h / 2;

		e->startX = e->x;
		e->startY = e->y;

		e->endX = self->x;
		e->endY = self->y;

		e->thinkTime = 15;

		e->health = 230;

		e->maxHealth = 230;

		e->mental = 230;

		calculatePath(e->startX, e->startY, e->endX, e->endY, &e->dirX, &e->dirY);
	}

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		playSoundToMap("sound/boss/sorceror/electrocute", BOSS_CHANNEL, self->x, self->y, 0);

		self->endX = player.x + player.w / 2;
		self->endY = player.y + player.h / 2;

		self->thinkTime = 300;

		self->touch = &disintegrationTouch;

		self->action = &disintegrationSpellAttack;

		self->draw = &drawDisintegrationSpell;

		self->layer = BACKGROUND_LAYER;

		self->flags &= ~NO_DRAW;
	}
}
Beispiel #2
0
static void spinnerAttack()
{
	Entity *e;

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		e = getFreeEntity();

		if (e == NULL)
		{
			showErrorAndExit("No free slots to add a spinner");
		}

		loadProperties("boss/snake_boss_special_shot", e);

		setEntityAnimation(e, "STAND");

		e->x = self->x + self->w / 2;
		e->y = self->y + self->h / 2;

		e->targetX = self->x - e->w;
		e->targetY = self->y + self->h / 2;

		calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

		e->flags |= (NO_DRAW|HELPLESS|TELEPORTING|NO_END_TELEPORT_SOUND);

		e->flags |= FLY|NO_DRAW;

		e->head = self;

		e->face = RIGHT;

		e->action = &spinnerMove;

		e->draw = &drawLoopingAnimationToMap;

		e->type = ENEMY;

		self->action = &spinnerAttackFinish;
	}

	self->maxThinkTime--;

	checkToMap(self);
}
Beispiel #3
0
static void attackFinish()
{
	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		self->targetY = self->startY + (self->endY - self->startY) / 2;

		calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

		self->dirX *= self->speed;
		self->dirY *= self->speed;

		self->action = &moveToTarget;
	}
}
Beispiel #4
0
static void die()
{
    long onGround = self->flags & ON_GROUND;

    self->action = &die;

    checkToMap(self);

    if (self->flags & FLY)
    {
        if (atTarget())
        {
            self->dirX = self->dirY = 0;

            self->thinkTime = 120;

            self->action = &fallToGround;
        }
    }

    else
    {
        if (self->flags & ON_GROUND)
        {
            self->dirX = 0;

            if (onGround == 0)
            {
                addSmokeAlongBody();
            }

            self->thinkTime--;

            if (self->thinkTime <= 0)
            {
                calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

                self->dirX *= 2;
                self->dirY *= 2;

                self->flags |= FLY;
            }
        }
    }

    alignBodyToHead();
}
Beispiel #5
0
void recSwap(int * list, int k, int m)
{
    if(k == m)
    {
        calculatePath(list);
    }
    else
    {
        for(int i = k; i <= m; i++)
        {
            swap(&list[k], &list[i]);

            recSwap(list, k + 1, m);

            swap(&list[k], &list[i]);
        }
    }
}
Beispiel #6
0
static void biteAttackInit()
{
    /*facePlayer();*/

    setEntityAnimation(self, "ATTACK_1");

    self->targetX = self->endX + (self->face == LEFT ? -32 : 32);
    self->targetY = self->endY - 32;

    calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

    self->dirX *= 4;
    self->dirY *= 4;

    self->action = &biteAttackWindUp;

    self->maxThinkTime = 1 + prand() % 3;
}
Beispiel #7
0
static void attackFinished()
{
    setEntityAnimation(self, "STAND");

    self->flags &= ~UNBLOCKABLE;

    self->flags |= FLY;

    self->targetX = self->endX;
    self->targetY = self->endY - 64;

    calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

    self->dirX *= self->speed;
    self->dirY *= self->speed;

    self->action = &returnToStart;
}
Beispiel #8
0
static void headBiteInit()
{
	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		self->startX = self->x;
		self->startY = self->y;

		self->targetX = player.x;
		self->targetY = player.y;

		calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

		self->dirX *= 16;
		self->dirY *= 16;

		self->action = &headBite;

		self->reactToBlock = &headBiteReactToBlock;
	}

	if (self->head->health <= 0)
	{
		self->die();
	}

	alignBodyToHead();

	self->damage = self->head->damage;

	self->face = self->head->face;

	if (self->head->flags & FLASH)
	{
		self->flags |= FLASH;
	}

	else
	{
		self->flags &= ~FLASH;
	}
}
Beispiel #9
0
static void offscreenTeleportInit()
{
	Entity *e = getFreeEntity();

	if (e == NULL)
	{
		showErrorAndExit("No free slots to add the Sorceror Spell");
	}

	loadProperties("boss/sorceror_teleport_spell", e);

	setEntityAnimation(e, "STAND");

	e->face = self->face;

	if (self->face == LEFT)
	{
		e->x = self->x + self->w - e->w - e->offsetX;
	}

	else
	{
		e->x = self->x + e->offsetX;
	}

	e->y = self->y + e->offsetY;

	e->action = &spellMove;

	calculatePath(e->x, e->y, player.x + player.w / 2, player.y + player.h / 2, &e->dirX, &e->dirY);

	e->dirX *= e->speed;
	e->dirY *= e->speed;

	e->draw = &drawLoopingAnimationToMap;

	e->touch = &teleportPlayerOffscreen;

	self->thinkTime = 60;

	self->action = &teleportOffscreenWait;
}
Beispiel #10
0
static void shotAttackInit()
{
    /*facePlayer();*/

    setEntityAnimation(self, "ATTACK_1");

    self->targetX = self->endX + (self->face == LEFT ? -50 : 50);
    self->targetY = self->endY - 32;

    calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

    self->dirX *= 4;
    self->dirY *= 4;

    self->action = &shotAttackWindUp;

    self->flags |= UNBLOCKABLE;

    self->startX = 0;
}
static void ballWait()
{
	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

		self->dirX *= self->speed;
		self->dirY *= self->speed;

		self->action = &moveToSorceror;
	}

	else
	{
		self->endY += 5;

		self->y = self->startY + cos(DEG_TO_RAD(self->endY)) * 16;
	}
}
Beispiel #12
0
static void headBite()
{
	checkToMap(self);

	if (atTarget() || self->dirX == 0 || self->dirY == 0)
	{
		self->targetX = self->startX;
		self->targetY = self->startY;

		calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

		self->dirX *= 16;
		self->dirY *= 16;

		self->flags |= UNBLOCKABLE;

		self->action = &headBiteReturn;
	}

	if (self->head->health <= 0)
	{
		self->die();
	}

	alignBodyToHead();

	self->damage = self->head->damage;

	self->face = self->head->face;

	if (self->head->flags & FLASH)
	{
		self->flags |= FLASH;
	}

	else
	{
		self->flags &= ~FLASH;
	}
}
int main(){
	int n,mark=0,x,y;
	long long **mat;
	scanf("%d",&n);
	mat=(long long**)malloc(n*sizeof(long long *));
	int i,j;
	for(i=0;i<n;i++){
		mat[i]=(long long*)malloc(n*sizeof(long long));
		for(j=0;j<n;j++){
			scanf("%lld",&mat[i][j]);
			if(mat[i][j]==0){
                mat[i][j]=10;
                mark=1;
                x=i;
                y=j;
			}
		}
	}
	calculatePath(mat,n,mark,x,y);
	free(mat);
	return 0;
}
Beispiel #14
0
static void blueDie()
{
	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		if (self->maxThinkTime == 4)
		{
			increaseKillCount();

			entityDie();
		}

		else
		{
			calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

			self->flags |= (NO_DRAW|HELPLESS|TELEPORTING);

			playSoundToMap("sound/common/teleport", BOSS_CHANNEL, self->x, self->y, 0);

			self->touch = &entityTouch;

			self->action = &blueWait;

			self->active = FALSE;

			self->startX = self->targetX;
			self->startY = self->targetY;

			self->health = self->maxHealth;
		}
	}

	else
	{
		shudder();
	}
}
Beispiel #15
0
static void addRiftEnergy(int x, int y)
{
	Entity *e;

	e = addBasicDecoration(x, y, "decoration/rift_energy");

	e->x += prand() % 128 * (prand() % 2 == 0 ? -1 : 1);
	e->y += prand() % 128 * (prand() % 2 == 0 ? -1 : 1);

	x -= e->w / 2;
	y -= e->h / 2;

	e->targetX = x;
	e->targetY = y;

	calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

	e->dirX *= 8;
	e->dirY *= 8;

	e->action = &energyMoveToRift;
}
Beispiel #16
0
static void teleportPlayerOffscreen(Entity *other)
{
	Target *t;

	t = getTargetByName("SORCEROR_PLAYER_TARGET");

	if (t == NULL)
	{
		showErrorAndExit("Sorceror cannot find target");
	}

	player.targetX = t->x;
	player.targetY = t->y;

	calculatePath(player.x, player.y, player.targetX, player.targetY, &player.dirX, &player.dirY);

	player.flags |= (NO_DRAW|HELPLESS|TELEPORTING);

	playSoundToMap("sound/common/spell", EDGAR_CHANNEL, self->x, self->y, 0);

	self->inUse = FALSE;
}
Beispiel #17
0
static void createLightningWaveInit()
{
	Entity *e;

	if (self->endX == 0)
	{
		e = addThunderCloud(self->x, self->y, "enemy/thunder_cloud");

		e->x = self->x + self->w / 2;
		e->y = self->y + self->h / 2;

		e->x -= e->w / 2;
		e->y -= e->h / 2;

		e->targetX = self->targetX;
		e->targetY = getMapCeiling(self->x, self->y);

		calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

		e->flags |= (NO_DRAW|HELPLESS|TELEPORTING|NO_END_TELEPORT_SOUND);

		playSoundToMap("sound/common/spell", -1, self->x, self->y, 0);

		e->head = self;

		e->face = RIGHT;

		setEntityAnimation(e, "STAND");

		e->action = &lightningWaveStart;

		self->endX = 1;
	}

	checkToMap(self);

	hover();
}
Beispiel #18
0
static void raiseDeadInit()
{
	Target *t = getTargetByName("AZRIEL_TOP_TARGET");

	if (t == NULL)
	{
		showErrorAndExit("Azriel cannot find target");
	}

	self->targetX = t->x;
	self->targetY = t->y;

	calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

	self->dirX *= self->speed;
	self->dirY *= self->speed;

	self->action = &raiseDeadMoveToTopTarget;

	checkToMap(self);

	becomeTransparent();
}
Beispiel #19
0
static void specialShotTouch(Entity *other)
{
    Entity *e;

    if (other->type == WEAPON && (other->flags & ATTACKING))
    {
        e = addProjectile("boss/snake_boss_special_shot", &player, self->x, self->y, 0, 0);

        e->targetX = self->target->x + self->target->w / 2;
        e->targetY = self->target->y + self->target->h / 2;

        calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

        e->dirX *= 12;
        e->dirY *= 12;

        e->dirX = (player.face == RIGHT ? fabs(e->dirX) : fabs(e->dirX) * -1);

        e->damage = 10;

        self->inUse = FALSE;
    }
}
Beispiel #20
0
static void phantasmalBoltInit()
{
	Target *t;

	if (prand() % 2 == 0)
	{
		t = getTargetByName("AZRIEL_LEFT_TARGET");

		self->face = RIGHT;
	}

	else
	{
		t = getTargetByName("AZRIEL_RIGHT_TARGET");

		self->face = LEFT;
	}

	if (t == NULL)
	{
		showErrorAndExit("Azriel cannot find target");
	}

	self->targetX = t->x;
	self->targetY = t->y;

	calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

	self->dirX *= self->speed;
	self->dirY *= self->speed;

	self->action = &phantasmalBoltMoveToTarget;

	checkToMap(self);

	becomeTransparent();
}
Beispiel #21
0
static void teleportPlayer()
{
	int frame;
	float timer, x, y;

	if (self->target != NULL)
	{
		getCheckpoint(&x, &y);

		self->target->targetX = x;
		self->target->targetY = y;

		calculatePath(self->target->x, self->target->y, self->target->targetX, self->target->targetY, &self->target->dirX, &self->target->dirY);

		self->target->flags |= (NO_DRAW|HELPLESS|TELEPORTING);

		playSoundToMap("sound/common/teleport", (self->target->type == PLAYER ? EDGAR_CHANNEL : -1), self->target->x, self->target->y, 0);

		self->target = NULL;
	}

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		frame = self->currentFrame;
		timer = self->frameTimer;

		setEntityAnimation(self, "STAND");

		self->currentFrame = frame;
		self->frameTimer = timer;

		self->action = strcmpignorecase("enemy/blue_scanner", self->name) == 0 ? &closedEyeMove : &lookForPlayer;
	}
}
Beispiel #22
0
static void crushAttackMoveToPosition()
{
    calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

    self->dirX *= 9;
    self->dirY *= 9;

    checkToMap(self);

    if (atTarget())
    {
        self->y = self->targetY;

        self->x = self->targetX;

        self->dirY = 0;

        self->dirX = 0;

        self->action = &crushAttack;
    }

    alignBodyToHead();
}
Beispiel #23
0
static void plasmaTakeDamage(Entity *other, int damage)
{
	Entity *sorceror;

	sorceror = self->parent;

	self->parent = &playerWeapon;

	self->targetX = sorceror->x + sorceror->w / 2 - self->w / 2;
	self->targetY = sorceror->y + sorceror->h / 2 - self->h / 2;

	calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

	self->dirX *= 12;
	self->dirY *= 12;

	self->thinkTime = 300;

	self->damage = 50;

	self->reactToBlock = &bounceOffShield;

	self->takeDamage = NULL;
}
Beispiel #24
0
static void teleportToOtherSide()
{
	Target *t;

	if (strcmpignorecase(self->name, "enemy/large_red_book") == 0)
	{
		t = getTargetByName("RED_BOOK_LEFT_SIDE");

		if (t == NULL)
		{
			showErrorAndExit("Red Book cannot find target");
		}

		if ((int)t->x == (int)self->x)
		{
			t = getTargetByName("RED_BOOK_TARGET_1");

			if (t == NULL)
			{
				showErrorAndExit("Red Book cannot find target");
			}
		}

		self->action = &fireAttackPause;
	}

	else if (strcmpignorecase(self->name, "enemy/large_blue_book") == 0)
	{
		t = getTargetByName("BLUE_BOOK_RIGHT_SIDE");

		if (t == NULL)
		{
			showErrorAndExit("Blue Book cannot find target");
		}

		if ((int)t->x == (int)self->x)
		{
			t = getTargetByName("BLUE_BOOK_TARGET_1");

			if (t == NULL)
			{
				showErrorAndExit("Blue Book cannot find target");
			}
		}

		self->action = &castIceFinish;
	}

	else if (strcmpignorecase(self->name, "enemy/large_yellow_book") == 0)
	{
		t = getTargetByName("YELLOW_BOOK_RIGHT_SIDE");

		if (t == NULL)
		{
			showErrorAndExit("Yellow Book cannot find target");
		}

		if ((int)t->x == (int)self->x)
		{
			t = getTargetByName("YELLOW_BOOK_TARGET_1");

			if (t == NULL)
			{
				showErrorAndExit("Yellow Book cannot find target");
			}
		}

		self->action = &castLightningFinish;
	}

	else
	{
		t = getTargetByName("GREEN_BOOK_RIGHT_SIDE");

		if (t == NULL)
		{
			showErrorAndExit("Green Book cannot find target");
		}

		if ((int)t->x == (int)self->x)
		{
			t = getTargetByName("GREEN_BOOK_TARGET_2");

			if (t == NULL)
			{
				showErrorAndExit("Green Book cannot find target");
			}
		}

		self->action = &physicalAttackPause;
	}

	self->targetX = t->x;
	self->targetY = t->y;

	calculatePath(self->x, self->y, self->targetX, self->targetY, &self->dirX, &self->dirY);

	self->flags |= (NO_DRAW|HELPLESS|TELEPORTING);

	playSoundToMap("sound/common/teleport", BOSS_CHANNEL, self->x, self->y, 0);
}
Beispiel #25
0
static void summonEnemies()
{
	char summonList[MAX_VALUE_LENGTH], enemyToSummon[MAX_VALUE_LENGTH];
	char *token;
	int i, summonIndex = 0, summonCount = 0;
	Entity *e;

	for (i=0;i<2;i++)
	{
		summonCount = 0;

		summonIndex = 0;

		STRNCPY(summonList, self->requires, MAX_VALUE_LENGTH);

		token = strtok(summonList, "|");

		while (token != NULL)
		{
			token = strtok(NULL, "|");

			summonCount++;
		}

		if (summonCount == 0)
		{
			showErrorAndExit("Scanner at %f %f has no summon list", self->x, self->y);
		}

		summonIndex = prand() % summonCount;

		STRNCPY(summonList, self->requires, MAX_VALUE_LENGTH);

		summonCount = 0;

		token = strtok(summonList, "|");

		while (token != NULL)
		{
			if (summonCount == summonIndex)
			{
				break;
			}

			token = strtok(NULL, "|");

			summonCount++;
		}

		snprintf(enemyToSummon, MAX_VALUE_LENGTH, "enemy/%s", token);

		e = addEnemy(enemyToSummon, self->x, self->y);

		e->x = self->x;

		e->y = self->y;

		e->targetX = self->x + (i == 0 ? -64 : 64);

		e->targetY = self->y;

		calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

		e->flags |= (NO_DRAW|HELPLESS|TELEPORTING);
	}
}
Beispiel #26
0
static void summon()
{
	Entity *e;

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		e = addBook(self->x, self->y, "enemy/green_book");

		e->pain = &enemyPain;

		e->targetX = player.x + player.w / 2 - e->w / 2 + 32;
		e->targetY = player.y - 32 - prand() % 64;

		e->startY = e->targetY;

		e->x = e->targetX;
		e->y = e->targetY;

		if (isValidOnMap(e) == TRUE)
		{
			e->x = self->x + self->w / 2;
			e->y = self->y + self->h / 2;

			e->x -= e->w / 2;
			e->y -= e->h / 2;

			e->health = 30;

			calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

			e->flags |= (NO_DRAW|HELPLESS|TELEPORTING|NO_END_TELEPORT_SOUND);

			playSoundToMap("sound/common/spell", -1, self->x, self->y, 0);

			e->face = RIGHT;

			self->endX--;
		}

		else
		{
			e->inUse = FALSE;
		}

		if (self->endX <= 0)
		{
			self->thinkTime = 300;

			self->action = &physicalAttackFinish;
		}

		else
		{
			self->thinkTime = 45;
		}
	}

	checkToMap(self);

	hover();
}
Beispiel #27
0
static void summon2()
{
	int i;
	Entity *e;

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		i = prand() % 4;

		switch (i)
		{
			case 0:
				e = addBook(self->x, self->y, "enemy/green_book");
			break;

			case 1:
				e = addBook(self->x, self->y, "enemy/yellow_book");
			break;

			case 2:
				e = addBook(self->x, self->y, "enemy/red_book");
			break;

			default:
				e = addBook(self->x, self->y, "enemy/blue_book");
			break;
		}

		e->pain = &enemyPain;

		e->targetX = player.x + player.w / 2 - e->w / 2 + (self->face == RIGHT ? 64 : -64);
		e->targetY = player.y - 32 - prand() % 64;

		e->startY = e->targetY;

		e->x = e->targetX;
		e->y = e->targetY;

		if (isValidOnMap(e) == TRUE)
		{
			e->x = self->x + self->w / 2;
			e->y = self->y + self->h / 2;

			e->x -= e->w / 2;
			e->y -= e->h / 2;

			e->health = 30;

			calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

			e->flags |= (NO_DRAW|HELPLESS|TELEPORTING|NO_END_TELEPORT_SOUND);

			playSoundToMap("sound/common/spell", -1, self->x, self->y, 0);

			e->face = RIGHT;

			self->endX--;
		}

		else
		{
			e->inUse = FALSE;
		}

		if (self->endX <= 0)
		{
			self->thinkTime = 120;

			self->action = &physicalAttackFinish;
		}

		else
		{
			self->thinkTime = 45;
		}
	}

	facePlayer();

	checkToMap(self);

	hover();
}
Beispiel #28
0
static void createIceBlock()
{
	int x, y;
	Entity *e;

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		e = getFreeEntity();

		if (e == NULL)
		{
			showErrorAndExit("No free slots to add Ice Block");
		}

		loadProperties("edgar/edgar_frozen", e);

		setEntityAnimation(e, "STAND");

		x = player.x + player.w / 2;
		y = self->y - 100 - (prand() % 60);

		e->x = x;
		e->y = y;

		if (isValidOnMap(e) == TRUE)
		{
			e->x = self->x + self->w / 2;
			e->y = self->y + self->h / 2;

			e->x -= e->w / 2;
			e->y -= e->h / 2;

			e->targetX = x;
			e->targetY = y;

			e->damage = 1;

			e->health = 50;

			calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

			e->flags |= (NO_DRAW|HELPLESS|TELEPORTING|NO_END_TELEPORT_SOUND);

			playSoundToMap("sound/common/spell", -1, self->x, self->y, 0);

			e->action = &iceBlockDrop;
			e->draw = &drawLoopingAnimationToMap;
			e->touch = &entityTouch;
			e->pain = &enemyPain;
			e->die = &iceBlockDie;

			e->head = self;

			e->face = self->face;

			e->type = ENEMY;

			e->thinkTime = 30;

			e->flags |= FLY|DO_NOT_PERSIST;

			self->endX--;

			if (self->endX <= 0)
			{
				self->thinkTime = 0;

				self->action = &castIceFinish;
			}

			else
			{
				self->thinkTime = 60;
			}
		}

		else
		{
			e->inUse = FALSE;
		}
	}

	checkToMap(self);

	hover();
}
Beispiel #29
0
static void castLightningBolt()
{
	Entity *e;

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		e = getFreeEntity();

		if (e == NULL)
		{
			showErrorAndExit("No free slots to add lightning");
		}

		loadProperties("enemy/lightning", e);

		setEntityAnimation(e, "STAND");

		e->x = self->x + self->w / 2;
		e->y = self->y + self->h / 2;

		e->x -= e->w / 2;
		e->y -= e->h / 2;

		e->targetX = player.x + player.w / 2 - e->w / 2;
		e->targetY = getMapCeiling(self->x, self->y);

		e->startY = e->targetY;
		e->endY   = getMapFloor(e->targetX, e->targetY);

		calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

		e->flags |= (NO_DRAW|HELPLESS|TELEPORTING|NO_END_TELEPORT_SOUND);

		playSoundToMap("sound/common/spell", -1, self->x, self->y, 0);

		e->head = self;

		e->face = RIGHT;

		e->action = &lightningBolt;

		e->draw = &drawLoopingAnimationToMap;

		e->head = self;

		e->face = self->face;

		e->type = ENEMY;

		e->thinkTime = 0;

		e->flags |= FLY|DO_NOT_PERSIST;

		self->mental--;

		if (self->mental <= 0)
		{
			self->thinkTime = 60;

			self->action = &attackFinished;
		}

		else
		{
			self->thinkTime = 30;
		}
	}

	hover();
}
Beispiel #30
0
static void callSummoners()
{
	int r;
	Entity *e;
	Target *t;

	self->thinkTime--;

	if (self->thinkTime <= 0)
	{
		setEntityAnimation(self, "ATTACK_1");

		self->mental--;

		playSoundToMap("sound/common/spell", BOSS_CHANNEL, self->x, self->y, 0);

		e = addEnemy("enemy/sorceror_dark_summoner", 0, 0);

		e->x = self->x + self->w / 2 - e->w / 2;
		e->y = self->y + self->h / 2 - e->h / 2;

		r = prand() % 3;

		switch (r)
		{
			case 0:
				t = getTargetByName("DARK_SUMMONER_TARGET_0");
			break;

			case 1:
				t = getTargetByName("DARK_SUMMONER_TARGET_1");
			break;

			default:
				t = getTargetByName("DARK_SUMMONER_TARGET_2");
			break;
		}

		if (t == NULL)
		{
			showErrorAndExit("Sorceror cannot find target");
		}

		e->targetX = t->x;
		e->targetY = t->y;

		e->startX = e->targetX;
		e->startY = e->targetY;

		e->maxThinkTime = self->maxThinkTime;

		calculatePath(e->x, e->y, e->targetX, e->targetY, &e->dirX, &e->dirY);

		e->flags |= (NO_DRAW|HELPLESS|TELEPORTING);

		e->head = self;

		if (self->mental <= 0)
		{
			setEntityAnimation(self, "STAND");

			self->maxThinkTime++;

			self->action = &callSummonersWait;
		}

		self->thinkTime = 30;
	}

	hover();
}