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

📄 monsterai.cpp

📁 天之炼狱1服务器端源文件游戏服务端不完整
💻 CPP
📖 第 1 页 / 共 4 页
字号:
//////////////////////////////////////////////////////////////////////////////// Filename    : MonsterAI.cpp// Written By  : excel96// Description : //////////////////////////////////////////////////////////////////////////////#include "MonsterAI.h"#include "Zone.h"#include "Slayer.h"#include "Vampire.h"#include "Monster.h"#include "MonsterInfo.h"#include "EffectManager.h"#include "SkillInfo.h"#include "skill/SkillHandlerManager.h"#include "Directive.h"#include "ZoneUtil.h"#include "Tile.h"#include "MonsterManager.h"#include "MasterLairManager.h"#include "VariableManager.h"#include "Effect.h"#include "Profile.h"#define ABS(X) ((X)>=0)?X:-X//#define __PROFILE_MONSTER__#ifdef __PROFILE_MONSTER__	#define __BEGIN_PROFILE_MONSTER(name)	beginProfileEx(name);	#define __END_PROFILE_MONSTER(name)		endProfileEx(name);#else	#define __BEGIN_PROFILE_MONSTER(name)	((void)0);	#define __END_PROFILE_MONSTER(name)		((void)0);#endifTPOINT getSafeTile(Zone* pZone, ZoneCoord_t x, ZoneCoord_t y){	TPOINT ptAcid;	ptAcid = findSuitablePositionForEffect( pZone, x, y, Effect::EFFECT_CLASS_ACID_SWAMP );	/*	TPOINT ptBloody;	ptBloody = findSuitablePositionForEffect( pZone, x, y, Effect::EFFECT_CLASS_BLOODY_WALL );	*/	return ptAcid;}int getStrongValue(Creature* pCreature){	HP_t currentHP = 0;	HP_t maxHP = 0;	int  strongValue = 0;	if (pCreature->isSlayer())	{		Slayer* pSlayer = dynamic_cast<Slayer*>(pCreature);		currentHP = pSlayer->getHP(ATTR_CURRENT);		maxHP = pSlayer->getHP(ATTR_MAX);		strongValue = pSlayer->getSTR() + 						pSlayer->getDEX() + 						pSlayer->getINT() + 						pSlayer->getProtection() + 						pSlayer->getDefense();	}	else if (pCreature->isVampire())	{		Vampire* pVampire = dynamic_cast<Vampire*>(pCreature);		currentHP = pVampire->getHP(ATTR_CURRENT);		maxHP = pVampire->getHP(ATTR_MAX);		strongValue = pVampire->getSTR() + 						pVampire->getDEX() + 						pVampire->getINT() +						pVampire->getProtection() + 						pVampire->getDefense();	}	else if (pCreature->isOusters())	{		Ousters* pOusters = dynamic_cast<Ousters*>(pCreature);		currentHP = pOusters->getHP(ATTR_CURRENT);		maxHP = pOusters->getHP(ATTR_MAX);		strongValue = pOusters->getSTR() + 						pOusters->getDEX() + 						pOusters->getINT() +						pOusters->getProtection() + 						pOusters->getDefense();	}	else if (pCreature->isMonster())	{		Monster* pMonster = dynamic_cast<Monster*>(pCreature);		currentHP = pMonster->getHP(ATTR_CURRENT);		maxHP = pMonster->getHP(ATTR_MAX);		strongValue = pMonster->getSTR() + 						pMonster->getDEX() + 						pMonster->getINT() +						pMonster->getProtection() + 						pMonster->getDefense();	}	else return 0;	// pCreature HP啊 120捞惑 	if (currentHP>=120)	{		strongValue += 200;	}		// HP percentage啊 60% 捞惑捞扼搁 	if (currentHP*100 >= maxHP*60)	{		strongValue += 200;	}	return strongValue;}////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////TPOINT randPos(int ox, int oy, int threshold, Zone* pZone) 	throw(){	int tx = ox + (rand()%(threshold*2)) - threshold;	int ty = oy + (rand()%(threshold*2)) - threshold;	if (tx < 0) tx = 0;	else if (tx >= pZone->getWidth()) tx = pZone->getWidth() - 1;	if (ty < 0) ty = 0;	else if (ty >= pZone->getHeight()) ty = pZone->getHeight() - 1;	TPOINT pt;	pt.x = tx;	pt.y = ty;	return pt;}//////////////////////////////////////////////////////////////////////////////// 积己磊/家戈磊//////////////////////////////////////////////////////////////////////////////MonsterAI::MonsterAI(Monster* pMonster, uint type)	throw(){	__BEGIN_TRY	Assert(pMonster != NULL);	// by sigi	m_pBody         = pMonster;	m_AIType        = type;	m_Panic         = 5;	m_PanicMax      = 5;	m_Courage       = 20;	m_CourageMax    = 20;	m_bDamaged      = false;	m_LastAction    = LAST_ACTION_NONE;	m_MoveRule 		= MOVE_RULE_NORMAL;	m_BlockedDir	= DIR_NONE;	m_WallCount		= 0;	m_pDirectiveSet = g_pDirectiveSetManager->getDirectiveSet(type);	m_pCondChecker[DIRECTIVE_COND_ENEMY_RANGE_MELEE]           = checkEnemyRangeMelee;	m_pCondChecker[DIRECTIVE_COND_ENEMY_RANGE_MISSILE]         = checkEnemyRangeMissile;	m_pCondChecker[DIRECTIVE_COND_ENEMY_RANGE_CLOSE]           = checkEnemyRangeClose;	m_pCondChecker[DIRECTIVE_COND_ENEMY_RANGE_OUT_OF_SIGHT]    = checkEnemyRangeOutOfSight;	m_pCondChecker[DIRECTIVE_COND_ENEMY_DYING]                 = checkEnemyDying;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_BLOOD_DRAINED]     = checkEnemyNotBloodDrained;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_GREEN_POISONED]    = checkEnemyNotGreenPoisoned;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_YELLOW_POISONED]   = checkEnemyNotYellowPoisoned;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_DARKBLUE_POISONED] = checkEnemyNotDarkbluePoisoned;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_GREEN_STALKERED]   = checkEnemyNotGreenStalkered;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_PARALYZED]         = checkEnemyNotParalyzed;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_DOOMED]            = checkEnemyNotDoomed;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_BLINDED]           = checkEnemyNotBlinded;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_IN_DARKNESS]       = checkEnemyNotInDarkness;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_SEDUCTION]      = checkEnemyNotSeduction;	m_pCondChecker[DIRECTIVE_COND_IM_OK]                       = checkImOK;	m_pCondChecker[DIRECTIVE_COND_IM_DYING]                    = checkImDying;	m_pCondChecker[DIRECTIVE_COND_IM_DAMAGED]                  = checkImDamaged;	m_pCondChecker[DIRECTIVE_COND_IM_HIDING]                   = checkImHiding;	m_pCondChecker[DIRECTIVE_COND_IM_WOLF]                     = checkImWolf;	m_pCondChecker[DIRECTIVE_COND_IM_BAT]                      = checkImBat;	m_pCondChecker[DIRECTIVE_COND_IM_INVISIBLE]                = checkImInvisible;	m_pCondChecker[DIRECTIVE_COND_IM_WALKING_WALL]             = checkImWalkingWall;	m_pCondChecker[DIRECTIVE_COND_TIMING_BLOOD_DRAIN]          = checkTimingBloodDrain;	m_pCondChecker[DIRECTIVE_COND_MASTER_SUMMON_TIMING]        = checkMasterSummonTiming;	m_pCondChecker[DIRECTIVE_COND_MASTER_NOT_READY]            = checkMasterNotReady;	m_pCondChecker[DIRECTIVE_COND_IM_IN_BAD_POSITION]          = checkImInBadPosition;	m_pCondChecker[DIRECTIVE_COND_FIND_WEAK_ENEMY]             = checkFindWeakEnemy;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_DEATH]            = checkEnemyNotDeath;	m_pCondChecker[DIRECTIVE_COND_ENEMY_NOT_HALLUCINATION]    = checkEnemyNotHallucination;	m_pCondChecker[DIRECTIVE_COND_TIMING_MASTER_BLOOD_DRAIN]  = checkTimingMasterBloodDrain;	m_pCondChecker[DIRECTIVE_COND_TIMING_DUPLICATE_SELF]  	   = checkTimingDuplicateSelf;	m_pCondChecker[DIRECTIVE_COND_ENEMY_RANGE_IN_MISSILE]         = checkEnemyRangeInMissile;	m_pCondChecker[DIRECTIVE_COND_POSSIBLE_SUMMON_MONSTERS]   = checkPossibleSummonMonsters;	m_pCondChecker[DIRECTIVE_COND_ENEMY_TILE_NOT_ACID_SWAMP]	= checkEnemyTileNotAcidSwamp;	m_pCondChecker[DIRECTIVE_COND_ENEMY_ON_AIR]					= checkEnemyOnAir;	m_pCondChecker[DIRECTIVE_COND_ENEMY_ON_SAFE_ZONE]			= checkEnemyOnSafeZone;	__END_CATCH}MonsterAI::~MonsterAI()	throw(){	__BEGIN_TRY	__END_CATCH}////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////void MonsterAI::addDirective(Directive* pDirective)	throw(){	__BEGIN_TRY	m_pDirectiveSet->addDirective(pDirective);	__END_CATCH}//////////////////////////////////////////////////////////////////////////////// 炼扒 窃荐//////////////////////////////////////////////////////////////////////////////bool MonsterAI::checkCondition(int condition, Creature* pEnemy)	throw(){	__BEGIN_TRY	Assert(0 <= condition && condition < DIRECTIVE_COND_MAX);//	cout << m_pBody->toString() << " check condition " << condition << " to" << pEnemy->toString() << endl;	return m_pCondChecker[condition](m_pBody, pEnemy);	__END_CATCH}bool MonsterAI::checkDirective(Directive* pDirective, Creature* pEnemy)	throw(){	__BEGIN_TRY	if (pDirective == NULL) return false;	// 牧叼记 府胶飘甫 掘绢郴绊...	list<int>& conditionList = pDirective->getConditions();	bool       rValue        = true;	// 炼扒 吝俊 窍唱扼档 父练窍瘤 臼绰 巴捞 乐促搁,	// false甫 府畔茄促.	list<int>::iterator itr = conditionList.begin();	for (; itr != conditionList.end(); itr++)	{		if (checkCondition(*itr, pEnemy) == false)		{			rValue = false;			break;		}	}	return rValue;	__END_CATCH}//////////////////////////////////////////////////////////////////////////////// 焊烹狼 框流烙//////////////////////////////////////////////////////////////////////////////bool MonsterAI::moveNormal(ZoneCoord_t ex, ZoneCoord_t ey, ZoneCoord_t& nx, ZoneCoord_t& ny, Dir_t& ndir)	throw(){	//Zone*       pZone   = m_pBody->getZone();	Dir_t       bestDir = DIR_NONE;	Dir_t curDir = m_pBody->getDir();	////////////////////////////////////////////////////////////	// 格利瘤痢栏肺 氢窍绰 弥急狼 规氢阑 茫绰促.	////////////////////////////////////////////////////////////	if (m_pBody->getX() < ex) 	{		if (m_pBody->getY() < ey)      bestDir = RIGHTDOWN;		else if (m_pBody->getY() > ey) bestDir = RIGHTUP;		else                           bestDir = RIGHT;// m_pBody->getY() == ey	} 	else if (m_pBody->getX() > ex) 	{		if (m_pBody->getY() < ey)      bestDir = LEFTDOWN;		else if (m_pBody->getY() > ey) bestDir = LEFTUP;		else                           bestDir = LEFT;// m_pBody->getY() == ey	} 	else 	{			if (m_pBody->getY() < ey)      bestDir = DOWN; // m_pBody->getX() == ex		else if (m_pBody->getY() > ey) bestDir = UP;		else                           bestDir = DIR_NONE; // m_pBody->getY() == ey	}	////////////////////////////////////////////////////////////	// search surrounding tiles	////////////////////////////////////////////////////////////	int diffLevel = 0;	// 规氢苞 规氢 荤捞狼 瞒捞甫 唱鸥辰促. diffLevel == 1 俊辑, diff == 0 捞扁 困秦辑	// 0 栏肺 檬扁拳秦具 茄促. 弊犯瘤 臼栏搁, garbage 蔼栏肺 牢秦 坷幅啊 唱霸 等促.	int diff = 0;	// 促澜 规氢捞 惯斑登菌绰啊?	bool found = false;	// 快急 bestDir 何磐 眉农秦夯促. unsigned type 捞 登绢辑绰 救等促.	ndir = bestDir;	// 促澜 谅钎	nx = m_pBody->getX() + dirMoveMask[ndir].x;	ny = m_pBody->getY() + dirMoveMask[ndir].y;	bool bBlocked[DIR_MAX] = { false, };	const Dir_t DIR_MAX_1 = DIR_MAX - 1;	// bestDir 规氢捞 阜囚 乐促搁, previous Dir 规氢阑 扁霖栏肺 +- 窍搁辑 眉农茄促.	// 捞锭 粮狼 版拌甫 逞绢辑绰瘤 眉农甫 秦具 茄促.	bool bCanMove = m_pBody->canMove(nx,ny);	// 付胶磐牢 版快俊绰 官蹿俊 救 亮篮霸 绝绢具 茄促. - -; by sigi. 2002.9.12	/*	if (bCanMove && m_pBody->isMaster())	{		Tile& tile = m_pBody->getZone()->getTile(nx, ny);		if (tile.hasEffect())		{			if (tile.getEffect(Effect::EFFECT_CLASS_ACID_SWAMP)!=NULL				&& tile.getEffect(Effect::EFFECT_CLASS_GROUND_ATTACK)!=NULL)			{			}			else bCanMove = false;		}	}	*/	if (!bCanMove)	{		bBlocked[ndir] = true;		// best direction捞 寒捞扼搁 促澜何磐 寒鸥扁甫 茄促.		// 冠零唱 hide吝捞 酒聪绢具 茄促.		if (!m_pBody->isBlockedByCreature(nx,ny)			&& !m_pBody->isFlag(Effect::EFFECT_CLASS_TRANSFORM_TO_BAT)			&& !m_pBody->isFlag(Effect::EFFECT_CLASS_HIDE))		{			setMoveRule( MOVE_RULE_RIGHTWALL ); // 咯扁搏 喊 狼固绝促.			m_BlockedDir = bestDir;			// 捞锅 畔俊绰 弊成 哎 规氢阑 搬沥窍搁 等促.		}		while (true) 		{			// 弥檬老 版快, diffLevel == 1 捞 等促. 捞绰 m_pBody->getDir() 规氢阑 眉农窍扼绰 舵捞促.			diffLevel ++;			// 利例茄 规氢阑 茫疽芭唱, 歹捞惑 茫阑 荐 绝促搁 场辰促.			if (found || diffLevel > 8) break;			////////////////////////////////////////////////////////////			// diffLevel 阑 2 肺 唱传 蔼捞 鞍促绰 舵篮, 辑肺 措莫登绰			// 规氢捞扼绰 舵捞促.  弊 吝 娄荐甫 父唱搁 弥檬肺 diff 甫 			// 拌魂秦辑 茄率 规氢阑 眉农窍哥, 圈荐甫 父唱搁 捞傈 风橇俊辑			// 馆措祈 规氢捞 眉农登菌促绰 舵捞骨肺, 拌魂等 diff 狼			// 澜荐甫 荤侩秦辑 促弗祈 规氢阑 眉农窍搁 登摆促.			////////////////////////////////////////////////////////////			if ((diffLevel & 0x00000001) == 0) 	// % 2 牢单.. 官插寸.. せせ by sigi 			{				//diff = (int)(diffLevel >> 1) * (bSelectLeft ? 1 : -1);				diff = diffLevel >> 1;				Dir_t dir1 = (m_pBody->getDir() + diff) & DIR_MAX_1;				Dir_t dir2 = (m_pBody->getDir() + DIR_MAX - diff) & DIR_MAX_1;				// bestDir俊 啊鳖款 率阑 刚历 急琶秦焊磊.				if ((abs(ndir+DIR_MAX-dir1) & DIR_MAX_1) 						< (abs(ndir+DIR_MAX-dir2) & DIR_MAX_1))				{					ndir = dir1;				}				else				{					diff = -diff;					ndir = dir2;				}			} 			else ndir = m_pBody->getDir() + DIR_MAX - diff;			////////////////////////////////////////////////////////////			// ndir 捞 overflow, underflow 且 版快 蔼阑 焊沥秦拎具 茄促.			// overflow  : -1 -> 7 , -2 -> 6 , -3 -> 5 , ...			// underflow :  8 -> 0 ,  9 -> 1 , 10 -> 2 , ...			////////////////////////////////////////////////////////////			//if (ndir >= DIR_MAX) // overflow			//{				//	ndir = Directions(DIR_MAX - ndir);			//} 			//else if (ndir < 0) // underflow			//{				//	ndir = Directions(DIR_MAX + ndir);			//}			ndir &= DIR_MAX_1;			// 促澜 谅钎甫 备茄促.			nx = m_pBody->getX() + dirMoveMask[ndir].x;			ny = m_pBody->getY() + dirMoveMask[ndir].y;			// 促澜 规氢捞 厚菌栏搁, 风橇甫 狐廉唱哎 荐 乐促.			// 捞锭 粮狼 版拌甫 逞绢辑绰瘤 眉农甫 秦具 茄促.			if (m_pBody->canMove(nx,ny))			{				// 付胶磐牢 版快俊绰 官蹿俊 救 亮篮霸 绝绢具 茄促. - -; by sigi. 2002.9.12				/*				if (m_pBody->isMaster())				{					Tile& tile = m_pBody->getZone()->getTile(nx, ny);					if (tile.hasEffect())					{						if (tile.getEffect(Effect::EFFECT_CLASS_ACID_SWAMP)!=NULL							&& tile.getEffect(Effect::EFFECT_CLASS_GROUND_ATTACK)!=NULL)						{							found = true;						}					}				}				else				*/				{					found = true;				}			}			bBlocked[ndir] = true;		}//while	} 	else found = true;	// 谅荐/快荐甫 犬角洒 搬沥秦霖促.	if (found 		&& m_MoveRule!=MOVE_RULE_NORMAL)	{		bool leftWall = bBlocked[(ndir+2) & DIR_MAX_1];		bool rightWall = bBlocked[(ndir+DIR_MAX-2) & DIR_MAX_1];		// 笛 促 阜躯栏搁 规氢俊 蝶扼辑.. 荤官荤官		if (leftWall && rightWall)		{			if (ndir>curDir && ndir<curDir+4				|| curDir>4 && (ndir>curDir || ndir<curDir-4))			{				setMoveRule( MOVE_RULE_RIGHTWALL );				//cout << "set RightWall : " << (int)curDir << " to " << (int)ndir << " - " << (int)m_BlockedDir << " - " << m_pBody->getName() << endl;			}			else			{				setMoveRule( MOVE_RULE_LEFTWALL );				//cout << "set LeftWall : " << (int)curDir << " to " << (int)ndir << " - " << (int)m_BlockedDir << " - " << m_pBody->getName() << endl;			}		}		// 谅荐过 利侩		else if (leftWall)		{			setMoveRule( MOVE_RULE_LEFTWALL );			//cout << "set LeftWall : " << (int)curDir << " to " << (int)ndir << " - " << (int)m_BlockedDir << " - " << m_pBody->getName() << endl;		}		// 快荐过 利侩		else if (rightWall)		{			setMoveRule( MOVE_RULE_RIGHTWALL );			//cout << "set RightWall : " << (int)curDir << " to " << (int)ndir << " - " << (int)m_BlockedDir << " - " << m_pBody->getName() << endl;		}		// 寒捞 绝促搁 寒鸥扁 救茄促.		else		{			setMoveRule( MOVE_RULE_NORMAL );		}	}	else	{		setMoveRule( MOVE_RULE_NORMAL );	}	return found;}//////////////////////////////////////////////////////////////////////////////// 寒鸥绊 捞悼窍扁//////////////////////////////////////////////////////////////////////////////bool MonsterAI::moveWall(ZoneCoord_t ex, ZoneCoord_t ey, ZoneCoord_t& nx, ZoneCoord_t& ny, Dir_t& ndir, bool bLeft)	throw(){	//Zone*       pZone   = m_pBody->getZone();	//cout << "MoveWall[" << (bLeft? "Left" : "Right") << "] : " << m_pBody->getName() << endl;	////////////////////////////////////////////////////////////	// search surrounding tiles	////////////////////////////////////////////////////////////	// 快急 格钎 规氢栏肺 啊杭妨绊 茄促.	ndir = m_BlockedDir;	// 促澜 谅钎	nx = m_pBody->getX() + dirMoveMask[ndir].x;	ny = m_pBody->getY() + dirMoveMask[ndir].y;	m_WallCount++;	// 格钎茄 规氢栏肺 哎 荐 乐绰 版快	bool bCanMove = m_pBody->canMove(nx,ny); 	// 付胶磐牢 版快俊绰 官蹿俊 救 亮篮霸 绝绢具 茄促. - -; by sigi. 2002.9.12	/*	if (bCanMove && m_pBody->isMaster())	{		Tile& tile = m_pBody->getZone()->getTile(nx, ny);		if (tile.hasEffect())		{			if (tile.getEffect(Effect::EFFECT_CLASS_ACID_SWAMP)!=NULL				&& tile.getEffect(Effect::EFFECT_CLASS_GROUND_ATTACK)!=NULL)			{			}			else bCanMove = false;		}	}	*/	if (bCanMove)	{

⌨️ 快捷键说明

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