⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 p_henemy.c

📁 The source code of Doom legacy for windows
💻 C
📖 第 1 页 / 共 3 页
字号:
// Emacs style mode select   -*- C++ -*- //-----------------------------------------------------------------------------//// $Id: p_henemy.c,v 1.4 2001/04/17 22:26:07 calumr Exp $//// Copyright (C) 1993-1996 by Raven Software, Corp.// Portions Copyright (C) 1998-2000 by DooM Legacy Team.//// This program is free software; you can redistribute it and/or// modify it under the terms of the GNU General Public License// as published by the Free Software Foundation; either version 2// of the License, or (at your option) any later version.//// This program is distributed in the hope that it will be useful,// but WITHOUT ANY WARRANTY; without even the implied warranty of// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the// GNU General Public License for more details.////// $Log: p_henemy.c,v $// Revision 1.4  2001/04/17 22:26:07  calumr// Initial Mac add//// Revision 1.3  2001/02/24 13:35:20  bpereira// no message//////// DESCRIPTION://   this file is include by P_enemy.c//   it contain all heretic enemey specific////-----------------------------------------------------------------------------// Macros#define MAX_BOSS_SPOTS 8// Typestypedef struct{	fixed_t x;	fixed_t y;	angle_t angle;} BossSpot_t;// Private Datastatic int BossSpotCount;static BossSpot_t BossSpots[MAX_BOSS_SPOTS];// Proto//----------------------------------------------------------------------------//// PROC P_InitMonsters//// Called at level load.////----------------------------------------------------------------------------void P_InitMonsters(void){	BossSpotCount = 0;}//----------------------------------------------------------------------------//// PROC P_AddBossSpot////----------------------------------------------------------------------------void P_AddBossSpot(fixed_t x, fixed_t y, angle_t angle){	if(BossSpotCount == MAX_BOSS_SPOTS)	{		I_Error("Too many boss spots.");	}	BossSpots[BossSpotCount].x = x;	BossSpots[BossSpotCount].y = y;	BossSpots[BossSpotCount].angle = angle;	BossSpotCount++;}//---------------------------------------------------------------------------//// FUNC P_LookForMonsters////---------------------------------------------------------------------------#define MONS_LOOK_RANGE (20*64*FRACUNIT)#define MONS_LOOK_LIMIT 64boolean P_LookForMonsters(mobj_t *actor){	int count;	mobj_t *mo;	thinker_t *think;	if(!P_CheckSight(players[0].mo, actor))	{ // Player can't see monster		return(false);	}	count = 0;	for(think = thinkercap.next; think != &thinkercap; think = think->next)	{		if(think->function.acp1 != (actionf_p1)P_MobjThinker)		{ // Not a mobj thinker			continue;		}		mo = (mobj_t *)think;		if(!(mo->flags&MF_COUNTKILL) || (mo == actor) || (mo->health <= 0))		{ // Not a valid monster			continue;		}		if(P_AproxDistance(actor->x-mo->x, actor->y-mo->y)			> MONS_LOOK_RANGE)		{ // Out of range			continue;		}		if(P_Random() < 16)		{ // Skip			continue;		}		if(count++ > MONS_LOOK_LIMIT)		{ // Stop searching			return(false);		}		if(!P_CheckSight(actor, mo))		{ // Out of sight			continue;		}		// Found a target monster		actor->target = mo;		return(true);	}	return(false);}/*===============================================================================						ACTION ROUTINES===============================================================================*///----------------------------------------------------------------------------//// PROC A_DripBlood////----------------------------------------------------------------------------void A_DripBlood(mobj_t *actor){	mobj_t *mo;        int r,s;        // evaluation order isn't define in C        r = P_SignedRandom();        s = P_SignedRandom();	mo = P_SpawnMobj(actor->x+(r<<11),		         actor->y+(s<<11), actor->z, MT_BLOOD);	mo->momx = P_SignedRandom()<<10;	mo->momy = P_SignedRandom()<<10;	mo->flags2 |= MF2_LOGRAV;}//----------------------------------------------------------------------------//// PROC A_KnightAttack////----------------------------------------------------------------------------void A_KnightAttack(mobj_t *actor){	if(!actor->target)	{		return;	}	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, HITDICE(3));		S_StartSound(actor, sfx_kgtat2);		return;	}	// Throw axe	S_StartSound(actor, actor->info->attacksound);	if(actor->type == MT_KNIGHTGHOST || P_Random() < 40)	{ // Red axe		P_SpawnMissile(actor, actor->target, MT_REDAXE);		return;	}	// Green axe	P_SpawnMissile(actor, actor->target, MT_KNIGHTAXE);}//----------------------------------------------------------------------------//// PROC A_ImpExplode////----------------------------------------------------------------------------void A_ImpExplode(mobj_t *actor){	mobj_t *mo;	mo = P_SpawnMobj(actor->x, actor->y, actor->z, MT_IMPCHUNK1);	mo->momx = P_SignedRandom()<<10;	mo->momy = P_SignedRandom()<<10;	mo->momz = 9*FRACUNIT;	mo = P_SpawnMobj(actor->x, actor->y, actor->z, MT_IMPCHUNK2);	mo->momx = P_SignedRandom()<<10;	mo->momy = P_SignedRandom()<<10;	mo->momz = 9*FRACUNIT;	if(actor->special1 == 666)	{ // Extreme death crash	    P_SetMobjState(actor, S_IMP_XCRASH1);	}}//----------------------------------------------------------------------------//// PROC A_BeastPuff////----------------------------------------------------------------------------void A_BeastPuff(mobj_t *actor){    if(P_Random() > 64)    {        int r,s,t;        r = P_SignedRandom();        s = P_SignedRandom();        t = P_SignedRandom();                P_SpawnMobj(actor->x+(r<<10),                    actor->y+(s<<10),                    actor->z+(t<<10), MT_PUFFY);    }}//----------------------------------------------------------------------------//// PROC A_ImpMeAttack////----------------------------------------------------------------------------void A_ImpMeAttack(mobj_t *actor){	if(!actor->target)	{		return;	}	S_StartSound(actor, actor->info->attacksound);	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, 5+(P_Random()&7));	}}//----------------------------------------------------------------------------//// PROC A_ImpMsAttack////----------------------------------------------------------------------------void A_ImpMsAttack(mobj_t *actor){	mobj_t *dest;	angle_t an;	int dist;	if(!actor->target || P_Random() > 64)	{		P_SetMobjState(actor, actor->info->seestate);		return;	}	dest = actor->target;	actor->flags |= MF_SKULLFLY;	S_StartSound(actor, actor->info->attacksound);	A_FaceTarget(actor);	an = actor->angle >> ANGLETOFINESHIFT;	actor->momx = FixedMul(12*FRACUNIT, finecosine[an]);	actor->momy = FixedMul(12*FRACUNIT, finesine[an]);	dist = P_AproxDistance(dest->x-actor->x, dest->y-actor->y);	dist = dist/(12*FRACUNIT);	if(dist < 1)	{		dist = 1;	}	actor->momz = (dest->z+(dest->height>>1)-actor->z)/dist;}//----------------------------------------------------------------------------//// PROC A_ImpMsAttack2//// Fireball attack of the imp leader.////----------------------------------------------------------------------------void A_ImpMsAttack2(mobj_t *actor){	if(!actor->target)	{		return;	}	S_StartSound(actor, actor->info->attacksound);	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, 5+(P_Random()&7));		return;	}	P_SpawnMissile(actor, actor->target, MT_IMPBALL);}//----------------------------------------------------------------------------//// PROC A_ImpDeath////----------------------------------------------------------------------------void A_ImpDeath(mobj_t *actor){	actor->flags &= ~MF_SOLID;	actor->flags2 |= MF2_FOOTCLIP;        actor->flags  |= MF_CORPSE|MF_DROPOFF;        actor->height >>= 2;        actor->radius -= (actor->radius>>4);      //for solid corpses	if(actor->z <= actor->floorz)	{	    P_SetMobjState(actor, S_IMP_CRASH1);            actor->flags &= ~MF_CORPSE;	}}//----------------------------------------------------------------------------//// PROC A_ImpXDeath1////----------------------------------------------------------------------------void A_ImpXDeath1(mobj_t *actor){	actor->flags &= ~MF_SOLID;	actor->flags |= MF_NOGRAVITY;        actor->flags  |= MF_CORPSE|MF_DROPOFF;        actor->height >>= 2;        actor->radius -= (actor->radius>>4);      //for solid corpses	actor->flags2 |= MF2_FOOTCLIP;	actor->special1 = 666; // Flag the crash routine}//----------------------------------------------------------------------------//// PROC A_ImpXDeath2////----------------------------------------------------------------------------void A_ImpXDeath2(mobj_t *actor){	actor->flags &= ~MF_NOGRAVITY;	if(actor->z <= actor->floorz)	{            P_SetMobjState(actor, S_IMP_CRASH1);            actor->flags &= ~MF_CORPSE;	}}//----------------------------------------------------------------------------//// FUNC P_UpdateChicken//// Returns true if the chicken morphs.////----------------------------------------------------------------------------#define TELEFOGHEIGHT (32*FRACUNIT)boolean P_UpdateChicken(mobj_t *actor, int tics){	mobj_t *fog;	fixed_t x;	fixed_t y;	fixed_t z;	mobjtype_t moType;	mobj_t *mo;	mobj_t oldChicken;	actor->special1 -= tics;	if(actor->special1 > 0)	{		return(false);	}	moType = actor->special2;	x = actor->x;	y = actor->y;	z = actor->z;	oldChicken = *actor;	P_SetMobjState(actor, S_FREETARGMOBJ);	mo = P_SpawnMobj(x, y, z, moType);	if(P_TestMobjLocation(mo) == false)	{ // Didn't fit		P_RemoveMobj(mo);		mo = P_SpawnMobj(x, y, z, MT_CHICKEN);		mo->angle = oldChicken.angle;		mo->flags = oldChicken.flags;		mo->health = oldChicken.health;		mo->target = oldChicken.target;		mo->special1 = 5*35; // Next try in 5 seconds		mo->special2 = moType;		return(false);	}	mo->angle = oldChicken.angle;	mo->target = oldChicken.target;	fog = P_SpawnMobj(x, y, z+TELEFOGHEIGHT, MT_TFOG);	S_StartSound(fog, sfx_telept);	return(true);}//----------------------------------------------------------------------------//// PROC A_ChicAttack////----------------------------------------------------------------------------void A_ChicAttack(mobj_t *actor){	if(P_UpdateChicken(actor, 18))	{		return;	}	if(!actor->target)	{		return;	}	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, 1+(P_Random()&1));	}}//----------------------------------------------------------------------------//// PROC A_ChicLook////----------------------------------------------------------------------------void A_ChicLook(mobj_t *actor){	if(P_UpdateChicken(actor, 10))	{		return;	}	A_Look(actor);}//----------------------------------------------------------------------------//// PROC A_ChicChase////----------------------------------------------------------------------------void A_ChicChase(mobj_t *actor){	if(P_UpdateChicken(actor, 3))	{		return;	}	A_Chase(actor);}//----------------------------------------------------------------------------//// PROC A_ChicPain////----------------------------------------------------------------------------void A_ChicPain(mobj_t *actor){	if(P_UpdateChicken(actor, 10))	{		return;	}	S_StartSound(actor, actor->info->painsound);}//----------------------------------------------------------------------------//// PROC A_Feathers////----------------------------------------------------------------------------void A_Feathers(mobj_t *actor){	int i;	int count;	mobj_t *mo;	if(actor->health > 0)	{ // Pain		count = P_Random() < 32 ? 2 : 1;	}	else	{ // Death		count = 5+(P_Random()&3);	}	for(i = 0; i < count; i++)	{		mo = P_SpawnMobj(actor->x, actor->y, actor->z+20*FRACUNIT,			MT_FEATHER);		mo->target = actor;		mo->momx = P_SignedRandom()<<8;		mo->momy = P_SignedRandom()<<8;		mo->momz = FRACUNIT+(P_Random()<<9);		P_SetMobjState(mo, S_FEATHER1+(P_Random()&7));	}}//----------------------------------------------------------------------------//// PROC A_MummyAttack////----------------------------------------------------------------------------void A_MummyAttack(mobj_t *actor){	if(!actor->target)	{		return;	}	S_StartSound(actor, actor->info->attacksound);	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, HITDICE(2));		S_StartSound(actor, sfx_mumat2);		return;	}	S_StartSound(actor, sfx_mumat1);}//----------------------------------------------------------------------------//// PROC A_MummyAttack2//// Mummy leader missile attack.////----------------------------------------------------------------------------void A_MummyAttack2(mobj_t *actor){	mobj_t *mo;	if(!actor->target)	{		return;	}	//S_StartSound(actor, actor->info->attacksound);	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, HITDICE(2));		return;	}	mo = P_SpawnMissile(actor, actor->target, MT_MUMMYFX1);	//mo = P_SpawnMissile(actor, actor->target, MT_EGGFX);	if(mo != NULL)	{		mo->special1 = (int)actor->target;	}}//----------------------------------------------------------------------------//// PROC A_MummyFX1Seek////----------------------------------------------------------------------------void A_MummyFX1Seek(mobj_t *actor){	P_SeekerMissile(actor, ANGLE_1*10, ANGLE_1*20);}//----------------------------------------------------------------------------//// PROC A_MummySoul////----------------------------------------------------------------------------void A_MummySoul(mobj_t *mummy){	mobj_t *mo;	mo = P_SpawnMobj(mummy->x, mummy->y, mummy->z+10*FRACUNIT, MT_MUMMYSOUL);	mo->momz = FRACUNIT;}//----------------------------------------------------------------------------//// PROC A_Sor1Pain////----------------------------------------------------------------------------void A_Sor1Pain(mobj_t *actor){	actor->special1 = 20; // Number of steps to walk fast	A_Pain(actor);}//----------------------------------------------------------------------------//// PROC A_Sor1Chase////----------------------------------------------------------------------------void A_Sor1Chase(mobj_t *actor){	if(actor->special1)	{		actor->special1--;		actor->tics -= 3;	}	A_Chase(actor);}//----------------------------------------------------------------------------//// PROC A_Srcr1Attack//// Sorcerer demon attack.////----------------------------------------------------------------------------void A_Srcr1Attack(mobj_t *actor){	mobj_t *mo;	fixed_t momz;	angle_t angle;	if(!actor->target)	{		return;	}	S_StartSound(actor, actor->info->attacksound);	if(P_CheckMeleeRange(actor))	{		P_DamageMobj(actor->target, actor, actor, HITDICE(8));		return;	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -