#include "StdAfx.h" #include "actionattack.h" #include "../Common/Protocol.h" #include "Monster.h" #include "SkillManager.h" #include "Player.h" #include "gamesrv.h" #include "SkillScript.h" #include "ObjectManager.h" cActionAttack::cActionAttack(void) : cAction( eACT_ATTACK ) { } cActionAttack::~cActionAttack(void) { } void cActionAttack::ActionInit( cMonster* pMonster, unsigned long accumTime ) { if( pMonster == NULL ) return; cAction::ActionInit( pMonster, accumTime ); const sMonsterScript* pMonsterScript = pMonster->GetMonsterInfo(); if( pMonsterScript == NULL ) { assert(NULL); NETWORK2->PostServerEvent("cActionAttack::ActionInit pMonsterScript == NULL"); return; } /// ÃßÀû¿¡¼­ ¼±ÅÃµÈ °ø°Ý ¹æ½ÄÀ¸·Î ¸ÕÀú °ø°ÝÀ» ÇÑ´Ù cBaseObject* pTarget = (cPlayer*)pMonster->GetTarget(); if( pTarget == NULL ) return; /// ½ºÅ³ »ç¿ëÈÄ Áö¿¬½Ã°£ üũ if( pMonster->IsSkillWaitEnd() == false ) return; /// ¸ðµå ½ºÅ³ÀÌ °¡´ÉÇÏ¸é ¸ðµå½ºÅ³À» ¾´´Ù eMONSTERATTACK_TYPE attackType = pMonster->GetModeSkill(); if( attackType == eMONSTERATTACK_MAX ) attackType = pMonster->GetAttackType(); /// ½ºÅ³index üũ sMonsterSkillScript* pSkillInfo = SKILLSCRIPT->GetMonsterSkillInfo( pMonster->GetRaceGender(), pMonster->GetAttackType() ); if( pSkillInfo == NULL ) return; if( pMonster->IsCantSkill( pSkillInfo->mAttributeType ) == true ) return; sObject target = { pTarget->GetObjectType(), pTarget->GetObjectID() }; SKILLMANAGER->MonsterAttack( pMonster->GetObjectID(), attackType, target ); //if( SKILLMANAGER->MonsterAttack( pMonster->GetObjectID(), attackType, target ) == true ) //{ // /// ½ºÅ³index üũ // sMonsterSkillScript* pSkillInfo = SKILLSCRIPT->GetMonsterSkillInfo( pMonster->GetRaceGender(), pMonster->GetAttackType() ); // if( pSkillInfo == NULL ) // { // assert(NULL); // NETWORK2->PostServerEvent("MonsterAttack - GetMonsterSkillInfo[%d,%d]", pMonster->GetRaceGender(), pMonster->GetAttackType() ); // return; // } // unsigned long attackEndTime = 0; // if( pMonster->GetAttackType() == eMONSTERATTACK_NORMAL1 || // pMonster->GetAttackType() == eMONSTERATTACK_NORMAL2 ) // { // attackEndTime = accumTime + (unsigned long)( pSkillInfo->mAttackSpd * ( 2.0f - pMonster->GetAttackSpeed() ) ); // } // else // attackEndTime = accumTime + pSkillInfo->mAttackSpd; // pMonster->CalcSkillWaitTime( attackEndTime ); //} } eACTION_CHANGE cActionAttack::Action( cMonster* pMonster, unsigned long /*deltaTime*/, unsigned long accumTime ) { if( pMonster == NULL ) return eACTCH_ERROR; const sMonsterScript* pMonsterScript = pMonster->GetMonsterInfo(); if( pMonsterScript == NULL ) { assert(NULL); NETWORK2->PostServerEvent("cActionAttack::Action pMonsterScript == NULL"); return eACTCH_ERROR; } /// ½ºÅ³ »ç¿ëÀÌ ³¡³¯¶§ ±îÁö Åë°ú if( SKILLMANAGER->IsUsingSkill( eOBJECTTYPE_MONSTER, pMonster->GetObjectID() ) ) return eACTCH_CONTINUE; /// Ç÷¹À̾ »ç¶óÁ³°Å³ª Ç÷¹À̾ ÀÖ´Àµ¥ Á×Àº°æ¿ì cBaseObject* pTarget = (cBaseObject*)pMonster->GetTarget(); if( pTarget == NULL || pTarget->GetStateDie() == true || pTarget->GetObjectType() == eOBJECTTYPE_MONSTER ) { /// 081205 PKH Ÿ°Ù ¼±Á¤ pMonster->ChangeActionTarget(); return eACTCH_CONTINUE; } if( pMonster->GetStateOddity( eODDITYTYPE_SLEEP ) != 0 ) return eACTCH_CONTINUE; if( pMonster->GetStateOddity( eODDITYTYPE_STUN ) != 0 ) return eACTCH_CONTINUE; if( pMonster->GetIdleEndTime() > accumTime ) return eACTCH_CONTINUE; ////////////////////////////////////////////////////////////////////////// /// µµ¸Á °ø°Ý½Ã ¾Ö´Ï¸ÞÀÌ¼Ç ½ºÅµÇö»ó¶§¹®¿¡ °ø°Ý¼Óµµ³¡³¯¶§±îÁö ´Ù¸¥ Çൿ¾ÈÇÔ ///// ½ºÅ³ »ç¿ëÈÄ Áö¿¬½Ã°£ üũ //if( pMonster->IsSkillWaitEnd() == false ) //{ // float range; // = pMonster->CalcStatusSkillRange( pSkillInfo->mTargetDist, pSkillInfo->mRangeType ); // //range = OBJECTMANAGER->ObjectSizeRange( pMonster, pPlayer, range ); // range = OBJECTMANAGER->ObjectSizeRange( pMonster, pPlayer, 0 ); // cRangeCheck skillRangeCheck( range ); // NiPoint3 attackerPos( pMonster->GetXPos(), pMonster->GetYPos(), pMonster->Height() ); // NiPoint3 targetPos( pPlayer->GetXPos(), pPlayer->GetYPos(), pPlayer->Height() ); // /// ½ºÅ³ »ç°Å¸® ¹Û¿¡ Ÿ°ÙÀÌ ÀÖ´Ù. // if( skillRangeCheck.IsNotRange( attackerPos, targetPos ) == true ) // return eATTCH_ATTACK_FOLLOW; // else // return eACTCH_CONTINUE; //} ////////////////////////////////////////////////////////////////////////// /// ½ºÅ³ »ç¿ëÈÄ Áö¿¬½Ã°£ üũ if( pMonster->IsSkillWaitEnd() == false ) return eACTCH_CONTINUE; pMonster->SetAttackType( eMONSTERATTACK_MAX ); /// ½ºÅ³ »ç¿ë ºÒ°¡ »óÅ eMONSTERATTACK_TYPE attackType = pMonster->SelectSkill(); if( attackType == eMONSTERATTACK_MAX ) return eATTCH_ATTACK_FOLLOW; pTarget = pMonster->GetTarget(); pTarget = (cBaseObject*)pMonster->GetTarget(); if( pTarget == NULL || pTarget->GetStateDie() == true ) { return eACTCH_CONTINUE; } float targetDist = 0; eRANGETYPE rangeType = eRANGETYPE_CLOSE; unsigned long attackSpeed = 1000; /// ½ºÅ³index üũ sMonsterSkillScript* pSkillInfo = SKILLSCRIPT->GetMonsterSkillInfo( pMonster->GetRaceGender(), attackType ); if( pSkillInfo == NULL ) { NETWORK2->PostServerEvent("cActionAttack::Action pSkillInfo[%d,%d] == NULL", pMonster->GetRaceGender(), attackType ); } else { targetDist = pSkillInfo->mTargetDist; rangeType = pSkillInfo->mRangeType; attackSpeed = pSkillInfo->mAttackSpd; } float range = pMonster->CalcStatusSkillRange( targetDist, rangeType ); range = OBJECTMANAGER->ObjectSizeRange( pMonster, pTarget, range ); //range = OBJECTMANAGER->ObjectSizeRange( pMonster, pPlayer, 0 ); cRangeCheck skillRangeCheck( range ); NiPoint3 attackerPos( pMonster->GetXPos(), pMonster->GetYPos(), pMonster->Height() ); NiPoint3 targetPos( pTarget->GetXPos(), pTarget->GetYPos(), pTarget->Height() ); /// ½ºÅ³ »ç°Å¸® ¹Û¿¡ Ÿ°ÙÀÌ ÀÖ´Ù. if( skillRangeCheck.IsNotRange( attackerPos, targetPos ) == true ) return eATTCH_ATTACK_FOLLOW; sObject target = { pTarget->GetObjectType(), pTarget->GetObjectID() }; if( SKILLMANAGER->MonsterAttack( pMonster->GetObjectID(), attackType, target ) == false ) return eATTCH_ATTACK_FOLLOW; /// ½ºÅ³ »ç¿ë ºÒ°¡ »óÅÂÀ̹ǷΠÃßÀû //unsigned long attackEndTime = 0; //if( pMonster->GetAttackType() == eMONSTERATTACK_NORMAL1 || // pMonster->GetAttackType() == eMONSTERATTACK_NORMAL2 ) //{ // attackEndTime = accumTime + (unsigned long)( attackSpeed * ( 2.0f - pMonster->GetAttackSpeed() ) ); //} //else // attackEndTime = accumTime + attackSpeed; //pMonster->CalcSkillWaitTime( attackEndTime ); /// °ø°Ý ¼º°øÀ̸é ÃßÀû ½Ã°£ Àç¼³Á¤ pMonster->SetFollowEndTime( accumTime + pMonsterScript->mFollowTime ); /// °ø°Ý ÇÁ·Î¼¼½º °è¼Ó ¼öÇà return eACTCH_CONTINUE; }