port 2V2-d.1: ActorInstance/InstanceBase closure creates the main character
Port the ActorInstance*/InstanceBase* siblings plus GameUtil, FlyTarget, PhysicsObject, GameEventManager, WeaponTrace, MapUtil and lineintersect_utils verbatim and drop their pending stand-ins; CGameEventManager and CPythonSystem join PythonBoot in CPythonApplication member order. Root cause of the intermittent Loading-phase header 7: TPlayerSkill::tNextRead is time_t, 32-bit in 40250 (_USE_32BIT_TIME_T) but 64-bit on LP64, so SKILL_LEVEL (76) was read as 2551 bytes instead of 1531. Packet.h now uses LONG with a static_assert, and the fake server sends SKILL_LEVEL in Loading. The fake server's CHARACTER_ADD now uses CHAR_TYPE_PC; port.login_flow asserts the main instance exists with race 0. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
996d793f0c
commit
5266b00c6e
@@ -12,6 +12,7 @@
|
||||
#include "UserInterface/PythonPlayer.h"
|
||||
#include "GameLib/FlyingObjectManager.h"
|
||||
#include "GameLib/RaceManager.h"
|
||||
#include "GameLib/GameEventManager.h"
|
||||
#include "EffectLib/EffectManager.h"
|
||||
#include "GameLib/ItemManager.h"
|
||||
#include "UserInterface/PythonCharacterManager.h"
|
||||
@@ -28,6 +29,7 @@
|
||||
#include "UserInterface/PythonMessenger.h"
|
||||
#include "UserInterface/PythonSafeBox.h"
|
||||
#include "UserInterface/PythonGuild.h"
|
||||
#include "UserInterface/PythonSystem.h"
|
||||
#include "UserInterface/AbstractApplication.h"
|
||||
#include "UserInterface/PythonApplication.h"
|
||||
#include "EterBase/Timer.h"
|
||||
@@ -59,6 +61,7 @@ std::unique_ptr<CAccountConnector> g_account_connector;
|
||||
std::unique_ptr<CPythonPlayer> g_player;
|
||||
std::unique_ptr<CFlyingManager> g_flying_manager;
|
||||
std::unique_ptr<CRaceManager> g_race_manager;
|
||||
std::unique_ptr<CGameEventManager> g_game_event_manager;
|
||||
std::unique_ptr<CEffectManager> g_effect_manager;
|
||||
// PORT: CPythonApplication is not constructed by the Godot host yet. GamePhase calls the
|
||||
// 40250 IAbstractApplication singleton, so expose the host's current timer and camera surface.
|
||||
@@ -113,6 +116,7 @@ struct GameSingletons
|
||||
CPythonMessenger pyManager;
|
||||
CPythonSafeBox pySafeBox;
|
||||
CPythonGuild pyGuild;
|
||||
CPythonSystem pySystem; // last CPythonApplication member (m_pySystem)
|
||||
};
|
||||
std::unique_ptr<GameSingletons> g_game_singletons;
|
||||
|
||||
@@ -301,6 +305,7 @@ bool Start(const char* stdlib_path, std::string* error)
|
||||
g_player = std::make_unique<CPythonPlayer>();
|
||||
g_flying_manager = std::make_unique<CFlyingManager>();
|
||||
g_race_manager = std::make_unique<CRaceManager>();
|
||||
g_game_event_manager = std::make_unique<CGameEventManager>();
|
||||
g_effect_manager = std::make_unique<CEffectManager>();
|
||||
g_game_application = std::make_unique<GameApplicationAdapter>();
|
||||
g_game_singletons = std::make_unique<GameSingletons>();
|
||||
@@ -496,6 +501,7 @@ void Stop()
|
||||
g_game_singletons.reset();
|
||||
g_game_application.reset();
|
||||
g_effect_manager.reset();
|
||||
g_game_event_manager.reset();
|
||||
g_race_manager.reset();
|
||||
g_flying_manager.reset();
|
||||
g_player.reset();
|
||||
|
||||
@@ -164,12 +164,8 @@ void CPythonApplication::SetForceSightRange(int) { MT_PLATFORM_STUB(); }
|
||||
|
||||
void CMovieMan::PlayLogo(const char*) { MT_PLATFORM_STUB(); }
|
||||
|
||||
float GetDegreeDifference(float, float) { MT_PLATFORM_STUB(); return 0; }
|
||||
int GetRotatingDirection(float, float) { MT_PLATFORM_STUB(); return 0; }
|
||||
|
||||
BOOL PERF_CHECKER_RENDER_GAME = FALSE;
|
||||
BOOL SKILL_EFFECT_UPGRADE_ENABLE = FALSE;
|
||||
BOOL USE_WEAPON_SPECULAR = FALSE;
|
||||
D3DXCOLOR g_fSpecularColor;
|
||||
double g_specularSpd = 0;
|
||||
|
||||
|
||||
@@ -1,559 +0,0 @@
|
||||
// Stand-in for the 40250 logic unit GameLib/ActorInstance.cpp, not ported yet: the members the ported units
|
||||
// reference, as platform_stub.py stubs. Delete this file in the commit that ports the unit into port/
|
||||
// (docs/PORT-PLAN.md).
|
||||
#include "GameLib/StdAfx.h"
|
||||
#include "GameLib/ActorInstance.h"
|
||||
|
||||
#include "../../PlatformStub.h"
|
||||
|
||||
auto CActorInstance::IEventHandler::GetEmptyPtr() -> IEventHandler *
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<IEventHandler *>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsDirLine() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetMaterialColor(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetEventHandler(IEventHandler *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanAct() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanMove() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanAttack() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanUseSkill() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::AttachWeapon(DWORD, DWORD, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::RefreshActorInstance() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::UpdateAttachingInstances() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetMotionMode(int) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetMotionMode() -> int
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<int>();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetLoopMotion(DWORD, float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::InterceptOnceMotion(DWORD, float, UINT, float) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::InterceptLoopMotion(DWORD, float) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsPushing() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsUsingSkill() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanCancelSkill() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::UpdatePointInstance() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::TestCollisionWithDynamicSphere(const CDynamicSphereInstance &) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::UpdateAdvancingPointInstance() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::AvoidObject(const CGraphicObjectInstance &) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsBlockObject(const CGraphicObjectInstance &) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::BlockMovement() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::TestPhysicsBlendingCollision(CActorInstance &) -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::isAttacking() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsUsingMovingSkill() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsActEmotion() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetBlendingPosition(const TPixelPosition &, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetBattleHitEffect(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetMovementVectorRef() -> const D3DXVECTOR3 &
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<const D3DXVECTOR3 &>();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetCurPixelPosition(const TPixelPosition &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_SetSrcPixelPosition(const TPixelPosition &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_SetDstPixelPosition(const TPixelPosition &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_SetDstPixelPositionZ(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_GetCurPixelPositionRef() -> const TPixelPosition &
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<const TPixelPosition &>();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_GetSrcPixelPositionRef() -> const TPixelPosition &
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<const TPixelPosition &>();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_GetDstPixelPositionRef() -> const TPixelPosition &
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<const TPixelPosition &>();
|
||||
}
|
||||
|
||||
auto CActorInstance::NEW_GetLastPixelPositionRef() -> const TPixelPosition &
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<const TPixelPosition &>();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetPixelPosition(TPixelPosition *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetRotation() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetTargetRotation() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetAdvancingRotation() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetRotation(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetAdvancingRotation(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::RestoreRenderMode() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetBlendRenderMode() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetAlphaValue(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::GetAlphaValue() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CActorInstance::BlendAlphaValue(float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetAddRenderMode() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetAddColor(const D3DXCOLOR &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetModulateRenderMode() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetRenderMode(int) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::RenderTrace() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::RenderCollisionData() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::RenderToShadowMap() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanFishing() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::IsFishing() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CActorInstance::OnGetFlyTargetPosition() -> D3DXVECTOR3
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<D3DXVECTOR3>();
|
||||
}
|
||||
|
||||
auto CActorInstance::OnShootDamage() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::AddFlyTarget(const CFlyTarget &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetFlyTarget(const CFlyTarget &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::CanChangeTarget() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::HORSE_MotionProcess(BOOL) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::MotionProcess(BOOL) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::RotationProcess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::ComboProcess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::ShakeProcess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::TraceProcess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::OnRender() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__ClearAttachingEffect() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__ClearCombo() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__ClearMotion() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__IsWaitMotion() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__IsMoveMotion() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__IsDamageMotion() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__IsKnockDownMotion() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__IsDieMotion() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__GetCurrentMotionIndex() -> WORD
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<WORD>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__DestroyWeaponTrace() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__InitializePositionData() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__OnSyncing() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__OnWaiting() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__OnMoving() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::EnableSkipCollision() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::DisableSkipCollision() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__InitializeCollisionData() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__BlendAlpha_Initialize() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__BlendAlpha_Update() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::__IsSyncing() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::__OnStop() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::TEMP_Push(int, int) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::ShowDirectionLine(bool) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::AttachEffectByName(DWORD, const char *, const char *) -> DWORD
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<DWORD>();
|
||||
}
|
||||
|
||||
auto CActorInstance::PushOnceMotion(DWORD, float, float) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::PushLoopMotion(DWORD, float, float) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetXYRotation(float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::SetWeaponTraceTexture(const char *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::UseTextureWeaponTrace() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CActorInstance::UseAlphaWeaponTrace() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
@@ -1,32 +0,0 @@
|
||||
// Stand-in for the 40250 logic unit GameLib/FlyTarget.cpp, not ported yet: the members the ported units
|
||||
// reference, as platform_stub.py stubs. Delete this file in the commit that ports the unit into port/
|
||||
// (docs/PORT-PLAN.md).
|
||||
#include "GameLib/StdAfx.h"
|
||||
#include "GameLib/FlyTarget.h"
|
||||
|
||||
#include "../../PlatformStub.h"
|
||||
|
||||
CFlyTarget::CFlyTarget(IFlyTargetableObject *)
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
CFlyTarget::CFlyTarget(const D3DXVECTOR3 &)
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
CFlyTarget::~CFlyTarget()
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
CFlyTarget::CFlyTarget()
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CFlyTarget::NotifyTargetClear() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
@@ -59,3 +59,39 @@ auto CItemData::GetSpecularPowerf() const -> float
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CItemData::GetModelThing() -> CGraphicThing *
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<CGraphicThing *>();
|
||||
}
|
||||
|
||||
auto CItemData::GetSubModelThing() -> CGraphicThing *
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<CGraphicThing *>();
|
||||
}
|
||||
|
||||
auto CItemData::GetLODModelThingCount() -> DWORD
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<DWORD>();
|
||||
}
|
||||
|
||||
auto CItemData::GetLODModelThingPointer(DWORD, CGraphicThing **) -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CItemData::GetAttachingDataCount() -> DWORD
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<DWORD>();
|
||||
}
|
||||
|
||||
auto CItemData::GetAttachingDataPointer(DWORD, const NRaceData::TAttachingData **) -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
@@ -1,7 +0,0 @@
|
||||
// Pending MapUtil.cpp dependency of the physics object. The interpolation unit remains 2V3 work.
|
||||
#include "GameLib/StdAfx.h"
|
||||
#include "GameLib/MapUtil.h"
|
||||
#include "../../PlatformStub.h"
|
||||
|
||||
CEaseOutInterpolation::CEaseOutInterpolation() { MT_PLATFORM_STUB(); }
|
||||
CEaseOutInterpolation::~CEaseOutInterpolation() { MT_PLATFORM_STUB(); }
|
||||
@@ -1,43 +0,0 @@
|
||||
// Stand-in for the 40250 logic unit GameLib/PhysicsObject.cpp, not ported yet: the members the ported units
|
||||
// reference, as platform_stub.py stubs. Delete this file in the commit that ports the unit into port/
|
||||
// (docs/PORT-PLAN.md).
|
||||
#include "GameLib/StdAfx.h"
|
||||
#include "GameLib/PhysicsObject.h"
|
||||
|
||||
#include "../../PlatformStub.h"
|
||||
|
||||
decltype(IObjectManager::ms_ObjManager) IObjectManager::ms_ObjManager{};
|
||||
|
||||
decltype(IPhysicsWorld::ms_pWorld) IPhysicsWorld::ms_pWorld{};
|
||||
|
||||
CPhysicsObject::CPhysicsObject()
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
CPhysicsObject::~CPhysicsObject()
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPhysicsObject::Initialize() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPhysicsObject::Update(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPhysicsObject::GetXMovement() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CPhysicsObject::GetYMovement() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
@@ -1,467 +0,0 @@
|
||||
// Stand-in for the 40250 logic unit UserInterface/InstanceBase.cpp, not ported yet: the members the ported units
|
||||
// reference, as platform_stub.py stubs. Delete this file in the commit that ports the unit into port/
|
||||
// (docs/PORT-PLAN.md).
|
||||
#include "UserInterface/StdAfx.h"
|
||||
#include "UserInterface/InstanceBase.h"
|
||||
|
||||
#include "../../PlatformStub.h"
|
||||
|
||||
auto CInstanceBase::RegisterEffect(UINT, const char *, const char *, bool) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__AttachEffect(UINT) -> DWORD
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<DWORD>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__DetachEffect(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::CreateSpecialEffect(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::AttachSpecialEffect(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
decltype(CInstanceBase::ms_adwCRCAffectEffect) CInstanceBase::ms_adwCRCAffectEffect{};
|
||||
|
||||
decltype(CInstanceBase::ms_fDustGap) CInstanceBase::ms_fDustGap{};
|
||||
|
||||
decltype(CInstanceBase::ms_fHorseDustGap) CInstanceBase::ms_fHorseDustGap{};
|
||||
|
||||
auto CInstanceBase::DeleteBlendOut() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::AttachTextTail() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::DetachTextTail() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::UpdateTextTailLevel(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RefreshTextTail() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RefreshTextTailTitle() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::UpdateDeleting() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::ActDualEmotion(CInstanceBase &, WORD, WORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::ActEmotion(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::LevelUp() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SkillUp() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::Stun() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::Die() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::IsPVPInstance(CInstanceBase &) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::IsAffect(UINT) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetEventHandler(CActorInstance::IEventHandler *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::NEW_UseSkill(UINT, UINT, UINT, bool) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::NEW_GetDistanceFromDestPixelPosition(const TPixelPosition &) -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::NEW_GetDistanceFromDestInstance(CInstanceBase &) -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::NEW_SetPixelPosition(const TPixelPosition &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RunNormalAttack(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RunComboAttack(float, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::CheckAdvancing() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::StartFishing(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::StopFishing() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::ReactFishing() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::CatchSuccess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::CatchFail() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SCRIPT_SetPixelPosition(float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::NEW_GetPixelPosition(TPixelPosition *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::NEW_LookAtDestInstance(CInstanceBase &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::GetRotation() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::GetAdvancingRotation() -> float
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<float>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetRotation(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::BlendRotation(float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetMotionMode(int) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::PushOnceMotion(WORD, float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__ClearAffects() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetAffectFlagContainer(const CAffectFlagContainer &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetEmoticon(UINT) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetFishEmoticon() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__EnableChangingTCPState() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__ComboProcess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::AttackProcess() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__AttachSelectEffect() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__DetachSelectEffect() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__AttachTargetEffect() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__DetachTargetEffect() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__AttachEmpireEffect(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__EffectContainer_Initialize() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__EffectContainer_Destroy() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__StoneSmoke_Inialize() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__StoneSmoke_Destroy() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::ProcessDamage() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::AddDamageEffect(DWORD, BYTE, BOOL, BOOL) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::ClearPVPKeySystem() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::InsertPVPKey(DWORD, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RemovePVPKey(DWORD, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::InsertGVGKey(DWORD, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RemoveGVGKey(DWORD, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::InsertDUELKey(DWORD, DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__FindDUELKey(DWORD, DWORD) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::GetEventHandlerRef() -> CActorInstance::IEventHandler &
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<CActorInstance::IEventHandler &>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::IsUsingSkill() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::isLock() -> BOOL
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<BOOL>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__EffectContainer_AttachEffect(DWORD) -> DWORD
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<DWORD>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::__EffectContainer_DetachEffect(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RegisterTitleName(int, const char *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RegisterNameColor(UINT, UINT, UINT, UINT) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::RegisterTitleColor(UINT, UINT, UINT, UINT) -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetDustGap(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetHorseDustGap(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetEmpireNameMode(bool) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SCRIPT_SetAffect(UINT, bool) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetAlpha(float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::Revive() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::Hide() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::Show() -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetDirection(int) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::SetLoopMotion(WORD, float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::PushLoopMotion(WORD, float, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CInstanceBase::IsPossibleEmoticon() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
// Stand-in for the 40250 logic unit UserInterface/PythonSystem.cpp, not ported yet: the members the ported units
|
||||
// reference, as platform_stub.py stubs. Delete this file in the commit that ports the unit into port/
|
||||
// (docs/PORT-PLAN.md).
|
||||
#include "UserInterface/StdAfx.h"
|
||||
#include "UserInterface/PythonSystem.h"
|
||||
|
||||
#include "../../PlatformStub.h"
|
||||
|
||||
CPythonSystem::CPythonSystem()
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
CPythonSystem::~CPythonSystem()
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonSystem::IsShowDamage() -> bool
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
return mt_platform_stub_return<bool>();
|
||||
}
|
||||
@@ -20,3 +20,33 @@ auto CPythonTextTail::RegisterChatTail(DWORD, const char *) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonTextTail::RegisterCharacterTextTail(DWORD, DWORD, const D3DXCOLOR &, float) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonTextTail::SetCharacterTextTailColor(DWORD, const D3DXCOLOR &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonTextTail::DeleteCharacterTextTail(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonTextTail::AttachTitle(DWORD, const char *, const D3DXCOLOR &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonTextTail::DetachTitle(DWORD) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
auto CPythonTextTail::AttachLevel(DWORD, const char *, const D3DXCOLOR &) -> void
|
||||
{
|
||||
MT_PLATFORM_STUB();
|
||||
}
|
||||
|
||||
@@ -0,0 +1,849 @@
|
||||
/**************************************************************************************
|
||||
| File: lineintersect_utils.cpp
|
||||
| Purpose: Implementation of line segment intersection utility functions
|
||||
| Book Title: Game Programming Gems II
|
||||
| Chapter Title: Fast, Robust Intersection of 3D Line Segments
|
||||
| Author: Graham Rhodes
|
||||
| Revisions: 05-Apr-2001 - GSR. Original.
|
||||
**************************************************************************************/
|
||||
#include "StdAfx.h"
|
||||
#include <math.h>
|
||||
#include "lineintersect_utils.h"
|
||||
#include <assert.h>
|
||||
|
||||
// uncomment the following line to have the code check intermediate results
|
||||
//#define CHECK_ANSWERS
|
||||
|
||||
// uncomment the following line to use Cramer's rule instead of Gaussian elimination
|
||||
//#define USE_CRAMERS_RULE
|
||||
|
||||
#define FMAX(a,b) ((a) > (b) ? (a) : (b))
|
||||
#define FMIN(a,b) ((a) > (b) ? (b) : (a))
|
||||
#define FABS(a) ((a) < 0.0f ? -(a) : (a))
|
||||
#define OUT_OF_RANGE(a) ((a) < 0.0f || (a) > 1.f)
|
||||
|
||||
#define MY_EPSILON 0.1f
|
||||
|
||||
__forceinline void FindNearestPointOnLineSegment(const D3DXVECTOR3 & A1,
|
||||
const D3DXVECTOR3 & L,
|
||||
const D3DXVECTOR3 & B,
|
||||
D3DXVECTOR3 & Nearest,
|
||||
float ¶meter)
|
||||
{
|
||||
// Line/Segment is degenerate --- special case #1
|
||||
float D = D3DXVec3LengthSq(&L);
|
||||
if (D < MY_EPSILON*MY_EPSILON)
|
||||
{
|
||||
Nearest = A1;
|
||||
return;
|
||||
}
|
||||
|
||||
D3DXVECTOR3 AB = B-A1;
|
||||
|
||||
// parameter is computed from Equation (20).
|
||||
parameter = (D3DXVec3Dot(&AB,&L)) / D;
|
||||
|
||||
//if (false == infinite_line)
|
||||
parameter = FMAX(0.0f, FMIN(1.0f, parameter));
|
||||
|
||||
Nearest = A1 + parameter * L;
|
||||
return;
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
|
|
||||
| Method: FindNearestPointOfParallelLineSegments
|
||||
|
|
||||
| Purpose: Given two lines (segments) that are known to be parallel, find
|
||||
| a representative point on each that is nearest to the other. If
|
||||
| the lines are considered to be finite then it is possible that there
|
||||
| is one true point on each line that is nearest to the other. This
|
||||
| code properly handles this case.
|
||||
|
|
||||
| This is the most difficult line intersection case to handle, since
|
||||
| there is potentially a family, or locus of points on each line/segment
|
||||
| that are nearest to the other.
|
||||
| Parameters: Input:
|
||||
| ------
|
||||
| A1x, A1y, A1z - Coordinates of first defining point of line/segment A
|
||||
| A2x, A2y, A2z - Coordinates of second defining point of line/segment A
|
||||
| Lax, Lay, Laz - Vector from (A1x, A1y, A1z) to the (A2x, A2y, A2z).
|
||||
| B1x, B1y, B1z - Coordinates of first defining point of line/segment B
|
||||
| B2x, B2y, B2z - Coordinates of second defining point of line/segment B
|
||||
| Lbx, Lby, Lbz - Vector from (B1x, B1y, B1z) to the (B2x, B2y, B2z).
|
||||
| infinite_lines - set to true if lines are to be treated as infinite
|
||||
| epsilon_squared - tolerance value to be used to check for degenerate
|
||||
| and parallel lines, and to check for true intersection.
|
||||
|
|
||||
| Output:
|
||||
| -------
|
||||
| PointOnSegAx, - Coordinates of the point on segment A that are nearest
|
||||
| PointOnSegAy, to segment B. This corresponds to point C in the text.
|
||||
| PointOnSegAz
|
||||
| PointOnSegBx, - Coordinates of the point on segment B that are nearest
|
||||
| PointOnSegBy, to segment A. This corresponds to point D in the text.
|
||||
| PointOnSegBz
|
||||
|
||||
**************************************************************************/
|
||||
__forceinline void FindNearestPointOfParallelLineSegments(const D3DXVECTOR3 & A1,
|
||||
const D3DXVECTOR3 & A2,
|
||||
const D3DXVECTOR3 & La,
|
||||
const D3DXVECTOR3 & B1,
|
||||
const D3DXVECTOR3 & B2,
|
||||
const D3DXVECTOR3 & Lb,
|
||||
//bool infinite_lines, float epsilon_squared,
|
||||
D3DXVECTOR3 & OutA,
|
||||
D3DXVECTOR3 & OutB)
|
||||
{
|
||||
float s[2], temp;
|
||||
FindNearestPointOnLineSegment(A1, La, B1, OutA, s[0]);
|
||||
/*if (true == infinite_lines)
|
||||
{
|
||||
PointOnSegBx = B1x;
|
||||
PointOnSegBy = B1y;
|
||||
PointOnSegBz = B1z;
|
||||
}
|
||||
else*/
|
||||
{
|
||||
//float tp[3];
|
||||
D3DXVECTOR3 tp;
|
||||
FindNearestPointOnLineSegment(A1, La, B2,
|
||||
tp, s[1]);
|
||||
if (s[0] < 0.f && s[1] < 0.f)
|
||||
{
|
||||
OutA = A1;
|
||||
if (s[0] < s[1])
|
||||
{
|
||||
OutB =B2;
|
||||
}
|
||||
else
|
||||
{
|
||||
OutB = B1;
|
||||
}
|
||||
}
|
||||
else if (s[0] > 1.f && s[1] > 1.f)
|
||||
{
|
||||
OutA = A2;
|
||||
if (s[0] < s[1])
|
||||
{
|
||||
OutB = B1;
|
||||
}
|
||||
else
|
||||
{
|
||||
OutB = B2;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
temp = 0.5f*(FMAX(0.0f, FMIN(1.0f, s[0])) + FMAX(0.0f, FMIN(1.0f, s[1])));
|
||||
OutA = A1 + temp * La;
|
||||
FindNearestPointOnLineSegment(B1, Lb,
|
||||
OutA, OutB, temp);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
|
|
||||
| Method: AdjustNearestPoints
|
||||
|
|
||||
| Purpose: Given nearest point information for two infinite lines, adjust
|
||||
| to model finite line segments.
|
||||
|
|
||||
| Parameters: Input:
|
||||
| ------
|
||||
| A1x, A1y, A1z - Coordinates of first defining point of line/segment A
|
||||
| Lax, Lay, Laz - Vector from (A1x, A1y, A1z) to the (A2x, A2y, A2z).
|
||||
| B1x, B1y, B1z - Coordinates of first defining point of line/segment B
|
||||
| Lbx, Lby, Lbz - Vector from (B1x, B1y, B1z) to the (B2x, B2y, B2z).
|
||||
| epsilon_squared - tolerance value to be used to check for degenerate
|
||||
| and parallel lines, and to check for true intersection.
|
||||
| s - parameter representing nearest point on infinite line A
|
||||
| t - parameter representing nearest point on infinite line B
|
||||
|
|
||||
| Output:
|
||||
| -------
|
||||
| PointOnSegAx, - Coordinates of the point on segment A that are nearest
|
||||
| PointOnSegAy, to segment B. This corresponds to point C in the text.
|
||||
| PointOnSegAz
|
||||
| PointOnSegBx, - Coordinates of the point on segment B that are nearest
|
||||
| PointOnSegBy, to segment A. This corresponds to point D in the text.
|
||||
| PointOnSegBz
|
||||
**************************************************************************/
|
||||
__forceinline void AdjustNearestPoints(const D3DXVECTOR3 & A1,
|
||||
const D3DXVECTOR3 & La,
|
||||
const D3DXVECTOR3 & B1,
|
||||
const D3DXVECTOR3 & Lb,
|
||||
float s, float t,
|
||||
D3DXVECTOR3 & OutA,
|
||||
D3DXVECTOR3 & OutB)
|
||||
{
|
||||
// handle the case where both parameter s and t are out of range
|
||||
if (OUT_OF_RANGE(s) && OUT_OF_RANGE(t))
|
||||
{
|
||||
s = FMAX(0.0f, FMIN(1.0f, s));
|
||||
OutA = A1 + s*La;
|
||||
FindNearestPointOnLineSegment(B1, Lb,
|
||||
OutA,
|
||||
OutB, t);
|
||||
if (OUT_OF_RANGE(t))
|
||||
{
|
||||
t = FMAX(0.0f, FMIN(1.0f, t));
|
||||
OutB = B1 + t*Lb;
|
||||
FindNearestPointOnLineSegment(A1, La, OutB,
|
||||
OutA, s);
|
||||
FindNearestPointOnLineSegment(B1, Lb, OutA,
|
||||
OutB, t);
|
||||
}
|
||||
}
|
||||
// otherwise, handle the case where the parameter for only one segment is
|
||||
// out of range
|
||||
else if (OUT_OF_RANGE(s))
|
||||
{
|
||||
s = FMAX(0.0f, FMIN(1.0f, s));
|
||||
OutA = A1 + s*La;
|
||||
FindNearestPointOnLineSegment(B1, Lb,
|
||||
OutA,
|
||||
OutB, t);
|
||||
}
|
||||
else if (OUT_OF_RANGE(t))
|
||||
{
|
||||
t = FMAX(0.0f, FMIN(1.0f, t));
|
||||
OutB = B1 + t*Lb;
|
||||
FindNearestPointOnLineSegment(A1, La, OutB,
|
||||
OutA, s);
|
||||
}
|
||||
else
|
||||
{
|
||||
assert(0);
|
||||
}
|
||||
}
|
||||
|
||||
void IntersectLineSegments(const D3DXVECTOR3 & A1,
|
||||
const D3DXVECTOR3 & A2,
|
||||
const D3DXVECTOR3 & B1,
|
||||
const D3DXVECTOR3 & B2,
|
||||
//bool infinite_lines, /*float epsilon,*/
|
||||
D3DXVECTOR3 & OutA,
|
||||
D3DXVECTOR3 & OutB)
|
||||
{
|
||||
float temp = 0.f;
|
||||
const float epsilon = MY_EPSILON;
|
||||
const float epsilon_squared = MY_EPSILON*MY_EPSILON;
|
||||
|
||||
// Compute parameters from Equations (1) and (2) in the text
|
||||
D3DXVECTOR3 La = A2-A1;
|
||||
D3DXVECTOR3 Lb = B2-B1;
|
||||
// From Equation (15)
|
||||
float L11 = D3DXVec3LengthSq(&La);
|
||||
float L22 = D3DXVec3LengthSq(&Lb);
|
||||
|
||||
// Line/Segment A is degenerate ---- Special Case #1
|
||||
if (L11 < epsilon_squared)
|
||||
{
|
||||
OutA = A1;
|
||||
FindNearestPointOnLineSegment(B1, Lb, A1,
|
||||
OutB, temp);
|
||||
}
|
||||
// Line/Segment B is degenerate ---- Special Case #1
|
||||
else if (L22 < epsilon_squared)
|
||||
{
|
||||
OutB = B1;
|
||||
FindNearestPointOnLineSegment(A1, La, B1,
|
||||
OutA, temp);
|
||||
}
|
||||
// Neither line/segment is degenerate
|
||||
else
|
||||
{
|
||||
// Compute more parameters from Equation (3) in the text.
|
||||
D3DXVECTOR3 AB = B1 - A1;
|
||||
|
||||
// and from Equation (15).
|
||||
float L12 = -D3DXVec3Dot(&La, &Lb);
|
||||
|
||||
float DetL = L11 * L22 - L12 * L12;
|
||||
// Lines/Segments A and B are parallel ---- special case #2.
|
||||
if (FABS(DetL) < epsilon)
|
||||
{
|
||||
FindNearestPointOfParallelLineSegments(A1, A2,
|
||||
La,
|
||||
B1, B2,
|
||||
Lb,
|
||||
OutA, OutB);
|
||||
}
|
||||
// The general case
|
||||
else
|
||||
{
|
||||
// from Equation (15)
|
||||
float ra = D3DXVec3Dot(&La, &AB);//Lax * ABx + Lay * ABy + Laz * ABz;
|
||||
float rb = D3DXVec3Dot(&Lb, &AB);//-Lbx * ABx - Lby * ABy - Lbz * ABz;
|
||||
|
||||
float t = (L11 * rb - ra * L12)/DetL; // Equation (12)
|
||||
|
||||
#ifdef USE_CRAMERS_RULE
|
||||
float s = (L22 * ra - rb * L12)/DetL;
|
||||
#else
|
||||
float s = (ra-L12*t)/L11; // Equation (13)
|
||||
#endif // USE_CRAMERS_RULE
|
||||
|
||||
#ifdef CHECK_ANSWERS
|
||||
float check_ra = s*L11 + t*L12;
|
||||
float check_rb = s*L12 + t*L22;
|
||||
assert(FABS(check_ra-ra) < epsilon);
|
||||
assert(FABS(check_rb-rb) < epsilon);
|
||||
#endif // CHECK_ANSWERS
|
||||
|
||||
// if we are dealing with infinite lines or if parameters s and t both
|
||||
// lie in the range [0,1] then just compute the points using Equations
|
||||
// (1) and (2) from the text.
|
||||
OutA = (A1 + s * La);
|
||||
OutB = (B1 + t * Lb);
|
||||
// otherwise, at least one of s and t is outside of [0,1] and we have to
|
||||
// handle this case.
|
||||
if ((OUT_OF_RANGE(s) || OUT_OF_RANGE(t)))
|
||||
{
|
||||
AdjustNearestPoints(A1,La,B1,Lb,
|
||||
s, t,
|
||||
OutA,
|
||||
OutB);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void IntersectLineSegments(const float A1x, const float A1y, const float A1z,
|
||||
const float A2x, const float A2y, const float A2z,
|
||||
const float B1x, const float B1y, const float B1z,
|
||||
const float B2x, const float B2y, const float B2z,
|
||||
bool infinite_lines, float epsilon, float &PointOnSegAx,
|
||||
float &PointOnSegAy, float &PointOnSegAz, float &PointOnSegBx,
|
||||
float &PointOnSegBy, float &PointOnSegBz)
|
||||
{
|
||||
float temp = 0.f;
|
||||
float epsilon_squared = epsilon * epsilon;
|
||||
|
||||
// Compute parameters from Equations (1) and (2) in the text
|
||||
float Lax = A2x - A1x;
|
||||
float Lay = A2y - A1y;
|
||||
float Laz = A2z - A1z;
|
||||
float Lbx = B2x - B1x;
|
||||
float Lby = B2y - B1y;
|
||||
float Lbz = B2z - B1z;
|
||||
// From Equation (15)
|
||||
float L11 = (Lax * Lax) + (Lay * Lay) + (Laz * Laz);
|
||||
float L22 = (Lbx * Lbx) + (Lby * Lby) + (Lbz * Lbz);
|
||||
|
||||
// Line/Segment A is degenerate ---- Special Case #1
|
||||
if (L11 < epsilon_squared)
|
||||
{
|
||||
PointOnSegAx = A1x;
|
||||
PointOnSegAy = A1y;
|
||||
PointOnSegAz = A1z;
|
||||
FindNearestPointOnLineSegment(B1x, B1y, B1z, Lbx, Lby, Lbz, A1x, A1y, A1z,
|
||||
infinite_lines, epsilon, PointOnSegBx, PointOnSegBy,
|
||||
PointOnSegBz, temp);
|
||||
}
|
||||
// Line/Segment B is degenerate ---- Special Case #1
|
||||
else if (L22 < epsilon_squared)
|
||||
{
|
||||
PointOnSegBx = B1x;
|
||||
PointOnSegBy = B1y;
|
||||
PointOnSegBz = B1z;
|
||||
FindNearestPointOnLineSegment(A1x, A1y, A1z, Lax, Lay, Laz, B1x, B1y, B1z,
|
||||
infinite_lines, epsilon, PointOnSegAx, PointOnSegAy,
|
||||
PointOnSegAz, temp);
|
||||
}
|
||||
// Neither line/segment is degenerate
|
||||
else
|
||||
{
|
||||
// Compute more parameters from Equation (3) in the text.
|
||||
float ABx = B1x - A1x;
|
||||
float ABy = B1y - A1y;
|
||||
float ABz = B1z - A1z;
|
||||
|
||||
// and from Equation (15).
|
||||
float L12 = -(Lax * Lbx) - (Lay * Lby) - (Laz * Lbz);
|
||||
|
||||
float DetL = L11 * L22 - L12 * L12;
|
||||
// Lines/Segments A and B are parallel ---- special case #2.
|
||||
if (FABS(DetL) < epsilon)
|
||||
{
|
||||
FindNearestPointOfParallelLineSegments(A1x, A1y, A1z, A2x, A2y, A2z,
|
||||
Lax, Lay, Laz,
|
||||
B1x, B1y, B1z, B2x, B2y, B2z,
|
||||
Lbx, Lby, Lbz,
|
||||
infinite_lines, epsilon,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz);
|
||||
}
|
||||
// The general case
|
||||
else
|
||||
{
|
||||
// from Equation (15)
|
||||
float ra = Lax * ABx + Lay * ABy + Laz * ABz;
|
||||
float rb = -Lbx * ABx - Lby * ABy - Lbz * ABz;
|
||||
|
||||
float t = (L11 * rb - ra * L12)/DetL; // Equation (12)
|
||||
|
||||
#ifdef USE_CRAMERS_RULE
|
||||
float s = (L22 * ra - rb * L12)/DetL;
|
||||
#else
|
||||
float s = (ra-L12*t)/L11; // Equation (13)
|
||||
#endif // USE_CRAMERS_RULE
|
||||
|
||||
#ifdef CHECK_ANSWERS
|
||||
float check_ra = s*L11 + t*L12;
|
||||
float check_rb = s*L12 + t*L22;
|
||||
assert(FABS(check_ra-ra) < epsilon);
|
||||
assert(FABS(check_rb-rb) < epsilon);
|
||||
#endif // CHECK_ANSWERS
|
||||
|
||||
// if we are dealing with infinite lines or if parameters s and t both
|
||||
// lie in the range [0,1] then just compute the points using Equations
|
||||
// (1) and (2) from the text.
|
||||
PointOnSegAx = (A1x + s * Lax);
|
||||
PointOnSegAy = (A1y + s * Lay);
|
||||
PointOnSegAz = (A1z + s * Laz);
|
||||
PointOnSegBx = (B1x + t * Lbx);
|
||||
PointOnSegBy = (B1y + t * Lby);
|
||||
PointOnSegBz = (B1z + t * Lbz);
|
||||
// otherwise, at least one of s and t is outside of [0,1] and we have to
|
||||
// handle this case.
|
||||
if (false == infinite_lines && (OUT_OF_RANGE(s) || OUT_OF_RANGE(t)))
|
||||
{
|
||||
AdjustNearestPoints(A1x, A1y, A1z, Lax, Lay, Laz,
|
||||
B1x, B1y, B1z, Lbx, Lby, Lbz,
|
||||
epsilon, s, t,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
// pragma to get rid of math.h inline function removal warnings.
|
||||
#pragma warning(disable:4514)
|
||||
|
||||
/**************************************************************************
|
||||
|
|
||||
| Method: IntersectLineSegments
|
||||
|
|
||||
| Purpose: Find the nearest point between two finite length line segments
|
||||
| or two infinite lines in 3-dimensional space. The function calculates
|
||||
| the point on each line/line segment that is closest to the other
|
||||
| line/line segment, the midpoint between the nearest points, and
|
||||
| the vector between these two points. If the two nearest points
|
||||
| are close within a tolerance, a flag is set indicating the lines
|
||||
| have a "true" intersection.
|
||||
|
|
||||
| Parameters: Input:
|
||||
| ------
|
||||
| A1x, A1y, A1z - Coordinates of first defining point of line/segment A
|
||||
| A2x, A2y, A2z - Coordinates of second defining point of line/segment A
|
||||
| B1x, B1y, B1z - Coordinates of first defining point of line/segment B
|
||||
| B2x, B2y, B2z - Coordinates of second defining point of line/segment B
|
||||
| infinite_lines - set to true if lines are to be treated as infinite
|
||||
| epsilon - tolerance value to be used to check for degenerate
|
||||
| and parallel lines, and to check for true intersection.
|
||||
|
|
||||
| Output:
|
||||
| -------
|
||||
| PointOnSegAx, - Coordinates of the point on segment A that are nearest
|
||||
| PointOnSegAy, to segment B. This corresponds to point C in the text.
|
||||
| PointOnSegAz
|
||||
| PointOnSegBx, - Coordinates of the point on segment B that are nearest
|
||||
| PointOnSegBy, to segment A. This corresponds to point D in the text.
|
||||
| PointOnSegBz
|
||||
| NearestPointX, - Midpoint between the two nearest points. This can be
|
||||
| NearestPointY, treated as *the* intersection point if nearest points
|
||||
| NearestPointZ are sufficiently close. This corresponds to point P
|
||||
| in the text.
|
||||
| NearestVectorX, - Vector between the nearest point on A to the nearest
|
||||
| point on segment B. This vector is normal to both
|
||||
| lines if the lines are infinite, but is not guaranteed
|
||||
| to be normal to both lines if both lines are finite
|
||||
| length.
|
||||
| true_intersection - true if the nearest points are close within a small
|
||||
| tolerance.
|
||||
**************************************************************************/
|
||||
void IntersectLineSegments(const float A1x, const float A1y, const float A1z,
|
||||
const float A2x, const float A2y, const float A2z,
|
||||
const float B1x, const float B1y, const float B1z,
|
||||
const float B2x, const float B2y, const float B2z,
|
||||
bool infinite_lines, float epsilon, float &PointOnSegAx,
|
||||
float &PointOnSegAy, float &PointOnSegAz, float &PointOnSegBx,
|
||||
float &PointOnSegBy, float &PointOnSegBz, float &NearestPointX,
|
||||
float &NearestPointY, float &NearestPointZ, float &NearestVectorX,
|
||||
float &NearestVectorY, float &NearestVectorZ, bool &true_intersection)
|
||||
{
|
||||
float temp = 0.f;
|
||||
float epsilon_squared = epsilon * epsilon;
|
||||
|
||||
// Compute parameters from Equations (1) and (2) in the text
|
||||
float Lax = A2x - A1x;
|
||||
float Lay = A2y - A1y;
|
||||
float Laz = A2z - A1z;
|
||||
float Lbx = B2x - B1x;
|
||||
float Lby = B2y - B1y;
|
||||
float Lbz = B2z - B1z;
|
||||
// From Equation (15)
|
||||
float L11 = (Lax * Lax) + (Lay * Lay) + (Laz * Laz);
|
||||
float L22 = (Lbx * Lbx) + (Lby * Lby) + (Lbz * Lbz);
|
||||
|
||||
// Line/Segment A is degenerate ---- Special Case #1
|
||||
if (L11 < epsilon_squared)
|
||||
{
|
||||
PointOnSegAx = A1x;
|
||||
PointOnSegAy = A1y;
|
||||
PointOnSegAz = A1z;
|
||||
FindNearestPointOnLineSegment(B1x, B1y, B1z, Lbx, Lby, Lbz, A1x, A1y, A1z,
|
||||
infinite_lines, epsilon, PointOnSegBx, PointOnSegBy,
|
||||
PointOnSegBz, temp);
|
||||
}
|
||||
// Line/Segment B is degenerate ---- Special Case #1
|
||||
else if (L22 < epsilon_squared)
|
||||
{
|
||||
PointOnSegBx = B1x;
|
||||
PointOnSegBy = B1y;
|
||||
PointOnSegBz = B1z;
|
||||
FindNearestPointOnLineSegment(A1x, A1y, A1z, Lax, Lay, Laz, B1x, B1y, B1z,
|
||||
infinite_lines, epsilon, PointOnSegAx, PointOnSegAy,
|
||||
PointOnSegAz, temp);
|
||||
}
|
||||
// Neither line/segment is degenerate
|
||||
else
|
||||
{
|
||||
// Compute more parameters from Equation (3) in the text.
|
||||
float ABx = B1x - A1x;
|
||||
float ABy = B1y - A1y;
|
||||
float ABz = B1z - A1z;
|
||||
|
||||
// and from Equation (15).
|
||||
float L12 = -(Lax * Lbx) - (Lay * Lby) - (Laz * Lbz);
|
||||
|
||||
float DetL = L11 * L22 - L12 * L12;
|
||||
// Lines/Segments A and B are parallel ---- special case #2.
|
||||
if (FABS(DetL) < epsilon)
|
||||
{
|
||||
FindNearestPointOfParallelLineSegments(A1x, A1y, A1z, A2x, A2y, A2z,
|
||||
Lax, Lay, Laz,
|
||||
B1x, B1y, B1z, B2x, B2y, B2z,
|
||||
Lbx, Lby, Lbz,
|
||||
infinite_lines, epsilon,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz);
|
||||
}
|
||||
// The general case
|
||||
else
|
||||
{
|
||||
// from Equation (15)
|
||||
float ra = Lax * ABx + Lay * ABy + Laz * ABz;
|
||||
float rb = -Lbx * ABx - Lby * ABy - Lbz * ABz;
|
||||
|
||||
float t = (L11 * rb - ra * L12)/DetL; // Equation (12)
|
||||
|
||||
#ifdef USE_CRAMERS_RULE
|
||||
float s = (L22 * ra - rb * L12)/DetL;
|
||||
#else
|
||||
float s = (ra-L12*t)/L11; // Equation (13)
|
||||
#endif // USE_CRAMERS_RULE
|
||||
|
||||
#ifdef CHECK_ANSWERS
|
||||
float check_ra = s*L11 + t*L12;
|
||||
float check_rb = s*L12 + t*L22;
|
||||
assert(FABS(check_ra-ra) < epsilon);
|
||||
assert(FABS(check_rb-rb) < epsilon);
|
||||
#endif // CHECK_ANSWERS
|
||||
|
||||
// if we are dealing with infinite lines or if parameters s and t both
|
||||
// lie in the range [0,1] then just compute the points using Equations
|
||||
// (1) and (2) from the text.
|
||||
PointOnSegAx = (A1x + s * Lax);
|
||||
PointOnSegAy = (A1y + s * Lay);
|
||||
PointOnSegAz = (A1z + s * Laz);
|
||||
PointOnSegBx = (B1x + t * Lbx);
|
||||
PointOnSegBy = (B1y + t * Lby);
|
||||
PointOnSegBz = (B1z + t * Lbz);
|
||||
// otherwise, at least one of s and t is outside of [0,1] and we have to
|
||||
// handle this case.
|
||||
if (false == infinite_lines && (OUT_OF_RANGE(s) || OUT_OF_RANGE(t)))
|
||||
{
|
||||
AdjustNearestPoints(A1x, A1y, A1z, Lax, Lay, Laz,
|
||||
B1x, B1y, B1z, Lbx, Lby, Lbz,
|
||||
epsilon, s, t,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
NearestPointX = 0.5f * (PointOnSegAx + PointOnSegBx);
|
||||
NearestPointY = 0.5f * (PointOnSegAy + PointOnSegBy);
|
||||
NearestPointZ = 0.5f * (PointOnSegAz + PointOnSegBz);
|
||||
|
||||
NearestVectorX = PointOnSegBx - PointOnSegAx;
|
||||
NearestVectorY = PointOnSegBy - PointOnSegAy;
|
||||
NearestVectorZ = PointOnSegBz - PointOnSegAz;
|
||||
|
||||
// optional check to indicate if the lines truly intersect
|
||||
true_intersection = (FABS(NearestVectorX) +
|
||||
FABS(NearestVectorY) +
|
||||
FABS(NearestVectorZ)) < epsilon ? true : false;
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
|
|
||||
| Method: FindNearestPointOnLineSegment
|
||||
|
|
||||
| Purpose: Given a line (segment) and a point in 3-dimensional space,
|
||||
| find the point on the line (segment) that is closest to the
|
||||
| point.
|
||||
|
|
||||
| Parameters: Input:
|
||||
| ------
|
||||
| A1x, A1y, A1z - Coordinates of first defining point of the line/segment
|
||||
| Lx, Ly, Lz - Vector from (A1x, A1y, A1z) to the second defining point
|
||||
| of the line/segment.
|
||||
| Bx, By, Bz - Coordinates of the point
|
||||
| infinite_lines - set to true if lines are to be treated as infinite
|
||||
| epsilon_squared - tolerance value to be used to check for degenerate
|
||||
| and parallel lines, and to check for true intersection.
|
||||
|
|
||||
| Output:
|
||||
| -------
|
||||
| NearestPointX, - Point on line/segment that is closest to (Bx, By, Bz)
|
||||
| NearestPointY,
|
||||
| NearestPointZ
|
||||
| parameter - Parametric coordinate of the nearest point along the
|
||||
| line/segment. parameter = 0 at (A1x, A1y, A1z) and
|
||||
| parameter = 1 at the second defining point of the line/
|
||||
| segmetn
|
||||
**************************************************************************/
|
||||
void FindNearestPointOnLineSegment(const float A1x, const float A1y, const float A1z,
|
||||
const float Lx, const float Ly, const float Lz,
|
||||
const float Bx, const float By, const float Bz,
|
||||
bool infinite_line, float epsilon_squared, float &NearestPointX,
|
||||
float &NearestPointY, float &NearestPointZ,
|
||||
float ¶meter)
|
||||
{
|
||||
// Line/Segment is degenerate --- special case #1
|
||||
float D = Lx * Lx + Ly * Ly + Lz * Lz;
|
||||
if (D < epsilon_squared)
|
||||
{
|
||||
NearestPointX = A1x;
|
||||
NearestPointY = A1y;
|
||||
NearestPointZ = A1z;
|
||||
return;
|
||||
}
|
||||
|
||||
float ABx = Bx - A1x;
|
||||
float ABy = By - A1y;
|
||||
float ABz = Bz - A1z;
|
||||
|
||||
// parameter is computed from Equation (20).
|
||||
parameter = (Lx * ABx + Ly * ABy + Lz * ABz) / D;
|
||||
|
||||
if (false == infinite_line) parameter = FMAX(0.0f, FMIN(1.0f, parameter));
|
||||
|
||||
NearestPointX = A1x + parameter * Lx;
|
||||
NearestPointY = A1y + parameter * Ly;
|
||||
NearestPointZ = A1z + parameter * Lz;
|
||||
return;
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
|
|
||||
| Method: FindNearestPointOfParallelLineSegments
|
||||
|
|
||||
| Purpose: Given two lines (segments) that are known to be parallel, find
|
||||
| a representative point on each that is nearest to the other. If
|
||||
| the lines are considered to be finite then it is possible that there
|
||||
| is one true point on each line that is nearest to the other. This
|
||||
| code properly handles this case.
|
||||
|
|
||||
| This is the most difficult line intersection case to handle, since
|
||||
| there is potentially a family, or locus of points on each line/segment
|
||||
| that are nearest to the other.
|
||||
| Parameters: Input:
|
||||
| ------
|
||||
| A1x, A1y, A1z - Coordinates of first defining point of line/segment A
|
||||
| A2x, A2y, A2z - Coordinates of second defining point of line/segment A
|
||||
| Lax, Lay, Laz - Vector from (A1x, A1y, A1z) to the (A2x, A2y, A2z).
|
||||
| B1x, B1y, B1z - Coordinates of first defining point of line/segment B
|
||||
| B2x, B2y, B2z - Coordinates of second defining point of line/segment B
|
||||
| Lbx, Lby, Lbz - Vector from (B1x, B1y, B1z) to the (B2x, B2y, B2z).
|
||||
| infinite_lines - set to true if lines are to be treated as infinite
|
||||
| epsilon_squared - tolerance value to be used to check for degenerate
|
||||
| and parallel lines, and to check for true intersection.
|
||||
|
|
||||
| Output:
|
||||
| -------
|
||||
| PointOnSegAx, - Coordinates of the point on segment A that are nearest
|
||||
| PointOnSegAy, to segment B. This corresponds to point C in the text.
|
||||
| PointOnSegAz
|
||||
| PointOnSegBx, - Coordinates of the point on segment B that are nearest
|
||||
| PointOnSegBy, to segment A. This corresponds to point D in the text.
|
||||
| PointOnSegBz
|
||||
|
||||
**************************************************************************/
|
||||
void FindNearestPointOfParallelLineSegments(float A1x, float A1y, float A1z,
|
||||
float A2x, float A2y, float A2z,
|
||||
float Lax, float Lay, float Laz,
|
||||
float B1x, float B1y, float B1z,
|
||||
float B2x, float B2y, float B2z,
|
||||
float Lbx, float Lby, float Lbz,
|
||||
bool infinite_lines, float epsilon_squared,
|
||||
float &PointOnSegAx, float &PointOnSegAy, float &PointOnSegAz,
|
||||
float &PointOnSegBx, float &PointOnSegBy, float &PointOnSegBz)
|
||||
{
|
||||
float s[2], temp;
|
||||
FindNearestPointOnLineSegment(A1x, A1y, A1z, Lax, Lay, Laz, B1x, B1y, B1z,
|
||||
true, epsilon_squared, PointOnSegAx, PointOnSegAy, PointOnSegAz, s[0]);
|
||||
if (true == infinite_lines)
|
||||
{
|
||||
PointOnSegBx = B1x;
|
||||
PointOnSegBy = B1y;
|
||||
PointOnSegBz = B1z;
|
||||
}
|
||||
else
|
||||
{
|
||||
float tp[3];
|
||||
FindNearestPointOnLineSegment(A1x, A1y, A1z, Lax, Lay, Laz, B2x, B2y, B2z,
|
||||
true, epsilon_squared, tp[0], tp[1], tp[2], s[1]);
|
||||
if (s[0] < 0.f && s[1] < 0.f)
|
||||
{
|
||||
PointOnSegAx = A1x;
|
||||
PointOnSegAy = A1y;
|
||||
PointOnSegAz = A1z;
|
||||
if (s[0] < s[1])
|
||||
{
|
||||
PointOnSegBx = B2x;
|
||||
PointOnSegBy = B2y;
|
||||
PointOnSegBz = B2z;
|
||||
}
|
||||
else
|
||||
{
|
||||
PointOnSegBx = B1x;
|
||||
PointOnSegBy = B1y;
|
||||
PointOnSegBz = B1z;
|
||||
}
|
||||
}
|
||||
else if (s[0] > 1.f && s[1] > 1.f)
|
||||
{
|
||||
PointOnSegAx = A2x;
|
||||
PointOnSegAy = A2y;
|
||||
PointOnSegAz = A2z;
|
||||
if (s[0] < s[1])
|
||||
{
|
||||
PointOnSegBx = B1x;
|
||||
PointOnSegBy = B1y;
|
||||
PointOnSegBz = B1z;
|
||||
}
|
||||
else
|
||||
{
|
||||
PointOnSegBx = B2x;
|
||||
PointOnSegBy = B2y;
|
||||
PointOnSegBz = B2z;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
temp = 0.5f*(FMAX(0.0f, FMIN(1.0f, s[0])) + FMAX(0.0f, FMIN(1.0f, s[1])));
|
||||
PointOnSegAx = (A1x + temp * Lax);
|
||||
PointOnSegAy = (A1y + temp * Lay);
|
||||
PointOnSegAz = (A1z + temp * Laz);
|
||||
FindNearestPointOnLineSegment(B1x, B1y, B1z, Lbx, Lby, Lbz,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz, true,
|
||||
epsilon_squared, PointOnSegBx, PointOnSegBy, PointOnSegBz, temp);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
|
|
||||
| Method: AdjustNearestPoints
|
||||
|
|
||||
| Purpose: Given nearest point information for two infinite lines, adjust
|
||||
| to model finite line segments.
|
||||
|
|
||||
| Parameters: Input:
|
||||
| ------
|
||||
| A1x, A1y, A1z - Coordinates of first defining point of line/segment A
|
||||
| Lax, Lay, Laz - Vector from (A1x, A1y, A1z) to the (A2x, A2y, A2z).
|
||||
| B1x, B1y, B1z - Coordinates of first defining point of line/segment B
|
||||
| Lbx, Lby, Lbz - Vector from (B1x, B1y, B1z) to the (B2x, B2y, B2z).
|
||||
| epsilon_squared - tolerance value to be used to check for degenerate
|
||||
| and parallel lines, and to check for true intersection.
|
||||
| s - parameter representing nearest point on infinite line A
|
||||
| t - parameter representing nearest point on infinite line B
|
||||
|
|
||||
| Output:
|
||||
| -------
|
||||
| PointOnSegAx, - Coordinates of the point on segment A that are nearest
|
||||
| PointOnSegAy, to segment B. This corresponds to point C in the text.
|
||||
| PointOnSegAz
|
||||
| PointOnSegBx, - Coordinates of the point on segment B that are nearest
|
||||
| PointOnSegBy, to segment A. This corresponds to point D in the text.
|
||||
| PointOnSegBz
|
||||
**************************************************************************/
|
||||
void AdjustNearestPoints(float A1x, float A1y, float A1z,
|
||||
float Lax, float Lay, float Laz,
|
||||
float B1x, float B1y, float B1z,
|
||||
float Lbx, float Lby, float Lbz,
|
||||
float epsilon_squared, float s, float t,
|
||||
float &PointOnSegAx, float &PointOnSegAy, float &PointOnSegAz,
|
||||
float &PointOnSegBx, float &PointOnSegBy, float &PointOnSegBz)
|
||||
{
|
||||
// handle the case where both parameter s and t are out of range
|
||||
if (OUT_OF_RANGE(s) && OUT_OF_RANGE(t))
|
||||
{
|
||||
s = FMAX(0.0f, FMIN(1.0f, s));
|
||||
PointOnSegAx = (A1x + s * Lax);
|
||||
PointOnSegAy = (A1y + s * Lay);
|
||||
PointOnSegAz = (A1z + s * Laz);
|
||||
FindNearestPointOnLineSegment(B1x, B1y, B1z, Lbx, Lby, Lbz, PointOnSegAx,
|
||||
PointOnSegAy, PointOnSegAz, true, epsilon_squared,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz, t);
|
||||
if (OUT_OF_RANGE(t))
|
||||
{
|
||||
t = FMAX(0.0f, FMIN(1.0f, t));
|
||||
PointOnSegBx = (B1x + t * Lbx);
|
||||
PointOnSegBy = (B1y + t * Lby);
|
||||
PointOnSegBz = (B1z + t * Lbz);
|
||||
FindNearestPointOnLineSegment(A1x, A1y, A1z, Lax, Lay, Laz, PointOnSegBx,
|
||||
PointOnSegBy, PointOnSegBz, false, epsilon_squared,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz, s);
|
||||
FindNearestPointOnLineSegment(B1x, B1y, B1z, Lbx, Lby, Lbz, PointOnSegAx,
|
||||
PointOnSegAy, PointOnSegAz, false, epsilon_squared,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz, t);
|
||||
}
|
||||
}
|
||||
// otherwise, handle the case where the parameter for only one segment is
|
||||
// out of range
|
||||
else if (OUT_OF_RANGE(s))
|
||||
{
|
||||
s = FMAX(0.0f, FMIN(1.0f, s));
|
||||
PointOnSegAx = (A1x + s * Lax);
|
||||
PointOnSegAy = (A1y + s * Lay);
|
||||
PointOnSegAz = (A1z + s * Laz);
|
||||
FindNearestPointOnLineSegment(B1x, B1y, B1z, Lbx, Lby, Lbz, PointOnSegAx,
|
||||
PointOnSegAy, PointOnSegAz, false, epsilon_squared,
|
||||
PointOnSegBx, PointOnSegBy, PointOnSegBz, t);
|
||||
}
|
||||
else if (OUT_OF_RANGE(t))
|
||||
{
|
||||
t = FMAX(0.0f, FMIN(1.0f, t));
|
||||
PointOnSegBx = (B1x + t * Lbx);
|
||||
PointOnSegBy = (B1y + t * Lby);
|
||||
PointOnSegBz = (B1z + t * Lbz);
|
||||
FindNearestPointOnLineSegment(A1x, A1y, A1z, Lax, Lay, Laz, PointOnSegBx,
|
||||
PointOnSegBy, PointOnSegBz, false, epsilon_squared,
|
||||
PointOnSegAx, PointOnSegAy, PointOnSegAz, s);
|
||||
}
|
||||
else
|
||||
{
|
||||
assert(0);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
/* Copyright (C) Graham Rhodes, 2001.
|
||||
* All rights reserved worldwide.
|
||||
*
|
||||
* This software is provided "as is" without express or implied
|
||||
* warranties. You may freely copy and compile this source into
|
||||
* applications you distribute provided that the copyright text
|
||||
* below is included in the resulting source code, for example:
|
||||
* "Portions Copyright (C) Graham Rhodes, 2001"
|
||||
*/
|
||||
/**************************************************************************************
|
||||
|
|
||||
| File: lineintersect_utils.h
|
||||
|
|
||||
| Purpose: Function prototypes for line segment intersection utility functions
|
||||
|
|
||||
| Book Title: Game Programming Gems II
|
||||
|
|
||||
| Chapter Title: Fast, Robust Intersection of 3D Line Segments
|
||||
|
|
||||
| Author: Graham Rhodes
|
||||
|
|
||||
| Revisions: 05-Apr-2001 - GSR. Original.
|
||||
|
|
||||
**************************************************************************************/
|
||||
#ifndef _lineintersect_utils_h
|
||||
#define _lineintersect_utils_h
|
||||
|
||||
void IntersectLineSegments(const D3DXVECTOR3 & A1,
|
||||
const D3DXVECTOR3 & A2,
|
||||
const D3DXVECTOR3 & B1,
|
||||
const D3DXVECTOR3 & B2,
|
||||
//bool infinite_lines, /*float epsilon,*/
|
||||
D3DXVECTOR3 & OutA,
|
||||
D3DXVECTOR3 & OutB);
|
||||
|
||||
|
||||
void IntersectLineSegments(const float A1x, const float A1y, const float A1z,
|
||||
const float A2x, const float A2y, const float A2z,
|
||||
const float B1x, const float B1y, const float B1z,
|
||||
const float B2x, const float B2y, const float B2z,
|
||||
bool infinite_lines, float epsilon, float &PointOnSegAx,
|
||||
float &PointOnSegAy, float &PointOnSegAz, float &PointOnSegBx,
|
||||
float &PointOnSegBy, float &PointOnSegBz, float &NearestPointX,
|
||||
float &NearestPointY, float &NearestPointZ, float &NearestVectorX,
|
||||
float &NearestVectorY, float &NearestVectorZ, bool &true_intersection);
|
||||
|
||||
void IntersectLineSegments(const float A1x, const float A1y, const float A1z,
|
||||
const float A2x, const float A2y, const float A2z,
|
||||
const float B1x, const float B1y, const float B1z,
|
||||
const float B2x, const float B2y, const float B2z,
|
||||
bool infinite_lines, float epsilon, float &PointOnSegAx,
|
||||
float &PointOnSegAy, float &PointOnSegAz, float &PointOnSegBx,
|
||||
float &PointOnSegBy, float &PointOnSegBz);
|
||||
|
||||
void FindNearestPointOnLineSegment(const float A1x, const float A1y, const float A1z,
|
||||
const float Lx, const float Ly, const float Lz,
|
||||
const float Bx, const float By, const float Bz,
|
||||
bool infinite_line, float epsilon_squared, float &NearestPointX,
|
||||
float &NearestPointY, float &NearestPointZ,
|
||||
float ¶meter);
|
||||
|
||||
void FindNearestPointOfParallelLineSegments(float A1x, float A1y, float A1z,
|
||||
float A2x, float A2y, float A2z,
|
||||
float Lax, float Lay, float Laz,
|
||||
float B1x, float B1y, float B1z,
|
||||
float B2x, float B2y, float B2z,
|
||||
float Lbx, float Lby, float Lbz,
|
||||
bool infinite_lines, float epsilon_squared,
|
||||
float &PointOnSegAx, float &PointOnSegAy, float &PointOnSegAz,
|
||||
float &PointOnSegBx, float &PointOnSegBy, float &PointOnSegBz);
|
||||
|
||||
void AdjustNearestPoints(float A1x, float A1y, float A1z,
|
||||
float Lax, float Lay, float Laz,
|
||||
float B1x, float B1y, float B1z,
|
||||
float Lbx, float Lby, float Lbz,
|
||||
float epsilon_squared, float s, float t,
|
||||
float &PointOnSegAx, float &PointOnSegAy, float &PointOnSegAz,
|
||||
float &PointOnSegBx, float &PointOnSegBy, float &PointOnSegBz);
|
||||
|
||||
#endif // _lineintersect_utils_h
|
||||
@@ -0,0 +1,606 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EffectLib/EffectManager.h"
|
||||
|
||||
#include "ActorInstance.h"
|
||||
#include "ItemData.h"
|
||||
#include "ItemManager.h"
|
||||
#include "RaceData.h"
|
||||
#include "WeaponTrace.h"
|
||||
|
||||
BOOL USE_WEAPON_SPECULAR = TRUE;
|
||||
|
||||
BOOL USE_VIETNAM_CONVERT_WEAPON_VNUM = FALSE;
|
||||
|
||||
DWORD Vietnam_ConvertWeaponVnum(DWORD vnum)
|
||||
{
|
||||
DWORD base = vnum / 10 * 10;
|
||||
DWORD rest = vnum % 10;
|
||||
switch (base)
|
||||
{
|
||||
case 10:base = 5000;break;
|
||||
case 20:base = 5010;break;
|
||||
case 30:base = 5020;break;
|
||||
case 40:base = 5030;break;
|
||||
case 50:base = 5030;break;
|
||||
case 60:base = 5040;break;
|
||||
case 70:base = 5040;break;
|
||||
case 80:base = 5050;break;
|
||||
case 90:base = 5050;break;
|
||||
case 100:base = 5060;break;
|
||||
case 110:base = 5060;break;
|
||||
case 120:base = 5070;break;
|
||||
case 130:base = 5070;break;
|
||||
case 140:base = 5080;break;
|
||||
case 150:base = 5080;break;
|
||||
case 160:base = 5090;break;
|
||||
case 170:base = 5090;break;
|
||||
case 180:base = 5100;break;
|
||||
case 190:base = 5100;break;
|
||||
case 200:base = 5110;break;
|
||||
case 210:base = 5110;break;
|
||||
case 220:base = 5120;break;
|
||||
case 230:base = 5120;break;
|
||||
case 240:base = 5130;break;
|
||||
case 250:base = 5130;break;
|
||||
case 260:base = 5140;break;
|
||||
case 270:base = 5140;break;
|
||||
case 280:base = 5150;break;
|
||||
case 290:base = 5150;break;
|
||||
case 1000:base = 5000;break;
|
||||
case 1010:base = 5010;break;
|
||||
case 1020:base = 5020;break;
|
||||
case 1030:base = 5030;break;
|
||||
case 1040:base = 5040;break;
|
||||
case 1050:base = 5050;break;
|
||||
case 1060:base = 5060;break;
|
||||
case 1070:base = 5070;break;
|
||||
case 1080:base = 5080;break;
|
||||
case 1090:base = 5090;break;
|
||||
case 1100:base = 5100;break;
|
||||
case 1110:base = 5110;break;
|
||||
case 1120:base = 5120;break;
|
||||
case 1130:base = 5130;break;
|
||||
case 1140:base = 5140;break;
|
||||
case 1150:base = 5150;break;
|
||||
case 1160:base = 5150;break;
|
||||
case 1170:base = 5150;break;
|
||||
case 3000:base = 5000;break;
|
||||
case 3010:base = 5010;break;
|
||||
case 3020:base = 5020;break;
|
||||
case 3030:base = 5030;break;
|
||||
case 3040:base = 5040;break;
|
||||
case 3050:base = 5050;break;
|
||||
case 3060:base = 5060;break;
|
||||
case 3070:base = 5070;break;
|
||||
case 3080:base = 5080;break;
|
||||
case 3090:base = 5090;break;
|
||||
case 3100:base = 5100;break;
|
||||
case 3110:base = 5100;break;
|
||||
case 3120:base = 5110;break;
|
||||
case 3130:base = 5110;break;
|
||||
case 3140:base = 5120;break;
|
||||
case 3150:base = 5120;break;
|
||||
case 3160:base = 5130;break;
|
||||
case 3170:base = 5130;break;
|
||||
case 3180:base = 5140;break;
|
||||
case 3190:base = 5140;break;
|
||||
case 3200:base = 5150;break;
|
||||
case 3210:base = 5150;break;
|
||||
}
|
||||
return base + rest;
|
||||
}
|
||||
|
||||
|
||||
DWORD CActorInstance::AttachSmokeEffect(DWORD eSmoke)
|
||||
{
|
||||
if (!m_pkCurRaceData)
|
||||
return 0;
|
||||
|
||||
DWORD dwSmokeEffectID=m_pkCurRaceData->GetSmokeEffectID(eSmoke);
|
||||
|
||||
return AttachEffectByID(0, m_pkCurRaceData->GetSmokeBone().c_str(), dwSmokeEffectID);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsLeftHandWeapon(DWORD type)
|
||||
{
|
||||
if (CItemData::WEAPON_DAGGER == type || (CItemData::WEAPON_FAN == type && __IsMountingHorse()))
|
||||
return true;
|
||||
else if (CItemData::WEAPON_BOW == type)
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsRightHandWeapon(DWORD type)
|
||||
{
|
||||
if (CItemData::WEAPON_DAGGER == type || (CItemData::WEAPON_FAN == type && __IsMountingHorse()))
|
||||
return true;
|
||||
else if (CItemData::WEAPON_BOW == type)
|
||||
return false;
|
||||
else
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsWeaponTrace(DWORD weaponType)
|
||||
{
|
||||
switch(weaponType)
|
||||
{
|
||||
case CItemData::WEAPON_BELL:
|
||||
case CItemData::WEAPON_FAN:
|
||||
case CItemData::WEAPON_BOW:
|
||||
return false;
|
||||
default:
|
||||
return true;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::AttachWeapon(DWORD dwItemIndex,DWORD dwParentPartIndex, DWORD dwPartIndex)
|
||||
{
|
||||
if (dwPartIndex>=CRaceData::PART_MAX_NUM)
|
||||
return;
|
||||
|
||||
m_adwPartItemID[dwPartIndex]=dwItemIndex;
|
||||
|
||||
if (USE_VIETNAM_CONVERT_WEAPON_VNUM)
|
||||
dwItemIndex = Vietnam_ConvertWeaponVnum(dwItemIndex);
|
||||
|
||||
CItemData * pItemData;
|
||||
if (!CItemManager::Instance().GetItemDataPointer(dwItemIndex, &pItemData))
|
||||
{
|
||||
RegisterModelThing(dwPartIndex, NULL);
|
||||
SetModelInstance(dwPartIndex, dwPartIndex, 0);
|
||||
|
||||
RegisterModelThing(CRaceData::PART_WEAPON_LEFT, NULL);
|
||||
SetModelInstance(CRaceData::PART_WEAPON_LEFT, CRaceData::PART_WEAPON_LEFT, 0);
|
||||
|
||||
RefreshActorInstance();
|
||||
return;
|
||||
}
|
||||
|
||||
__DestroyWeaponTrace();
|
||||
//양손무기(자객 이도류) 왼손,오른손 모두에 장착.
|
||||
if (__IsRightHandWeapon(pItemData->GetWeaponType()))
|
||||
AttachWeapon(dwParentPartIndex, CRaceData::PART_WEAPON, pItemData);
|
||||
if (__IsLeftHandWeapon(pItemData->GetWeaponType()))
|
||||
AttachWeapon(dwParentPartIndex, CRaceData::PART_WEAPON_LEFT, pItemData);
|
||||
}
|
||||
|
||||
BOOL CActorInstance::GetAttachingBoneName(DWORD dwPartIndex, const char ** c_pszBoneName)
|
||||
{
|
||||
return m_pkCurRaceData->GetAttachingBoneName(dwPartIndex, c_pszBoneName);
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::AttachWeapon(DWORD dwParentPartIndex, DWORD dwPartIndex, CItemData * pItemData)
|
||||
{
|
||||
// assert(m_pkCurRaceData);
|
||||
if (!pItemData)
|
||||
return;
|
||||
|
||||
const char * szBoneName;
|
||||
if (!GetAttachingBoneName(dwPartIndex, &szBoneName))
|
||||
return;
|
||||
|
||||
// NOTE : (이도류처리)단도일 경우 형태가 다른 것으로 얻는다. 없을 경우 디폴트를 리턴
|
||||
if (CRaceData::PART_WEAPON_LEFT == dwPartIndex)
|
||||
{
|
||||
RegisterModelThing(dwPartIndex, pItemData->GetSubModelThing());
|
||||
}
|
||||
else
|
||||
{
|
||||
RegisterModelThing(dwPartIndex, pItemData->GetModelThing());
|
||||
}
|
||||
|
||||
for (DWORD i = 0; i < pItemData->GetLODModelThingCount(); ++i)
|
||||
{
|
||||
CGraphicThing * pThing;
|
||||
|
||||
if (!pItemData->GetLODModelThingPointer(i, &pThing))
|
||||
continue;
|
||||
|
||||
RegisterLODThing(dwPartIndex, pThing);
|
||||
}
|
||||
|
||||
SetModelInstance(dwPartIndex, dwPartIndex, 0);
|
||||
AttachModelInstance(dwParentPartIndex, szBoneName, dwPartIndex);
|
||||
|
||||
// 20041208.myevan.무기스펙큘러(값옷은 SetShape에서 직접 해준다.)
|
||||
if (USE_WEAPON_SPECULAR)
|
||||
{
|
||||
SMaterialData kMaterialData;
|
||||
kMaterialData.pImage = NULL;
|
||||
kMaterialData.isSpecularEnable = TRUE;
|
||||
kMaterialData.fSpecularPower = pItemData->GetSpecularPowerf();
|
||||
kMaterialData.bSphereMapIndex = 1;
|
||||
SetMaterialData(dwPartIndex, NULL, kMaterialData);
|
||||
}
|
||||
|
||||
// Weapon Trace
|
||||
if (__IsWeaponTrace(pItemData->GetWeaponType()))
|
||||
{
|
||||
CWeaponTrace * pWeaponTrace = CWeaponTrace::New();
|
||||
pWeaponTrace->SetWeaponInstance(this, dwPartIndex, szBoneName);
|
||||
m_WeaponTraceVector.push_back(pWeaponTrace);
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::DettachEffect(DWORD dwEID)
|
||||
{
|
||||
std::list<TAttachingEffect>::iterator i = m_AttachingEffectList.begin();
|
||||
|
||||
while (i != m_AttachingEffectList.end())
|
||||
{
|
||||
TAttachingEffect & rkAttEft = (*i);
|
||||
|
||||
if (rkAttEft.dwEffectIndex == dwEID)
|
||||
{
|
||||
i = m_AttachingEffectList.erase(i);
|
||||
CEffectManager::Instance().DestroyEffectInstance(dwEID);
|
||||
}
|
||||
else
|
||||
{
|
||||
++i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
DWORD CActorInstance::AttachEffectByName(DWORD dwParentPartIndex, const char * c_pszBoneName, const char * c_pszEffectName)
|
||||
{
|
||||
std::string str;
|
||||
DWORD dwCRC;
|
||||
StringPath(c_pszEffectName, str);
|
||||
dwCRC = GetCaseCRC32(str.c_str(), str.length());
|
||||
|
||||
return AttachEffectByID(dwParentPartIndex, c_pszBoneName, dwCRC);
|
||||
}
|
||||
|
||||
DWORD CActorInstance::AttachEffectByID(DWORD dwParentPartIndex, const char * c_pszBoneName, DWORD dwEffectID, const D3DXVECTOR3 * c_pv3Position)
|
||||
{
|
||||
TAttachingEffect ae;
|
||||
ae.iLifeType = EFFECT_LIFE_INFINITE;
|
||||
ae.dwEndTime = 0;
|
||||
ae.dwModelIndex = dwParentPartIndex;
|
||||
ae.dwEffectIndex = CEffectManager::Instance().GetEmptyIndex();
|
||||
ae.isAttaching = TRUE;
|
||||
if (c_pv3Position)
|
||||
{
|
||||
D3DXMatrixTranslation(&ae.matTranslation, c_pv3Position->x, c_pv3Position->y, c_pv3Position->z);
|
||||
}
|
||||
else
|
||||
{
|
||||
D3DXMatrixIdentity(&ae.matTranslation);
|
||||
}
|
||||
CEffectManager& rkEftMgr=CEffectManager::Instance();
|
||||
rkEftMgr.CreateEffectInstance(ae.dwEffectIndex, dwEffectID);
|
||||
|
||||
if (c_pszBoneName)
|
||||
{
|
||||
int iBoneIndex;
|
||||
|
||||
if (!FindBoneIndex(dwParentPartIndex,c_pszBoneName, &iBoneIndex))
|
||||
{
|
||||
ae.iBoneIndex = -1;
|
||||
//Tracef("Cannot get Bone Index\n");
|
||||
//assert(false && "Cannot get Bone Index");
|
||||
}
|
||||
else
|
||||
{
|
||||
ae.iBoneIndex = iBoneIndex;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
ae.iBoneIndex = -1;
|
||||
}
|
||||
|
||||
m_AttachingEffectList.push_back(ae);
|
||||
|
||||
return ae.dwEffectIndex;
|
||||
}
|
||||
|
||||
void CActorInstance::RefreshActorInstance()
|
||||
{
|
||||
if (!m_pkCurRaceData)
|
||||
{
|
||||
TraceError("void CActorInstance::RefreshActorInstance() - m_pkCurRaceData=NULL");
|
||||
return;
|
||||
}
|
||||
|
||||
// This is Temporary place before making the weapon detection system
|
||||
// Setup Collison Detection Data
|
||||
m_BodyPointInstanceList.clear();
|
||||
//m_AttackingPointInstanceList.clear();
|
||||
m_DefendingPointInstanceList.clear();
|
||||
|
||||
// Base
|
||||
for (DWORD i = 0; i < m_pkCurRaceData->GetAttachingDataCount(); ++i)
|
||||
{
|
||||
const NRaceData::TAttachingData * c_pAttachingData;
|
||||
|
||||
if (!m_pkCurRaceData->GetAttachingDataPointer(i, &c_pAttachingData))
|
||||
continue;
|
||||
|
||||
switch (c_pAttachingData->dwType)
|
||||
{
|
||||
case NRaceData::ATTACHING_DATA_TYPE_COLLISION_DATA:
|
||||
{
|
||||
const NRaceData::TCollisionData * c_pCollisionData = c_pAttachingData->pCollisionData;
|
||||
|
||||
TCollisionPointInstance PointInstance;
|
||||
if (NRaceData::COLLISION_TYPE_ATTACKING == c_pCollisionData->iCollisionType)
|
||||
continue;
|
||||
|
||||
if (!CreateCollisionInstancePiece(CRaceData::PART_MAIN, c_pAttachingData, &PointInstance))
|
||||
continue;
|
||||
|
||||
switch (c_pCollisionData->iCollisionType)
|
||||
{
|
||||
case NRaceData::COLLISION_TYPE_ATTACKING:
|
||||
//m_AttackingPointInstanceList.push_back(PointInstance);
|
||||
break;
|
||||
case NRaceData::COLLISION_TYPE_DEFENDING:
|
||||
m_DefendingPointInstanceList.push_back(PointInstance);
|
||||
break;
|
||||
case NRaceData::COLLISION_TYPE_BODY:
|
||||
m_BodyPointInstanceList.push_back(PointInstance);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case NRaceData::ATTACHING_DATA_TYPE_EFFECT:
|
||||
// if (!m_bEffectInitialized)
|
||||
// {
|
||||
// DWORD dwCRC;
|
||||
// StringPath(c_pAttachingData->pEffectData->strFileName);
|
||||
// dwCRC = GetCaseCRC32(c_pAttachingData->pEffectData->strFileName.c_str(),c_pAttachingData->pEffectData->strFileName.length());
|
||||
//
|
||||
// TAttachingEffect ae;
|
||||
// ae.iLifeType = EFFECT_LIFE_INFINITE;
|
||||
// ae.dwEndTime = 0;
|
||||
// ae.dwModelIndex = 0;
|
||||
// ae.dwEffectIndex = CEffectManager::Instance().GetEmptyIndex();
|
||||
// ae.isAttaching = TRUE;
|
||||
// CEffectManager::Instance().CreateEffectInstance(ae.dwEffectIndex, dwCRC);
|
||||
//
|
||||
// if (c_pAttachingData->isAttaching)
|
||||
// {
|
||||
// int iBoneIndex;
|
||||
// if (!FindBoneIndex(0,c_pAttachingData->strAttachingBoneName.c_str(), &iBoneIndex))
|
||||
// {
|
||||
// Tracef("Cannot get Bone Index\n");
|
||||
// assert(false/*Cannot get Bone Index*/);
|
||||
// }
|
||||
//
|
||||
// ae.iBoneIndex = iBoneIndex;
|
||||
// }
|
||||
// else
|
||||
// {
|
||||
// ae.iBoneIndex = -1;
|
||||
// }
|
||||
//
|
||||
// m_AttachingEffectList.push_back(ae);
|
||||
// }
|
||||
|
||||
if (c_pAttachingData->isAttaching)
|
||||
{
|
||||
AttachEffectByName(0, c_pAttachingData->strAttachingBoneName.c_str(), c_pAttachingData->pEffectData->strFileName.c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
AttachEffectByName(0, 0, c_pAttachingData->pEffectData->strFileName.c_str());
|
||||
}
|
||||
break;
|
||||
|
||||
case NRaceData::ATTACHING_DATA_TYPE_OBJECT:
|
||||
break;
|
||||
|
||||
default:
|
||||
assert(false/*NOT_IMPLEMENTED*/);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for (DWORD j = 0; j < CRaceData::PART_MAX_NUM; ++j)
|
||||
{
|
||||
if (0 == m_adwPartItemID[j])
|
||||
continue;
|
||||
|
||||
CItemData * pItemData;
|
||||
if (!CItemManager::Instance().GetItemDataPointer(m_adwPartItemID[j], &pItemData))
|
||||
return;
|
||||
|
||||
for (DWORD k = 0; k < pItemData->GetAttachingDataCount(); ++k)
|
||||
{
|
||||
const NRaceData::TAttachingData * c_pAttachingData;
|
||||
|
||||
if (!pItemData->GetAttachingDataPointer(k, &c_pAttachingData))
|
||||
continue;
|
||||
|
||||
switch(c_pAttachingData->dwType)
|
||||
{
|
||||
case NRaceData::ATTACHING_DATA_TYPE_COLLISION_DATA:
|
||||
{
|
||||
const NRaceData::TCollisionData * c_pCollisionData = c_pAttachingData->pCollisionData;
|
||||
|
||||
// FIXME : 첫번째 인자는 Part의 번호다.
|
||||
// Base는 무조건 0인가? - [levites]
|
||||
TCollisionPointInstance PointInstance;
|
||||
if (NRaceData::COLLISION_TYPE_ATTACKING == c_pCollisionData->iCollisionType)
|
||||
continue;
|
||||
if (!CreateCollisionInstancePiece(j, c_pAttachingData, &PointInstance))
|
||||
continue;
|
||||
|
||||
switch (c_pCollisionData->iCollisionType)
|
||||
{
|
||||
case NRaceData::COLLISION_TYPE_ATTACKING:
|
||||
//m_AttackingPointInstanceList.push_back(PointInstance);
|
||||
break;
|
||||
case NRaceData::COLLISION_TYPE_DEFENDING:
|
||||
m_DefendingPointInstanceList.push_back(PointInstance);
|
||||
break;
|
||||
case NRaceData::COLLISION_TYPE_BODY:
|
||||
m_BodyPointInstanceList.push_back(PointInstance);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case NRaceData::ATTACHING_DATA_TYPE_EFFECT:
|
||||
if (!m_bEffectInitialized)
|
||||
{
|
||||
DWORD dwCRC;
|
||||
StringPath(c_pAttachingData->pEffectData->strFileName);
|
||||
dwCRC = GetCaseCRC32(c_pAttachingData->pEffectData->strFileName.c_str(),c_pAttachingData->pEffectData->strFileName.length());
|
||||
|
||||
TAttachingEffect ae;
|
||||
ae.iLifeType = EFFECT_LIFE_INFINITE;
|
||||
ae.dwEndTime = 0;
|
||||
ae.dwModelIndex = j;
|
||||
ae.dwEffectIndex = CEffectManager::Instance().GetEmptyIndex();
|
||||
ae.isAttaching = TRUE;
|
||||
CEffectManager::Instance().CreateEffectInstance(ae.dwEffectIndex, dwCRC);
|
||||
|
||||
int iBoneIndex;
|
||||
if (!FindBoneIndex(j,c_pAttachingData->strAttachingBoneName.c_str(), &iBoneIndex))
|
||||
{
|
||||
Tracef("Cannot get Bone Index\n");
|
||||
assert(false/*Cannot get Bone Index*/);
|
||||
}
|
||||
Tracef("Creating %p %d %d\n", this, j,k);
|
||||
|
||||
ae.iBoneIndex = iBoneIndex;
|
||||
|
||||
m_AttachingEffectList.push_back(ae);
|
||||
}
|
||||
break;
|
||||
|
||||
case NRaceData::ATTACHING_DATA_TYPE_OBJECT:
|
||||
break;
|
||||
|
||||
default:
|
||||
assert(false/*NOT_IMPLEMENTED*/);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
m_bEffectInitialized = true;
|
||||
}
|
||||
|
||||
void CActorInstance::SetWeaponTraceTexture(const char * szTextureName)
|
||||
{
|
||||
std::vector<CWeaponTrace*>::iterator it;
|
||||
for (it = m_WeaponTraceVector.begin(); it != m_WeaponTraceVector.end(); ++it)
|
||||
{
|
||||
(*it)->SetTexture(szTextureName);
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::UseTextureWeaponTrace()
|
||||
{
|
||||
for_each(
|
||||
m_WeaponTraceVector.begin(),
|
||||
m_WeaponTraceVector.end(),
|
||||
std::mem_fn(&CWeaponTrace::UseTexture)
|
||||
);
|
||||
}
|
||||
|
||||
void CActorInstance::UseAlphaWeaponTrace()
|
||||
{
|
||||
for_each(
|
||||
m_WeaponTraceVector.begin(),
|
||||
m_WeaponTraceVector.end(),
|
||||
std::mem_fn(&CWeaponTrace::UseAlpha)
|
||||
);
|
||||
}
|
||||
|
||||
void CActorInstance::UpdateAttachingInstances()
|
||||
{
|
||||
CEffectManager& rkEftMgr=CEffectManager::Instance();
|
||||
|
||||
std::list<TAttachingEffect>::iterator it;
|
||||
DWORD dwCurrentTime = CTimer::Instance().GetCurrentMillisecond();
|
||||
for (it = m_AttachingEffectList.begin(); it!= m_AttachingEffectList.end();)
|
||||
{
|
||||
if (EFFECT_LIFE_WITH_MOTION == it->iLifeType)
|
||||
{
|
||||
++it;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((EFFECT_LIFE_NORMAL == it->iLifeType && it->dwEndTime < dwCurrentTime) ||
|
||||
!rkEftMgr.IsAliveEffect(it->dwEffectIndex))
|
||||
{
|
||||
rkEftMgr.DestroyEffectInstance(it->dwEffectIndex);
|
||||
it = m_AttachingEffectList.erase(it);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (it->isAttaching)
|
||||
{
|
||||
rkEftMgr.SelectEffectInstance(it->dwEffectIndex);
|
||||
|
||||
if (it->iBoneIndex == -1)
|
||||
{
|
||||
D3DXMATRIX matTransform;
|
||||
matTransform = it->matTranslation;
|
||||
matTransform *= m_worldMatrix;
|
||||
rkEftMgr.SetEffectInstanceGlobalMatrix(matTransform);
|
||||
}
|
||||
else
|
||||
{
|
||||
D3DXMATRIX * pBoneMat;
|
||||
if (GetBoneMatrix(it->dwModelIndex, it->iBoneIndex, &pBoneMat))
|
||||
{
|
||||
D3DXMATRIX matTransform;
|
||||
matTransform = *pBoneMat;
|
||||
matTransform *= it->matTranslation;
|
||||
matTransform *= m_worldMatrix;
|
||||
rkEftMgr.SetEffectInstanceGlobalMatrix(matTransform);
|
||||
}
|
||||
else
|
||||
{
|
||||
//TraceError("GetBoneMatrix(modelIndex(%d), boneIndex(%d)).NOT_FOUND_BONE",
|
||||
// it->dwModelIndex, it->iBoneIndex);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
++it;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::ShowAllAttachingEffect()
|
||||
{
|
||||
std::list<TAttachingEffect>::iterator it;
|
||||
for(it = m_AttachingEffectList.begin(); it!= m_AttachingEffectList.end();++it)
|
||||
{
|
||||
CEffectManager::Instance().SelectEffectInstance(it->dwEffectIndex);
|
||||
CEffectManager::Instance().ShowEffect();
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::HideAllAttachingEffect()
|
||||
{
|
||||
std::list<TAttachingEffect>::iterator it;
|
||||
for(it = m_AttachingEffectList.begin(); it!= m_AttachingEffectList.end();++it)
|
||||
{
|
||||
CEffectManager::Instance().SelectEffectInstance(it->dwEffectIndex);
|
||||
CEffectManager::Instance().HideEffect();
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__ClearAttachingEffect()
|
||||
{
|
||||
m_bEffectInitialized = false;
|
||||
|
||||
std::list<TAttachingEffect>::iterator it;
|
||||
for(it = m_AttachingEffectList.begin(); it!= m_AttachingEffectList.end();++it)
|
||||
{
|
||||
CEffectManager::Instance().DestroyEffectInstance(it->dwEffectIndex);
|
||||
}
|
||||
m_AttachingEffectList.clear();
|
||||
}
|
||||
@@ -0,0 +1,967 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EffectLib/EffectManager.h"
|
||||
#include "../MilesLib/SoundManager.h"
|
||||
|
||||
#include "ActorInstance.h"
|
||||
#include "RaceData.h"
|
||||
|
||||
void CActorInstance::SetBattleHitEffect(DWORD dwID)
|
||||
{
|
||||
m_dwBattleHitEffectID = dwID;
|
||||
}
|
||||
|
||||
void CActorInstance::SetBattleAttachEffect(DWORD dwID)
|
||||
{
|
||||
m_dwBattleAttachEffectID = dwID;
|
||||
}
|
||||
|
||||
bool CActorInstance::CanAct()
|
||||
{
|
||||
if (IsDead())
|
||||
return false;
|
||||
|
||||
if (IsStun())
|
||||
return false;
|
||||
|
||||
if (IsParalysis())
|
||||
return false;
|
||||
|
||||
if (IsFaint())
|
||||
return false;
|
||||
|
||||
if (IsSleep())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::CanUseSkill()
|
||||
{
|
||||
if (!CanAct())
|
||||
return false;
|
||||
|
||||
DWORD dwCurMotionIndex=__GetCurrentMotionIndex();
|
||||
|
||||
// Locked during attack
|
||||
switch (dwCurMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_FISHING_THROW:
|
||||
case CRaceMotionData::NAME_FISHING_WAIT:
|
||||
case CRaceMotionData::NAME_FISHING_STOP:
|
||||
case CRaceMotionData::NAME_FISHING_REACT:
|
||||
case CRaceMotionData::NAME_FISHING_CATCH:
|
||||
case CRaceMotionData::NAME_FISHING_FAIL:
|
||||
return TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
// Locked during using skill
|
||||
if (IsUsingSkill())
|
||||
{
|
||||
if (m_pkCurRaceMotionData->IsCancelEnableSkill())
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::CanMove()
|
||||
{
|
||||
if (!CanAct())
|
||||
return false;
|
||||
|
||||
if (isLock())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::CanAttack()
|
||||
{
|
||||
if (!CanAct())
|
||||
return false;
|
||||
|
||||
if (IsUsingSkill())
|
||||
{
|
||||
if (!CanCancelSkill())
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::CanFishing()
|
||||
{
|
||||
if (!CanAct())
|
||||
return false;
|
||||
|
||||
if (IsUsingSkill())
|
||||
return false;
|
||||
|
||||
switch (__GetCurrentMotionIndex())
|
||||
{
|
||||
case CRaceMotionData::NAME_WAIT:
|
||||
case CRaceMotionData::NAME_WALK:
|
||||
case CRaceMotionData::NAME_RUN:
|
||||
break;
|
||||
default:
|
||||
return false;
|
||||
break;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::IsClickableDistanceDestInstance(CActorInstance & rkInstDst, float fDistance)
|
||||
{
|
||||
TPixelPosition kPPosSrc;
|
||||
GetPixelPosition(&kPPosSrc);
|
||||
|
||||
D3DXVECTOR3 kD3DVct3Src(kPPosSrc);
|
||||
|
||||
TCollisionPointInstanceList& rkLstkDefPtInst=rkInstDst.m_DefendingPointInstanceList;
|
||||
TCollisionPointInstanceList::iterator i;
|
||||
|
||||
for (i=rkLstkDefPtInst.begin(); i!=rkLstkDefPtInst.end(); ++i)
|
||||
{
|
||||
CDynamicSphereInstanceVector& rkVctkDefSphere = (*i).SphereInstanceVector;
|
||||
|
||||
CDynamicSphereInstanceVector::iterator j;
|
||||
for (j=rkVctkDefSphere.begin(); j!=rkVctkDefSphere.end(); ++j)
|
||||
{
|
||||
CDynamicSphereInstance& rkSphere=(*j);
|
||||
|
||||
const auto vv = D3DXVECTOR3(rkSphere.v3Position - kD3DVct3Src);
|
||||
float fMovDistance=D3DXVec3Length(&vv);
|
||||
float fAtkDistance=rkSphere.fRadius+fDistance;
|
||||
|
||||
if (fAtkDistance>fMovDistance)
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
void CActorInstance::InputNormalAttackCommand(float fDirRot)
|
||||
{
|
||||
if (!__CanInputNormalAttackCommand())
|
||||
return;
|
||||
|
||||
m_fAtkDirRot=fDirRot;
|
||||
NormalAttack(m_fAtkDirRot);
|
||||
}
|
||||
|
||||
bool CActorInstance::InputComboAttackCommand(float fDirRot)
|
||||
{
|
||||
m_fAtkDirRot=fDirRot;
|
||||
|
||||
if (m_isPreInput)
|
||||
return false;
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// Process Input
|
||||
if (0 == m_dwcurComboIndex)
|
||||
{
|
||||
__RunNextCombo();
|
||||
return true;
|
||||
}
|
||||
else if (m_pkCurRaceMotionData->IsComboInputTimeData())
|
||||
{
|
||||
// 동작 경과 시간
|
||||
float fElapsedTime = GetAttackingElapsedTime();
|
||||
|
||||
// 이미 입력 한계 시간이 지났다면..
|
||||
if (fElapsedTime > m_pkCurRaceMotionData->GetComboInputEndTime())
|
||||
{
|
||||
//Tracen("입력 한계 시간 지남");
|
||||
if (IsBowMode())
|
||||
m_isNextPreInput = TRUE;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (fElapsedTime > m_pkCurRaceMotionData->GetNextComboTime()) // 콤보 발동 시간 이 후라면
|
||||
{
|
||||
//Tracen("다음 콤보 동작");
|
||||
// args : BlendingTime
|
||||
__RunNextCombo();
|
||||
return true;
|
||||
}
|
||||
else if (fElapsedTime > m_pkCurRaceMotionData->GetComboInputStartTime()) // 선 입력 시간 범위 라면..
|
||||
{
|
||||
//Tracen("선 입력 설정");
|
||||
m_isPreInput = TRUE;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float fElapsedTime = GetAttackingElapsedTime();
|
||||
if (fElapsedTime > m_pkCurRaceMotionData->GetMotionDuration()*0.9f) // 콤보 발동 시간 이 후라면
|
||||
{
|
||||
//Tracen("다음 콤보 동작");
|
||||
// args : BlendingTime
|
||||
__RunNextCombo();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
// Process Input
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void CActorInstance::ComboProcess()
|
||||
{
|
||||
// If combo is on action
|
||||
if (0 != m_dwcurComboIndex)
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
{
|
||||
Tracef("Attacking motion data is NULL! : %d\n", m_dwcurComboIndex);
|
||||
__ClearCombo();
|
||||
return;
|
||||
}
|
||||
|
||||
float fElapsedTime = GetAttackingElapsedTime();
|
||||
|
||||
// Process PreInput
|
||||
if (m_isPreInput)
|
||||
{
|
||||
//Tracenf("선입력 %f 다음콤보시간 %f", fElapsedTime, m_pkCurRaceMotionData->GetNextComboTime());
|
||||
if (fElapsedTime > m_pkCurRaceMotionData->GetNextComboTime())
|
||||
{
|
||||
__RunNextCombo();
|
||||
m_isPreInput = FALSE;
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
m_isPreInput = FALSE;
|
||||
|
||||
if (!IsUsingSkill()) // m_isNextPreInput는 활모드 일때만 사용하는 변수
|
||||
if (m_isNextPreInput) // 활일때만 스킬이 캔슬 되는건 이곳 때문임
|
||||
{
|
||||
__RunNextCombo();
|
||||
m_isNextPreInput = FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__RunNextCombo()
|
||||
{
|
||||
++m_dwcurComboIndex;
|
||||
///////////////////////////
|
||||
|
||||
WORD wComboIndex = m_dwcurComboIndex;
|
||||
WORD wComboType = __GetCurrentComboType();
|
||||
|
||||
if (wComboIndex==0)
|
||||
{
|
||||
TraceError("CActorInstance::__RunNextCombo(wComboType=%d, wComboIndex=%d)", wComboType, wComboIndex);
|
||||
return;
|
||||
}
|
||||
|
||||
DWORD dwComboArrayIndex = wComboIndex - 1;
|
||||
|
||||
CRaceData::TComboData * pComboData;
|
||||
|
||||
if (!m_pkCurRaceData->GetComboDataPointer(m_wcurMotionMode, wComboType, &pComboData))
|
||||
{
|
||||
TraceError("CActorInstance::__RunNextCombo(wComboType=%d, wComboIndex=%d) - m_pkCurRaceData->GetComboDataPointer(m_wcurMotionMode=%d, &pComboData) == NULL",
|
||||
wComboType, wComboIndex, m_wcurMotionMode);
|
||||
return;
|
||||
}
|
||||
|
||||
if (dwComboArrayIndex >= pComboData->ComboIndexVector.size())
|
||||
{
|
||||
TraceError("CActorInstance::__RunNextCombo(wComboType=%d, wComboIndex=%d) - (dwComboArrayIndex=%d) >= (pComboData->ComboIndexVector.size()=%d)",
|
||||
wComboType, wComboIndex, dwComboArrayIndex, pComboData->ComboIndexVector.size());
|
||||
return;
|
||||
}
|
||||
|
||||
WORD wcurComboMotionIndex = pComboData->ComboIndexVector[dwComboArrayIndex];
|
||||
ComboAttack(wcurComboMotionIndex, m_fAtkDirRot, 0.1f);
|
||||
|
||||
////////////////////////////////
|
||||
// 콤보가 끝났다면
|
||||
if (m_dwcurComboIndex == pComboData->ComboIndexVector.size())
|
||||
{
|
||||
__OnEndCombo();
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__OnEndCombo()
|
||||
{
|
||||
if (__IsMountingHorse())
|
||||
{
|
||||
m_dwcurComboIndex = 1;
|
||||
}
|
||||
|
||||
// 여기서 콤보를 초기화 해선 안된다.
|
||||
// 콤보가 초기화 되는 곳은 마지막 콤보가 끝나고 Motion 이 자동으로 Wait 으로 돌아가는 시점이다.
|
||||
}
|
||||
|
||||
void CActorInstance::__ClearCombo()
|
||||
{
|
||||
m_dwcurComboIndex = 0;
|
||||
m_isPreInput = FALSE;
|
||||
m_pkCurRaceMotionData = NULL;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
BOOL CActorInstance::isAttacking()
|
||||
{
|
||||
if (isNormalAttacking())
|
||||
return TRUE;
|
||||
|
||||
if (isComboAttacking())
|
||||
return TRUE;
|
||||
|
||||
if (IsSplashAttacking())
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::isValidAttacking()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return FALSE;
|
||||
|
||||
if (!m_pkCurRaceMotionData->isAttackingMotion())
|
||||
return FALSE;
|
||||
|
||||
const NRaceData::TMotionAttackData * c_pData = m_pkCurRaceMotionData->GetMotionAttackDataPointer();
|
||||
float fElapsedTime = GetAttackingElapsedTime();
|
||||
NRaceData::THitDataContainer::const_iterator itor = c_pData->HitDataContainer.begin();
|
||||
for (; itor != c_pData->HitDataContainer.end(); ++itor)
|
||||
{
|
||||
const NRaceData::THitData & c_rHitData = *itor;
|
||||
if (fElapsedTime > c_rHitData.fAttackStartTime &&
|
||||
fElapsedTime < c_rHitData.fAttackEndTime)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::CanCheckAttacking()
|
||||
{
|
||||
if (isAttacking())
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsInSplashTime()
|
||||
{
|
||||
if (m_kSplashArea.fDisappearingTime>GetLocalTime())
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::isNormalAttacking()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return FALSE;
|
||||
|
||||
if (!m_pkCurRaceMotionData->isAttackingMotion())
|
||||
return FALSE;
|
||||
|
||||
const NRaceData::TMotionAttackData * c_pData = m_pkCurRaceMotionData->GetMotionAttackDataPointer();
|
||||
if (NRaceData::MOTION_TYPE_NORMAL != c_pData->iMotionType)
|
||||
return FALSE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::isComboAttacking()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return FALSE;
|
||||
|
||||
if (!m_pkCurRaceMotionData->isAttackingMotion())
|
||||
return FALSE;
|
||||
|
||||
const NRaceData::TMotionAttackData * c_pData = m_pkCurRaceMotionData->GetMotionAttackDataPointer();
|
||||
if (NRaceData::MOTION_TYPE_COMBO != c_pData->iMotionType)
|
||||
return FALSE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::IsSplashAttacking()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return FALSE;
|
||||
|
||||
if (m_pkCurRaceMotionData->HasSplashMotionEvent())
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::__IsMovingSkill(WORD wSkillNumber)
|
||||
{
|
||||
enum
|
||||
{
|
||||
HORSE_DASH_SKILL_NUMBER = 137,
|
||||
};
|
||||
|
||||
return HORSE_DASH_SKILL_NUMBER == wSkillNumber;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::IsActEmotion()
|
||||
{
|
||||
DWORD dwCurMotionIndex=__GetCurrentMotionIndex();
|
||||
switch (dwCurMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_START+0:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_START+1:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_START+2:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_START+3:
|
||||
case CRaceMotionData::NAME_KISS_START+0:
|
||||
case CRaceMotionData::NAME_KISS_START+1:
|
||||
case CRaceMotionData::NAME_KISS_START+2:
|
||||
case CRaceMotionData::NAME_KISS_START+3:
|
||||
return TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::IsUsingMovingSkill()
|
||||
{
|
||||
return __IsMovingSkill(m_kCurMotNode.uSkill);
|
||||
}
|
||||
|
||||
DWORD CActorInstance::GetComboIndex()
|
||||
{
|
||||
return m_dwcurComboIndex;
|
||||
}
|
||||
|
||||
float CActorInstance::GetAttackingElapsedTime()
|
||||
{
|
||||
return (GetLocalTime() - m_kCurMotNode.fStartTime) * m_kCurMotNode.fSpeedRatio;
|
||||
// return (GetLocalTime() - m_kCurMotNode.fStartTime) * __GetAttackSpeed();
|
||||
}
|
||||
|
||||
bool CActorInstance::__CanInputNormalAttackCommand()
|
||||
{
|
||||
if (IsWaiting())
|
||||
return true;
|
||||
|
||||
if (isNormalAttacking())
|
||||
{
|
||||
float fElapsedTime = GetAttackingElapsedTime();
|
||||
|
||||
if (fElapsedTime > m_pkCurRaceMotionData->GetMotionDuration()*0.9f)
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::NormalAttack(float fDirRot, float fBlendTime)
|
||||
{
|
||||
WORD wMotionIndex;
|
||||
if (!m_pkCurRaceData->GetNormalAttackIndex(m_wcurMotionMode, &wMotionIndex))
|
||||
return FALSE;
|
||||
|
||||
BlendRotation(fDirRot, fBlendTime);
|
||||
SetAdvancingRotation(fDirRot);
|
||||
InterceptOnceMotion(wMotionIndex, 0.1f, 0, __GetAttackSpeed());
|
||||
|
||||
__OnAttack(wMotionIndex);
|
||||
|
||||
NEW_SetAtkPixelPosition(NEW_GetCurPixelPositionRef());
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::ComboAttack(DWORD dwMotionIndex, float fDirRot, float fBlendTime)
|
||||
{
|
||||
BlendRotation(fDirRot, fBlendTime);
|
||||
SetAdvancingRotation(fDirRot);
|
||||
|
||||
InterceptOnceMotion(dwMotionIndex, fBlendTime, 0, __GetAttackSpeed());
|
||||
|
||||
__OnAttack(dwMotionIndex);
|
||||
|
||||
NEW_SetAtkPixelPosition(NEW_GetCurPixelPositionRef());
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void CActorInstance::__ProcessMotionEventAttackSuccess(DWORD dwMotionKey, BYTE byEventIndex, CActorInstance & rVictim)
|
||||
{
|
||||
CRaceMotionData * pMotionData;
|
||||
|
||||
if (!m_pkCurRaceData->GetMotionDataPointer(dwMotionKey, &pMotionData))
|
||||
return;
|
||||
|
||||
if (byEventIndex >= pMotionData->GetMotionEventDataCount())
|
||||
return;
|
||||
|
||||
const CRaceMotionData::TMotionAttackingEventData * pMotionEventData;
|
||||
if (!pMotionData->GetMotionAttackingEventDataPointer(byEventIndex, &pMotionEventData))
|
||||
return;
|
||||
|
||||
const D3DXVECTOR3& c_rv3VictimPos=rVictim.GetPositionVectorRef();
|
||||
__ProcessDataAttackSuccess(pMotionEventData->AttackData, rVictim, c_rv3VictimPos);
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::__ProcessMotionAttackSuccess(DWORD dwMotionKey, CActorInstance & rVictim)
|
||||
{
|
||||
CRaceMotionData * c_pMotionData;
|
||||
|
||||
if (!m_pkCurRaceData->GetMotionDataPointer(dwMotionKey, &c_pMotionData))
|
||||
return;
|
||||
|
||||
const D3DXVECTOR3& c_rv3VictimPos=rVictim.GetPositionVectorRef();
|
||||
__ProcessDataAttackSuccess(c_pMotionData->GetMotionAttackDataReference(), rVictim, c_rv3VictimPos);
|
||||
}
|
||||
|
||||
|
||||
DWORD CActorInstance::__GetOwnerVID()
|
||||
{
|
||||
return m_dwOwnerVID;
|
||||
}
|
||||
|
||||
float CActorInstance::__GetOwnerTime()
|
||||
{
|
||||
return GetLocalTime()-m_fOwnerBaseTime;
|
||||
}
|
||||
|
||||
bool IS_HUGE_RACE(unsigned int vnum)
|
||||
{
|
||||
switch (vnum)
|
||||
{
|
||||
case 2493:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CActorInstance::__CanPushDestActor(CActorInstance& rkActorDst)
|
||||
{
|
||||
if (rkActorDst.IsBuilding())
|
||||
return false;
|
||||
|
||||
if (rkActorDst.IsDoor())
|
||||
return false;
|
||||
|
||||
if (rkActorDst.IsStone())
|
||||
return false;
|
||||
|
||||
if (rkActorDst.IsNPC())
|
||||
return false;
|
||||
|
||||
// 거대 몬스터 밀림 제외
|
||||
extern bool IS_HUGE_RACE(unsigned int vnum);
|
||||
if (IS_HUGE_RACE(rkActorDst.GetRace()))
|
||||
return false;
|
||||
|
||||
if (rkActorDst.IsStun())
|
||||
return true;
|
||||
|
||||
if (rkActorDst.__GetOwnerVID()!=GetVirtualID())
|
||||
return false;
|
||||
|
||||
if (rkActorDst.__GetOwnerTime()>3.0f)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool IS_PARTY_HUNTING_RACE(unsigned int vnum)
|
||||
{
|
||||
return true;
|
||||
|
||||
// 모든 몬스터 파티 사냥 적용
|
||||
/*
|
||||
if (vnum < 8) // 플레이어
|
||||
return true;
|
||||
|
||||
if (vnum >= 8000 && vnum <= 8112) // 메틴석
|
||||
return true;
|
||||
|
||||
if (vnum >= 2400 && vnum < 5000) // 천의 동굴 이후 몬스터
|
||||
return true;
|
||||
|
||||
return false;
|
||||
*/
|
||||
}
|
||||
|
||||
void CActorInstance::__ProcessDataAttackSuccess(const NRaceData::TAttackData & c_rAttackData, CActorInstance & rVictim, const D3DXVECTOR3 & c_rv3Position, UINT uiSkill, BOOL isSendPacket)
|
||||
{
|
||||
if (NRaceData::HIT_TYPE_NONE == c_rAttackData.iHittingType)
|
||||
return;
|
||||
|
||||
InsertDelay(c_rAttackData.fStiffenTime);
|
||||
|
||||
if (__CanPushDestActor(rVictim) && c_rAttackData.fExternalForce > 0.0f)
|
||||
{
|
||||
__PushCircle(rVictim);
|
||||
|
||||
// VICTIM_COLLISION_TEST
|
||||
const D3DXVECTOR3& kVictimPos = rVictim.GetPosition();
|
||||
rVictim.m_PhysicsObject.IncreaseExternalForce(kVictimPos, c_rAttackData.fExternalForce); //*nForceRatio/100.0f);
|
||||
|
||||
// VICTIM_COLLISION_TEST_END
|
||||
}
|
||||
|
||||
// Invisible Time
|
||||
if (IS_PARTY_HUNTING_RACE(rVictim.GetRace()))
|
||||
{
|
||||
if (uiSkill) // 파티 사냥 몬스터라도 스킬이면 무적시간 적용
|
||||
rVictim.m_fInvisibleTime = CTimer::Instance().GetCurrentSecond() + c_rAttackData.fInvisibleTime;
|
||||
|
||||
if (m_isMain) // #0000794: [M2KR] 폴리모프 - 밸런싱 문제 타인 공격에 의한 무적 타임은 고려하지 않고 자신 공격에 의한것만 체크한다
|
||||
rVictim.m_fInvisibleTime = CTimer::Instance().GetCurrentSecond() + c_rAttackData.fInvisibleTime;
|
||||
}
|
||||
else // 파티 사냥 몬스터가 아닐 경우만 적용
|
||||
{
|
||||
rVictim.m_fInvisibleTime = CTimer::Instance().GetCurrentSecond() + c_rAttackData.fInvisibleTime;
|
||||
}
|
||||
|
||||
// Stiffen Time
|
||||
rVictim.InsertDelay(c_rAttackData.fStiffenTime);
|
||||
|
||||
// Hit Effect
|
||||
D3DXVECTOR3 vec3Effect(rVictim.m_x, rVictim.m_y, rVictim.m_z);
|
||||
|
||||
// #0000780: [M2KR] 수룡 타격구 문제
|
||||
extern bool IS_HUGE_RACE(unsigned int vnum);
|
||||
if (IS_HUGE_RACE(rVictim.GetRace()))
|
||||
{
|
||||
vec3Effect = c_rv3Position;
|
||||
}
|
||||
|
||||
const D3DXVECTOR3 & v3Pos = GetPosition();
|
||||
|
||||
float fHeight = D3DXToDegree(atan2(-vec3Effect.x + v3Pos.x,+vec3Effect.y - v3Pos.y));
|
||||
|
||||
// 2004.08.03.myevan.빌딩이나 문의 경우 타격 효과가 보이지 않는다
|
||||
if (rVictim.IsBuilding()||rVictim.IsDoor())
|
||||
{
|
||||
D3DXVECTOR3 vec3Delta=vec3Effect-v3Pos;
|
||||
D3DXVec3Normalize(&vec3Delta, &vec3Delta);
|
||||
vec3Delta*=30.0f;
|
||||
|
||||
CEffectManager& rkEftMgr=CEffectManager::Instance();
|
||||
if (m_dwBattleHitEffectID)
|
||||
rkEftMgr.CreateEffect(m_dwBattleHitEffectID, v3Pos+vec3Delta, D3DXVECTOR3(0.0f, 0.0f, 0.0f));
|
||||
}
|
||||
else
|
||||
{
|
||||
CEffectManager& rkEftMgr=CEffectManager::Instance();
|
||||
if (m_dwBattleHitEffectID)
|
||||
rkEftMgr.CreateEffect(m_dwBattleHitEffectID, vec3Effect, D3DXVECTOR3(0.0f, 0.0f, fHeight));
|
||||
if (m_dwBattleAttachEffectID)
|
||||
rVictim.AttachEffectByID(0, NULL, m_dwBattleAttachEffectID);
|
||||
}
|
||||
|
||||
if (rVictim.IsBuilding())
|
||||
{
|
||||
// 2004.08.03.빌딩의 경우 흔들리면 이상하다
|
||||
}
|
||||
else if (rVictim.IsStone() || rVictim.IsDoor())
|
||||
{
|
||||
__HitStone(rVictim);
|
||||
}
|
||||
else
|
||||
{
|
||||
///////////
|
||||
// Motion
|
||||
if (NRaceData::HIT_TYPE_GOOD == c_rAttackData.iHittingType || rVictim.IsResistFallen())
|
||||
{
|
||||
__HitGood(rVictim);
|
||||
}
|
||||
else if (NRaceData::HIT_TYPE_GREAT == c_rAttackData.iHittingType)
|
||||
{
|
||||
__HitGreate(rVictim);
|
||||
}
|
||||
else
|
||||
{
|
||||
TraceError("ProcessSucceedingAttacking: Unknown AttackingData.iHittingType %d", c_rAttackData.iHittingType);
|
||||
}
|
||||
}
|
||||
|
||||
__OnHit(uiSkill, rVictim, isSendPacket);
|
||||
}
|
||||
|
||||
void CActorInstance::OnShootDamage()
|
||||
{
|
||||
if (IsStun())
|
||||
{
|
||||
Die();
|
||||
}
|
||||
else
|
||||
{
|
||||
__Shake(100);
|
||||
|
||||
if (!isLock() && !__IsKnockDownMotion() && !__IsStandUpMotion())
|
||||
{
|
||||
if (InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE))
|
||||
PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__Shake(DWORD dwDuration)
|
||||
{
|
||||
DWORD dwCurTime=ELTimer_GetMSec();
|
||||
m_dwShakeTime=dwCurTime+dwDuration;
|
||||
}
|
||||
|
||||
void CActorInstance::ShakeProcess()
|
||||
{
|
||||
if (m_dwShakeTime)
|
||||
{
|
||||
D3DXVECTOR3 v3Pos(0.0f, 0.0f, 0.0f);
|
||||
|
||||
DWORD dwCurTime=ELTimer_GetMSec();
|
||||
|
||||
if (m_dwShakeTime<dwCurTime)
|
||||
{
|
||||
m_dwShakeTime=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
int nShakeSize=10;
|
||||
|
||||
switch (rand()%2)
|
||||
{
|
||||
case 0:v3Pos.x+=rand()%nShakeSize;break;
|
||||
case 1:v3Pos.x-=rand()%nShakeSize;break;
|
||||
}
|
||||
|
||||
switch (rand()%2)
|
||||
{
|
||||
case 0:v3Pos.y+=rand()%nShakeSize;break;
|
||||
case 1:v3Pos.y-=rand()%nShakeSize;break;
|
||||
}
|
||||
|
||||
switch (rand()%2)
|
||||
{
|
||||
case 0:v3Pos.z+=rand()%nShakeSize;break;
|
||||
case 1:v3Pos.z-=rand()%nShakeSize;break;
|
||||
}
|
||||
}
|
||||
|
||||
m_worldMatrix._41 += v3Pos.x;
|
||||
m_worldMatrix._42 += v3Pos.y;
|
||||
m_worldMatrix._43 += v3Pos.z;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__HitStone(CActorInstance& rVictim)
|
||||
{
|
||||
if (rVictim.IsStun())
|
||||
{
|
||||
rVictim.Die();
|
||||
}
|
||||
else
|
||||
{
|
||||
rVictim.__Shake(100);
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__HitGood(CActorInstance& rVictim)
|
||||
{
|
||||
if (rVictim.IsKnockDown())
|
||||
return;
|
||||
|
||||
if (rVictim.IsStun())
|
||||
{
|
||||
rVictim.Die();
|
||||
}
|
||||
else
|
||||
{
|
||||
rVictim.__Shake(100);
|
||||
|
||||
if (!rVictim.isLock())
|
||||
{
|
||||
float fRotRad = D3DXToRadian(GetRotation());
|
||||
float fVictimRotRad = D3DXToRadian(rVictim.GetRotation());
|
||||
|
||||
D3DXVECTOR2 v2Normal(sin(fRotRad), cos(fRotRad));
|
||||
D3DXVECTOR2 v2VictimNormal(sin(fVictimRotRad), cos(fVictimRotRad));
|
||||
|
||||
D3DXVec2Normalize(&v2Normal, &v2Normal);
|
||||
D3DXVec2Normalize(&v2VictimNormal, &v2VictimNormal);
|
||||
|
||||
float fScalar = D3DXVec2Dot(&v2Normal, &v2VictimNormal);
|
||||
|
||||
if (fScalar < 0.0f)
|
||||
{
|
||||
if (rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE))
|
||||
rVictim.PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_BACK))
|
||||
rVictim.PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
else if (rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE))
|
||||
rVictim.PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__HitGreate(CActorInstance& rVictim)
|
||||
{
|
||||
// DISABLE_KNOCKDOWN_ATTACK
|
||||
if (rVictim.IsKnockDown())
|
||||
return;
|
||||
if (rVictim.__IsStandUpMotion())
|
||||
return;
|
||||
// END_OF_DISABLE_KNOCKDOWN_ATTACK
|
||||
|
||||
float fRotRad = D3DXToRadian(GetRotation());
|
||||
float fVictimRotRad = D3DXToRadian(rVictim.GetRotation());
|
||||
|
||||
D3DXVECTOR2 v2Normal(sin(fRotRad), cos(fRotRad));
|
||||
D3DXVECTOR2 v2VictimNormal(sin(fVictimRotRad), cos(fVictimRotRad));
|
||||
|
||||
D3DXVec2Normalize(&v2Normal, &v2Normal);
|
||||
D3DXVec2Normalize(&v2VictimNormal, &v2VictimNormal);
|
||||
|
||||
float fScalar = D3DXVec2Dot(&v2Normal, &v2VictimNormal);
|
||||
|
||||
rVictim.__Shake(100);
|
||||
|
||||
if (rVictim.IsUsingSkill())
|
||||
return;
|
||||
|
||||
if (rVictim.IsStun())
|
||||
{
|
||||
if (fScalar < 0.0f)
|
||||
rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING);
|
||||
else
|
||||
{
|
||||
if (!rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING_BACK))
|
||||
rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING);
|
||||
}
|
||||
|
||||
rVictim.m_isRealDead=true;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (fScalar < 0.0f)
|
||||
{
|
||||
if (rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING))
|
||||
{
|
||||
rVictim.PushOnceMotion(CRaceMotionData::NAME_STAND_UP);
|
||||
rVictim.PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING_BACK))
|
||||
{
|
||||
if (rVictim.InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING))
|
||||
{
|
||||
rVictim.PushOnceMotion(CRaceMotionData::NAME_STAND_UP);
|
||||
rVictim.PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
rVictim.PushOnceMotion(CRaceMotionData::NAME_STAND_UP_BACK);
|
||||
rVictim.PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::SetBlendingPosition(const TPixelPosition & c_rPosition, float fBlendingTime)
|
||||
{
|
||||
//return;
|
||||
TPixelPosition Position;
|
||||
|
||||
Position.x = c_rPosition.x - m_x;
|
||||
Position.y = c_rPosition.y - m_y;
|
||||
Position.z = 0;
|
||||
|
||||
m_PhysicsObject.SetLastPosition(Position, fBlendingTime);
|
||||
}
|
||||
|
||||
void CActorInstance::ResetBlendingPosition()
|
||||
{
|
||||
m_PhysicsObject.Initialize();
|
||||
}
|
||||
|
||||
void CActorInstance::GetBlendingPosition(TPixelPosition * pPosition)
|
||||
{
|
||||
if (m_PhysicsObject.isBlending())
|
||||
{
|
||||
m_PhysicsObject.GetLastPosition(pPosition);
|
||||
pPosition->x += m_x;
|
||||
pPosition->y += m_y;
|
||||
pPosition->z += m_z;
|
||||
}
|
||||
else
|
||||
{
|
||||
pPosition->x = m_x;
|
||||
pPosition->y = m_y;
|
||||
pPosition->z = m_z;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__PushCircle(CActorInstance & rVictim)
|
||||
{
|
||||
const TPixelPosition& c_rkPPosAtk=NEW_GetAtkPixelPositionRef();
|
||||
|
||||
D3DXVECTOR3 v3SrcPos(c_rkPPosAtk.x, -c_rkPPosAtk.y, c_rkPPosAtk.z);
|
||||
|
||||
const D3DXVECTOR3& c_rv3SrcPos = v3SrcPos;
|
||||
const D3DXVECTOR3& c_rv3DstPos = rVictim.GetPosition();
|
||||
|
||||
D3DXVECTOR3 v3Direction;
|
||||
v3Direction.x = c_rv3DstPos.x - c_rv3SrcPos.x;
|
||||
v3Direction.y = c_rv3DstPos.y - c_rv3SrcPos.y;
|
||||
v3Direction.z = 0.0f;
|
||||
D3DXVec3Normalize(&v3Direction, &v3Direction);
|
||||
|
||||
rVictim.__SetFallingDirection(v3Direction.x, v3Direction.y);
|
||||
}
|
||||
|
||||
void CActorInstance::__PushDirect(CActorInstance & rVictim)
|
||||
{
|
||||
D3DXVECTOR3 v3Direction;
|
||||
v3Direction.x = cosf(D3DXToRadian(m_fcurRotation + 270.0f));
|
||||
v3Direction.y = sinf(D3DXToRadian(m_fcurRotation + 270.0f));
|
||||
v3Direction.z = 0.0f;
|
||||
|
||||
rVictim.__SetFallingDirection(v3Direction.x, v3Direction.y);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
bool CActorInstance::__isInvisible()
|
||||
{
|
||||
if (IsDead())
|
||||
return true;
|
||||
|
||||
if (CTimer::Instance().GetCurrentSecond() >= m_fInvisibleTime)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CActorInstance::__SetFallingDirection(float fx, float fy)
|
||||
{
|
||||
m_PhysicsObject.SetDirection(D3DXVECTOR3(fx, fy, 0.0f));
|
||||
}
|
||||
@@ -0,0 +1,83 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
|
||||
void CActorInstance::BlendAlphaValue(float fDstAlpha, float fDuration)
|
||||
{
|
||||
__BlendAlpha_Apply(fDstAlpha, fDuration);
|
||||
}
|
||||
|
||||
void CActorInstance::SetBlendRenderMode()
|
||||
{
|
||||
m_iRenderMode = RENDER_MODE_BLEND;
|
||||
}
|
||||
|
||||
void CActorInstance::SetAlphaValue(float fAlpha)
|
||||
{
|
||||
m_fAlphaValue = fAlpha;
|
||||
}
|
||||
|
||||
float CActorInstance::GetAlphaValue()
|
||||
{
|
||||
return m_fAlphaValue;
|
||||
}
|
||||
|
||||
void CActorInstance::__BlendAlpha_Initialize()
|
||||
{
|
||||
m_kBlendAlpha.m_isBlending=false;
|
||||
m_kBlendAlpha.m_fBaseTime=0.0f;
|
||||
m_kBlendAlpha.m_fDuration=0.0f;
|
||||
m_kBlendAlpha.m_fBaseAlpha=0.0f;
|
||||
m_kBlendAlpha.m_fDstAlpha=0.0f;
|
||||
m_kBlendAlpha.m_iOldRenderMode=RENDER_MODE_NORMAL;
|
||||
}
|
||||
|
||||
void CActorInstance::__BlendAlpha_Apply(float fDstAlpha, float fDuration)
|
||||
{
|
||||
m_kBlendAlpha.m_isBlending=true;
|
||||
m_kBlendAlpha.m_fBaseAlpha=GetAlphaValue();
|
||||
m_kBlendAlpha.m_fBaseTime=GetLocalTime();
|
||||
m_kBlendAlpha.m_fDuration=fDuration;
|
||||
m_kBlendAlpha.m_fDstAlpha=fDstAlpha;
|
||||
m_kBlendAlpha.m_iOldRenderMode=m_iRenderMode;
|
||||
}
|
||||
|
||||
void CActorInstance::__BlendAlpha_Update()
|
||||
{
|
||||
if (!m_kBlendAlpha.m_isBlending)
|
||||
return;
|
||||
|
||||
float fElapsedTime=__BlendAlpha_GetElapsedTime();
|
||||
|
||||
if (fElapsedTime<m_kBlendAlpha.m_fDuration)
|
||||
{
|
||||
float fCurAlpha=m_kBlendAlpha.m_fBaseAlpha+(m_kBlendAlpha.m_fDstAlpha-m_kBlendAlpha.m_fBaseAlpha)*fElapsedTime/m_kBlendAlpha.m_fDuration;
|
||||
SetBlendRenderMode();
|
||||
SetAlphaValue(fCurAlpha);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (1.0f>m_kBlendAlpha.m_fDstAlpha)
|
||||
{
|
||||
SetBlendRenderMode();
|
||||
}
|
||||
else
|
||||
{
|
||||
m_iRenderMode=m_kBlendAlpha.m_iOldRenderMode;
|
||||
}
|
||||
|
||||
SetAlphaValue(m_kBlendAlpha.m_fDstAlpha);
|
||||
|
||||
__BlendAlpha_UpdateComplete();
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__BlendAlpha_UpdateComplete()
|
||||
{
|
||||
m_kBlendAlpha.m_isBlending=false;
|
||||
}
|
||||
|
||||
float CActorInstance::__BlendAlpha_GetElapsedTime()
|
||||
{
|
||||
float fCurTime=GetLocalTime();
|
||||
return fCurTime-m_kBlendAlpha.m_fBaseTime;
|
||||
}
|
||||
@@ -0,0 +1,744 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EterLib/GrpMath.h"
|
||||
|
||||
#include "ActorInstance.h"
|
||||
|
||||
void CActorInstance::__InitializeCollisionData()
|
||||
{
|
||||
m_canSkipCollision=false;
|
||||
}
|
||||
|
||||
void CActorInstance::EnableSkipCollision()
|
||||
{
|
||||
m_canSkipCollision=true;
|
||||
}
|
||||
|
||||
void CActorInstance::DisableSkipCollision()
|
||||
{
|
||||
m_canSkipCollision=false;
|
||||
}
|
||||
|
||||
bool CActorInstance::CanSkipCollision()
|
||||
{
|
||||
return m_canSkipCollision;
|
||||
}
|
||||
|
||||
void CActorInstance::UpdatePointInstance()
|
||||
{
|
||||
TCollisionPointInstanceListIterator itor;
|
||||
for (itor = m_DefendingPointInstanceList.begin(); itor != m_DefendingPointInstanceList.end(); ++itor)
|
||||
UpdatePointInstance(&(*itor));
|
||||
}
|
||||
|
||||
void CActorInstance::UpdatePointInstance(TCollisionPointInstance * pPointInstance)
|
||||
{
|
||||
if (!pPointInstance)
|
||||
{
|
||||
assert(!"CActorInstance::UpdatePointInstance - pPointInstance is NULL"); // 레퍼런스로 교체하시오
|
||||
return;
|
||||
}
|
||||
|
||||
D3DXMATRIX matBone;
|
||||
|
||||
if (pPointInstance->isAttached)
|
||||
{
|
||||
if (pPointInstance->dwModelIndex>=m_LODControllerVector.size())
|
||||
{
|
||||
//Tracenf("CActorInstance::UpdatePointInstance - rInstance.dwModelIndex=%d >= m_LODControllerVector.size()=%d",
|
||||
// pPointInstance->dwModelIndex>m_LODControllerVector.size());
|
||||
return;
|
||||
}
|
||||
|
||||
CGrannyLODController* pGrnLODController=m_LODControllerVector[pPointInstance->dwModelIndex];
|
||||
if (!pGrnLODController)
|
||||
{
|
||||
//Tracenf("CActorInstance::UpdatePointInstance - m_LODControllerVector[pPointInstance->dwModelIndex=%d] is NULL", pPointInstance->dwModelIndex);
|
||||
return;
|
||||
}
|
||||
|
||||
CGrannyModelInstance * pModelInstance = pGrnLODController->GetModelInstance();
|
||||
if (!pModelInstance)
|
||||
{
|
||||
//Tracenf("CActorInstance::UpdatePointInstance - pGrnLODController->GetModelInstance() is NULL");
|
||||
return;
|
||||
}
|
||||
|
||||
D3DXMATRIX * pmatBone = (D3DXMATRIX *)pModelInstance->GetBoneMatrixPointer(pPointInstance->dwBoneIndex);
|
||||
matBone = *(D3DXMATRIX *)pModelInstance->GetCompositeBoneMatrixPointer(pPointInstance->dwBoneIndex);
|
||||
matBone._41 = pmatBone->_41;
|
||||
matBone._42 = pmatBone->_42;
|
||||
matBone._43 = pmatBone->_43;
|
||||
matBone *= m_worldMatrix;
|
||||
}
|
||||
else
|
||||
{
|
||||
matBone = m_worldMatrix;
|
||||
}
|
||||
|
||||
// Update Collsion Sphere
|
||||
CSphereCollisionInstanceVector::const_iterator sit = pPointInstance->c_pCollisionData->SphereDataVector.begin();
|
||||
CDynamicSphereInstanceVector::iterator dit=pPointInstance->SphereInstanceVector.begin();
|
||||
for (;sit!=pPointInstance->c_pCollisionData->SphereDataVector.end();++sit,++dit)
|
||||
{
|
||||
const TSphereData & c = sit->GetAttribute();//c_pCollisionData->SphereDataVector[j].GetAttribute();
|
||||
|
||||
D3DXMATRIX matPoint;
|
||||
D3DXMatrixTranslation(&matPoint, c.v3Position.x, c.v3Position.y, c.v3Position.z);
|
||||
matPoint = matPoint * matBone;
|
||||
|
||||
dit->v3LastPosition = dit->v3Position;
|
||||
dit->v3Position.x = matPoint._41;
|
||||
dit->v3Position.y = matPoint._42;
|
||||
dit->v3Position.z = matPoint._43;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::UpdateAdvancingPointInstance()
|
||||
{
|
||||
// 말을 탔을 경우 사람은 이동값을 가지고 있지 않기 때문에 말로 부터 얻어와야 한다 - [levites]
|
||||
D3DXVECTOR3 v3Movement = m_v3Movement;
|
||||
if (m_pkHorse)
|
||||
v3Movement = m_pkHorse->m_v3Movement;
|
||||
|
||||
// 말은 업데이트 하지 않아도 된다 - [levites]
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->UpdateAdvancingPointInstance();
|
||||
|
||||
D3DXMATRIX matPoint;
|
||||
D3DXMATRIX matCenter;
|
||||
|
||||
TCollisionPointInstanceListIterator itor = m_BodyPointInstanceList.begin();
|
||||
for (; itor != m_BodyPointInstanceList.end(); ++itor)
|
||||
{
|
||||
TCollisionPointInstance & rInstance = *itor;
|
||||
|
||||
if (rInstance.isAttached)
|
||||
{
|
||||
if (rInstance.dwModelIndex>=m_LODControllerVector.size())
|
||||
{
|
||||
Tracenf("CActorInstance::UpdateAdvancingPointInstance - rInstance.dwModelIndex=%d >= m_LODControllerVector.size()=%d",
|
||||
rInstance.dwModelIndex, m_LODControllerVector.size());
|
||||
continue;
|
||||
}
|
||||
|
||||
CGrannyLODController* pGrnLODController=m_LODControllerVector[rInstance.dwModelIndex];
|
||||
if (!pGrnLODController)
|
||||
{
|
||||
Tracenf("CActorInstance::UpdateAdvancingPointInstance - m_LODControllerVector[rInstance.dwModelIndex=%d] is NULL", rInstance.dwModelIndex);
|
||||
continue;
|
||||
}
|
||||
|
||||
CGrannyModelInstance * pModelInstance = pGrnLODController->GetModelInstance();
|
||||
if (!pModelInstance)
|
||||
{
|
||||
//Tracenf("CActorInstance::UpdateAdvancingPointInstance - pGrnLODController->GetModelInstance() is NULL");
|
||||
continue;
|
||||
}
|
||||
|
||||
matCenter = *(D3DXMATRIX *)pModelInstance->GetBoneMatrixPointer(rInstance.dwBoneIndex);
|
||||
matCenter *= m_worldMatrix;
|
||||
}
|
||||
else
|
||||
{
|
||||
matCenter = m_worldMatrix;
|
||||
}
|
||||
|
||||
// Update Collision Sphere
|
||||
const NRaceData::TCollisionData * c_pCollisionData = rInstance.c_pCollisionData;
|
||||
if (c_pCollisionData)
|
||||
{
|
||||
for (DWORD j = 0; j < c_pCollisionData->SphereDataVector.size(); ++j)
|
||||
{
|
||||
const TSphereData & c = c_pCollisionData->SphereDataVector[j].GetAttribute();
|
||||
CDynamicSphereInstance & rSphereInstance = rInstance.SphereInstanceVector[j];
|
||||
|
||||
D3DXMatrixTranslation(&matPoint, c.v3Position.x, c.v3Position.y, c.v3Position.z);
|
||||
matPoint = matPoint * matCenter;
|
||||
|
||||
rSphereInstance.v3LastPosition.x = matPoint._41;
|
||||
rSphereInstance.v3LastPosition.y = matPoint._42;
|
||||
rSphereInstance.v3LastPosition.z = matPoint._43;
|
||||
rSphereInstance.v3Position = rSphereInstance.v3LastPosition;
|
||||
rSphereInstance.v3Position += v3Movement;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool CActorInstance::CheckCollisionDetection(const CDynamicSphereInstanceVector * c_pAttackingSphereVector, D3DXVECTOR3 * pv3Position)
|
||||
{
|
||||
if (!c_pAttackingSphereVector)
|
||||
{
|
||||
assert(!"CActorInstance::CheckCollisionDetection - c_pAttackingSphereVector is NULL"); // 레퍼런스로 교체하시오
|
||||
return false;
|
||||
}
|
||||
|
||||
TCollisionPointInstanceListIterator itor;
|
||||
for (itor = m_DefendingPointInstanceList.begin(); itor != m_DefendingPointInstanceList.end(); ++itor)
|
||||
{
|
||||
const CDynamicSphereInstanceVector * c_pDefendingSphereVector = &(*itor).SphereInstanceVector;
|
||||
|
||||
for (DWORD i = 0; i < c_pAttackingSphereVector->size(); ++i)
|
||||
for (DWORD j = 0; j < c_pDefendingSphereVector->size(); ++j)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rAttackingSphere = c_pAttackingSphereVector->at(i);
|
||||
const CDynamicSphereInstance & c_rDefendingSphere = c_pDefendingSphereVector->at(j);
|
||||
|
||||
if (DetectCollisionDynamicSphereVSDynamicSphere(c_rAttackingSphere, c_rDefendingSphere))
|
||||
{
|
||||
// FIXME : 두 원의 교점을 찾아내는 식으로 바꿔야 한다.
|
||||
*pv3Position = (c_rAttackingSphere.v3Position + c_rDefendingSphere.v3Position) / 2.0f;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CActorInstance::CreateCollisionInstancePiece(DWORD dwAttachingModelIndex, const NRaceData::TAttachingData * c_pAttachingData, TCollisionPointInstance * pPointInstance)
|
||||
{
|
||||
if (!c_pAttachingData)
|
||||
{
|
||||
assert(!"CActorInstance::CreateCollisionInstancePiece - c_pAttachingData is NULL"); // 레퍼런스로 교체하시오
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!c_pAttachingData->pCollisionData)
|
||||
{
|
||||
assert(!"CActorInstance::CreateCollisionInstancePiece - c_pAttachingData->pCollisionData is NULL"); // 레퍼런스로 교체하시오
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!pPointInstance)
|
||||
{
|
||||
assert(!"CActorInstance::CreateCollisionInstancePiece - pPointInstance is NULL"); // 레퍼런스로 교체하시오
|
||||
return false;
|
||||
}
|
||||
|
||||
pPointInstance->dwModelIndex = dwAttachingModelIndex;
|
||||
pPointInstance->isAttached = FALSE;
|
||||
pPointInstance->dwBoneIndex = 0;
|
||||
pPointInstance->c_pCollisionData = c_pAttachingData->pCollisionData;
|
||||
|
||||
if (c_pAttachingData->isAttaching)
|
||||
{
|
||||
int iAttachingBoneIndex;
|
||||
|
||||
CGrannyModelInstance * pModelInstance = m_LODControllerVector[dwAttachingModelIndex]->GetModelInstance();
|
||||
|
||||
if (pModelInstance && pModelInstance->GetBoneIndexByName(c_pAttachingData->strAttachingBoneName.c_str(),
|
||||
&iAttachingBoneIndex))
|
||||
{
|
||||
pPointInstance->isAttached = TRUE;
|
||||
pPointInstance->dwBoneIndex = iAttachingBoneIndex;
|
||||
}
|
||||
else
|
||||
{
|
||||
//TraceError("CActorInstance::CreateCollisionInstancePiece: Cannot get matrix of bone %s ModelInstance 0x%p", c_pAttachingData->strAttachingBoneName.c_str(), pModelInstance);
|
||||
pPointInstance->isAttached = TRUE;
|
||||
pPointInstance->dwBoneIndex = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
const CSphereCollisionInstanceVector & c_rSphereDataVector = c_pAttachingData->pCollisionData->SphereDataVector;
|
||||
|
||||
pPointInstance->SphereInstanceVector.clear();
|
||||
pPointInstance->SphereInstanceVector.reserve(c_rSphereDataVector.size());
|
||||
|
||||
CSphereCollisionInstanceVector::const_iterator it;
|
||||
CDynamicSphereInstance dsi;
|
||||
|
||||
dsi.v3LastPosition = D3DXVECTOR3(0.0f,0.0f,0.0f);
|
||||
dsi.v3Position = D3DXVECTOR3(0.0f,0.0f,0.0f);
|
||||
for (it = c_rSphereDataVector.begin(); it!=c_rSphereDataVector.end(); ++it)
|
||||
{
|
||||
const TSphereData & c_rSphereData = it->GetAttribute();
|
||||
dsi.fRadius = c_rSphereData.fRadius;
|
||||
pPointInstance->SphereInstanceVector.push_back(dsi);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
BOOL CActorInstance::__SplashAttackProcess(CActorInstance & rVictim)
|
||||
{
|
||||
D3DXVECTOR3 v3Distance(rVictim.m_x - m_x, rVictim.m_z - m_z, rVictim.m_z - m_z);
|
||||
float fDistance = D3DXVec3LengthSq(&v3Distance);
|
||||
if (fDistance >= 1000.0f*1000.0f)
|
||||
return FALSE;
|
||||
|
||||
// Check Distance
|
||||
if (!__IsInSplashTime())
|
||||
return FALSE;
|
||||
|
||||
const CRaceMotionData::TMotionAttackingEventData * c_pAttackingEvent = m_kSplashArea.c_pAttackingEvent;
|
||||
const NRaceData::TAttackData & c_rAttackData = c_pAttackingEvent->AttackData;
|
||||
THittedInstanceMap & rHittedInstanceMap = m_kSplashArea.HittedInstanceMap;
|
||||
|
||||
// NOTE : 이미 때렸다면 때릴 수 없음
|
||||
if (rHittedInstanceMap.end() != rHittedInstanceMap.find(&rVictim))
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// NOTE : Snipe 모드이고..
|
||||
if (NRaceData::ATTACK_TYPE_SNIPE == c_rAttackData.iAttackType)
|
||||
{
|
||||
// Target 이 PC 라면..
|
||||
if (__IsFlyTargetPC())
|
||||
// 다른 객체는 때릴 수 없다
|
||||
if (!__IsSameFlyTarget(&rVictim))
|
||||
return FALSE;
|
||||
|
||||
/*
|
||||
if (IsFlyTargetObject())
|
||||
{
|
||||
CActorInstance * pActorInstance = (CActorInstance *)m_kFlyTarget.GetFlyTarget();
|
||||
|
||||
// NOTE : Target 이 PC 일때는 한명만 때릴 수 있다.
|
||||
if (pActorInstance->IsPC())
|
||||
if (&rVictim != pActorInstance)
|
||||
return FALSE;
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
D3DXVECTOR3 v3HitPosition;
|
||||
if (rVictim.CheckCollisionDetection(&m_kSplashArea.SphereInstanceVector, &v3HitPosition))
|
||||
{
|
||||
rHittedInstanceMap.insert(std::make_pair(&rVictim, GetLocalTime()+c_rAttackData.fInvisibleTime));
|
||||
|
||||
int iCurrentHitCount = rHittedInstanceMap.size();
|
||||
int iMaxHitCount = (0 == c_rAttackData.iHitLimitCount ? 16 : c_rAttackData.iHitLimitCount);
|
||||
//Tracef(" ------------------- Splash Hit : %d\n", iCurrentHitCount);
|
||||
|
||||
if (iCurrentHitCount > iMaxHitCount)
|
||||
{
|
||||
//Tracef(" ------------------- OVER FLOW :: Splash Hit Count : %d\n", iCurrentHitCount);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
NEW_SetAtkPixelPosition(NEW_GetCurPixelPositionRef());
|
||||
__ProcessDataAttackSuccess(c_rAttackData, rVictim, v3HitPosition, m_kSplashArea.uSkill, m_kSplashArea.isEnableHitProcess);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::__NormalAttackProcess(CActorInstance & rVictim)
|
||||
{
|
||||
// Check Distance
|
||||
// NOTE - 일단 근접 체크만 하고 있음
|
||||
D3DXVECTOR3 v3Distance(rVictim.m_x - m_x, rVictim.m_z - m_z, rVictim.m_z - m_z);
|
||||
float fDistance = D3DXVec3LengthSq(&v3Distance);
|
||||
|
||||
extern bool IS_HUGE_RACE(unsigned int vnum);
|
||||
if (IS_HUGE_RACE(rVictim.GetRace()))
|
||||
{
|
||||
if (fDistance >= 500.0f*500.0f)
|
||||
return FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (fDistance >= 300.0f*300.0f)
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (!isValidAttacking())
|
||||
return FALSE;
|
||||
|
||||
const float c_fAttackRadius = 20.0f;
|
||||
const NRaceData::TMotionAttackData * pad = m_pkCurRaceMotionData->GetMotionAttackDataPointer();
|
||||
|
||||
const float motiontime = GetAttackingElapsedTime();
|
||||
|
||||
NRaceData::THitDataContainer::const_iterator itorHitData = pad->HitDataContainer.begin();
|
||||
for (; itorHitData != pad->HitDataContainer.end(); ++itorHitData)
|
||||
{
|
||||
const NRaceData::THitData & c_rHitData = *itorHitData;
|
||||
|
||||
// NOTE : 이미 맞았는지 체크
|
||||
THitDataMap::iterator itHitData = m_HitDataMap.find(&c_rHitData);
|
||||
if (itHitData != m_HitDataMap.end())
|
||||
{
|
||||
THittedInstanceMap & rHittedInstanceMap = itHitData->second;
|
||||
|
||||
THittedInstanceMap::iterator itInstance;
|
||||
if ((itInstance=rHittedInstanceMap.find(&rVictim)) != rHittedInstanceMap.end())
|
||||
{
|
||||
if (pad->iMotionType==NRaceData::MOTION_TYPE_COMBO || itInstance->second > GetLocalTime())
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
NRaceData::THitTimePositionMap::const_iterator range_start, range_end;
|
||||
range_start = c_rHitData.mapHitPosition.lower_bound(motiontime-CTimer::Instance().GetElapsedSecond());
|
||||
range_end = c_rHitData.mapHitPosition.upper_bound(motiontime);
|
||||
float c = cosf(D3DXToRadian(GetRotation()));
|
||||
float s = sinf(D3DXToRadian(GetRotation()));
|
||||
|
||||
for(;range_start!=range_end;++range_start)
|
||||
{
|
||||
const CDynamicSphereInstance& dsiSrc=range_start->second;
|
||||
|
||||
CDynamicSphereInstance dsi;
|
||||
dsi = dsiSrc;
|
||||
dsi.fRadius = c_fAttackRadius;
|
||||
{
|
||||
D3DXVECTOR3 v3SrcDir=dsiSrc.v3Position-dsiSrc.v3LastPosition;
|
||||
v3SrcDir*=__GetReachScale();
|
||||
|
||||
const D3DXVECTOR3& v3Src = dsiSrc.v3LastPosition+v3SrcDir;
|
||||
D3DXVECTOR3& v3Dst = dsi.v3Position;
|
||||
v3Dst.x = v3Src.x * c - v3Src.y * s;
|
||||
v3Dst.y = v3Src.x * s + v3Src.y * c;
|
||||
v3Dst += GetPosition();
|
||||
}
|
||||
{
|
||||
const D3DXVECTOR3& v3Src = dsiSrc.v3LastPosition;
|
||||
D3DXVECTOR3& v3Dst = dsi.v3LastPosition;
|
||||
v3Dst.x = v3Src.x * c - v3Src.y * s;
|
||||
v3Dst.y = v3Src.x * s + v3Src.y * c;
|
||||
v3Dst += GetPosition();
|
||||
}
|
||||
|
||||
|
||||
TCollisionPointInstanceList::iterator cpit;
|
||||
for(cpit = rVictim.m_DefendingPointInstanceList.begin(); cpit!=rVictim.m_DefendingPointInstanceList.end();++cpit)
|
||||
{
|
||||
int index = 0;
|
||||
const CDynamicSphereInstanceVector & c_DefendingSphereVector = cpit->SphereInstanceVector;
|
||||
CDynamicSphereInstanceVector::const_iterator dsit;
|
||||
for(dsit = c_DefendingSphereVector.begin(); dsit!= c_DefendingSphereVector.end();++dsit, ++index)
|
||||
{
|
||||
const CDynamicSphereInstance& sub = *dsit;
|
||||
if (DetectCollisionDynamicZCylinderVSDynamicZCylinder(dsi, sub))
|
||||
{
|
||||
THitDataMap::iterator itHitData = m_HitDataMap.find(&c_rHitData);
|
||||
if (itHitData == m_HitDataMap.end())
|
||||
{
|
||||
THittedInstanceMap HittedInstanceMap;
|
||||
HittedInstanceMap.insert(std::make_pair(&rVictim, GetLocalTime()+pad->fInvisibleTime));
|
||||
//HittedInstanceMap.insert(std::make_pair(&rVictim, GetLocalTime()+HIT_COOL_TIME));
|
||||
m_HitDataMap.insert(std::make_pair(&c_rHitData, HittedInstanceMap));
|
||||
|
||||
//Tracef(" ----------- First Hit\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
itHitData->second.insert(std::make_pair(&rVictim, GetLocalTime()+pad->fInvisibleTime));
|
||||
//itHitData->second.insert(std::make_pair(&rVictim, GetLocalTime()+HIT_COOL_TIME));
|
||||
|
||||
//Tracef(" ----------- Next Hit : %d\n", itHitData->second.size());
|
||||
|
||||
int iCurrentHitCount = itHitData->second.size();
|
||||
// NOTE : 보통 공격은 16명이 한계
|
||||
if (NRaceData::MOTION_TYPE_COMBO == pad->iMotionType || NRaceData::MOTION_TYPE_NORMAL == pad->iMotionType)
|
||||
{
|
||||
if (iCurrentHitCount > 16)
|
||||
{
|
||||
//Tracef(" Type NORMAL :: Overflow - Can't process, skip\n");
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (iCurrentHitCount > pad->iHitLimitCount)
|
||||
{
|
||||
//Tracef(" Type SKILL :: Overflow - Can't process, skip\n");
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
D3DXVECTOR3 v3HitPosition = (GetPosition() + rVictim.GetPosition()) *0.5f;
|
||||
|
||||
// #0000780: [M2KR] 수룡 타격구 문제
|
||||
extern bool IS_HUGE_RACE(unsigned int vnum);
|
||||
if (IS_HUGE_RACE(rVictim.GetRace()))
|
||||
{
|
||||
v3HitPosition = (GetPosition() + sub.v3Position) * 0.5f;
|
||||
}
|
||||
|
||||
__ProcessDataAttackSuccess(*pad, rVictim, v3HitPosition, m_kCurMotNode.uSkill);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::AttackingProcess(CActorInstance & rVictim)
|
||||
{
|
||||
if (rVictim.__isInvisible())
|
||||
return FALSE;
|
||||
|
||||
if (__SplashAttackProcess(rVictim))
|
||||
return TRUE;
|
||||
|
||||
if (__NormalAttackProcess(rVictim))
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::TestPhysicsBlendingCollision(CActorInstance & rVictim)
|
||||
{
|
||||
if (rVictim.IsDead())
|
||||
return FALSE;
|
||||
|
||||
TPixelPosition kPPosLast;
|
||||
GetBlendingPosition( &kPPosLast );
|
||||
|
||||
D3DXVECTOR3 v3Distance = D3DXVECTOR3(rVictim.m_x - kPPosLast.x, rVictim.m_y - kPPosLast.y, rVictim.m_z - kPPosLast.z);
|
||||
float fDistance = D3DXVec3LengthSq(&v3Distance);
|
||||
if (fDistance > 800.0f*800.0f)
|
||||
return FALSE;
|
||||
|
||||
// NOTE : 공격 중일때는 Defending Sphere로 Collision Check를 합니다.
|
||||
// NOTE : Wait로 블렌딩 되는 도중에 뚫고 들어가는 문제가 있어서.. - [levites]
|
||||
TCollisionPointInstanceList * pMainList;
|
||||
TCollisionPointInstanceList * pVictimList;
|
||||
if (isAttacking() || IsWaiting())
|
||||
{
|
||||
pMainList = &m_DefendingPointInstanceList;
|
||||
pVictimList = &rVictim.m_DefendingPointInstanceList;
|
||||
}
|
||||
else
|
||||
{
|
||||
pMainList = &m_BodyPointInstanceList;
|
||||
pVictimList = &rVictim.m_BodyPointInstanceList;
|
||||
}
|
||||
|
||||
TPixelPosition kPDelta;
|
||||
m_PhysicsObject.GetLastPosition(&kPDelta);
|
||||
|
||||
D3DXVECTOR3 prevLastPosition, prevPosition;
|
||||
const int nSubCheckCount = 50;
|
||||
|
||||
TCollisionPointInstanceListIterator itorMain = pMainList->begin();
|
||||
TCollisionPointInstanceListIterator itorVictim = pVictimList->begin();
|
||||
for (; itorMain != pMainList->end(); ++itorMain)
|
||||
{
|
||||
for (; itorVictim != pVictimList->end(); ++itorVictim)
|
||||
{
|
||||
CDynamicSphereInstanceVector & c_rMainSphereVector = (*itorMain).SphereInstanceVector;
|
||||
CDynamicSphereInstanceVector & c_rVictimSphereVector = (*itorVictim).SphereInstanceVector;
|
||||
|
||||
for (DWORD i = 0; i < c_rMainSphereVector.size(); ++i)
|
||||
{
|
||||
CDynamicSphereInstance & c_rMainSphere = c_rMainSphereVector[i];
|
||||
//adjust main sphere center
|
||||
prevLastPosition = c_rMainSphere.v3LastPosition;
|
||||
prevPosition = c_rMainSphere.v3Position;
|
||||
|
||||
c_rMainSphere.v3LastPosition = prevPosition;
|
||||
|
||||
for( int i = 1; i <= nSubCheckCount; ++ i )
|
||||
{
|
||||
c_rMainSphere.v3Position = prevPosition + (float)(i/(float)nSubCheckCount) * kPDelta;
|
||||
|
||||
for (DWORD j = 0; j < c_rVictimSphereVector.size(); ++j)
|
||||
{
|
||||
CDynamicSphereInstance & c_rVictimSphere = c_rVictimSphereVector[j];
|
||||
|
||||
if (DetectCollisionDynamicSphereVSDynamicSphere(c_rMainSphere, c_rVictimSphere))
|
||||
{
|
||||
BOOL bResult = GetVector3Distance(c_rMainSphere.v3Position, c_rVictimSphere.v3Position) <= GetVector3Distance(c_rMainSphere.v3LastPosition, c_rVictimSphere.v3Position);
|
||||
|
||||
c_rMainSphere.v3LastPosition = prevLastPosition;
|
||||
c_rMainSphere.v3Position = prevPosition;
|
||||
|
||||
return bResult;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//restore
|
||||
c_rMainSphere.v3LastPosition = prevLastPosition;
|
||||
c_rMainSphere.v3Position = prevPosition;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
BOOL CActorInstance::TestActorCollision(CActorInstance & rVictim)
|
||||
{
|
||||
/*
|
||||
if (m_pkHorse)
|
||||
{
|
||||
if (m_pkHorse->TestActorCollision(rVictim))
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
*/
|
||||
|
||||
if (rVictim.IsDead())
|
||||
return FALSE;
|
||||
|
||||
// Check Distance
|
||||
// NOTE : 적당히 멀면 체크 안함
|
||||
// 프레임 스킵시나 대상 오브젝트의 크기가 클경우 문제가 생길 여지가 있음
|
||||
// 캐릭터가 자신의 Body Sphere Radius 보다 더 크게 이동했는지를 체크하고,
|
||||
// 만약 그렇지 않다면 거리로 체크해서 걸러준다.
|
||||
D3DXVECTOR3 v3Distance = D3DXVECTOR3(rVictim.m_x - m_x, rVictim.m_y - m_y, rVictim.m_z - m_z);
|
||||
float fDistance = D3DXVec3LengthSq(&v3Distance);
|
||||
if (fDistance > 800.0f*800.0f)
|
||||
return FALSE;
|
||||
|
||||
// NOTE : 공격 중일때는 Defending Sphere로 Collision Check를 합니다.
|
||||
// NOTE : Wait로 블렌딩 되는 도중에 뚫고 들어가는 문제가 있어서.. - [levites]
|
||||
TCollisionPointInstanceList * pMainList;
|
||||
TCollisionPointInstanceList * pVictimList;
|
||||
if (isAttacking() || IsWaiting())
|
||||
{
|
||||
pMainList = &m_DefendingPointInstanceList;
|
||||
pVictimList = &rVictim.m_DefendingPointInstanceList;
|
||||
}
|
||||
else
|
||||
{
|
||||
pMainList = &m_BodyPointInstanceList;
|
||||
pVictimList = &rVictim.m_BodyPointInstanceList;
|
||||
}
|
||||
|
||||
TCollisionPointInstanceListIterator itorMain = pMainList->begin();
|
||||
TCollisionPointInstanceListIterator itorVictim = pVictimList->begin();
|
||||
for (; itorMain != pMainList->end(); ++itorMain)
|
||||
for (; itorVictim != pVictimList->end(); ++itorVictim)
|
||||
{
|
||||
const CDynamicSphereInstanceVector & c_rMainSphereVector = (*itorMain).SphereInstanceVector;
|
||||
const CDynamicSphereInstanceVector & c_rVictimSphereVector = (*itorVictim).SphereInstanceVector;
|
||||
|
||||
for (DWORD i = 0; i < c_rMainSphereVector.size(); ++i)
|
||||
for (DWORD j = 0; j < c_rVictimSphereVector.size(); ++j)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rMainSphere = c_rMainSphereVector[i];
|
||||
const CDynamicSphereInstance & c_rVictimSphere = c_rVictimSphereVector[j];
|
||||
|
||||
if (DetectCollisionDynamicSphereVSDynamicSphere(c_rMainSphere, c_rVictimSphere))
|
||||
{
|
||||
if (GetVector3Distance(c_rMainSphere.v3Position, c_rVictimSphere.v3Position) <=
|
||||
GetVector3Distance(c_rMainSphere.v3LastPosition, c_rVictimSphere.v3Position))
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
bool CActorInstance::AvoidObject(const CGraphicObjectInstance& c_rkBGObj)
|
||||
{
|
||||
#ifdef __MOVIE_MODE__
|
||||
if (IsMovieMode())
|
||||
return false;
|
||||
#endif
|
||||
|
||||
if (this==&c_rkBGObj)
|
||||
return false;
|
||||
|
||||
if (!__TestObjectCollision(&c_rkBGObj))
|
||||
return false;
|
||||
|
||||
__AdjustCollisionMovement(&c_rkBGObj);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::IsBlockObject(const CGraphicObjectInstance& c_rkBGObj)
|
||||
{
|
||||
if (this==&c_rkBGObj)
|
||||
return false;
|
||||
|
||||
if (!__TestObjectCollision(&c_rkBGObj))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CActorInstance::BlockMovement()
|
||||
{
|
||||
if (m_pkHorse)
|
||||
{
|
||||
m_pkHorse->__InitializeMovement();
|
||||
return;
|
||||
}
|
||||
|
||||
__InitializeMovement();
|
||||
}
|
||||
|
||||
BOOL CActorInstance::__TestObjectCollision(const CGraphicObjectInstance * c_pObjectInstance)
|
||||
{
|
||||
if (m_pkHorse)
|
||||
{
|
||||
if (m_pkHorse->__TestObjectCollision(c_pObjectInstance))
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (m_canSkipCollision)
|
||||
return FALSE;
|
||||
|
||||
if (m_v3Movement.x == 0.0f && m_v3Movement.y == 0.0f && m_v3Movement.z == 0.0f)
|
||||
return FALSE;
|
||||
|
||||
TCollisionPointInstanceListIterator itorMain = m_BodyPointInstanceList.begin();
|
||||
for (; itorMain != m_BodyPointInstanceList.end(); ++itorMain)
|
||||
{
|
||||
const CDynamicSphereInstanceVector & c_rMainSphereVector = (*itorMain).SphereInstanceVector;
|
||||
for (DWORD i = 0; i < c_rMainSphereVector.size(); ++i)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rMainSphere = c_rMainSphereVector[i];
|
||||
|
||||
if (c_pObjectInstance->MovementCollisionDynamicSphere(c_rMainSphere))
|
||||
{
|
||||
//const D3DXVECTOR3 & c_rv3Position = c_pObjectInstance->GetPosition();
|
||||
//if (GetVector3Distance(c_rMainSphere.v3Position, c_rv3Position) <
|
||||
// GetVector3Distance(c_rMainSphere.v3LastPosition, c_rv3Position))
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
//return FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
bool CActorInstance::TestCollisionWithDynamicSphere(const CDynamicSphereInstance & dsi)
|
||||
{
|
||||
TCollisionPointInstanceListIterator itorMain = m_BodyPointInstanceList.begin();
|
||||
for (; itorMain != m_BodyPointInstanceList.end(); ++itorMain)
|
||||
{
|
||||
const CDynamicSphereInstanceVector & c_rMainSphereVector = (*itorMain).SphereInstanceVector;
|
||||
for (DWORD i = 0; i < c_rMainSphereVector.size(); ++i)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rMainSphere = c_rMainSphereVector[i];
|
||||
|
||||
if (DetectCollisionDynamicSphereVSDynamicSphere(c_rMainSphere, dsi))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
@@ -0,0 +1,180 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
|
||||
void CActorInstance::__OnSyncing()
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
rkEventHandler.OnSyncing(kState);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnWaiting()
|
||||
{
|
||||
assert(!IsPushing());
|
||||
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
rkEventHandler.OnWaiting(kState);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnMoving()
|
||||
{
|
||||
assert(!IsPushing());
|
||||
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
const TPixelPosition& c_rkPPosCur=NEW_GetCurPixelPositionRef();
|
||||
const TPixelPosition& c_rkPPosDst=NEW_GetDstPixelPositionRef();
|
||||
|
||||
TPixelPosition kPPosDir=c_rkPPosDst-c_rkPPosCur;
|
||||
float distance=sqrt(kPPosDir.x*kPPosDir.x+kPPosDir.y*kPPosDir.y);
|
||||
|
||||
IEventHandler::SState kState;
|
||||
|
||||
if (distance>1000.0f)
|
||||
{
|
||||
D3DXVec3Normalize(&kPPosDir, &kPPosDir);
|
||||
D3DXVec3Scale(&kPPosDir, &kPPosDir, 1000.0f);
|
||||
D3DXVec3Add(&kState.kPPosSelf, &kPPosDir, &c_rkPPosCur);
|
||||
}
|
||||
else
|
||||
{
|
||||
kState.kPPosSelf=c_rkPPosDst;
|
||||
}
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
rkEventHandler.OnMoving(kState);
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::__OnMove()
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
rkEventHandler.OnMove(kState);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnStop()
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
rkEventHandler.OnStop(kState);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnWarp()
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
rkEventHandler.OnWarp(kState);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnAttack(WORD wMotionIndex)
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetTargetRotation();
|
||||
rkEventHandler.OnAttack(kState, wMotionIndex);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnUseSkill(UINT uMotSkill, UINT uLoopCount, bool isMovingSkill)
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
|
||||
IEventHandler::SState kState;
|
||||
kState.kPPosSelf=NEW_GetCurPixelPositionRef();
|
||||
kState.fAdvRotSelf=GetAdvancingRotation();
|
||||
|
||||
UINT uArg=uLoopCount;
|
||||
if (isMovingSkill)
|
||||
uArg|=1<<4;
|
||||
|
||||
rkEventHandler.OnUseSkill(kState, uMotSkill, uArg);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnHit(UINT uSkill, CActorInstance& rkActorVictm, BOOL isSendPacket)
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
rkEventHandler.OnHit(uSkill, rkActorVictm, isSendPacket);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnClearAffects()
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
rkEventHandler.OnClearAffects();
|
||||
}
|
||||
|
||||
void CActorInstance::__OnSetAffect(UINT uAffect)
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
rkEventHandler.OnSetAffect(uAffect);
|
||||
}
|
||||
|
||||
void CActorInstance::__OnResetAffect(UINT uAffect)
|
||||
{
|
||||
IEventHandler& rkEventHandler=__GetEventHandlerRef();
|
||||
rkEventHandler.OnResetAffect(uAffect);
|
||||
}
|
||||
|
||||
|
||||
CActorInstance::IEventHandler& CActorInstance::__GetEventHandlerRef()
|
||||
{
|
||||
assert(m_pkEventHandler!=NULL && "CActorInstance::GetEventHandlerRef");
|
||||
return *m_pkEventHandler;
|
||||
}
|
||||
|
||||
CActorInstance::IEventHandler* CActorInstance::__GetEventHandlerPtr()
|
||||
{
|
||||
return m_pkEventHandler;
|
||||
}
|
||||
|
||||
void CActorInstance::SetEventHandler(IEventHandler* pkEventHandler)
|
||||
{
|
||||
m_pkEventHandler=pkEventHandler;
|
||||
}
|
||||
|
||||
CActorInstance::IEventHandler* CActorInstance::IEventHandler::GetEmptyPtr()
|
||||
{
|
||||
static class CEmptyEventHandler : public IEventHandler
|
||||
{
|
||||
public:
|
||||
CEmptyEventHandler() {}
|
||||
virtual ~CEmptyEventHandler() {}
|
||||
|
||||
virtual void OnSyncing(const SState& c_rkState) {}
|
||||
virtual void OnWaiting(const SState& c_rkState) {}
|
||||
virtual void OnMoving(const SState& c_rkState) {}
|
||||
virtual void OnMove(const SState& c_rkState) {}
|
||||
virtual void OnStop(const SState& c_rkState) {}
|
||||
virtual void OnWarp(const SState& c_rkState) {}
|
||||
|
||||
virtual void OnClearAffects() {}
|
||||
virtual void OnSetAffect(UINT uAffect) {}
|
||||
virtual void OnResetAffect(UINT uAffect) {}
|
||||
|
||||
virtual void OnAttack(const SState& c_rkState, WORD wMotionIndex) {}
|
||||
virtual void OnUseSkill(const SState& c_rkState, UINT uMotSkill, UINT uMotLoopCount) {}
|
||||
|
||||
virtual void OnHit(UINT uMotAttack, CActorInstance& rkActorVictim, BOOL isSendPacket) {}
|
||||
|
||||
virtual void OnChangeShape() {}
|
||||
|
||||
} s_kEmptyEventHandler;
|
||||
|
||||
return &s_kEmptyEventHandler;
|
||||
}
|
||||
@@ -0,0 +1,117 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
|
||||
D3DXVECTOR3 CActorInstance::OnGetFlyTargetPosition()
|
||||
{
|
||||
D3DXVECTOR3 v3Center;
|
||||
if (m_fRadius<=0)
|
||||
{
|
||||
BuildBoundingSphere();
|
||||
v3Center = m_v3Center;
|
||||
}
|
||||
else
|
||||
{
|
||||
v3Center = m_v3Center;
|
||||
}
|
||||
|
||||
D3DXVec3TransformCoord(&v3Center, &v3Center, &GetTransform());
|
||||
return v3Center;
|
||||
}
|
||||
|
||||
void CActorInstance::ClearFlyTarget()
|
||||
{
|
||||
m_kFlyTarget.Clear();
|
||||
m_kBackupFlyTarget.Clear();
|
||||
m_kQue_kFlyTarget.clear();
|
||||
}
|
||||
|
||||
bool CActorInstance::IsFlyTargetObject()
|
||||
{
|
||||
return m_kFlyTarget.IsObject();
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsFlyTargetPC()
|
||||
{
|
||||
if (!IsFlyTargetObject())
|
||||
return false;
|
||||
|
||||
CActorInstance * pFlyInstance = (CActorInstance *)m_kFlyTarget.GetFlyTarget();
|
||||
if (pFlyInstance->IsPC())
|
||||
return true;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsSameFlyTarget(CActorInstance * pInstance)
|
||||
{
|
||||
if (!IsFlyTargetObject())
|
||||
return false;
|
||||
|
||||
CActorInstance * pFlyInstance = (CActorInstance *)m_kFlyTarget.GetFlyTarget();
|
||||
if (pInstance == pFlyInstance)
|
||||
return true;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
D3DXVECTOR3 CActorInstance::__GetFlyTargetPosition()
|
||||
{
|
||||
if (!m_kFlyTarget.IsValidTarget())
|
||||
{
|
||||
return D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
}
|
||||
|
||||
return m_kFlyTarget.GetFlyTargetPosition();
|
||||
}
|
||||
|
||||
float CActorInstance::GetFlyTargetDistance()
|
||||
{
|
||||
const D3DXVECTOR3& c_rv3FlyTargetPos=m_kFlyTarget.GetFlyTargetPosition();
|
||||
const D3DXVECTOR3& c_rkPosSrc=GetPosition();
|
||||
|
||||
D3DXVECTOR3 kPPosDelta=c_rv3FlyTargetPos-c_rkPosSrc;
|
||||
kPPosDelta.z=0;
|
||||
|
||||
return D3DXVec3Length(&kPPosDelta);
|
||||
}
|
||||
|
||||
void CActorInstance::LookAtFlyTarget()
|
||||
{
|
||||
if (!IsFlyTargetObject())
|
||||
return;
|
||||
|
||||
const D3DXVECTOR3& c_rv3FlyTargetPos=m_kFlyTarget.GetFlyTargetPosition();
|
||||
LookAt(c_rv3FlyTargetPos.x, c_rv3FlyTargetPos.y);
|
||||
}
|
||||
|
||||
void CActorInstance::AddFlyTarget(const CFlyTarget & cr_FlyTarget)
|
||||
{
|
||||
if (m_kFlyTarget.IsValidTarget())
|
||||
m_kQue_kFlyTarget.push_back(cr_FlyTarget);
|
||||
else
|
||||
SetFlyTarget(cr_FlyTarget);
|
||||
}
|
||||
|
||||
void CActorInstance::SetFlyTarget(const CFlyTarget & cr_FlyTarget)
|
||||
{
|
||||
m_kFlyTarget = cr_FlyTarget;
|
||||
}
|
||||
|
||||
void CActorInstance::ClearFlyEventHandler()
|
||||
{
|
||||
m_pFlyEventHandler = 0;
|
||||
}
|
||||
|
||||
void CActorInstance::SetFlyEventHandler(IFlyEventHandler * pHandler)
|
||||
{
|
||||
m_pFlyEventHandler = pHandler;
|
||||
}
|
||||
|
||||
// 2004. 07. 07. [levites] - 스킬 사용중 타겟이 바뀌는 문제 해결을 위한 코드
|
||||
bool CActorInstance::CanChangeTarget()
|
||||
{
|
||||
if (__IsNeedFlyTargetMotion())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -0,0 +1,911 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
#include "RaceData.h"
|
||||
#include "FlyHandler.h"
|
||||
|
||||
UINT CActorInstance::__GetMotionType()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return CRaceMotionData::TYPE_NONE;
|
||||
|
||||
return m_pkCurRaceMotionData->GetType();
|
||||
}
|
||||
|
||||
void CActorInstance::__MotionEventProcess(BOOL isPC)
|
||||
{
|
||||
if (isAttacking())
|
||||
{
|
||||
DWORD dwNextFrame = DWORD(GetAttackingElapsedTime() * g_fGameFPS);
|
||||
for (; m_kCurMotNode.dwcurFrame < dwNextFrame; ++m_kCurMotNode.dwcurFrame)
|
||||
{
|
||||
MotionEventProcess();
|
||||
SoundEventProcess(!isPC);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
MotionEventProcess();
|
||||
SoundEventProcess(!isPC);
|
||||
|
||||
++m_kCurMotNode.dwcurFrame;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::MotionProcess(BOOL isPC)
|
||||
{
|
||||
__MotionEventProcess(isPC);
|
||||
CurrentMotionProcess();
|
||||
ReservingMotionProcess();
|
||||
}
|
||||
|
||||
void CActorInstance::HORSE_MotionProcess(BOOL isPC)
|
||||
{
|
||||
__MotionEventProcess(isPC);
|
||||
|
||||
if (MOTION_TYPE_LOOP == m_kCurMotNode.iMotionType)
|
||||
if (m_kCurMotNode.dwcurFrame >= m_kCurMotNode.dwFrameCount)
|
||||
m_kCurMotNode.dwcurFrame = 0;
|
||||
}
|
||||
|
||||
void CActorInstance::ReservingMotionProcess()
|
||||
{
|
||||
if (m_MotionDeque.empty())
|
||||
return;
|
||||
|
||||
TReservingMotionNode & rReservingMotionNode = m_MotionDeque.front();
|
||||
|
||||
float fCurrentTime = GetLocalTime();
|
||||
if (rReservingMotionNode.fStartTime > fCurrentTime)
|
||||
return;
|
||||
|
||||
DWORD dwNextMotionIndex = GET_MOTION_INDEX(rReservingMotionNode.dwMotionKey);
|
||||
switch (dwNextMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_STAND_UP:
|
||||
case CRaceMotionData::NAME_STAND_UP_BACK:
|
||||
if (IsFaint())
|
||||
{
|
||||
//Tracenf("일어서려고 했으나 기절중");
|
||||
|
||||
SetEndStopMotion();
|
||||
|
||||
// 이후의 모션 전부 1초씩 딜레이
|
||||
TMotionDeque::iterator itor = m_MotionDeque.begin();
|
||||
for (; itor != m_MotionDeque.end(); ++itor)
|
||||
{
|
||||
TReservingMotionNode & rNode = *itor;
|
||||
rNode.fStartTime += 1.0f;
|
||||
}
|
||||
return;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
SCurrentMotionNode kPrevMotionNode=m_kCurMotNode;
|
||||
|
||||
EMotionPushType iMotionType=rReservingMotionNode.iMotionType;
|
||||
float fSpeedRatio=rReservingMotionNode.fSpeedRatio;
|
||||
float fBlendTime=rReservingMotionNode.fBlendTime;
|
||||
|
||||
DWORD dwMotionKey=rReservingMotionNode.dwMotionKey;
|
||||
|
||||
m_MotionDeque.pop_front();
|
||||
|
||||
DWORD dwCurrentMotionIndex=GET_MOTION_INDEX(dwMotionKey);
|
||||
switch (dwCurrentMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_STAND_UP:
|
||||
case CRaceMotionData::NAME_STAND_UP_BACK:
|
||||
if (IsDead())
|
||||
{
|
||||
//Tracenf("일어서려고 했으나 사망");
|
||||
// 예전 데이터로 복구
|
||||
m_kCurMotNode=kPrevMotionNode;
|
||||
__ClearMotion();
|
||||
|
||||
// 이전 동작 마지막 상태 유지
|
||||
SetEndStopMotion();
|
||||
return;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
//Tracenf("MOTION %d", GET_MOTION_INDEX(dwMotionKey));
|
||||
|
||||
int iLoopCount;
|
||||
if (MOTION_TYPE_ONCE == iMotionType)
|
||||
iLoopCount=1;
|
||||
else
|
||||
iLoopCount=0;
|
||||
|
||||
SSetMotionData kSetMotData;
|
||||
kSetMotData.dwMotKey=dwMotionKey;
|
||||
kSetMotData.fBlendTime=fBlendTime;
|
||||
kSetMotData.fSpeedRatio=fSpeedRatio;
|
||||
kSetMotData.iLoopCount=iLoopCount;
|
||||
|
||||
DWORD dwRealMotionKey = __SetMotion(kSetMotData);
|
||||
|
||||
if (0 == dwRealMotionKey)
|
||||
return;
|
||||
|
||||
// FIX: 위에서 호출한 __SetMotion 함수 안에서 랜덤으로 다른 모션을 재생할 가능성도 있으므로 duration은 '현재 재생중인' 모션의 duration값을 사용해야 함.
|
||||
//float fDurationTime=rReservingMotionNode.fDuration;
|
||||
float fDurationTime = GetMotionDuration(dwRealMotionKey) / fSpeedRatio;
|
||||
float fStartTime = rReservingMotionNode.fStartTime;
|
||||
float fEndTime = fStartTime + fDurationTime;
|
||||
|
||||
if (dwRealMotionKey == 16777473)
|
||||
{
|
||||
int bp = 0;
|
||||
bp++;
|
||||
}
|
||||
|
||||
m_kCurMotNode.uSkill = 0;
|
||||
m_kCurMotNode.iMotionType = iMotionType;
|
||||
m_kCurMotNode.fSpeedRatio = fSpeedRatio;
|
||||
m_kCurMotNode.fStartTime = fStartTime;
|
||||
m_kCurMotNode.fEndTime = fEndTime;
|
||||
m_kCurMotNode.dwMotionKey = dwRealMotionKey;
|
||||
m_kCurMotNode.dwcurFrame = 0;
|
||||
m_kCurMotNode.dwFrameCount = fDurationTime / (1.0f / g_fGameFPS);
|
||||
}
|
||||
|
||||
void CActorInstance::CurrentMotionProcess()
|
||||
{
|
||||
if (MOTION_TYPE_LOOP == m_kCurMotNode.iMotionType) // 임시다. 최종적인 목표는 Once도 절대로 넘어가선 안된다. - [levites]
|
||||
if (m_kCurMotNode.dwcurFrame >= m_kCurMotNode.dwFrameCount)
|
||||
m_kCurMotNode.dwcurFrame = 0;
|
||||
|
||||
if (IsDead())
|
||||
return;
|
||||
|
||||
if (!m_MotionDeque.empty())
|
||||
return;
|
||||
|
||||
float fCurrentTime = GetLocalTime();
|
||||
|
||||
DWORD dwMotionIndex=GET_MOTION_INDEX(m_kCurMotNode.dwMotionKey);
|
||||
|
||||
bool isLooping=false;
|
||||
|
||||
// 끝났다면 Playing Flag를 끈다
|
||||
if (m_pkCurRaceMotionData && m_pkCurRaceMotionData->IsLoopMotion())
|
||||
{
|
||||
if (m_kCurMotNode.iLoopCount > 1 || m_kCurMotNode.iLoopCount == -1)
|
||||
{
|
||||
if (fCurrentTime - m_kCurMotNode.fStartTime > m_pkCurRaceMotionData->GetLoopEndTime())
|
||||
{
|
||||
m_kCurMotNode.dwcurFrame = DWORD(m_pkCurRaceMotionData->GetLoopStartTime() * g_fGameFPS);
|
||||
__SetLocalTime(m_kCurMotNode.fStartTime + m_pkCurRaceMotionData->GetLoopStartTime());
|
||||
if (-1 != m_kCurMotNode.iLoopCount)
|
||||
--m_kCurMotNode.iLoopCount;
|
||||
|
||||
isLooping=true;
|
||||
}
|
||||
}
|
||||
else if (!m_kQue_kFlyTarget.empty())
|
||||
{
|
||||
if (!m_kBackupFlyTarget.IsObject())
|
||||
{
|
||||
m_kBackupFlyTarget = m_kFlyTarget;
|
||||
}
|
||||
|
||||
if (fCurrentTime - m_kCurMotNode.fStartTime > m_pkCurRaceMotionData->GetLoopEndTime())
|
||||
{
|
||||
m_kCurMotNode.dwcurFrame = DWORD(m_pkCurRaceMotionData->GetLoopStartTime() * g_fGameFPS);
|
||||
__SetLocalTime(m_kCurMotNode.fStartTime + m_pkCurRaceMotionData->GetLoopStartTime());
|
||||
|
||||
SetFlyTarget(m_kQue_kFlyTarget.front());
|
||||
m_kQue_kFlyTarget.pop_front();
|
||||
|
||||
isLooping=true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!isLooping)
|
||||
{
|
||||
if (fCurrentTime > m_kCurMotNode.fEndTime)
|
||||
{
|
||||
if (m_kBackupFlyTarget.IsValidTarget())
|
||||
{
|
||||
m_kFlyTarget = m_kBackupFlyTarget;
|
||||
m_kBackupFlyTarget.Clear();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////
|
||||
|
||||
if (MOTION_TYPE_ONCE == m_kCurMotNode.iMotionType)
|
||||
{
|
||||
switch (dwMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_DAMAGE_FLYING:
|
||||
case CRaceMotionData::NAME_DAMAGE_FLYING_BACK:
|
||||
case CRaceMotionData::NAME_DEAD:
|
||||
case CRaceMotionData::NAME_INTRO_SELECTED:
|
||||
case CRaceMotionData::NAME_INTRO_NOT_SELECTED:
|
||||
m_kCurMotNode.fEndTime+=3.0f;
|
||||
SetEndStopMotion();
|
||||
break;
|
||||
default:
|
||||
InterceptLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if (MOTION_TYPE_LOOP == m_kCurMotNode.iMotionType)
|
||||
{
|
||||
if (CRaceMotionData::NAME_WAIT == dwMotionIndex)
|
||||
{
|
||||
PushLoopMotion(CRaceMotionData::NAME_WAIT, 0.5f);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::SetMotionMode(int iMotionMode)
|
||||
{
|
||||
if (IsPoly())
|
||||
iMotionMode=CRaceMotionData::MODE_GENERAL;
|
||||
|
||||
m_wcurMotionMode = iMotionMode;
|
||||
}
|
||||
|
||||
int CActorInstance::GetMotionMode()
|
||||
{
|
||||
return m_wcurMotionMode;
|
||||
}
|
||||
|
||||
void CActorInstance::SetMotionLoopCount(int iCount)
|
||||
{
|
||||
assert(iCount >= -1 && iCount < 100);
|
||||
m_kCurMotNode.iLoopCount = iCount;
|
||||
}
|
||||
|
||||
void CActorInstance::PushMotion(EMotionPushType iMotionType, DWORD dwMotionKey, float fBlendTime, float fSpeedRatio)
|
||||
{
|
||||
if (!CheckMotionThingIndex(dwMotionKey))
|
||||
{
|
||||
Tracef(" Error - Not found want to using motion : %d\n", GET_MOTION_INDEX(dwMotionKey));
|
||||
return;
|
||||
}
|
||||
|
||||
TReservingMotionNode MotionNode;
|
||||
|
||||
MotionNode.iMotionType = iMotionType;
|
||||
MotionNode.dwMotionKey = dwMotionKey;
|
||||
MotionNode.fStartTime = GetLastMotionTime(fBlendTime);
|
||||
MotionNode.fBlendTime = fBlendTime;
|
||||
MotionNode.fSpeedRatio = fSpeedRatio;
|
||||
MotionNode.fDuration = GetMotionDuration(dwMotionKey);
|
||||
|
||||
m_MotionDeque.push_back(MotionNode);
|
||||
}
|
||||
|
||||
bool CActorInstance::InterceptOnceMotion(DWORD dwMotion, float fBlendTime, UINT uSkill, float fSpeedRatio)
|
||||
{
|
||||
return InterceptMotion(MOTION_TYPE_ONCE, dwMotion, fBlendTime, uSkill, fSpeedRatio);
|
||||
}
|
||||
|
||||
bool CActorInstance::InterceptLoopMotion(DWORD dwMotion, float fBlendTime)
|
||||
{
|
||||
return InterceptMotion(MOTION_TYPE_LOOP, dwMotion, fBlendTime);
|
||||
}
|
||||
|
||||
void CActorInstance::SetLoopMotion(DWORD dwMotion, float fBlendTime, float fSpeedRatio)
|
||||
{
|
||||
if (!m_pkCurRaceData)
|
||||
{
|
||||
Tracenf("CActorInstance::SetLoopMotion(dwMotion=%d, fBlendTime=%f, fSpeedRatio=%f)",
|
||||
dwMotion, fBlendTime, fSpeedRatio);
|
||||
return;
|
||||
}
|
||||
|
||||
MOTION_KEY dwMotionKey;
|
||||
if (!m_pkCurRaceData->GetMotionKey(m_wcurMotionMode, dwMotion, &dwMotionKey))
|
||||
{
|
||||
Tracenf("CActorInstance::SetLoopMotion(dwMotion=%d, fBlendTime=%f, fSpeedRatio=%f) - GetMotionKey(m_wcurMotionMode=%d, dwMotion=%d, &MotionKey) ERROR",
|
||||
dwMotion, fBlendTime, fSpeedRatio, m_wcurMotionMode, dwMotion);
|
||||
return;
|
||||
}
|
||||
|
||||
__ClearMotion();
|
||||
|
||||
SSetMotionData kSetMotData;
|
||||
kSetMotData.dwMotKey=dwMotionKey;
|
||||
kSetMotData.fBlendTime=fBlendTime;
|
||||
kSetMotData.fSpeedRatio=fSpeedRatio;
|
||||
|
||||
DWORD dwRealMotionKey = __SetMotion(kSetMotData);
|
||||
|
||||
if (0 == dwRealMotionKey)
|
||||
return;
|
||||
|
||||
m_kCurMotNode.iMotionType = MOTION_TYPE_LOOP;
|
||||
m_kCurMotNode.fStartTime = GetLocalTime();
|
||||
m_kCurMotNode.dwMotionKey = dwRealMotionKey;
|
||||
m_kCurMotNode.fEndTime = 0.0f;
|
||||
m_kCurMotNode.fSpeedRatio = fSpeedRatio;
|
||||
m_kCurMotNode.dwcurFrame = 0;
|
||||
m_kCurMotNode.dwFrameCount = GetMotionDuration(dwRealMotionKey) / (1.0f / g_fGameFPS);
|
||||
m_kCurMotNode.uSkill = 0;
|
||||
}
|
||||
|
||||
// 리턴값 == SetMotion의 리턴값 == 실제로 애니메이션 데이터를 플레이 했느냐?
|
||||
bool CActorInstance::InterceptMotion(EMotionPushType iMotionType, WORD wMotion, float fBlendTime, UINT uSkill, float fSpeedRatio)
|
||||
{
|
||||
if (!m_pkCurRaceData)
|
||||
{
|
||||
Tracef("CActorInstance::InterceptMotion(iMotionType=%d, wMotion=%d, fBlendTime=%f) - m_pkCurRaceData=NULL", iMotionType, wMotion, fBlendTime);
|
||||
return false;
|
||||
}
|
||||
|
||||
MOTION_KEY dwMotionKey;
|
||||
if (!m_pkCurRaceData->GetMotionKey(m_wcurMotionMode, wMotion, &dwMotionKey))
|
||||
{
|
||||
Tracenf("CActorInstance::InterceptMotion(iLoopType=%d, wMotionMode=%d, wMotion=%d, fBlendTime=%f) - GetMotionKey(m_wcurMotionMode=%d, wMotion=%d, &MotionKey) ERROR",
|
||||
iMotionType, m_wcurMotionMode, wMotion, fBlendTime, m_wcurMotionMode, wMotion);
|
||||
return false;
|
||||
}
|
||||
|
||||
__ClearMotion();
|
||||
|
||||
int iLoopCount;
|
||||
if (MOTION_TYPE_ONCE == iMotionType)
|
||||
iLoopCount=1;
|
||||
else
|
||||
iLoopCount=0;
|
||||
|
||||
SSetMotionData kSetMotData;
|
||||
kSetMotData.dwMotKey=dwMotionKey;
|
||||
kSetMotData.fBlendTime=fBlendTime;
|
||||
kSetMotData.iLoopCount=iLoopCount;
|
||||
kSetMotData.fSpeedRatio=fSpeedRatio;
|
||||
kSetMotData.uSkill=uSkill;
|
||||
|
||||
DWORD dwRealMotionKey = __SetMotion(kSetMotData);
|
||||
|
||||
if (0 == dwRealMotionKey)
|
||||
return false;
|
||||
|
||||
if (m_pFlyEventHandler)
|
||||
{
|
||||
if (__IsNeedFlyTargetMotion())
|
||||
{
|
||||
m_pFlyEventHandler->OnSetFlyTarget();
|
||||
}
|
||||
}
|
||||
|
||||
assert(NULL != m_pkCurRaceMotionData);
|
||||
|
||||
// FIX : 위에서 호출한 __SetMotion 함수 내에서 랜덤으로 다른 모션을 선택할 수도 있기 때문에 dwMotionKey값은 유효하지 않고
|
||||
// 따라서 해당 키로 산출한 duration은 유효하지 않음. 당연히 현재 play중인 모션의 시간을 구해야 함.. -_-;;
|
||||
// float fDuration=GetMotionDuration(dwMotionKey)/fSpeedRatio;
|
||||
float fDuration = GetMotionDuration(dwRealMotionKey) / fSpeedRatio;
|
||||
|
||||
m_kCurMotNode.iMotionType = iMotionType;
|
||||
m_kCurMotNode.fStartTime = GetLocalTime();
|
||||
m_kCurMotNode.fEndTime = m_kCurMotNode.fStartTime + fDuration;
|
||||
m_kCurMotNode.dwMotionKey = dwRealMotionKey;
|
||||
m_kCurMotNode.dwcurFrame = 0;
|
||||
m_kCurMotNode.dwFrameCount = fDuration / (1.0f / g_fGameFPS);
|
||||
m_kCurMotNode.uSkill = uSkill;
|
||||
m_kCurMotNode.fSpeedRatio = fSpeedRatio;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::PushOnceMotion(DWORD dwMotion, float fBlendTime, float fSpeedRatio)
|
||||
{
|
||||
assert(m_pkCurRaceData);
|
||||
|
||||
MOTION_KEY MotionKey;
|
||||
if (!m_pkCurRaceData->GetMotionKey(m_wcurMotionMode, dwMotion, &MotionKey))
|
||||
return false;
|
||||
|
||||
PushMotion(MOTION_TYPE_ONCE, MotionKey, fBlendTime, fSpeedRatio);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::PushLoopMotion(DWORD dwMotion, float fBlendTime, float fSpeedRatio)
|
||||
{
|
||||
assert(m_pkCurRaceData);
|
||||
|
||||
MOTION_KEY MotionKey;
|
||||
if (!m_pkCurRaceData->GetMotionKey(m_wcurMotionMode, dwMotion, &MotionKey))
|
||||
return false;
|
||||
|
||||
PushMotion(MOTION_TYPE_LOOP, MotionKey, fBlendTime, fSpeedRatio);
|
||||
return true;
|
||||
}
|
||||
|
||||
WORD CActorInstance::__GetCurrentMotionIndex()
|
||||
{
|
||||
return GET_MOTION_INDEX(m_kCurMotNode.dwMotionKey);
|
||||
}
|
||||
|
||||
DWORD CActorInstance::__GetCurrentMotionKey()
|
||||
{
|
||||
return m_kCurMotNode.dwMotionKey;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::IsUsingSkill()
|
||||
{
|
||||
DWORD dwCurMotionIndex=__GetCurrentMotionIndex();
|
||||
|
||||
if (dwCurMotionIndex>=CRaceMotionData::NAME_SKILL && dwCurMotionIndex<CRaceMotionData::NAME_SKILL_END)
|
||||
return TRUE;
|
||||
|
||||
switch (dwCurMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_SPECIAL_1:
|
||||
case CRaceMotionData::NAME_SPECIAL_2:
|
||||
case CRaceMotionData::NAME_SPECIAL_3:
|
||||
case CRaceMotionData::NAME_SPECIAL_4:
|
||||
case CRaceMotionData::NAME_SPECIAL_5:
|
||||
case CRaceMotionData::NAME_SPECIAL_6:
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::IsFishing()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return FALSE;
|
||||
|
||||
if (__GetCurrentMotionIndex() == CRaceMotionData::NAME_FISHING_WAIT ||
|
||||
__GetCurrentMotionIndex() == CRaceMotionData::NAME_FISHING_REACT)
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CActorInstance::CanCancelSkill()
|
||||
{
|
||||
assert(IsUsingSkill());
|
||||
return m_pkCurRaceMotionData->IsCancelEnableSkill();
|
||||
}
|
||||
|
||||
BOOL CActorInstance::isLock()
|
||||
{
|
||||
DWORD dwCurMotionIndex=__GetCurrentMotionIndex();
|
||||
|
||||
// Locked during attack
|
||||
switch (dwCurMotionIndex)
|
||||
{
|
||||
case CRaceMotionData::NAME_NORMAL_ATTACK:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_1:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_2:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_3:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_4:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_5:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_6:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_7:
|
||||
case CRaceMotionData::NAME_COMBO_ATTACK_8:
|
||||
case CRaceMotionData::NAME_SPECIAL_1:
|
||||
case CRaceMotionData::NAME_SPECIAL_2:
|
||||
case CRaceMotionData::NAME_SPECIAL_3:
|
||||
case CRaceMotionData::NAME_SPECIAL_4:
|
||||
case CRaceMotionData::NAME_SPECIAL_5:
|
||||
case CRaceMotionData::NAME_SPECIAL_6:
|
||||
case CRaceMotionData::NAME_FISHING_THROW:
|
||||
case CRaceMotionData::NAME_FISHING_WAIT:
|
||||
case CRaceMotionData::NAME_FISHING_STOP:
|
||||
case CRaceMotionData::NAME_FISHING_REACT:
|
||||
case CRaceMotionData::NAME_FISHING_CATCH:
|
||||
case CRaceMotionData::NAME_FISHING_FAIL:
|
||||
case CRaceMotionData::NAME_CLAP:
|
||||
case CRaceMotionData::NAME_DANCE_1:
|
||||
case CRaceMotionData::NAME_DANCE_2:
|
||||
case CRaceMotionData::NAME_DANCE_3:
|
||||
case CRaceMotionData::NAME_DANCE_4:
|
||||
case CRaceMotionData::NAME_DANCE_5:
|
||||
case CRaceMotionData::NAME_DANCE_6:
|
||||
case CRaceMotionData::NAME_CONGRATULATION:
|
||||
case CRaceMotionData::NAME_FORGIVE:
|
||||
case CRaceMotionData::NAME_ANGRY:
|
||||
case CRaceMotionData::NAME_ATTRACTIVE:
|
||||
case CRaceMotionData::NAME_SAD:
|
||||
case CRaceMotionData::NAME_SHY:
|
||||
case CRaceMotionData::NAME_CHEERUP:
|
||||
case CRaceMotionData::NAME_BANTER:
|
||||
case CRaceMotionData::NAME_JOY:
|
||||
case CRaceMotionData::NAME_CHEERS_1:
|
||||
case CRaceMotionData::NAME_CHEERS_2:
|
||||
case CRaceMotionData::NAME_KISS_WITH_WARRIOR:
|
||||
case CRaceMotionData::NAME_KISS_WITH_ASSASSIN:
|
||||
case CRaceMotionData::NAME_KISS_WITH_SURA:
|
||||
case CRaceMotionData::NAME_KISS_WITH_SHAMAN:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_WITH_WARRIOR:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_WITH_ASSASSIN:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_WITH_SURA:
|
||||
case CRaceMotionData::NAME_FRENCH_KISS_WITH_SHAMAN:
|
||||
case CRaceMotionData::NAME_SLAP_HIT_WITH_WARRIOR:
|
||||
case CRaceMotionData::NAME_SLAP_HIT_WITH_ASSASSIN:
|
||||
case CRaceMotionData::NAME_SLAP_HIT_WITH_SURA:
|
||||
case CRaceMotionData::NAME_SLAP_HIT_WITH_SHAMAN:
|
||||
case CRaceMotionData::NAME_SLAP_HURT_WITH_WARRIOR:
|
||||
case CRaceMotionData::NAME_SLAP_HURT_WITH_ASSASSIN:
|
||||
case CRaceMotionData::NAME_SLAP_HURT_WITH_SURA:
|
||||
case CRaceMotionData::NAME_SLAP_HURT_WITH_SHAMAN:
|
||||
return TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
// Locked during using skill
|
||||
if (IsUsingSkill())
|
||||
{
|
||||
if (m_pkCurRaceMotionData->IsCancelEnableSkill())
|
||||
return FALSE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
float CActorInstance::GetLastMotionTime(float fBlendTime)
|
||||
{
|
||||
if (m_MotionDeque.empty())
|
||||
{
|
||||
if (MOTION_TYPE_ONCE == m_kCurMotNode.iMotionType)
|
||||
return (m_kCurMotNode.fEndTime - fBlendTime);
|
||||
|
||||
return GetLocalTime();
|
||||
}
|
||||
|
||||
TReservingMotionNode & rMotionNode = m_MotionDeque[m_MotionDeque.size()-1];
|
||||
|
||||
return rMotionNode.fStartTime + rMotionNode.fDuration - fBlendTime;
|
||||
}
|
||||
|
||||
float CActorInstance::GetMotionDuration(DWORD dwMotionKey)
|
||||
{
|
||||
CGraphicThing * pMotion;
|
||||
|
||||
if (!GetMotionThingPointer(dwMotionKey, &pMotion))
|
||||
{
|
||||
Tracenf("CActorInstance::GetMotionDuration - Cannot get motion: %d / %d",
|
||||
GET_MOTION_MODE(dwMotionKey), GET_MOTION_INDEX(dwMotionKey));
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
if (0 == pMotion->GetMotionCount())
|
||||
{
|
||||
#ifdef _DEBUG
|
||||
Tracenf("CActorInstance::GetMotionDuration - Invalid Motion Key : %d, %d, %d",
|
||||
GET_MOTION_MODE(dwMotionKey), GET_MOTION_INDEX(dwMotionKey), GET_MOTION_SUB_INDEX(dwMotionKey));
|
||||
#endif
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
CGrannyMotion * pGrannyMotion = pMotion->GetMotionPointer(0);
|
||||
return pGrannyMotion->GetDuration();
|
||||
}
|
||||
|
||||
MOTION_KEY CActorInstance::GetRandomMotionKey(MOTION_KEY dwMotionKey)
|
||||
{
|
||||
// NOTE : 자주 호출 되는 부분은 아니지만 어느 정도의 최적화 여지가 있음 - [levites]
|
||||
// FIXME : 처음에 선택된 모션이 없는 것에 대한 처리가 되어 있지 않다.
|
||||
WORD wMode = GET_MOTION_MODE(dwMotionKey);
|
||||
WORD wIndex = GET_MOTION_INDEX(dwMotionKey);
|
||||
|
||||
const CRaceData::TMotionVector * c_pMotionVector;
|
||||
if (m_pkCurRaceData->GetMotionVectorPointer(wMode, wIndex, &c_pMotionVector))
|
||||
if (c_pMotionVector->size() > 1)
|
||||
{
|
||||
int iPercentage = random() % 100;
|
||||
for (DWORD i = 0; i < c_pMotionVector->size(); ++i)
|
||||
{
|
||||
const CRaceData::TMotion & c_rMotion = c_pMotionVector->at(i);
|
||||
iPercentage -= c_rMotion.byPercentage;
|
||||
|
||||
if (iPercentage < 0)
|
||||
{
|
||||
dwMotionKey = MAKE_RANDOM_MOTION_KEY(wMode, wIndex, i);
|
||||
|
||||
// Temporary
|
||||
// NOTE: 현재로선 여기서 해봤자 의미없다. 전체적으로 확인결과 아래는 씹히는 코드고 다른곳에서 해결해야 하므로 일단 주석처리함. 나중에 통채로 지우자..
|
||||
// m_kCurMotNode.fEndTime = m_kCurMotNode.fStartTime + GetMotionDuration(dwMotionKey);
|
||||
// Temporary
|
||||
|
||||
return dwMotionKey;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return dwMotionKey;
|
||||
}
|
||||
|
||||
void CActorInstance::PreAttack()
|
||||
{
|
||||
}
|
||||
|
||||
void CActorInstance::__ClearMotion()
|
||||
{
|
||||
__HideWeaponTrace();
|
||||
|
||||
m_MotionDeque.clear();
|
||||
m_kCurMotNode.dwcurFrame=0;
|
||||
m_kCurMotNode.dwFrameCount=0;
|
||||
m_kCurMotNode.uSkill=0;
|
||||
m_kCurMotNode.iLoopCount=0;
|
||||
m_kCurMotNode.iMotionType=MOTION_TYPE_NONE;
|
||||
}
|
||||
|
||||
|
||||
DWORD CActorInstance::__SetMotion(const SSetMotionData& c_rkSetMotData, DWORD dwRandMotKey)
|
||||
{
|
||||
DWORD dwMotKey = dwRandMotKey;
|
||||
|
||||
if (dwMotKey == 0)
|
||||
dwMotKey = GetRandomMotionKey(c_rkSetMotData.dwMotKey);
|
||||
|
||||
UINT uNextMot = GET_MOTION_INDEX(c_rkSetMotData.dwMotKey);
|
||||
|
||||
if (IsDead())
|
||||
{
|
||||
if (uNextMot!=CRaceMotionData::NAME_DAMAGE_FLYING && uNextMot!=CRaceMotionData::NAME_DAMAGE_FLYING_BACK && uNextMot!=CRaceMotionData::NAME_DEAD && uNextMot!=CRaceMotionData::NAME_DEAD_BACK)
|
||||
return 0;
|
||||
}
|
||||
if (IsUsingSkill())
|
||||
{
|
||||
__OnStop();
|
||||
}
|
||||
|
||||
if (__IsStandUpMotion())
|
||||
{
|
||||
__OnStop();
|
||||
}
|
||||
|
||||
|
||||
if (__IsMoveMotion())
|
||||
{
|
||||
if (uNextMot==CRaceMotionData::NAME_DAMAGE || uNextMot==CRaceMotionData::NAME_DAMAGE_BACK || uNextMot==CRaceMotionData::NAME_DAMAGE_FLYING || uNextMot==CRaceMotionData::NAME_DAMAGE_FLYING_BACK)
|
||||
{
|
||||
if (!m_isMain)
|
||||
{
|
||||
Logn(0, "\301\326\300\316\260\370\300\314 \276\306\264\317\266\363\270\351 \300\314\265\277\301\337\300\314\266\363 \265\245\271\314\301\366 \265\277\300\333\300\273 \303\353\307\317\301\366 \276\312\300\275");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
if (uNextMot!=CRaceMotionData::NAME_RUN &&
|
||||
uNextMot!=CRaceMotionData::NAME_WALK &&
|
||||
!__IsMovingSkill(c_rkSetMotData.uSkill))
|
||||
{
|
||||
__OnStop();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (uNextMot==CRaceMotionData::NAME_RUN || __IsMovingSkill(c_rkSetMotData.uSkill))
|
||||
{
|
||||
__OnMove();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// NOTE : 스킬 사용중 사라지는 문제를 위한 안전 장치 - [levites]
|
||||
if (__IsHiding())
|
||||
{
|
||||
__ShowEvent();
|
||||
}
|
||||
|
||||
|
||||
if (-1 != m_iFishingEffectID)
|
||||
{
|
||||
CEffectManager& rkEftMgr=CEffectManager::Instance();
|
||||
rkEftMgr.DeactiveEffectInstance(m_iFishingEffectID);
|
||||
|
||||
m_iFishingEffectID = -1;
|
||||
}
|
||||
|
||||
if (m_pkHorse)
|
||||
{
|
||||
WORD wMotionIndex = GET_MOTION_INDEX(dwMotKey);
|
||||
WORD wMotionSubIndex = GET_MOTION_SUB_INDEX(dwMotKey);
|
||||
DWORD dwChildMotKey = MAKE_RANDOM_MOTION_KEY(m_pkHorse->m_wcurMotionMode, wMotionIndex, wMotionSubIndex);
|
||||
|
||||
if (CRaceMotionData::NAME_DEAD == wMotionIndex)
|
||||
CGraphicThingInstance::ChangeMotion(dwMotKey, c_rkSetMotData.iLoopCount, c_rkSetMotData.fSpeedRatio);
|
||||
else
|
||||
CGraphicThingInstance::SetMotion(dwMotKey, c_rkSetMotData.fBlendTime, c_rkSetMotData.iLoopCount, c_rkSetMotData.fSpeedRatio);
|
||||
|
||||
m_pkHorse->SetMotion(dwChildMotKey, c_rkSetMotData.fBlendTime, c_rkSetMotData.iLoopCount, c_rkSetMotData.fSpeedRatio);
|
||||
m_pkHorse->__BindMotionData(dwChildMotKey);
|
||||
|
||||
if (c_rkSetMotData.iLoopCount)
|
||||
m_pkHorse->m_kCurMotNode.iMotionType = MOTION_TYPE_ONCE; // 무조건 이전 모션 타입으로 설정되고 있었음
|
||||
else
|
||||
m_pkHorse->m_kCurMotNode.iMotionType = MOTION_TYPE_LOOP;
|
||||
|
||||
m_pkHorse->m_kCurMotNode.dwFrameCount = m_pkHorse->GetMotionDuration(dwChildMotKey) / (1.0f / g_fGameFPS);
|
||||
m_pkHorse->m_kCurMotNode.dwcurFrame = 0;
|
||||
m_pkHorse->m_kCurMotNode.dwMotionKey = dwChildMotKey;
|
||||
}
|
||||
else
|
||||
{
|
||||
CGraphicThingInstance::SetMotion(dwMotKey, c_rkSetMotData.fBlendTime, c_rkSetMotData.iLoopCount, c_rkSetMotData.fSpeedRatio);
|
||||
}
|
||||
|
||||
__HideWeaponTrace();
|
||||
|
||||
if (__BindMotionData(dwMotKey))
|
||||
{
|
||||
int iLoopCount = __GetLoopCount();
|
||||
SetMotionLoopCount(iLoopCount);
|
||||
|
||||
if (__CanAttack())
|
||||
{
|
||||
// 여기서 공격 모션일 경우의 처리를 합니다 - [levites]
|
||||
__ShowWeaponTrace();
|
||||
|
||||
m_HitDataMap.clear();
|
||||
//PreAttack();
|
||||
}
|
||||
|
||||
if (__IsComboAttacking())
|
||||
{
|
||||
if (!__CanNextComboAttack())
|
||||
{
|
||||
// 2004.11.19.myevan.동물 변신시 이부분에서 바로 리셋되어 다음동작 안나온다
|
||||
m_dwcurComboIndex = 0; // 콤보 리셋 - [levites]
|
||||
|
||||
// NOTE : ClearCombo() 를 수행해서는 안된다.
|
||||
// 콤보 다음에 스킬을 이어서 사용할 경우 m_pkCurRaceMotionData까지 초기화 되어 버린다.
|
||||
//Tracef("MotionData에 콤보 데이타가 들어 있지 않습니다.\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return dwMotKey;
|
||||
}
|
||||
|
||||
bool CActorInstance::__BindMotionData(DWORD dwMotionKey)
|
||||
{
|
||||
if (!m_pkCurRaceData->GetMotionDataPointer(dwMotionKey, &m_pkCurRaceMotionData))
|
||||
{
|
||||
Tracen("Failed to bind motion.");
|
||||
m_pkCurRaceMotionData=NULL;
|
||||
m_dwcurComboIndex=0;
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
int CActorInstance::__GetLoopCount()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
{
|
||||
TraceError("CActorInstance::__GetLoopCount() - m_pkCurRaceMotionData==NULL");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return m_pkCurRaceMotionData->GetLoopCount();
|
||||
}
|
||||
|
||||
bool CActorInstance::__CanAttack()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
{
|
||||
TraceError("CActorInstance::__CanAttack() - m_pkCurRaceMotionData==NULL");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!m_pkCurRaceMotionData->isAttackingMotion())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::__CanNextComboAttack()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
{
|
||||
TraceError("CActorInstance::__CanNextComboAttack() - m_pkCurRaceMotionData==NULL");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!m_pkCurRaceMotionData->IsComboInputTimeData())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsComboAttacking()
|
||||
{
|
||||
if (0 == m_dwcurComboIndex)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsNeedFlyTargetMotion()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return true;
|
||||
|
||||
for (DWORD i = 0; i < m_pkCurRaceMotionData->GetMotionEventDataCount(); ++i)
|
||||
{
|
||||
const CRaceMotionData::TMotionEventData * c_pData;
|
||||
if (!m_pkCurRaceMotionData->GetMotionEventDataPointer(i, &c_pData))
|
||||
continue;
|
||||
|
||||
if (c_pData->iType == CRaceMotionData::MOTION_EVENT_TYPE_WARP)
|
||||
return true;
|
||||
|
||||
if (c_pData->iType == CRaceMotionData::MOTION_EVENT_TYPE_FLY)
|
||||
return true;
|
||||
|
||||
if (c_pData->iType == CRaceMotionData::MOTION_EVENT_TYPE_EFFECT_TO_TARGET)
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CActorInstance::__HasMotionFlyEvent()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return true;
|
||||
|
||||
for (DWORD i = 0; i < m_pkCurRaceMotionData->GetMotionEventDataCount(); ++i)
|
||||
{
|
||||
const CRaceMotionData::TMotionEventData * c_pData;
|
||||
if (!m_pkCurRaceMotionData->GetMotionEventDataPointer(i, &c_pData))
|
||||
continue;
|
||||
|
||||
if (c_pData->iType == CRaceMotionData::MOTION_EVENT_TYPE_FLY)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsWaitMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_WAIT);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsMoveMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_MOVE);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsAttackMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_ATTACK);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsComboAttackMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_COMBO);
|
||||
}
|
||||
|
||||
|
||||
bool CActorInstance::__IsDamageMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_DAMAGE);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsKnockDownMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_KNOCKDOWN);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsDieMotion()
|
||||
{
|
||||
if (__IsKnockDownMotion())
|
||||
return true;
|
||||
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_DIE);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsStandUpMotion()
|
||||
{
|
||||
return (__GetMotionType()==CRaceMotionData::TYPE_STANDUP);
|
||||
}
|
||||
@@ -0,0 +1,331 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EffectLib/EffectManager.h"
|
||||
#include "../MilesLib/SoundManager.h"
|
||||
|
||||
#include "ActorInstance.h"
|
||||
#include "FlyingObjectManager.h"
|
||||
#include "FlyingInstance.h"
|
||||
#include "GameEventManager.h"
|
||||
|
||||
#include "FlyHandler.h"
|
||||
|
||||
void CActorInstance::MotionEventProcess()
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return;
|
||||
|
||||
for (DWORD i = 0; i < m_pkCurRaceMotionData->GetMotionEventDataCount(); ++i)
|
||||
{
|
||||
const CRaceMotionData::TMotionEventData * c_pData;
|
||||
if (!m_pkCurRaceMotionData->GetMotionEventDataPointer(i, &c_pData))
|
||||
continue;
|
||||
|
||||
MotionEventProcess(m_kCurMotNode.dwcurFrame, i, c_pData);
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::SoundEventProcess(BOOL bCheckFrequency)
|
||||
{
|
||||
if (!m_pkCurRaceMotionData)
|
||||
return;
|
||||
|
||||
CSoundManager& rkSndMgr=CSoundManager::Instance();
|
||||
const NSound::TSoundInstanceVector* c_pkVct_kSndInst=m_pkCurRaceMotionData->GetSoundInstanceVectorPointer();
|
||||
rkSndMgr.UpdateSoundInstance(m_x, m_y, m_z, m_kCurMotNode.dwcurFrame, c_pkVct_kSndInst, bCheckFrequency);
|
||||
}
|
||||
|
||||
void CActorInstance::MotionEventProcess(DWORD dwcurFrame, int iIndex, const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (c_pData->dwFrame != dwcurFrame)
|
||||
return;
|
||||
|
||||
switch (c_pData->iType)
|
||||
{
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_EFFECT:
|
||||
ProcessMotionEventEffectEvent(c_pData);
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_EFFECT_TO_TARGET:
|
||||
ProcessMotionEventEffectToTargetEvent(c_pData);
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_SCREEN_WAVING:
|
||||
CGameEventManager::Instance().ProcessEventScreenWaving(this, (const CRaceMotionData::TScreenWavingEventData *)c_pData);
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_SPECIAL_ATTACKING:
|
||||
ProcessMotionEventSpecialAttacking(iIndex, c_pData);
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_SOUND:
|
||||
ProcessMotionEventSound(c_pData);
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_FLY:
|
||||
ProcessMotionEventFly(c_pData);
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_CHARACTER_SHOW:
|
||||
__ShowEvent();
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_CHARACTER_HIDE:
|
||||
__HideEvent();
|
||||
break;
|
||||
|
||||
case CRaceMotionData::MOTION_EVENT_TYPE_WARP:
|
||||
#ifndef WORLD_EDITOR
|
||||
ProcessMotionEventWarp(c_pData);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::__ShowEvent()
|
||||
{
|
||||
m_isHiding = FALSE;
|
||||
RestoreRenderMode();
|
||||
SetAlphaValue(1.0f);
|
||||
}
|
||||
|
||||
void CActorInstance::__HideEvent()
|
||||
{
|
||||
m_isHiding = TRUE;
|
||||
SetBlendRenderMode();
|
||||
SetAlphaValue(0.0f);
|
||||
}
|
||||
|
||||
BOOL CActorInstance::__IsHiding()
|
||||
{
|
||||
return m_isHiding;
|
||||
}
|
||||
|
||||
void CActorInstance::ProcessMotionEventEffectEvent(const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (CRaceMotionData::MOTION_EVENT_TYPE_EFFECT != c_pData->iType)
|
||||
return;
|
||||
|
||||
const CRaceMotionData::TMotionEffectEventData * c_pEffectData = (const CRaceMotionData::TMotionEffectEventData *)c_pData;
|
||||
|
||||
if (c_pEffectData->isIndependent)
|
||||
{
|
||||
int iIndex = CEffectManager::Instance().CreateEffect(c_pEffectData->dwEffectIndex, D3DXVECTOR3(0.0f, 0.0f, 0.0f), D3DXVECTOR3(0.0f, 0.0f, 0.0f));
|
||||
|
||||
D3DXMATRIX matLocalPosition;
|
||||
D3DXMatrixTranslation(&matLocalPosition, c_pEffectData->v3EffectPosition.x, c_pEffectData->v3EffectPosition.y, c_pEffectData->v3EffectPosition.z);
|
||||
|
||||
D3DXMATRIX matWorld;
|
||||
matWorld = matLocalPosition;
|
||||
matWorld *= m_worldMatrix;
|
||||
|
||||
CEffectManager::Instance().SelectEffectInstance(iIndex);
|
||||
CEffectManager::Instance().SetEffectInstanceGlobalMatrix(matWorld);
|
||||
return;
|
||||
}
|
||||
|
||||
if (c_pEffectData->isAttaching)
|
||||
{
|
||||
if (c_pEffectData->isFollowing)
|
||||
{
|
||||
AttachEffectByID(0,
|
||||
c_pEffectData->strAttachingBoneName.c_str(),
|
||||
c_pEffectData->dwEffectIndex,
|
||||
&c_pEffectData->v3EffectPosition);
|
||||
}
|
||||
else
|
||||
{
|
||||
int iBoneIndex;
|
||||
DWORD dwPartIndex = 0;
|
||||
if (FindBoneIndex(dwPartIndex, c_pEffectData->strAttachingBoneName.c_str(), &iBoneIndex))
|
||||
{
|
||||
D3DXMATRIX * pBoneMat;
|
||||
GetBoneMatrix(dwPartIndex, iBoneIndex, &pBoneMat);
|
||||
|
||||
D3DXMATRIX matLocalPosition;
|
||||
D3DXMatrixTranslation(&matLocalPosition, c_pEffectData->v3EffectPosition.x, c_pEffectData->v3EffectPosition.y, c_pEffectData->v3EffectPosition.z);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
D3DXMATRIX matWorld;
|
||||
matWorld = *pBoneMat;
|
||||
matWorld *= matLocalPosition;
|
||||
matWorld *= m_worldMatrix;
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
|
||||
int iIndex = CEffectManager::Instance().CreateEffect(c_pEffectData->dwEffectIndex,
|
||||
c_pEffectData->v3EffectPosition,
|
||||
D3DXVECTOR3(0.0f, 0.0f, 0.0f));
|
||||
CEffectManager::Instance().SelectEffectInstance(iIndex);
|
||||
CEffectManager::Instance().SetEffectInstanceGlobalMatrix(matWorld);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
AttachEffectByID(0, NULL, c_pEffectData->dwEffectIndex, &c_pEffectData->v3EffectPosition);
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::ProcessMotionEventEffectToTargetEvent(const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (CRaceMotionData::MOTION_EVENT_TYPE_EFFECT_TO_TARGET != c_pData->iType)
|
||||
return;
|
||||
|
||||
const CRaceMotionData::TMotionEffectToTargetEventData * c_pEffectToTargetData = (const CRaceMotionData::TMotionEffectToTargetEventData *)c_pData;
|
||||
|
||||
if (c_pEffectToTargetData->isFishingEffect)
|
||||
{
|
||||
CEffectManager& rkEftMgr=CEffectManager::Instance();
|
||||
|
||||
if (-1 != m_iFishingEffectID)
|
||||
{
|
||||
rkEftMgr.DeactiveEffectInstance(m_iFishingEffectID);
|
||||
}
|
||||
|
||||
m_iFishingEffectID = rkEftMgr.CreateEffect(c_pEffectToTargetData->dwEffectIndex, m_v3FishingPosition, D3DXVECTOR3(0.0f, 0.0f, 0.0f));
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!m_kFlyTarget.IsValidTarget())
|
||||
return;
|
||||
|
||||
if (c_pEffectToTargetData->isFollowing && IsFlyTargetObject())
|
||||
{
|
||||
CActorInstance * pTargetInstance = (CActorInstance *)m_kFlyTarget.GetFlyTarget();
|
||||
D3DXVECTOR3 v3Position( c_pEffectToTargetData->v3EffectPosition.x,
|
||||
c_pEffectToTargetData->v3EffectPosition.y,
|
||||
c_pEffectToTargetData->v3EffectPosition.z);
|
||||
pTargetInstance->AttachEffectByID(0, NULL, c_pEffectToTargetData->dwEffectIndex, &v3Position);
|
||||
}
|
||||
else
|
||||
{
|
||||
const D3DXVECTOR3 & c_rv3FlyTarget = m_kFlyTarget.GetFlyTargetPosition();
|
||||
D3DXVECTOR3 v3Position( c_rv3FlyTarget.x + c_pEffectToTargetData->v3EffectPosition.x,
|
||||
c_rv3FlyTarget.y + c_pEffectToTargetData->v3EffectPosition.y,
|
||||
c_rv3FlyTarget.z + c_pEffectToTargetData->v3EffectPosition.z);
|
||||
CEffectManager::Instance().CreateEffect(c_pEffectToTargetData->dwEffectIndex, v3Position, D3DXVECTOR3(0.0f, 0.0f, 0.0f));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::ProcessMotionEventSpecialAttacking(int iMotionEventIndex, const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (CRaceMotionData::MOTION_EVENT_TYPE_SPECIAL_ATTACKING != c_pData->iType)
|
||||
return;
|
||||
|
||||
const CRaceMotionData::TMotionAttackingEventData * c_pAttackingData = (const CRaceMotionData::TMotionAttackingEventData *)c_pData;
|
||||
|
||||
float fRadian = D3DXToRadian(270.0f + 360.0f - GetRotation());
|
||||
m_kSplashArea.isEnableHitProcess=c_pAttackingData->isEnableHitProcess;
|
||||
m_kSplashArea.uSkill=m_kCurMotNode.uSkill;
|
||||
m_kSplashArea.MotionKey = m_kCurMotNode.dwMotionKey;
|
||||
m_kSplashArea.fDisappearingTime = GetLocalTime() + c_pAttackingData->fDurationTime;
|
||||
m_kSplashArea.c_pAttackingEvent = c_pAttackingData;
|
||||
m_kSplashArea.HittedInstanceMap.clear();
|
||||
|
||||
m_kSplashArea.SphereInstanceVector.clear();
|
||||
m_kSplashArea.SphereInstanceVector.resize(c_pAttackingData->CollisionData.SphereDataVector.size());
|
||||
for (DWORD i = 0; i < c_pAttackingData->CollisionData.SphereDataVector.size(); ++i)
|
||||
{
|
||||
const TSphereData & c_rSphereData = c_pAttackingData->CollisionData.SphereDataVector[i].GetAttribute();
|
||||
CDynamicSphereInstance & rSphereInstance = m_kSplashArea.SphereInstanceVector[i];
|
||||
|
||||
rSphereInstance.fRadius = c_rSphereData.fRadius;
|
||||
//rSphereInstance.v3Advance = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
|
||||
rSphereInstance.v3Position.x = m_x + c_rSphereData.v3Position.x*sinf(fRadian) + c_rSphereData.v3Position.y*cosf(fRadian);
|
||||
rSphereInstance.v3Position.y = m_y + c_rSphereData.v3Position.x*cosf(fRadian) - c_rSphereData.v3Position.y*sinf(fRadian);
|
||||
rSphereInstance.v3Position.z = m_z + c_rSphereData.v3Position.z;
|
||||
rSphereInstance.v3LastPosition = rSphereInstance.v3Position;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::ProcessMotionEventSound(const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (CRaceMotionData::MOTION_EVENT_TYPE_SOUND != c_pData->iType)
|
||||
return;
|
||||
|
||||
const CRaceMotionData::TMotionSoundEventData * c_pSoundData = (const CRaceMotionData::TMotionSoundEventData *)c_pData;
|
||||
|
||||
Tracenf("PLAY SOUND: %s", c_pSoundData->strSoundFileName.c_str());
|
||||
CSoundManager::Instance().PlaySound3D(m_x, m_y, m_z, c_pSoundData->strSoundFileName.c_str());
|
||||
}
|
||||
|
||||
void CActorInstance::ProcessMotionEventFly(const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (CRaceMotionData::MOTION_EVENT_TYPE_FLY != c_pData->iType)
|
||||
return;
|
||||
|
||||
const CRaceMotionData::TMotionFlyEventData * c_pFlyData = (const CRaceMotionData::TMotionFlyEventData *)c_pData;
|
||||
|
||||
if (m_kFlyTarget.IsValidTarget())
|
||||
{
|
||||
CFlyingManager & rfm = CFlyingManager::Instance();
|
||||
|
||||
D3DXVECTOR3 v3Start(c_pFlyData->v3FlyPosition);
|
||||
v3Start += m_v3Position;
|
||||
|
||||
if (c_pFlyData->isAttaching)
|
||||
{
|
||||
D3DXMATRIX * pBoneMat;
|
||||
int iBoneIndex;
|
||||
DWORD dwPartIndex = 0;
|
||||
|
||||
if (FindBoneIndex(dwPartIndex, c_pFlyData->strAttachingBoneName.c_str(), &iBoneIndex))
|
||||
if (GetBoneMatrix(dwPartIndex,iBoneIndex,&pBoneMat))
|
||||
{
|
||||
v3Start.x += pBoneMat->_41;
|
||||
v3Start.y += pBoneMat->_42;
|
||||
v3Start.z += pBoneMat->_43;
|
||||
}
|
||||
}
|
||||
|
||||
CFlyingInstance * pInstance = rfm.CreateFlyingInstanceFlyTarget(c_pFlyData->dwFlyIndex,v3Start,m_kFlyTarget,true);
|
||||
if (pInstance)
|
||||
{
|
||||
pInstance->SetEventHandler(m_pFlyEventHandler);
|
||||
pInstance->SetOwner(this);
|
||||
pInstance->SetSkillIndex(m_kCurMotNode.uSkill);
|
||||
}
|
||||
|
||||
if (m_pFlyEventHandler)
|
||||
{
|
||||
m_pFlyEventHandler->OnShoot(m_kCurMotNode.uSkill);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//TraceError("ActorInstance::ProcessMotionEventFly No Target");
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::ProcessMotionEventWarp(const CRaceMotionData::TMotionEventData * c_pData)
|
||||
{
|
||||
if (CRaceMotionData::MOTION_EVENT_TYPE_WARP != c_pData->iType)
|
||||
return;
|
||||
|
||||
// FIXME : TMotionWarpEventData로 뺄 변수 - [levites]
|
||||
static const float sc_fDistanceFromTarget = 270.0f;
|
||||
|
||||
if (m_kFlyTarget.IsValidTarget())
|
||||
{
|
||||
D3DXVECTOR3 v3MainPosition(m_x, m_y, m_z);
|
||||
const D3DXVECTOR3 & c_rv3TargetPosition = __GetFlyTargetPosition();
|
||||
|
||||
D3DXVECTOR3 v3Distance = c_rv3TargetPosition - v3MainPosition;
|
||||
D3DXVec3Normalize(&v3Distance, &v3Distance);
|
||||
TPixelPosition DestPixelPosition = c_rv3TargetPosition - (v3Distance * sc_fDistanceFromTarget);
|
||||
|
||||
// 2004.07.05.myevan.궁신탄영 맵에 끼이는 문제해결. 목표위치가 이동 못하는 곳일 경우 이동하지 않는다
|
||||
IBackground& rkBG=GetBackground();
|
||||
if (!rkBG.IsBlock(DestPixelPosition.x, -DestPixelPosition.y))
|
||||
SetPixelPosition(DestPixelPosition);
|
||||
|
||||
LookAt(c_rv3TargetPosition.x, c_rv3TargetPosition.y);
|
||||
|
||||
__OnWarp();
|
||||
}
|
||||
else
|
||||
{
|
||||
//TraceError("ActorInstance::ProcessMotionEventFly No Target");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,119 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
|
||||
const TPixelPosition& CActorInstance::NEW_GetLastPixelPositionRef()
|
||||
{
|
||||
GetBlendingPosition(&m_kPPosLast);
|
||||
m_kPPosLast.y=-m_kPPosLast.y;
|
||||
|
||||
return m_kPPosLast;
|
||||
}
|
||||
|
||||
const D3DXVECTOR3& CActorInstance::GetPositionVectorRef()
|
||||
{
|
||||
m_v3Pos.x=m_x;
|
||||
m_v3Pos.y=m_y;
|
||||
m_v3Pos.z=m_z;
|
||||
return m_v3Pos;
|
||||
}
|
||||
|
||||
const D3DXVECTOR3& CActorInstance::GetMovementVectorRef()
|
||||
{
|
||||
if (m_pkHorse)
|
||||
return m_pkHorse->GetMovementVectorRef();
|
||||
|
||||
return m_v3Movement;
|
||||
}
|
||||
|
||||
void CActorInstance::NEW_SetAtkPixelPosition(const TPixelPosition& c_rkPPosAtk)
|
||||
{
|
||||
m_kPPosAtk=c_rkPPosAtk;
|
||||
}
|
||||
|
||||
void CActorInstance::SetCurPixelPosition(const TPixelPosition& c_rkPPosCur)
|
||||
{
|
||||
D3DXVECTOR3 v3PosCur;
|
||||
v3PosCur.x=+c_rkPPosCur.x;
|
||||
v3PosCur.y=-c_rkPPosCur.y;
|
||||
v3PosCur.z=+c_rkPPosCur.z;
|
||||
|
||||
SetPixelPosition(v3PosCur);
|
||||
}
|
||||
|
||||
void CActorInstance::NEW_SetSrcPixelPosition(const TPixelPosition& c_rkPPosSrc)
|
||||
{
|
||||
m_kPPosSrc=c_rkPPosSrc;
|
||||
}
|
||||
|
||||
void CActorInstance::NEW_SetDstPixelPositionZ(float z)
|
||||
{
|
||||
m_kPPosDst.z=z;
|
||||
}
|
||||
|
||||
void CActorInstance::NEW_SetDstPixelPosition(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
m_kPPosDst=c_rkPPosDst;
|
||||
}
|
||||
|
||||
const TPixelPosition& CActorInstance::NEW_GetAtkPixelPositionRef()
|
||||
{
|
||||
return m_kPPosAtk;
|
||||
}
|
||||
|
||||
const TPixelPosition& CActorInstance::NEW_GetSrcPixelPositionRef()
|
||||
{
|
||||
return m_kPPosSrc;
|
||||
}
|
||||
|
||||
|
||||
const TPixelPosition& CActorInstance::NEW_GetDstPixelPositionRef()
|
||||
{
|
||||
return m_kPPosDst;
|
||||
}
|
||||
|
||||
const TPixelPosition& CActorInstance::NEW_GetCurPixelPositionRef()
|
||||
{
|
||||
m_kPPosCur.x=+m_x;
|
||||
m_kPPosCur.y=-m_y;
|
||||
m_kPPosCur.z=+m_z;
|
||||
|
||||
return m_kPPosCur;
|
||||
}
|
||||
|
||||
void CActorInstance::GetPixelPosition(TPixelPosition * pPixelPosition)
|
||||
{
|
||||
pPixelPosition->x = m_x;
|
||||
pPixelPosition->y = m_y;
|
||||
pPixelPosition->z = m_z;
|
||||
}
|
||||
|
||||
void CActorInstance::SetPixelPosition(const TPixelPosition& c_rPixelPos)
|
||||
{
|
||||
if (m_pkTree)
|
||||
{
|
||||
__SetTreePosition(c_rPixelPos.x, c_rPixelPos.y, c_rPixelPos.z);
|
||||
}
|
||||
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->SetPixelPosition(c_rPixelPos);
|
||||
|
||||
m_x = c_rPixelPos.x;
|
||||
m_y = c_rPixelPos.y;
|
||||
m_z = c_rPixelPos.z;
|
||||
m_bNeedUpdateCollision = TRUE;
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::__InitializePositionData()
|
||||
{
|
||||
m_dwShakeTime = 0;
|
||||
|
||||
m_x = 0.0f;
|
||||
m_y = 0.0f;
|
||||
m_z = 0.0f;
|
||||
m_bNeedUpdateCollision = FALSE;
|
||||
|
||||
m_kPPosAtk=m_kPPosLast=m_kPPosDst=m_kPPosCur=m_kPPosSrc=TPixelPosition(0.0f, 0.0f, 0.0f);
|
||||
|
||||
__InitializeMovement();
|
||||
}
|
||||
@@ -0,0 +1,385 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EterLib/StateManager.h"
|
||||
|
||||
#include "ActorInstance.h"
|
||||
|
||||
bool CActorInstance::ms_isDirLine=false;
|
||||
|
||||
bool CActorInstance::IsDirLine()
|
||||
{
|
||||
return ms_isDirLine;
|
||||
}
|
||||
|
||||
void CActorInstance::ShowDirectionLine(bool isVisible)
|
||||
{
|
||||
ms_isDirLine=isVisible;
|
||||
}
|
||||
|
||||
void CActorInstance::SetMaterialColor(DWORD dwColor)
|
||||
{
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->SetMaterialColor(dwColor);
|
||||
|
||||
m_dwMtrlColor&=0xff000000;
|
||||
m_dwMtrlColor|=(dwColor&0x00ffffff);
|
||||
}
|
||||
|
||||
void CActorInstance::SetMaterialAlpha(DWORD dwAlpha)
|
||||
{
|
||||
m_dwMtrlAlpha=dwAlpha;
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::OnRender()
|
||||
{
|
||||
D3DMATERIAL8 kMtrl;
|
||||
STATEMANAGER.GetMaterial(&kMtrl);
|
||||
|
||||
kMtrl.Diffuse=D3DXCOLOR(m_dwMtrlColor);
|
||||
STATEMANAGER.SetMaterial(&kMtrl);
|
||||
|
||||
// 현재는 이렇게.. 최종적인 형태는 Diffuse와 Blend의 분리로..
|
||||
// 아니면 이런 형태로 가되 Texture & State Sorting 지원으로.. - [levites]
|
||||
STATEMANAGER.SaveRenderState(D3DRS_CULLMODE, D3DCULL_NONE);
|
||||
|
||||
switch(m_iRenderMode)
|
||||
{
|
||||
case RENDER_MODE_NORMAL:
|
||||
BeginDiffuseRender();
|
||||
RenderWithOneTexture();
|
||||
EndDiffuseRender();
|
||||
BeginOpacityRender();
|
||||
BlendRenderWithOneTexture();
|
||||
EndOpacityRender();
|
||||
break;
|
||||
case RENDER_MODE_BLEND:
|
||||
if (m_fAlphaValue == 1.0f)
|
||||
{
|
||||
BeginDiffuseRender();
|
||||
RenderWithOneTexture();
|
||||
EndDiffuseRender();
|
||||
BeginOpacityRender();
|
||||
BlendRenderWithOneTexture();
|
||||
EndOpacityRender();
|
||||
}
|
||||
else if (m_fAlphaValue > 0.0f)
|
||||
{
|
||||
BeginBlendRender();
|
||||
RenderWithOneTexture();
|
||||
BlendRenderWithOneTexture();
|
||||
EndBlendRender();
|
||||
}
|
||||
break;
|
||||
case RENDER_MODE_ADD:
|
||||
BeginAddRender();
|
||||
RenderWithOneTexture();
|
||||
BlendRenderWithOneTexture();
|
||||
EndAddRender();
|
||||
break;
|
||||
case RENDER_MODE_MODULATE:
|
||||
BeginModulateRender();
|
||||
RenderWithOneTexture();
|
||||
BlendRenderWithOneTexture();
|
||||
EndModulateRender();
|
||||
break;
|
||||
}
|
||||
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_CULLMODE);
|
||||
|
||||
kMtrl.Diffuse=D3DXCOLOR(0xffffffff);
|
||||
STATEMANAGER.SetMaterial(&kMtrl);
|
||||
|
||||
if (ms_isDirLine)
|
||||
{
|
||||
D3DXVECTOR3 kD3DVt3Cur(m_x, m_y, m_z);
|
||||
|
||||
D3DXVECTOR3 kD3DVt3LookDir(0.0f, -1.0f, 0.0f);
|
||||
D3DXMATRIX kD3DMatLook;
|
||||
D3DXMatrixRotationZ(&kD3DMatLook, D3DXToRadian(GetRotation()));
|
||||
D3DXVec3TransformCoord(&kD3DVt3LookDir, &kD3DVt3LookDir, &kD3DMatLook);
|
||||
D3DXVec3Scale(&kD3DVt3LookDir, &kD3DVt3LookDir, 200.0f);
|
||||
D3DXVec3Add(&kD3DVt3LookDir, &kD3DVt3LookDir, &kD3DVt3Cur);
|
||||
|
||||
D3DXVECTOR3 kD3DVt3AdvDir(0.0f, -1.0f, 0.0f);
|
||||
D3DXMATRIX kD3DMatAdv;
|
||||
D3DXMatrixRotationZ(&kD3DMatAdv, D3DXToRadian(GetAdvancingRotation()));
|
||||
D3DXVec3TransformCoord(&kD3DVt3AdvDir, &kD3DVt3AdvDir, &kD3DMatAdv);
|
||||
D3DXVec3Scale(&kD3DVt3AdvDir, &kD3DVt3AdvDir, 200.0f);
|
||||
D3DXVec3Add(&kD3DVt3AdvDir, &kD3DVt3AdvDir, &kD3DVt3Cur);
|
||||
|
||||
static CScreen s_kScreen;
|
||||
|
||||
STATEMANAGER.SaveTextureStageState(0, D3DTSS_COLORARG1, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SaveTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
|
||||
STATEMANAGER.SaveTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ZENABLE, FALSE);
|
||||
STATEMANAGER.SetRenderState(D3DRS_LIGHTING, FALSE);
|
||||
|
||||
s_kScreen.SetDiffuseColor(1.0f, 1.0f, 0.0f);
|
||||
s_kScreen.RenderLine3d(kD3DVt3Cur.x, kD3DVt3Cur.y, kD3DVt3Cur.z, kD3DVt3AdvDir.x, kD3DVt3AdvDir.y, kD3DVt3AdvDir.z);
|
||||
|
||||
s_kScreen.SetDiffuseColor(0.0f, 1.0f, 1.0f);
|
||||
s_kScreen.RenderLine3d(kD3DVt3Cur.x, kD3DVt3Cur.y, kD3DVt3Cur.z, kD3DVt3LookDir.x, kD3DVt3LookDir.y, kD3DVt3LookDir.z);
|
||||
|
||||
STATEMANAGER.SetRenderState(D3DRS_LIGHTING, TRUE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ZENABLE);
|
||||
|
||||
STATEMANAGER.RestoreTextureStageState(0, D3DTSS_COLORARG1);
|
||||
STATEMANAGER.RestoreTextureStageState(0, D3DTSS_COLOROP);
|
||||
STATEMANAGER.RestoreTextureStageState(0, D3DTSS_ALPHAOP);
|
||||
STATEMANAGER.RestoreVertexShader();
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::BeginDiffuseRender()
|
||||
{
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
|
||||
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHABLENDENABLE, FALSE);
|
||||
}
|
||||
|
||||
void CActorInstance::EndDiffuseRender()
|
||||
{
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHABLENDENABLE);
|
||||
}
|
||||
|
||||
void CActorInstance::BeginOpacityRender()
|
||||
{
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHATESTENABLE, TRUE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHAREF, 0);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHAFUNC, D3DCMP_GREATER);
|
||||
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
|
||||
}
|
||||
|
||||
void CActorInstance::EndOpacityRender()
|
||||
{
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHATESTENABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHAREF);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHAFUNC);
|
||||
}
|
||||
|
||||
void CActorInstance::BeginBlendRender()
|
||||
{
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
|
||||
STATEMANAGER.SetRenderState(D3DRS_TEXTUREFACTOR, D3DXCOLOR(1.0f, 1.0f, 1.0f, m_fAlphaValue));
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_TFACTOR);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG2);
|
||||
}
|
||||
|
||||
void CActorInstance::EndBlendRender()
|
||||
{
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHABLENDENABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_SRCBLEND);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_DESTBLEND);
|
||||
}
|
||||
|
||||
void CActorInstance::BeginAddRender()
|
||||
{
|
||||
STATEMANAGER.SetRenderState(D3DRS_TEXTUREFACTOR, m_AddColor);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
|
||||
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLORARG1, D3DTA_CURRENT);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLORARG2, D3DTA_TFACTOR);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_ADD);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHABLENDENABLE, FALSE);
|
||||
}
|
||||
|
||||
void CActorInstance::EndAddRender()
|
||||
{
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHABLENDENABLE);
|
||||
}
|
||||
|
||||
void CActorInstance::RestoreRenderMode()
|
||||
{
|
||||
// NOTE : This is temporary code. I wanna convert this code to that restore the mode to
|
||||
// model's default setting which had has as like specular or normal. - [levites]
|
||||
m_iRenderMode = RENDER_MODE_NORMAL;
|
||||
if (m_kBlendAlpha.m_isBlending)
|
||||
{
|
||||
m_kBlendAlpha.m_iOldRenderMode = m_iRenderMode;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::SetAddRenderMode()
|
||||
{
|
||||
m_iRenderMode = RENDER_MODE_ADD;
|
||||
if (m_kBlendAlpha.m_isBlending)
|
||||
{
|
||||
m_kBlendAlpha.m_iOldRenderMode = m_iRenderMode;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::SetRenderMode(int iRenderMode)
|
||||
{
|
||||
m_iRenderMode = iRenderMode;
|
||||
if (m_kBlendAlpha.m_isBlending)
|
||||
{
|
||||
m_kBlendAlpha.m_iOldRenderMode = iRenderMode;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::SetAddColor(const D3DXCOLOR & c_rColor)
|
||||
{
|
||||
m_AddColor = c_rColor;
|
||||
m_AddColor.a = 1.0f;
|
||||
}
|
||||
|
||||
void CActorInstance::BeginModulateRender()
|
||||
{
|
||||
STATEMANAGER.SetRenderState(D3DRS_TEXTUREFACTOR, m_AddColor);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
|
||||
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLORARG1, D3DTA_CURRENT);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLORARG2, D3DTA_TFACTOR);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHABLENDENABLE, FALSE);
|
||||
}
|
||||
|
||||
void CActorInstance::EndModulateRender()
|
||||
{
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHABLENDENABLE);
|
||||
}
|
||||
|
||||
void CActorInstance::SetModulateRenderMode()
|
||||
{
|
||||
m_iRenderMode = RENDER_MODE_MODULATE;
|
||||
if (m_kBlendAlpha.m_isBlending)
|
||||
{
|
||||
m_kBlendAlpha.m_iOldRenderMode = m_iRenderMode;
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::RenderCollisionData()
|
||||
{
|
||||
static CScreen s_Screen;
|
||||
|
||||
STATEMANAGER.SetRenderState(D3DRS_LIGHTING, FALSE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_CULLMODE, D3DCULL_NONE);
|
||||
if (m_pAttributeInstance)
|
||||
{
|
||||
for (DWORD col=0; col < GetCollisionInstanceCount(); ++col)
|
||||
{
|
||||
CBaseCollisionInstance * pInstance = GetCollisionInstanceData(col);
|
||||
pInstance->Render();
|
||||
}
|
||||
}
|
||||
|
||||
STATEMANAGER.SetRenderState(D3DRS_ZENABLE, FALSE);
|
||||
s_Screen.SetColorOperation();
|
||||
s_Screen.SetDiffuseColor(1.0f, 0.0f, 0.0f);
|
||||
TCollisionPointInstanceList::iterator itor;
|
||||
/*itor = m_AttackingPointInstanceList.begin();
|
||||
for (; itor != m_AttackingPointInstanceList.end(); ++itor)
|
||||
{
|
||||
const TCollisionPointInstance & c_rInstance = *itor;
|
||||
for (DWORD i = 0; i < c_rInstance.SphereInstanceVector.size(); ++i)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rSphereInstance = c_rInstance.SphereInstanceVector[i];
|
||||
s_Screen.RenderCircle3d(c_rSphereInstance.v3Position.x,
|
||||
c_rSphereInstance.v3Position.y,
|
||||
c_rSphereInstance.v3Position.z,
|
||||
c_rSphereInstance.fRadius);
|
||||
}
|
||||
}*/
|
||||
s_Screen.SetDiffuseColor(1.0f, (isShow())?1.0f:0.0f, 0.0f);
|
||||
D3DXVECTOR3 center;
|
||||
float r;
|
||||
GetBoundingSphere(center,r);
|
||||
s_Screen.RenderCircle3d(center.x,center.y,center.z,r);
|
||||
|
||||
s_Screen.SetDiffuseColor(0.0f, 0.0f, 1.0f);
|
||||
itor = m_DefendingPointInstanceList.begin();
|
||||
for (; itor != m_DefendingPointInstanceList.end(); ++itor)
|
||||
{
|
||||
const TCollisionPointInstance & c_rInstance = *itor;
|
||||
for (DWORD i = 0; i < c_rInstance.SphereInstanceVector.size(); ++i)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rSphereInstance = c_rInstance.SphereInstanceVector[i];
|
||||
s_Screen.RenderCircle3d(c_rSphereInstance.v3Position.x,
|
||||
c_rSphereInstance.v3Position.y,
|
||||
c_rSphereInstance.v3Position.z,
|
||||
c_rSphereInstance.fRadius);
|
||||
}
|
||||
}
|
||||
|
||||
s_Screen.SetDiffuseColor(0.0f, 1.0f, 0.0f);
|
||||
itor = m_BodyPointInstanceList.begin();
|
||||
for (; itor != m_BodyPointInstanceList.end(); ++itor)
|
||||
{
|
||||
const TCollisionPointInstance & c_rInstance = *itor;
|
||||
for (DWORD i = 0; i < c_rInstance.SphereInstanceVector.size(); ++i)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rSphereInstance = c_rInstance.SphereInstanceVector[i];
|
||||
s_Screen.RenderCircle3d(c_rSphereInstance.v3Position.x,
|
||||
c_rSphereInstance.v3Position.y,
|
||||
c_rSphereInstance.v3Position.z,
|
||||
c_rSphereInstance.fRadius);
|
||||
}
|
||||
}
|
||||
|
||||
s_Screen.SetDiffuseColor(1.0f, 0.0f, 0.0f);
|
||||
// if (m_SplashArea.fDisappearingTime > GetLocalTime())
|
||||
{
|
||||
CDynamicSphereInstanceVector::iterator itor = m_kSplashArea.SphereInstanceVector.begin();
|
||||
for (; itor != m_kSplashArea.SphereInstanceVector.end(); ++itor)
|
||||
{
|
||||
const CDynamicSphereInstance & c_rInstance = *itor;
|
||||
s_Screen.RenderCircle3d(c_rInstance.v3Position.x,
|
||||
c_rInstance.v3Position.y,
|
||||
c_rInstance.v3Position.z,
|
||||
c_rInstance.fRadius);
|
||||
}
|
||||
}
|
||||
|
||||
STATEMANAGER.SetRenderState(D3DRS_ZENABLE, TRUE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_CULLMODE);
|
||||
STATEMANAGER.SetRenderState(D3DRS_LIGHTING, TRUE);
|
||||
}
|
||||
|
||||
|
||||
void CActorInstance::RenderToShadowMap()
|
||||
{
|
||||
if (RENDER_MODE_BLEND == m_iRenderMode)
|
||||
if (GetAlphaValue() < 0.5f)
|
||||
return;
|
||||
|
||||
CGraphicThingInstance::RenderToShadowMap();
|
||||
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->RenderToShadowMap();
|
||||
}
|
||||
@@ -0,0 +1,128 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
|
||||
void CActorInstance::SetXYRotation(float fRotX, float fRotY)
|
||||
{
|
||||
m_rotX = fRotX;
|
||||
m_rotY = fRotY;
|
||||
}
|
||||
|
||||
void CActorInstance::SetRotation(float fRot)
|
||||
{
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->SetRotation(fRot);
|
||||
|
||||
m_fcurRotation = fRot;
|
||||
m_rotBegin = m_fcurRotation;
|
||||
m_rotEnd = m_fcurRotation;
|
||||
|
||||
m_rotBlendTime = 0.0f;
|
||||
m_rotBeginTime = 0.0f;
|
||||
m_rotEndTime = 0.0f;
|
||||
|
||||
m_bNeedUpdateCollision = TRUE;
|
||||
}
|
||||
|
||||
void CActorInstance::BlendRotation(float fRot, float fBlendTime)
|
||||
{
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->BlendRotation(fRot, fBlendTime);
|
||||
|
||||
if (m_fcurRotation == fRot)
|
||||
return;
|
||||
|
||||
m_rotBegin = fmod(m_fcurRotation, 360.0f);
|
||||
m_rotEnd = fRot;
|
||||
|
||||
m_rotBlendTime = fBlendTime;
|
||||
m_rotBeginTime = GetLocalTime();
|
||||
m_rotEndTime = m_rotBeginTime + m_rotBlendTime;
|
||||
}
|
||||
|
||||
void CActorInstance::SetAdvancingRotation(float fRot)
|
||||
{
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->SetAdvancingRotation(fRot);
|
||||
|
||||
m_fAdvancingRotation = fRot;
|
||||
}
|
||||
|
||||
void CActorInstance::RotationProcess()
|
||||
{
|
||||
if (m_pkHorse)
|
||||
m_pkHorse->RotationProcess();
|
||||
|
||||
if (GetLocalTime() < m_rotEndTime)
|
||||
{
|
||||
m_fcurRotation = GetInterpolatedRotation(m_rotBegin, m_rotEnd, (GetLocalTime() - m_rotBeginTime) / m_rotBlendTime);
|
||||
SetAdvancingRotation(m_fcurRotation);
|
||||
}
|
||||
else
|
||||
{
|
||||
m_fcurRotation = m_rotEnd;
|
||||
}
|
||||
|
||||
// FIXME : "건물일때만 체크"로 바꾼다. - [levites]
|
||||
if (0.0f != m_rotX || 0.0f != m_rotY)
|
||||
{
|
||||
CGraphicObjectInstance::SetRotation(m_rotX, m_rotY, m_fcurRotation);
|
||||
}
|
||||
else
|
||||
{
|
||||
CGraphicObjectInstance::SetRotation(m_fcurRotation);
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::LookAtFromXY(float x, float y, CActorInstance * pDestInstance)
|
||||
{
|
||||
float rot = GetDegreeFromPosition2(pDestInstance->m_x,
|
||||
pDestInstance->m_y,
|
||||
x,
|
||||
y);
|
||||
|
||||
LookAt(rot);
|
||||
}
|
||||
|
||||
void CActorInstance::LookAt(float fDirRot)
|
||||
{
|
||||
BlendRotation(fDirRot, 0.3f);
|
||||
}
|
||||
|
||||
void CActorInstance::LookAt(float fx, float fy)
|
||||
{
|
||||
float rot = GetDegreeFromPosition2(m_x, m_y, fx, fy);
|
||||
|
||||
LookAt(rot);
|
||||
}
|
||||
|
||||
void CActorInstance::LookAt(CActorInstance * pInstance)
|
||||
{
|
||||
TPixelPosition PixelPosition;
|
||||
pInstance->GetPixelPosition(&PixelPosition);
|
||||
LookAt(PixelPosition.x, PixelPosition.y);
|
||||
}
|
||||
|
||||
void CActorInstance::LookWith(CActorInstance * pInstance)
|
||||
{
|
||||
BlendRotation(pInstance->m_rotEnd, 0.3f);
|
||||
}
|
||||
|
||||
float CActorInstance::GetRotation()
|
||||
{
|
||||
return m_fcurRotation;
|
||||
}
|
||||
|
||||
float CActorInstance::GetTargetRotation()
|
||||
{
|
||||
return m_rotEnd;
|
||||
}
|
||||
|
||||
float CActorInstance::GetRotatingTime()
|
||||
{
|
||||
return m_rotEndTime;
|
||||
}
|
||||
|
||||
float CActorInstance::GetAdvancingRotation()
|
||||
{
|
||||
return m_fAdvancingRotation;
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
#include "RaceData.h"
|
||||
|
||||
|
||||
|
||||
void CActorInstance::__Push(int x, int y)
|
||||
{
|
||||
if (IsResistFallen())
|
||||
return;
|
||||
|
||||
//DWORD dwVID=GetVirtualID();
|
||||
//Tracenf("VID %d SyncPixelPosition %d %d", dwVID, x, y);
|
||||
|
||||
const D3DXVECTOR3& c_rv3Src=GetPosition();
|
||||
const D3DXVECTOR3 c_v3Dst=D3DXVECTOR3(x, -y, c_rv3Src.z);
|
||||
const D3DXVECTOR3 c_v3Delta=c_v3Dst-c_rv3Src;
|
||||
|
||||
const int LoopValue = 100;
|
||||
const D3DXVECTOR3 inc=c_v3Delta / LoopValue;
|
||||
|
||||
D3DXVECTOR3 v3Movement(0.0f, 0.0f, 0.0f);
|
||||
|
||||
IPhysicsWorld* pWorld = IPhysicsWorld::GetPhysicsWorld();
|
||||
|
||||
if (!pWorld)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
for(int i = 0; i < LoopValue; ++i)
|
||||
{
|
||||
if (pWorld->isPhysicalCollision(c_rv3Src + v3Movement))
|
||||
{
|
||||
ResetBlendingPosition();
|
||||
return;
|
||||
}
|
||||
v3Movement += inc;
|
||||
}
|
||||
|
||||
SetBlendingPosition(c_v3Dst);
|
||||
|
||||
if (!IsUsingSkill())
|
||||
{
|
||||
int len=sqrt(c_v3Delta.x*c_v3Delta.x+c_v3Delta.y*c_v3Delta.y);
|
||||
if (len>150.0f)
|
||||
{
|
||||
InterceptOnceMotion(CRaceMotionData::NAME_DAMAGE_FLYING);
|
||||
PushOnceMotion(CRaceMotionData::NAME_STAND_UP);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::TEMP_Push(int x, int y)
|
||||
{
|
||||
__Push(x, y);
|
||||
}
|
||||
|
||||
bool CActorInstance::__IsSyncing()
|
||||
{
|
||||
if (IsDead())
|
||||
return TRUE;
|
||||
|
||||
if (IsStun())
|
||||
return TRUE;
|
||||
|
||||
if (IsPushing())
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
bool CActorInstance::IsPushing()
|
||||
{
|
||||
return m_PhysicsObject.isBlending();
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
#include "StdAfx.h"
|
||||
#include "ActorInstance.h"
|
||||
#include "WeaponTrace.h"
|
||||
|
||||
void CActorInstance::TraceProcess()
|
||||
{
|
||||
if (!m_WeaponTraceVector.empty())
|
||||
{
|
||||
std::vector<CWeaponTrace*>::iterator it;
|
||||
for(it = m_WeaponTraceVector.begin(); it != m_WeaponTraceVector.end(); ++it)
|
||||
{
|
||||
CWeaponTrace * pWeaponTrace = (*it);
|
||||
pWeaponTrace->SetPosition(m_x, m_y, m_z);
|
||||
pWeaponTrace->SetRotation(m_fcurRotation);
|
||||
pWeaponTrace->Update(__GetReachScale());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CActorInstance::RenderTrace()
|
||||
{
|
||||
for_each(m_WeaponTraceVector.begin(), m_WeaponTraceVector.end(), std::mem_fn(&CWeaponTrace::Render));
|
||||
}
|
||||
|
||||
void CActorInstance::__DestroyWeaponTrace()
|
||||
{
|
||||
std::for_each(m_WeaponTraceVector.begin(), m_WeaponTraceVector.end(), CWeaponTrace::Delete);
|
||||
m_WeaponTraceVector.clear();
|
||||
}
|
||||
|
||||
void CActorInstance::__ShowWeaponTrace()
|
||||
{
|
||||
for_each(m_WeaponTraceVector.begin(), m_WeaponTraceVector.end(), std::mem_fn(&CWeaponTrace::TurnOn));
|
||||
}
|
||||
|
||||
void CActorInstance::__HideWeaponTrace()
|
||||
{
|
||||
for_each(m_WeaponTraceVector.begin(), m_WeaponTraceVector.end(), std::mem_fn(&CWeaponTrace::TurnOff));
|
||||
}
|
||||
|
||||
@@ -0,0 +1,114 @@
|
||||
#include "StdAfx.h"
|
||||
#include "FlyTarget.h"
|
||||
|
||||
CFlyTarget::CFlyTarget()
|
||||
{
|
||||
__Initialize();
|
||||
}
|
||||
|
||||
CFlyTarget::CFlyTarget(IFlyTargetableObject * pFlyTarget)
|
||||
{
|
||||
__Initialize();
|
||||
|
||||
m_eType=TYPE_OBJECT;
|
||||
m_pFlyTarget=pFlyTarget;
|
||||
m_pFlyTarget->AddFlyTargeter(this);
|
||||
}
|
||||
CFlyTarget::CFlyTarget(const D3DXVECTOR3& v3FlyTargetPosition)
|
||||
{
|
||||
__Initialize();
|
||||
|
||||
m_eType=TYPE_POSITION;
|
||||
m_v3FlyTargetPosition=v3FlyTargetPosition;
|
||||
}
|
||||
|
||||
CFlyTarget::CFlyTarget(const CFlyTarget& rhs)
|
||||
{
|
||||
__Initialize();
|
||||
|
||||
*this = rhs;
|
||||
}
|
||||
|
||||
CFlyTarget::~CFlyTarget()
|
||||
{
|
||||
if (m_pFlyTarget)
|
||||
m_pFlyTarget->RemoveFlyTargeter(this);
|
||||
}
|
||||
|
||||
void CFlyTarget::__Initialize()
|
||||
{
|
||||
m_v3FlyTargetPosition=D3DXVECTOR3(0.0f,0.0f,0.0f);
|
||||
m_pFlyTarget=NULL;
|
||||
m_eType=TYPE_NONE;
|
||||
}
|
||||
|
||||
void CFlyTarget::Clear()
|
||||
{
|
||||
m_eType = TYPE_NONE;
|
||||
m_pFlyTarget = 0;
|
||||
}
|
||||
|
||||
bool CFlyTarget::IsObject()
|
||||
{
|
||||
return (TYPE_OBJECT==GetType());
|
||||
}
|
||||
|
||||
bool CFlyTarget::IsPosition()
|
||||
{
|
||||
return (TYPE_POSITION==GetType());
|
||||
}
|
||||
|
||||
bool CFlyTarget::IsValidTarget()
|
||||
{
|
||||
return (TYPE_NONE!=GetType());
|
||||
}
|
||||
|
||||
void CFlyTarget::NotifyTargetClear()
|
||||
{
|
||||
//if (m_eType == FLY_TARGET_TYPE_OBJECT)
|
||||
m_eType = TYPE_POSITION;
|
||||
m_pFlyTarget = 0;
|
||||
}
|
||||
|
||||
CFlyTarget::EType CFlyTarget::GetType()
|
||||
{
|
||||
return m_eType;
|
||||
}
|
||||
|
||||
IFlyTargetableObject* CFlyTarget::GetFlyTarget()
|
||||
{
|
||||
assert(TYPE_OBJECT==GetType() && "CFly::GetFlyTarget");
|
||||
return m_pFlyTarget;
|
||||
}
|
||||
|
||||
const D3DXVECTOR3 & CFlyTarget::GetFlyTargetPosition() const
|
||||
{
|
||||
if (m_eType == TYPE_OBJECT)
|
||||
{
|
||||
m_v3FlyTargetPosition = m_pFlyTarget->OnGetFlyTargetPosition();
|
||||
}
|
||||
return m_v3FlyTargetPosition;
|
||||
}
|
||||
|
||||
CFlyTarget & CFlyTarget::operator = (const CFlyTarget & rhs)
|
||||
{
|
||||
if (m_pFlyTarget)
|
||||
{
|
||||
m_pFlyTarget->RemoveFlyTargeter(this);
|
||||
}
|
||||
m_eType = rhs.m_eType;
|
||||
m_v3FlyTargetPosition = rhs.m_v3FlyTargetPosition;
|
||||
m_pFlyTarget = rhs.m_pFlyTarget;
|
||||
if (m_pFlyTarget)
|
||||
{
|
||||
m_pFlyTarget->AddFlyTargeter(this);
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
void CFlyTarget::GetFlyTargetData(CFlyTarget * pFlyTarget)
|
||||
{
|
||||
pFlyTarget->m_eType = m_eType;
|
||||
pFlyTarget->m_v3FlyTargetPosition = m_v3FlyTargetPosition;
|
||||
pFlyTarget->m_pFlyTarget = m_pFlyTarget;
|
||||
}
|
||||
@@ -0,0 +1,111 @@
|
||||
#pragma once
|
||||
|
||||
#include "FlyTarget.h"
|
||||
#include "ActorInstanceInterface.h"
|
||||
|
||||
class CFlyingData;
|
||||
class CFlyTrace;
|
||||
class IFlyEventHandler;
|
||||
class CActorInstance;
|
||||
|
||||
class CFlyingInstance
|
||||
{
|
||||
public:
|
||||
// 2004. 3. 26. myevan. 적절한 네이밍이 필요. 게임에서 사용하지 않는다면 툴에서 툴 전용으로 상속받아 만들도록 하자
|
||||
void Clear(); // Destroy와 같다
|
||||
void SetDataPointer(CFlyingData * pData, const D3DXVECTOR3 & v3StartPosition);
|
||||
void SetFlyTarget(const CFlyTarget & cr_Target); // Shot at Target
|
||||
|
||||
public:
|
||||
friend class CSceneFly;
|
||||
|
||||
struct TAttachEffectInstance
|
||||
{
|
||||
int iAttachIndex;
|
||||
DWORD dwEffectInstanceIndex;
|
||||
|
||||
CFlyTrace * pFlyTrace;
|
||||
};
|
||||
|
||||
CFlyingInstance();
|
||||
virtual ~CFlyingInstance();
|
||||
|
||||
void Destroy();
|
||||
void Create(CFlyingData* pData, const D3DXVECTOR3& c_rv3StartPos, const CFlyTarget & c_rkTarget, bool canAttack);
|
||||
|
||||
bool Update();
|
||||
void Render();
|
||||
|
||||
bool IsAlive() { return m_bAlive; }
|
||||
|
||||
const D3DXVECTOR3 & GetPosition() { return m_v3Position; }
|
||||
|
||||
void AdjustDirectionForHoming(const D3DXVECTOR3 & v3TargetPosition);
|
||||
|
||||
typedef std::vector<TAttachEffectInstance> TAttachEffectInstanceVector;
|
||||
|
||||
void BuildAttachInstance();
|
||||
void UpdateAttachInstance();
|
||||
void RenderAttachInstance();
|
||||
void ClearAttachInstance();
|
||||
|
||||
void SetEventHandler(IFlyEventHandler * pHandler) { m_pHandler = pHandler; }
|
||||
void ClearEventHandler() { m_pHandler = 0; }
|
||||
|
||||
void SetPierceCount(int iCount) { m_iPierceCount = iCount; }
|
||||
void SetOwner(IActorInstance * pOwner) { m_pOwner = pOwner; }
|
||||
void SetSkillIndex(DWORD dwIndex) { m_dwSkillIndex = dwIndex; }
|
||||
|
||||
// FIXME : 툴에서 사용하고 있습니다. 임시로 위로.. - [levites]
|
||||
void __Explode(bool bBomb=true);
|
||||
void __Bomb();
|
||||
|
||||
DWORD ID;
|
||||
|
||||
protected:
|
||||
void __Initialize();
|
||||
|
||||
void __SetDataPointer(CFlyingData * pData, const D3DXVECTOR3 & v3StartPosition);
|
||||
void __SetTargetDirection(const CFlyTarget& c_rkTarget);
|
||||
void __SetTargetNormalizedDirection(const D3DXVECTOR3 & v3NormalizedDirection ); // 시작 타겟 방향 설정
|
||||
|
||||
protected:
|
||||
|
||||
CFlyingData * m_pData;
|
||||
D3DXQUATERNION m_qRot;
|
||||
|
||||
float m_fStartTime;
|
||||
|
||||
bool m_bAlive;
|
||||
bool m_canAttack;
|
||||
|
||||
int m_iPierceCount;
|
||||
DWORD m_dwSkillIndex;
|
||||
|
||||
D3DXVECTOR3 m_v3Position;
|
||||
D3DXVECTOR3 m_v3Velocity;
|
||||
D3DXVECTOR3 m_v3LocalVelocity;
|
||||
D3DXVECTOR3 m_v3Accel;
|
||||
|
||||
float m_fRemainRange;
|
||||
|
||||
CFlyTarget m_FlyTarget;
|
||||
|
||||
D3DXQUATERNION m_qAttachRotation;
|
||||
TAttachEffectInstanceVector m_vecAttachEffectInstance;
|
||||
|
||||
IFlyEventHandler * m_pHandler;
|
||||
|
||||
IActorInstance * m_pOwner;
|
||||
|
||||
BOOL m_bTargetHitted;
|
||||
std::set<IActorInstance *> m_HittedObjectSet;
|
||||
|
||||
public:
|
||||
static CFlyingInstance * New() { return ms_kPool.Alloc(); }
|
||||
static void Delete(CFlyingInstance * pInstance) { pInstance->Destroy(); ms_kPool.Free(pInstance); }
|
||||
|
||||
static void DestroySystem() { ms_kPool.Destroy(); }
|
||||
|
||||
static CDynamicPool<CFlyingInstance> ms_kPool;
|
||||
};
|
||||
@@ -0,0 +1,36 @@
|
||||
#include "StdAfx.h"
|
||||
#include "GameEventManager.h"
|
||||
|
||||
void CGameEventManager::SetCenterPosition(float fx, float fy, float fz)
|
||||
{
|
||||
m_CenterPosition.x = +fx;
|
||||
m_CenterPosition.y = -fy;
|
||||
m_CenterPosition.z = +fz;
|
||||
}
|
||||
|
||||
void CGameEventManager::Update()
|
||||
{
|
||||
}
|
||||
|
||||
void CGameEventManager::ProcessEventScreenWaving(CActorInstance * pActorInstance, const CRaceMotionData::TScreenWavingEventData * c_pData)
|
||||
{
|
||||
TPixelPosition PixelPosition;
|
||||
pActorInstance->GetPixelPosition(&PixelPosition);
|
||||
|
||||
float fdx = PixelPosition.x - m_CenterPosition.x;
|
||||
float fdy = PixelPosition.y - m_CenterPosition.y;
|
||||
float fdz = PixelPosition.z - m_CenterPosition.z;
|
||||
|
||||
if (fdx * fdx + fdy * fdy + fdz * fdz > c_pData->iAffectingRange * c_pData->iAffectingRange)
|
||||
return;
|
||||
|
||||
SetScreenEffectWaving(c_pData->fDurationTime, c_pData->iPower);
|
||||
}
|
||||
|
||||
CGameEventManager::CGameEventManager() : m_CenterPosition(0.0f, 0.0f, 0.0f)
|
||||
{
|
||||
}
|
||||
|
||||
CGameEventManager::~CGameEventManager()
|
||||
{
|
||||
}
|
||||
@@ -0,0 +1,434 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EterLib/lineintersect_utils.h"
|
||||
|
||||
#include "GameUtil.h"
|
||||
|
||||
bool DetectCollisionDynamicZCylinderVSDynamicZCylinder(const CDynamicSphereInstance & c_rSphere1, const CDynamicSphereInstance & c_rSphere2)
|
||||
{
|
||||
CDynamicSphereInstance c_rCylinder1=c_rSphere1;
|
||||
CDynamicSphereInstance c_rCylinder2=c_rSphere2;
|
||||
|
||||
c_rCylinder1.v3Position.z=0;
|
||||
c_rCylinder1.v3LastPosition.z=0;
|
||||
|
||||
c_rCylinder2.v3Position.z=0;
|
||||
c_rCylinder2.v3LastPosition.z=0;
|
||||
|
||||
float r = c_rCylinder1.fRadius+c_rCylinder2.fRadius;
|
||||
float rsq = r*r;
|
||||
|
||||
// AABB check
|
||||
D3DXVECTOR3 mi1=c_rCylinder1.v3LastPosition, mi2 = c_rCylinder1.v3Position;
|
||||
D3DXVECTOR3 mi3=c_rCylinder2.v3LastPosition, mi4 = c_rCylinder2.v3Position;
|
||||
if (mi1.x>mi2.x) std::swap(mi1.x,mi2.x);
|
||||
if (mi1.y>mi2.y) std::swap(mi1.y,mi2.y);
|
||||
if (mi1.z>mi2.z) std::swap(mi1.z,mi2.z);
|
||||
if (mi3.x>mi4.x) std::swap(mi3.x,mi4.x);
|
||||
if (mi3.y>mi4.y) std::swap(mi3.y,mi4.y);
|
||||
if (mi3.z>mi4.z) std::swap(mi3.z,mi4.z);
|
||||
mi1.x -= c_rCylinder1.fRadius; mi1.y -= c_rCylinder1.fRadius; mi1.z -= c_rCylinder1.fRadius;
|
||||
mi2.x += c_rCylinder1.fRadius; mi2.y += c_rCylinder1.fRadius; mi2.z += c_rCylinder1.fRadius;
|
||||
mi3.x -= c_rCylinder2.fRadius; mi3.y -= c_rCylinder2.fRadius; mi3.z -= c_rCylinder2.fRadius;
|
||||
mi4.x += c_rCylinder2.fRadius; mi4.y += c_rCylinder2.fRadius; mi4.z += c_rCylinder2.fRadius;
|
||||
if (mi4.x<mi1.x || mi2.x<mi3.x) return false;
|
||||
if (mi4.y<mi1.y || mi2.y<mi3.y) return false;
|
||||
if (mi4.z<mi1.z || mi2.z<mi3.z) return false;
|
||||
|
||||
D3DXVECTOR3 vA, vB;
|
||||
IntersectLineSegments(c_rCylinder1.v3LastPosition, c_rCylinder1.v3Position,
|
||||
c_rCylinder2.v3LastPosition, c_rCylinder2.v3Position,
|
||||
vA, vB);
|
||||
const auto vv = (vA - vB);
|
||||
return (D3DXVec3LengthSq(&vv)<=rsq);
|
||||
}
|
||||
|
||||
bool DetectCollisionDynamicSphereVSDynamicSphere(const CDynamicSphereInstance & c_rSphere1, const CDynamicSphereInstance & c_rSphere2)
|
||||
{
|
||||
float r = c_rSphere1.fRadius+c_rSphere2.fRadius;
|
||||
float rsq = r*r;
|
||||
|
||||
/*if (D3DXVec3LengthSq(&(c_rSphere1.v3Position -c_rSphere2.v3Position ))<=rsq) return true;
|
||||
if (D3DXVec3LengthSq(&(c_rSphere1.v3Position -c_rSphere2.v3LastPosition ))<=rsq) return true;
|
||||
if (D3DXVec3LengthSq(&(c_rSphere1.v3LastPosition -c_rSphere2.v3Position ))<=rsq) return true;
|
||||
if (D3DXVec3LengthSq(&(c_rSphere1.v3LastPosition -c_rSphere2.v3LastPosition ))<=rsq) return true;*/
|
||||
|
||||
/*
|
||||
if (square_distance_between_linesegment_and_point(
|
||||
c_rSphere1.v3Position,
|
||||
c_rSphere1.v3LastPosition,
|
||||
c_rSphere2.v3Position
|
||||
)<=rsq) return true;
|
||||
if (square_distance_between_linesegment_and_point(
|
||||
c_rSphere1.v3Position,
|
||||
c_rSphere1.v3LastPosition,
|
||||
c_rSphere2.v3LastPosition
|
||||
)<=rsq) return true;
|
||||
if (square_distance_between_linesegment_and_point(
|
||||
c_rSphere2.v3Position,
|
||||
c_rSphere2.v3LastPosition,
|
||||
c_rSphere1.v3Position
|
||||
)<=rsq) return true;
|
||||
if (square_distance_between_linesegment_and_point(
|
||||
c_rSphere2.v3Position,
|
||||
c_rSphere2.v3LastPosition,
|
||||
c_rSphere1.v3LastPosition
|
||||
)<=rsq) return true;
|
||||
|
||||
D3DXVECTOR3 da=c_rSphere1.v3Position-c_rSphere1.v3LastPosition;
|
||||
D3DXVECTOR3 db=c_rSphere2.v3Position-c_rSphere2.v3LastPosition;
|
||||
D3DXVECTOR3 n;
|
||||
float la = D3DXVec3Length(&da);
|
||||
float lb = D3DXVec3Length(&db);
|
||||
if (la==0||lb==0)
|
||||
{
|
||||
D3DXVECTOR3 vA, vB;
|
||||
IntersectLineSegments(
|
||||
c_rSphere1.v3LastPosition.x,c_rSphere1.v3LastPosition.y,c_rSphere1.v3LastPosition.z,
|
||||
c_rSphere1.v3Position.x, c_rSphere1.v3Position.y, c_rSphere1.v3Position.z,
|
||||
c_rSphere2.v3LastPosition.x,c_rSphere2.v3LastPosition.y,c_rSphere2.v3LastPosition.z,
|
||||
c_rSphere2.v3Position.x, c_rSphere2.v3Position.y, c_rSphere2.v3Position.z,
|
||||
false, 1.e-5f, vA.x, vA.y, vA.z, vB.x, vB.y, vB.z);
|
||||
return (D3DXVec3LengthSq(&(vA-vB))<=r*r);
|
||||
}
|
||||
D3DXVECTOR3 p=c_rSphere2.v3Position - c_rSphere1.v3LastPosition;
|
||||
D3DXVec3Cross(&n, &da, &db);
|
||||
float from_plane = D3DXVec3Dot(&n,&p)/la/lb;
|
||||
if (from_plane>r || from_plane<-r)
|
||||
return false;
|
||||
p-=(from_plane/la/lb)*n;
|
||||
float ta = D3DXVec3Dot(&p,&da)/la/la;
|
||||
float tb = D3DXVec3Dot(&p,&db)/lb/lb;
|
||||
|
||||
// FIXME 구 체크가 아니다
|
||||
|
||||
if (ta<0)
|
||||
return false;
|
||||
if (tb<0)
|
||||
return false;
|
||||
if (ta>1)
|
||||
return false;
|
||||
if (tb>1)
|
||||
return false;
|
||||
return true;
|
||||
|
||||
*/
|
||||
//*/
|
||||
// using gpg line-collision
|
||||
|
||||
// AABB check
|
||||
|
||||
D3DXVECTOR3 mi1=c_rSphere1.v3LastPosition, mi2 = c_rSphere1.v3Position;
|
||||
D3DXVECTOR3 mi3=c_rSphere2.v3LastPosition, mi4 = c_rSphere2.v3Position;
|
||||
if (mi1.x>mi2.x) std::swap(mi1.x,mi2.x);
|
||||
if (mi1.y>mi2.y) std::swap(mi1.y,mi2.y);
|
||||
if (mi1.z>mi2.z) std::swap(mi1.z,mi2.z);
|
||||
if (mi3.x>mi4.x) std::swap(mi3.x,mi4.x);
|
||||
if (mi3.y>mi4.y) std::swap(mi3.y,mi4.y);
|
||||
if (mi3.z>mi4.z) std::swap(mi3.z,mi4.z);
|
||||
mi1.x -= c_rSphere1.fRadius; mi1.y -= c_rSphere1.fRadius; mi1.z -= c_rSphere1.fRadius;
|
||||
mi2.x += c_rSphere1.fRadius; mi2.y += c_rSphere1.fRadius; mi2.z += c_rSphere1.fRadius;
|
||||
mi3.x -= c_rSphere2.fRadius; mi3.y -= c_rSphere2.fRadius; mi3.z -= c_rSphere2.fRadius;
|
||||
mi4.x += c_rSphere2.fRadius; mi4.y += c_rSphere2.fRadius; mi4.z += c_rSphere2.fRadius;
|
||||
if (mi4.x<mi1.x || mi2.x<mi3.x) return false;
|
||||
if (mi4.y<mi1.y || mi2.y<mi3.y) return false;
|
||||
if (mi4.z<mi1.z || mi2.z<mi3.z) return false;
|
||||
|
||||
D3DXVECTOR3 vA, vB;/*
|
||||
IntersectLineSegments(
|
||||
c_rSphere1.v3LastPosition.x,c_rSphere1.v3LastPosition.y,c_rSphere1.v3LastPosition.z,
|
||||
c_rSphere1.v3Position.x, c_rSphere1.v3Position.y, c_rSphere1.v3Position.z,
|
||||
c_rSphere2.v3LastPosition.x,c_rSphere2.v3LastPosition.y,c_rSphere2.v3LastPosition.z,
|
||||
c_rSphere2.v3Position.x, c_rSphere2.v3Position.y, c_rSphere2.v3Position.z,
|
||||
false, 1.e-1f, vA.x, vA.y, vA.z, vB.x, vB.y, vB.z);*/
|
||||
IntersectLineSegments(c_rSphere1.v3LastPosition, c_rSphere1.v3Position,
|
||||
c_rSphere2.v3LastPosition, c_rSphere2.v3Position,
|
||||
vA, vB);
|
||||
const auto vvv = (vA - vB);
|
||||
return (D3DXVec3LengthSq(&vvv)<=rsq);
|
||||
//*/
|
||||
|
||||
/*
|
||||
// NOTE : AABB 체크 할 것
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////
|
||||
D3DXVECTOR3 v3Distance = c_rSphere1.v3Position - c_rSphere2.v3Position;
|
||||
float fDistance = D3DXVec3Length(&v3Distance);
|
||||
float fRadiusSummary = c_rSphere1.fRadius + c_rSphere2.fRadius;
|
||||
|
||||
if (fDistance < fRadiusSummary)
|
||||
return true;
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////
|
||||
D3DXVECTOR3 v3LastDistance = c_rSphere1.v3LastPosition - c_rSphere2.v3LastPosition; // A
|
||||
D3DXVECTOR3 v3Advance = c_rSphere1.v3Advance - c_rSphere2.v3Advance; // B
|
||||
|
||||
float fdotAdvanceAdvance = D3DXVec3Dot(&v3Advance, &v3Advance);
|
||||
if (0.0f == fdotAdvanceAdvance)
|
||||
return false;
|
||||
|
||||
float fdotDistanceAdvance = D3DXVec3Dot(&v3LastDistance, &v3Advance);
|
||||
float fdotDistanceDistance = D3DXVec3Dot(&v3LastDistance, &v3LastDistance);
|
||||
float Value1 = fdotDistanceAdvance - fdotAdvanceAdvance * (fdotDistanceDistance - (fRadiusSummary * fRadiusSummary));
|
||||
if (Value1 < 0.0f)
|
||||
return false;
|
||||
|
||||
float Value2 = (-fdotDistanceAdvance - sqrtf(Value1)) / fdotAdvanceAdvance;
|
||||
if (Value2 < 0.0f)
|
||||
return false;
|
||||
if (Value2 >= 1.0f)
|
||||
return false;
|
||||
|
||||
return true;*/
|
||||
}
|
||||
|
||||
/*
|
||||
// Dynamic VS Static
|
||||
bool DetectCollisionDynamicSphereVSStaticPlane(const CDynamicSphereInstance & c_rSphere, const TPlaneData & c_rPlane)
|
||||
{
|
||||
D3DXVECTOR3 v3SpherePosition = c_rSphere.v3Position - c_rPlane.v3Position;
|
||||
D3DXVECTOR3 v3SphereLastPosition = c_rSphere.v3LastPosition - c_rPlane.v3Position;
|
||||
|
||||
float fPosition1 = D3DXVec3Dot(&c_rPlane.v3Normal, &v3SpherePosition);
|
||||
float fPosition2 = D3DXVec3Dot(&c_rPlane.v3Normal, &v3SphereLastPosition);
|
||||
|
||||
if (fPosition1 >0.0f && fPosition2 < 0.0f || fPosition1 <0.0f && fPosition2 >0.0f || (fPosition1) <= c_rSphere.fRadius && fPosition1 >= -c_rSphere.fRadius)
|
||||
{
|
||||
D3DXVECTOR3 v3QuadPosition1 = c_rSphere.v3Position - c_rPlane.v3QuadPosition[0];
|
||||
D3DXVECTOR3 v3QuadPosition2 = c_rSphere.v3Position - c_rPlane.v3QuadPosition[3];
|
||||
if (D3DXVec3Dot(&v3QuadPosition1, &c_rPlane.v3InsideVector[0]) < c_rSphere.fRadius)
|
||||
if (D3DXVec3Dot(&v3QuadPosition1, &c_rPlane.v3InsideVector[1]) < c_rSphere.fRadius)
|
||||
if (D3DXVec3Dot(&v3QuadPosition2, &c_rPlane.v3InsideVector[2]) < c_rSphere.fRadius)
|
||||
if (D3DXVec3Dot(&v3QuadPosition2, &c_rPlane.v3InsideVector[3]) < c_rSphere.fRadius)
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DetectCollisionDynamicSphereVSStaticSphere(const CDynamicSphereInstance & c_rSphere, const TSphereData & c_rSphereData)
|
||||
{
|
||||
D3DXVECTOR3 v3Distance = c_rSphere.v3Position - c_rSphereData.v3Position;
|
||||
float fDistanceSq = D3DXVec3LengthSq(&v3Distance);
|
||||
float fRadiusSummary = c_rSphere.fRadius + c_rSphereData.fRadius;
|
||||
if (fDistanceSq < fRadiusSummary*fRadiusSummary)
|
||||
return true;
|
||||
|
||||
//D3DXVECTOR3 v3LastDistance = c_rSphere.v3LastPosition - c_rSphereData.v3Position;
|
||||
//if (D3DXVec3Dot(&v3LastDistance, &v3Distance) < 0.0f)
|
||||
// return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DetectCollisionDynamicSphereVSStaticCylinder(const CDynamicSphereInstance & c_rSphere, const TCylinderData & c_rCylinderData)
|
||||
{
|
||||
if (c_rSphere.v3Position.z + c_rSphere.fRadius < c_rCylinderData.v3Position.z)
|
||||
return false;
|
||||
|
||||
if (c_rSphere.v3Position.z - c_rSphere.fRadius > c_rCylinderData.v3Position.z + c_rCylinderData.fHeight)
|
||||
return false;
|
||||
|
||||
D3DXVECTOR3 v3curDistance = c_rSphere.v3Position - c_rCylinderData.v3Position;
|
||||
float fDistance = D3DXVec3Length(&v3curDistance);
|
||||
|
||||
if (fDistance <= c_rSphere.fRadius + c_rCylinderData.fRadius)
|
||||
return true;
|
||||
|
||||
//D3DXVECTOR3 v3lastDistance = c_rSphere.v3LastPosition - c_rCylinderData.v3Position;
|
||||
|
||||
//if (D3DXVec3Dot(&v3curDistance, &v3lastDistance) < 0.0f)
|
||||
// return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
*/
|
||||
/*
|
||||
bool DetectCollisionDynamicSphereVSStaticBox(const TSphereInstance & c_rSphere, const TBoxData & c_rBoxData)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
*/
|
||||
// Static VS Static
|
||||
/*
|
||||
bool DetectCollisionStaticSphereVSStaticSphere(const TSphereData & c_rSphere1, const TSphereData & c_rSphere2)
|
||||
{
|
||||
D3DXVECTOR3 v3Distance = c_rSphere1.v3Position - c_rSphere2.v3Position;
|
||||
float fDistance = D3DXVec3Length(&v3Distance);
|
||||
|
||||
if (fDistance < c_rSphere1.fRadius + c_rSphere2.fRadius)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DetectCollisionStaticSphereVSStaticCylinder(const TSphereData & c_rSphere, const TCylinderData & c_rCylinder)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
*/
|
||||
/*bool DetectCollisionStaticSphereVSStaticBox(const TSphereData & c_rSphere, const TBoxData & c_rBox)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
*/
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
bool IsCWAcuteAngle(float begin, float end)
|
||||
{
|
||||
// 360 - src + dest // 시계 반대 방향
|
||||
// src - dest // 시계 방향
|
||||
return ((360.0f - begin + end) > (begin - end));
|
||||
}
|
||||
|
||||
bool IsCCWAcuteAngle(float begin, float end)
|
||||
{
|
||||
// abs(360 - dest + src) // 시계 방향
|
||||
// dest - src // 시계 반대 방향
|
||||
int fValue = abs((int) (360.0f - end + begin));
|
||||
return fValue >= (end - begin) ? true : false;
|
||||
}
|
||||
|
||||
bool IsCWRotation(float begin, float end)
|
||||
{
|
||||
return !IsCCWRotation(begin, end);
|
||||
}
|
||||
|
||||
bool IsCCWRotation(float begin, float end)
|
||||
{
|
||||
// 180
|
||||
// 270 90
|
||||
// 0
|
||||
//
|
||||
// 시계 반대
|
||||
return (begin - end < 0);
|
||||
}
|
||||
|
||||
float GetInterpolatedRotation(float begin, float end, float curRate)
|
||||
{
|
||||
if (IsCCWRotation(begin, end))
|
||||
{
|
||||
if (IsCCWAcuteAngle(begin, end))
|
||||
return GetLinearInterpolation(begin, end, curRate);
|
||||
|
||||
return (360.0f + GetLinearInterpolation(begin, end - 360.0f, curRate));
|
||||
}
|
||||
|
||||
if (IsCWAcuteAngle(begin, end))
|
||||
return GetLinearInterpolation(begin, end, curRate);
|
||||
|
||||
return GetLinearInterpolation(begin, end + 360.0f, curRate);
|
||||
}
|
||||
|
||||
float GetDegreeFromPosition(float x, float y)
|
||||
{
|
||||
D3DXVECTOR3 vtDir(floor(x), floor(y), 0.0f);
|
||||
D3DXVec3Normalize(&vtDir, &vtDir);
|
||||
|
||||
D3DXVECTOR3 vtStan(0, -1, 0);
|
||||
float ret = D3DXToDegree(acosf(D3DXVec3Dot(&vtDir, &vtStan)));
|
||||
|
||||
if (vtDir.x < 0.0f)
|
||||
ret = 360.0f - ret;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
float GetDegreeFromPosition2(float sx, float sy, float ex, float ey)
|
||||
{
|
||||
return GetDegreeFromPosition(ex - sx, ey - sy);
|
||||
}
|
||||
|
||||
float GetDegreeDifference(float fSource, float fTarget)
|
||||
{
|
||||
if (fSource < 180.0f)
|
||||
{
|
||||
if (fTarget < fSource)
|
||||
return fSource - fTarget;
|
||||
|
||||
else if(fTarget - fSource > 180.0f)
|
||||
return (360.0f - (fTarget - fSource));
|
||||
|
||||
return fTarget - fSource;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (fTarget > fSource)
|
||||
return fTarget - fSource;
|
||||
|
||||
else if (fSource - fTarget > 180.0f)
|
||||
{
|
||||
return (360.0f - (fSource - fTarget));
|
||||
}
|
||||
|
||||
return fSource - fTarget;
|
||||
}
|
||||
}
|
||||
int GetRotatingDirection(float fSource, float fTarget)
|
||||
{
|
||||
if (fSource < 180.0f)
|
||||
{
|
||||
if (fTarget < fSource)
|
||||
return DEGREE_DIRECTION_RIGHT;
|
||||
|
||||
else if((360.0f - fTarget) + fSource < 180.0f)
|
||||
return DEGREE_DIRECTION_RIGHT;
|
||||
|
||||
return DEGREE_DIRECTION_LEFT;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (fTarget > fSource)
|
||||
{
|
||||
return DEGREE_DIRECTION_LEFT;
|
||||
}
|
||||
else if ((360.0f - fSource) + fTarget < 180.0f)
|
||||
{
|
||||
return DEGREE_DIRECTION_LEFT;
|
||||
}
|
||||
|
||||
return DEGREE_DIRECTION_RIGHT;
|
||||
}
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
float CameraRotationToCharacterRotation(float fCameraRotation)
|
||||
{
|
||||
return fmod((540.0f - fCameraRotation), 360.0f);
|
||||
}
|
||||
|
||||
float CharacterRotationToCameraRotation(float fCharacterRotation)
|
||||
{
|
||||
return fmod((540.0f - fCharacterRotation), 360.0f);
|
||||
}
|
||||
|
||||
/*
|
||||
bool DetectCollisionDynamicSphereVSStaticPlane(const TSphereInstance & c_rSphere, const TPlaneData & c_rPlane)
|
||||
{
|
||||
D3DXVECTOR3 v3SpherePosition = c_rSphere.v3Position - c_rPlane.v3Position;
|
||||
D3DXVECTOR3 v3SphereLastPosition = c_rSphere.v3LastPosition - c_rPlane.v3Position;
|
||||
|
||||
float fPosition1 = D3DXVec3Dot(&c_rPlane.v3Normal, &v3SpherePosition);
|
||||
float fPosition2 = D3DXVec3Dot(&c_rPlane.v3Normal, &v3SphereLastPosition);
|
||||
|
||||
if (fPosition1 * fPosition2 < 0.0f || fabs(fPosition1) <= c_rSphere.fRadius)
|
||||
{
|
||||
float fT = -fPosition1 / D3DXVec3Dot(&c_rPlane.v3Normal, &c_rSphere.v3Advance);
|
||||
D3DXVECTOR3 v3CollisionPosition = c_rSphere.v3LastPosition + c_rSphere.v3Advance * fT;
|
||||
D3DXVECTOR3 v3QuadPosition1 = v3CollisionPosition - c_rPlane.v3BeginPosition;
|
||||
D3DXVECTOR3 v3QuadPosition2 = v3CollisionPosition - c_rPlane.v3EndPosition;
|
||||
D3DXVec3Normalize(&v3QuadPosition1, &v3QuadPosition1);
|
||||
D3DXVec3Normalize(&v3QuadPosition2, &v3QuadPosition2);
|
||||
|
||||
if (D3DXVec3Dot(&v3QuadPosition1, &c_rPlane.v3InsideVector[0]) < 0.0f)
|
||||
if (D3DXVec3Dot(&v3QuadPosition1, &c_rPlane.v3InsideVector[1]) < 0.0f)
|
||||
if (D3DXVec3Dot(&v3QuadPosition2, &c_rPlane.v3InsideVector[2]) < 0.0f)
|
||||
if (D3DXVec3Dot(&v3QuadPosition2, &c_rPlane.v3InsideVector[3]) < 0.0f)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
*/
|
||||
@@ -0,0 +1,307 @@
|
||||
#include "StdAfx.h"
|
||||
#include "MapUtil.h"
|
||||
#include <float.h> // PORT: FLT_EPSILON below; MSVC's <windows.h> pulled it in transitively
|
||||
|
||||
void Environment_Init(SEnvironmentData& envData)
|
||||
{
|
||||
for (int i = 0; i < ENV_DIRLIGHT_NUM; ++i)
|
||||
{
|
||||
envData.bDirLightsEnable[i] = false;
|
||||
envData.DirLights[i].Type = D3DLIGHT_DIRECTIONAL;
|
||||
envData.DirLights[i].Direction = D3DXVECTOR3(0.5f, 0.5f, -0.5f);
|
||||
envData.DirLights[i].Position = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
envData.DirLights[i].Specular = D3DXCOLOR(1.0f, 1.0f, 1.0f, 1.0f);
|
||||
envData.DirLights[i].Diffuse = D3DXCOLOR(1.0f, 1.0f, 1.0f, 1.0f);
|
||||
envData.DirLights[i].Ambient = D3DXCOLOR(0.5f, 0.5f, 0.5f, 1.0f);
|
||||
envData.DirLights[i].Range = 0.0f; // Used by Point Light & Spot Light
|
||||
envData.DirLights[i].Falloff = 1.0f; // Used by Spot Light
|
||||
envData.DirLights[i].Theta = 0.0f; // Used by Spot Light
|
||||
envData.DirLights[i].Phi = 0.0f; // Used by Spot Light
|
||||
envData.DirLights[i].Attenuation0 = 0.0f;
|
||||
envData.DirLights[i].Attenuation1 = 1.0f;
|
||||
envData.DirLights[i].Attenuation2 = 0.0f;
|
||||
}
|
||||
|
||||
envData.Material.Diffuse = D3DXCOLOR(0.8f, 0.8f, 0.8f, 1.0f);
|
||||
envData.Material.Ambient = D3DXCOLOR(0.8f, 0.8f, 0.8f, 1.0f);
|
||||
envData.Material.Emissive = D3DXCOLOR(0.8f, 0.8f, 0.8f, 1.0f);
|
||||
envData.Material.Specular = D3DXCOLOR(0.0f, 0.0f, 0.0f, 1.0f);
|
||||
envData.Material.Power = 0.0f;
|
||||
|
||||
envData.bFogEnable = FALSE;
|
||||
envData.bDensityFog = FALSE;
|
||||
envData.m_fFogNearDistance = 25600.0f * 0.5f;
|
||||
envData.m_fFogFarDistance = 25600.0f * 0.7f;
|
||||
envData.FogColor = D3DXCOLOR(0.5f, 0.5f, 0.5f, 1.0f);
|
||||
|
||||
envData.bFilteringEnable = FALSE;
|
||||
envData.FilteringColor = D3DXCOLOR(0.3f, 0.1f, 0.1f, 0.0f);
|
||||
envData.byFilteringAlphaSrc = D3DBLEND_ONE;
|
||||
envData.byFilteringAlphaDest = D3DBLEND_ONE;
|
||||
|
||||
envData.fWindStrength = 0.2f;
|
||||
envData.fWindRandom = 0.0f;
|
||||
|
||||
envData.v3SkyBoxScale = D3DXVECTOR3(3500.0f, 3500.0f, 3500.0f);
|
||||
envData.bySkyBoxGradientLevelUpper = 0;
|
||||
envData.bySkyBoxGradientLevelLower = 0;
|
||||
envData.bSkyBoxTextureRenderMode = FALSE;
|
||||
|
||||
envData.v2CloudScale = D3DXVECTOR2(200000.0f, 200000.0f);
|
||||
envData.fCloudHeight = 30000.0f;
|
||||
envData.v2CloudTextureScale = D3DXVECTOR2(4.0f, 4.0f);
|
||||
envData.v2CloudSpeed = D3DXVECTOR2(0.001f, 0.001f);
|
||||
envData.strCloudTextureFileName = "";
|
||||
envData.CloudGradientColor.m_FirstColor = .0f;
|
||||
envData.CloudGradientColor.m_SecondColor = .0f;
|
||||
|
||||
envData.SkyBoxGradientColorVector.clear();
|
||||
|
||||
envData.bLensFlareEnable = FALSE;
|
||||
envData.LensFlareBrightnessColor = D3DXCOLOR(1.0f, 1.0f, 1.0f, 1.0f);
|
||||
envData.fLensFlareMaxBrightness = 1.0f;
|
||||
|
||||
envData.bMainFlareEnable = FALSE;
|
||||
envData.strMainFlareTextureFileName = "";
|
||||
envData.fMainFlareSize = 0.2f;
|
||||
|
||||
envData.bReserve = FALSE;
|
||||
}
|
||||
|
||||
bool Environment_Load(SEnvironmentData& envData, const char* envFileName)
|
||||
{
|
||||
CTextFileLoader textLoader;
|
||||
|
||||
if (!textLoader.Load(envFileName))
|
||||
return false;
|
||||
|
||||
textLoader.SetTop();
|
||||
|
||||
textLoader.GetTokenBoolean("reserved", &envData.bReserve);
|
||||
|
||||
if (textLoader.SetChildNode("directionallight"))
|
||||
{
|
||||
D3DVECTOR v3Dir;
|
||||
textLoader.GetTokenDirection("direction", &v3Dir);
|
||||
|
||||
if (textLoader.SetChildNode("background"))
|
||||
{
|
||||
envData.DirLights[ENV_DIRLIGHT_BACKGROUND].Direction = v3Dir;
|
||||
textLoader.GetTokenBoolean("enable", &envData.bDirLightsEnable[ENV_DIRLIGHT_BACKGROUND]);
|
||||
textLoader.GetTokenColor("diffuse", &envData.DirLights[ENV_DIRLIGHT_BACKGROUND].Diffuse);
|
||||
textLoader.GetTokenColor("ambient", &envData.DirLights[ENV_DIRLIGHT_BACKGROUND].Ambient);
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
if (textLoader.SetChildNode("character"))
|
||||
{
|
||||
envData.DirLights[ENV_DIRLIGHT_CHARACTER].Direction = v3Dir;
|
||||
textLoader.GetTokenBoolean("enable", &envData.bDirLightsEnable[ENV_DIRLIGHT_CHARACTER]);
|
||||
textLoader.GetTokenColor("diffuse", &envData.DirLights[ENV_DIRLIGHT_CHARACTER].Diffuse);
|
||||
textLoader.GetTokenColor("ambient", &envData.DirLights[ENV_DIRLIGHT_CHARACTER].Ambient);
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
if (textLoader.SetChildNode("material"))
|
||||
{
|
||||
textLoader.GetTokenColor("diffuse", &envData.Material.Diffuse);
|
||||
textLoader.GetTokenColor("ambient", &envData.Material.Ambient);
|
||||
textLoader.GetTokenColor("emissive", &envData.Material.Emissive);
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
if (textLoader.SetChildNode("fog"))
|
||||
{
|
||||
textLoader.GetTokenBoolean("enable", &envData.bFogEnable);
|
||||
textLoader.GetTokenBoolean("isdensity", &envData.bDensityFog);
|
||||
textLoader.GetTokenFloat("neardistance", &envData.m_fFogNearDistance);
|
||||
textLoader.GetTokenFloat("fardistance", &envData.m_fFogFarDistance);
|
||||
textLoader.GetTokenColor("color", &envData.FogColor);
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
if (textLoader.SetChildNode("filter"))
|
||||
{
|
||||
textLoader.GetTokenBoolean("enable", (BOOL *) &envData.bFilteringEnable);
|
||||
textLoader.GetTokenColor("color", &envData.FilteringColor);
|
||||
textLoader.GetTokenByte("alphasrc", &envData.byFilteringAlphaSrc);
|
||||
textLoader.GetTokenByte("alphadest", &envData.byFilteringAlphaDest);
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
if (textLoader.SetChildNode("skybox"))
|
||||
{
|
||||
textLoader.GetTokenBoolean("btexturerendermode", (BOOL *) &envData.bSkyBoxTextureRenderMode);
|
||||
textLoader.GetTokenVector3("scale", &envData.v3SkyBoxScale);
|
||||
textLoader.GetTokenByte("gradientlevelupper", &envData.bySkyBoxGradientLevelUpper);
|
||||
textLoader.GetTokenByte("gradientlevellower", &envData.bySkyBoxGradientLevelLower);
|
||||
|
||||
textLoader.GetTokenString("frontfacefilename", &envData.strSkyBoxFaceFileName[0]);
|
||||
textLoader.GetTokenString("backfacefilename", &envData.strSkyBoxFaceFileName[1]);
|
||||
textLoader.GetTokenString("leftfacefilename", &envData.strSkyBoxFaceFileName[2]);
|
||||
textLoader.GetTokenString("rightfacefilename", &envData.strSkyBoxFaceFileName[3]);
|
||||
textLoader.GetTokenString("topfacefilename", &envData.strSkyBoxFaceFileName[4]);
|
||||
textLoader.GetTokenString("bottomfacefilename", &envData.strSkyBoxFaceFileName[5]);
|
||||
|
||||
|
||||
textLoader.GetTokenVector2("cloudscale", &envData.v2CloudScale);
|
||||
textLoader.GetTokenFloat("cloudheight", &envData.fCloudHeight);
|
||||
textLoader.GetTokenVector2("cloudtexturescale", &envData.v2CloudTextureScale);
|
||||
textLoader.GetTokenVector2("cloudspeed", &envData.v2CloudSpeed);
|
||||
textLoader.GetTokenString("cloudtexturefilename", &envData.strCloudTextureFileName);
|
||||
|
||||
CTokenVector * pTokenVectorCloudColor;
|
||||
if(textLoader.GetTokenVector("cloudcolor", &pTokenVectorCloudColor))
|
||||
if ( 0 == pTokenVectorCloudColor->size()%8)
|
||||
{
|
||||
envData.CloudGradientColor.m_FirstColor.r = atof(pTokenVectorCloudColor->at(0).c_str());
|
||||
envData.CloudGradientColor.m_FirstColor.g = atof(pTokenVectorCloudColor->at(1).c_str());
|
||||
envData.CloudGradientColor.m_FirstColor.b = atof(pTokenVectorCloudColor->at(2).c_str());
|
||||
envData.CloudGradientColor.m_FirstColor.a = atof(pTokenVectorCloudColor->at(3).c_str());
|
||||
|
||||
envData.CloudGradientColor.m_SecondColor.r = atof(pTokenVectorCloudColor->at(4).c_str());
|
||||
envData.CloudGradientColor.m_SecondColor.g = atof(pTokenVectorCloudColor->at(5).c_str());
|
||||
envData.CloudGradientColor.m_SecondColor.b = atof(pTokenVectorCloudColor->at(6).c_str());
|
||||
envData.CloudGradientColor.m_SecondColor.a = atof(pTokenVectorCloudColor->at(7).c_str());
|
||||
}
|
||||
|
||||
BYTE byGradientCount = envData.bySkyBoxGradientLevelUpper+envData.bySkyBoxGradientLevelLower;
|
||||
CTokenVector * pTokenVector;
|
||||
if (textLoader.GetTokenVector("gradient", &pTokenVector))
|
||||
if (0 == pTokenVector->size()%8)
|
||||
if (byGradientCount == pTokenVector->size()/8)
|
||||
{
|
||||
envData.SkyBoxGradientColorVector.clear();
|
||||
envData.SkyBoxGradientColorVector.resize(byGradientCount);
|
||||
for (DWORD i = 0; i < byGradientCount; ++i)
|
||||
{
|
||||
envData.SkyBoxGradientColorVector[i].m_FirstColor.r = atof(pTokenVector->at(i*8+0).c_str());
|
||||
envData.SkyBoxGradientColorVector[i].m_FirstColor.g = atof(pTokenVector->at(i*8+1).c_str());
|
||||
envData.SkyBoxGradientColorVector[i].m_FirstColor.b = atof(pTokenVector->at(i*8+2).c_str());
|
||||
envData.SkyBoxGradientColorVector[i].m_FirstColor.a = atof(pTokenVector->at(i*8+3).c_str());
|
||||
|
||||
envData.SkyBoxGradientColorVector[i].m_SecondColor.r = atof(pTokenVector->at(i*8+4).c_str());
|
||||
envData.SkyBoxGradientColorVector[i].m_SecondColor.g = atof(pTokenVector->at(i*8+5).c_str());
|
||||
envData.SkyBoxGradientColorVector[i].m_SecondColor.b = atof(pTokenVector->at(i*8+6).c_str());
|
||||
envData.SkyBoxGradientColorVector[i].m_SecondColor.a = atof(pTokenVector->at(i*8+7).c_str());
|
||||
}
|
||||
}
|
||||
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
|
||||
if (textLoader.SetChildNode("lensflare"))
|
||||
{
|
||||
textLoader.GetTokenBoolean("enable", &envData.bLensFlareEnable);
|
||||
textLoader.GetTokenColor("brightnesscolor", &envData.LensFlareBrightnessColor);
|
||||
textLoader.GetTokenFloat("maxbrightness", &envData.fLensFlareMaxBrightness);
|
||||
textLoader.GetTokenBoolean("mainflareenable", &envData.bMainFlareEnable);
|
||||
textLoader.GetTokenString("mainflaretexturefilename", &envData.strMainFlareTextureFileName);
|
||||
textLoader.GetTokenFloat("mainflaresize", &envData.fMainFlareSize);
|
||||
|
||||
textLoader.SetParentNode();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void GetInterpolatedPosition(float curPositionRate, TPixelPosition * PixelPosition)
|
||||
{
|
||||
}
|
||||
|
||||
float GetLinearInterpolation(float begin, float end, float curRate)
|
||||
{
|
||||
return (end - begin) * curRate + begin;
|
||||
}
|
||||
|
||||
void PixelPositionToAttributeCellPosition(TPixelPosition PixelPosition, TCellPosition * pAttrCellPosition)
|
||||
{
|
||||
pAttrCellPosition->x = PixelPosition.x / c_Section_xAttributeCellSize;
|
||||
pAttrCellPosition->y = PixelPosition.y / c_Section_yAttributeCellSize;
|
||||
}
|
||||
|
||||
void AttributeCellPositionToPixelPosition(TCellPosition AttrCellPosition, TPixelPosition * pPixelPosition)
|
||||
{
|
||||
pPixelPosition->x = AttrCellPosition.x * c_Section_xAttributeCellSize;
|
||||
pPixelPosition->y = AttrCellPosition.y * c_Section_yAttributeCellSize;
|
||||
}
|
||||
|
||||
float GetPixelPositionDistance(const TPixelPosition & c_rsrcPosition, const TPixelPosition & c_rdstPosition)
|
||||
{
|
||||
int idx = c_rsrcPosition.x - c_rdstPosition.x;
|
||||
int idy = c_rsrcPosition.y - c_rdstPosition.y;
|
||||
|
||||
return sqrtf(float(idx*idx + idy*idy));
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
CEaseOutInterpolation::CEaseOutInterpolation()
|
||||
{
|
||||
Initialize();
|
||||
}
|
||||
|
||||
CEaseOutInterpolation::~CEaseOutInterpolation()
|
||||
{
|
||||
}
|
||||
|
||||
void CEaseOutInterpolation::Initialize()
|
||||
{
|
||||
m_fRemainingTime = 0.0f;
|
||||
m_fValue = 0.0f;
|
||||
m_fSpeed = 0.0f;
|
||||
m_fAcceleration = 0.0f;
|
||||
m_fStartValue = 0.0f;
|
||||
m_fLastValue = 0.0f;
|
||||
}
|
||||
|
||||
|
||||
BOOL CEaseOutInterpolation::Setup(float fStart, float fEnd, float fTime)
|
||||
{
|
||||
//for safety
|
||||
if( fabs(fTime) < FLT_EPSILON )
|
||||
{
|
||||
fTime = 0.01f;
|
||||
}
|
||||
|
||||
m_fValue = fStart;
|
||||
m_fStartValue = fStart;
|
||||
m_fLastValue = fStart;
|
||||
|
||||
m_fSpeed = (2.0f * (fEnd - fStart)) / fTime;
|
||||
m_fAcceleration = 2.0f * (fEnd - fStart) / (fTime * fTime) - 2.0f * m_fSpeed / fTime;
|
||||
m_fRemainingTime = fTime;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void CEaseOutInterpolation::Interpolate(float fElapsedTime)
|
||||
{
|
||||
m_fLastValue = m_fValue;
|
||||
|
||||
m_fRemainingTime -= fElapsedTime;
|
||||
m_fSpeed += m_fAcceleration * fElapsedTime;
|
||||
m_fValue += m_fSpeed * fElapsedTime;
|
||||
|
||||
if (!isPlaying())
|
||||
{
|
||||
m_fValue = 0.0f;
|
||||
m_fLastValue = 0.0f;
|
||||
}
|
||||
}
|
||||
|
||||
BOOL CEaseOutInterpolation::isPlaying()
|
||||
{
|
||||
return m_fRemainingTime > 0.0f;
|
||||
}
|
||||
|
||||
float CEaseOutInterpolation::GetValue()
|
||||
{
|
||||
return m_fValue;
|
||||
}
|
||||
|
||||
float CEaseOutInterpolation::GetChangingValue()
|
||||
{
|
||||
return m_fValue - m_fLastValue;
|
||||
}
|
||||
@@ -0,0 +1,177 @@
|
||||
#include "StdAfx.h"
|
||||
#include "PhysicsObject.h"
|
||||
|
||||
const float c_fFrameTime = 0.02f;
|
||||
const float EPSILON = 0.001f;
|
||||
|
||||
IPhysicsWorld* IPhysicsWorld::ms_pWorld = NULL;
|
||||
IObjectManager* IObjectManager::ms_ObjManager = NULL;
|
||||
|
||||
void CPhysicsObject::Update(float fElapsedTime)
|
||||
{
|
||||
if (m_xPushingPosition.isPlaying())
|
||||
m_xPushingPosition.Interpolate(fElapsedTime);
|
||||
if (m_yPushingPosition.isPlaying())
|
||||
m_yPushingPosition.Interpolate(fElapsedTime);
|
||||
}
|
||||
|
||||
void CPhysicsObject::Accumulate(D3DXVECTOR3 * pv3Position)
|
||||
{
|
||||
// If object is moving, give minor power to object.
|
||||
float fForce = 0.0f;
|
||||
|
||||
if (fabs(m_v3Velocity.x) < EPSILON ||
|
||||
fabs(m_v3Velocity.y) < EPSILON ||
|
||||
fabs(m_v3Velocity.z) < EPSILON )
|
||||
{
|
||||
fForce -= (m_fMass * m_fFriction);
|
||||
}
|
||||
|
||||
m_v3Acceleration = m_v3Direction * (fForce / m_fMass);
|
||||
m_v3Velocity += m_v3Acceleration;
|
||||
if (m_v3Velocity.x * m_v3Direction.x < EPSILON)
|
||||
{
|
||||
m_v3Velocity.x = 0.0f;
|
||||
m_v3Direction.x = 0.0f;
|
||||
}
|
||||
if (m_v3Velocity.y * m_v3Direction.y < EPSILON)
|
||||
{
|
||||
m_v3Velocity.y = 0.0f;
|
||||
m_v3Direction.y = 0.0f;
|
||||
}
|
||||
if (m_v3Velocity.z * m_v3Direction.z < EPSILON)
|
||||
{
|
||||
m_v3Velocity.z = 0.0f;
|
||||
m_v3Direction.z = 0.0f;
|
||||
}
|
||||
|
||||
pv3Position->x += m_v3Velocity.x;
|
||||
pv3Position->y += m_v3Velocity.y;
|
||||
pv3Position->z += m_v3Velocity.z;
|
||||
}
|
||||
|
||||
void CPhysicsObject::IncreaseExternalForce(const D3DXVECTOR3 & c_rvBasePosition, float fForce)
|
||||
{
|
||||
// Accumulate Acceleration by External Force
|
||||
m_v3Acceleration = m_v3Direction * (fForce / m_fMass);
|
||||
m_v3Velocity = m_v3Acceleration;
|
||||
/*
|
||||
Tracenf("force %f, mass %f, accel (%f, %f, %f)", fForce, m_fMass,
|
||||
m_v3Acceleration.x,
|
||||
m_v3Acceleration.y,
|
||||
m_v3Acceleration.z);
|
||||
*/
|
||||
// NOTE : 최종 위치를 구해둔다. 근데 100보다 크다면? ;
|
||||
const int LoopValue = 100;
|
||||
D3DXVECTOR3 v3Movement(0.0f, 0.0f, 0.0f);
|
||||
|
||||
for(int i = 0; i < LoopValue; ++i)
|
||||
{
|
||||
Accumulate(&v3Movement);
|
||||
|
||||
// VICTIM_COLLISION_TEST
|
||||
IPhysicsWorld* pWorld = IPhysicsWorld::GetPhysicsWorld();
|
||||
if (pWorld)
|
||||
{
|
||||
if (pWorld->isPhysicalCollision(c_rvBasePosition + v3Movement))
|
||||
{
|
||||
Initialize();
|
||||
return;
|
||||
|
||||
//for (float fRatio = 0.0f; fRatio < 1.0f; fRatio += 0.1f)
|
||||
//{
|
||||
// // 좀더 정밀하게 체크한다
|
||||
// if (pWorld->isPhysicalCollision(c_rvBasePosition + v3Movement * fRatio))
|
||||
// {
|
||||
// v3Movement = D3DXVECTOR3 (0.0f, 0.0f, 0.0f);
|
||||
// break;
|
||||
// }
|
||||
//}
|
||||
//break;
|
||||
}
|
||||
}
|
||||
// VICTIM_COLLISION_TEST_END
|
||||
|
||||
if (fabs(m_v3Velocity.x) < EPSILON &&
|
||||
fabs(m_v3Velocity.y) < EPSILON &&
|
||||
fabs(m_v3Velocity.z) < EPSILON )
|
||||
break;
|
||||
}
|
||||
|
||||
SetLastPosition(v3Movement, float(LoopValue) * c_fFrameTime);
|
||||
|
||||
if( m_pActorInstance )
|
||||
{
|
||||
IObjectManager* pObjectManager = IObjectManager::GetObjectManager();
|
||||
pObjectManager->AdjustCollisionWithOtherObjects( m_pActorInstance );
|
||||
}
|
||||
}
|
||||
|
||||
void CPhysicsObject::SetLastPosition(const TPixelPosition & c_rPosition, float fBlendingTime)
|
||||
{
|
||||
m_v3LastPosition.x = float(c_rPosition.x);
|
||||
m_v3LastPosition.y = float(c_rPosition.y);
|
||||
m_v3LastPosition.z = float(c_rPosition.z);
|
||||
m_xPushingPosition.Setup(0.0f, c_rPosition.x, fBlendingTime);
|
||||
m_yPushingPosition.Setup(0.0f, c_rPosition.y, fBlendingTime);
|
||||
}
|
||||
|
||||
void CPhysicsObject::GetLastPosition(TPixelPosition * pPosition)
|
||||
{
|
||||
pPosition->x = (m_v3LastPosition.x);
|
||||
pPosition->y = (m_v3LastPosition.y);
|
||||
pPosition->z = (m_v3LastPosition.z);
|
||||
}
|
||||
|
||||
void CPhysicsObject::SetDirection(const D3DXVECTOR3 & c_rv3Direction)
|
||||
{
|
||||
m_v3Direction.x = c_rv3Direction.x;
|
||||
m_v3Direction.y = c_rv3Direction.y;
|
||||
m_v3Direction.z = c_rv3Direction.z;
|
||||
}
|
||||
|
||||
float CPhysicsObject::GetXMovement()
|
||||
{
|
||||
return m_xPushingPosition.GetChangingValue();
|
||||
}
|
||||
|
||||
float CPhysicsObject::GetYMovement()
|
||||
{
|
||||
return m_yPushingPosition.GetChangingValue();
|
||||
}
|
||||
|
||||
bool CPhysicsObject::isBlending()
|
||||
{
|
||||
// NOTE : IncreaseExternalForce() 에 의해 밀리는 처리중인가?
|
||||
if (0.0f != D3DXVec3Length(&m_v3Velocity))
|
||||
return true;
|
||||
|
||||
// NOTE : SetLastPosition() 에 의해 밀리는 처리중인가?
|
||||
if (m_xPushingPosition.isPlaying() ||
|
||||
m_yPushingPosition.isPlaying())
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void CPhysicsObject::Initialize()
|
||||
{
|
||||
m_fMass = 1.0f;
|
||||
m_fFriction = 0.3f;
|
||||
m_v3Direction = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
m_v3Acceleration = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
m_v3Velocity = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
m_v3LastPosition = D3DXVECTOR3(0.0f, 0.0f, 0.0f);
|
||||
|
||||
m_xPushingPosition.Initialize();
|
||||
m_yPushingPosition.Initialize();
|
||||
}
|
||||
|
||||
CPhysicsObject::CPhysicsObject()
|
||||
{
|
||||
m_pActorInstance = NULL;
|
||||
}
|
||||
|
||||
CPhysicsObject::~CPhysicsObject()
|
||||
{
|
||||
}
|
||||
@@ -0,0 +1,490 @@
|
||||
#include "StdAfx.h"
|
||||
#include "../EterLib/ResourceManager.h"
|
||||
#include "../EterLib/StateManager.h"
|
||||
|
||||
#include "WeaponTrace.h"
|
||||
|
||||
CDynamicPool<CWeaponTrace> CWeaponTrace::ms_kPool;
|
||||
|
||||
void CWeaponTrace::DestroySystem()
|
||||
{
|
||||
ms_kPool.Destroy();
|
||||
}
|
||||
|
||||
void CWeaponTrace::Delete(CWeaponTrace* pkWTDel)
|
||||
{
|
||||
assert(pkWTDel!=NULL && "CWeaponTrace::Delete");
|
||||
|
||||
pkWTDel->Clear();
|
||||
ms_kPool.Free(pkWTDel);
|
||||
}
|
||||
|
||||
CWeaponTrace* CWeaponTrace::New()
|
||||
{
|
||||
return ms_kPool.Alloc();
|
||||
}
|
||||
|
||||
void CWeaponTrace::Update(float fReachScale)
|
||||
{
|
||||
float fElapsedTime = CTimer::Instance().GetCurrentSecond() - m_fLastUpdate;
|
||||
m_fLastUpdate = CTimer::Instance().GetCurrentSecond();
|
||||
|
||||
if (!m_pInstance)
|
||||
return;
|
||||
{
|
||||
// 잔상을 남기는 시간 범위 내의 점들만 유지합니다.
|
||||
TTimePointList::iterator it;
|
||||
for(it=m_ShortTimePointList.begin();it!=m_ShortTimePointList.end();++it)
|
||||
{
|
||||
it->first += fElapsedTime;
|
||||
if (it->first>m_fLifeTime)
|
||||
{
|
||||
it++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (it!=m_ShortTimePointList.end())
|
||||
m_ShortTimePointList.erase(it,m_ShortTimePointList.end());
|
||||
for(it=m_LongTimePointList.begin();it!=m_LongTimePointList.end();++it)
|
||||
{
|
||||
it->first += fElapsedTime;
|
||||
if (it->first>m_fLifeTime)
|
||||
{
|
||||
it++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (it!=m_LongTimePointList.end())
|
||||
m_LongTimePointList.erase(it, m_LongTimePointList.end());
|
||||
}
|
||||
|
||||
if (m_isPlaying && m_fz>=0.0001f)
|
||||
{
|
||||
D3DXMATRIX * pMatrix;
|
||||
if (m_pInstance->GetCompositeBoneMatrix(m_dwModelInstanceIndex, m_iBoneIndex, &pMatrix))
|
||||
{
|
||||
D3DXMATRIX * pBoneMat;
|
||||
m_pInstance->GetBoneMatrix(m_dwModelInstanceIndex, m_iBoneIndex, &pBoneMat);
|
||||
D3DXMATRIX mat = *pMatrix;
|
||||
mat._41 = pBoneMat->_41;
|
||||
mat._42 = pBoneMat->_42;
|
||||
mat._43 = pBoneMat->_43;
|
||||
// 현재 위치를 추가합니다.
|
||||
D3DXMATRIX matPoint;
|
||||
D3DXMATRIX matTranslation;
|
||||
D3DXMATRIX matRotation;
|
||||
|
||||
//D3DXMatrixTranslation(&matTranslation, 0.0f, m_fLength, 0.0f);
|
||||
D3DXMatrixTranslation(&matTranslation, 0.0f, 0.0f, m_fLength*fReachScale);
|
||||
D3DXMatrixRotationZ(&matRotation, D3DXToRadian(m_fRotation));
|
||||
|
||||
|
||||
matPoint = /**pMatrix*/mat * matRotation;
|
||||
/*TPDTVertex PDTVertex;
|
||||
PDTVertex.position.x = m_fx + matPoint._41;
|
||||
PDTVertex.position.y = m_fy + matPoint._42;
|
||||
PDTVertex.position.z = m_fz + matPoint._43;
|
||||
PDTVertex.diffuse = D3DXCOLOR(1.0f, 1.0f, 1.0f, 0.1f);
|
||||
m_PDTVertexVector.push_back(PDTVertex);*/
|
||||
m_ShortTimePointList.push_front(
|
||||
TTimePoint(
|
||||
0.0f,
|
||||
D3DXVECTOR3(
|
||||
m_fx + matPoint._41,
|
||||
m_fy + matPoint._42,
|
||||
m_fz + matPoint._43
|
||||
)
|
||||
)
|
||||
);
|
||||
|
||||
matPoint = matTranslation * matPoint;
|
||||
/*PDTVertex.position.x = m_fx + matPoint._41;
|
||||
PDTVertex.position.y = m_fy + matPoint._42;
|
||||
PDTVertex.position.z = m_fz + matPoint._43;
|
||||
PDTVertex.diffuse = D3DXCOLOR(1.0f, 1.0f, 1.0f, 0.1f);
|
||||
m_PDTVertexVector.push_back(PDTVertex);*/
|
||||
m_LongTimePointList.push_front(
|
||||
TTimePoint(
|
||||
0.0f,
|
||||
D3DXVECTOR3(
|
||||
m_fx + matPoint._41,
|
||||
m_fy + matPoint._42,
|
||||
m_fz + matPoint._43
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
//if (!BuildVertex())
|
||||
// return;
|
||||
}
|
||||
|
||||
bool CWeaponTrace::BuildVertex()
|
||||
{
|
||||
const int max_size = 300;
|
||||
// calculate speed
|
||||
float h[max_size];
|
||||
float stk[max_size];
|
||||
int sp=0;
|
||||
D3DXVECTOR3 r[max_size];
|
||||
|
||||
if (m_LongTimePointList.size()<=1)
|
||||
return false;
|
||||
|
||||
|
||||
//Tracef("## %f %f %f\n", m_LongTimePointList[0].second.x, m_LongTimePointList[0].second.y, m_LongTimePointList[0].second.z);
|
||||
|
||||
/*m_LongTimePointList.clear();
|
||||
m_LongTimePointList.push_back(TTimePoint(0.00,D3DXVECTOR3(0,0,0)));
|
||||
m_LongTimePointList.push_back(TTimePoint(0.01,D3DXVECTOR3(0,1,0)));
|
||||
m_LongTimePointList.push_back(TTimePoint(0.04,D3DXVECTOR3(0,1,0)));
|
||||
m_LongTimePointList.push_back(TTimePoint(0.05,D3DXVECTOR3(0,0,0)));
|
||||
m_ShortTimePointList = m_LongTimePointList;
|
||||
|
||||
*/
|
||||
std::vector<TPDTVertex> m_ShortVertexVector, m_LongVertexVector;
|
||||
|
||||
float length = min(m_fLifeTime, m_LongTimePointList.back().first);
|
||||
|
||||
int n = m_LongTimePointList.size()-1;
|
||||
assert(n<max_size-1);
|
||||
|
||||
// cubic spline
|
||||
|
||||
for(int loop = 0; loop<=1; ++loop)
|
||||
{
|
||||
TTimePointList & Input = (loop) ? m_LongTimePointList : m_ShortTimePointList;
|
||||
std::vector<TPDTVertex> & Output = (loop) ? m_LongVertexVector : m_ShortVertexVector;
|
||||
TTimePointList::iterator it;
|
||||
int i;
|
||||
|
||||
for(i=0;i<n;++i)
|
||||
{
|
||||
h[i] = Input[i+1].first - Input[i].first;
|
||||
r[i] = (Input[i+1].second - Input[i].second)*(3/h[i]);
|
||||
}
|
||||
r[n] = D3DXVECTOR3(0.0f,0.0f,0.0f);
|
||||
for(i=n;i>0;i--)
|
||||
{
|
||||
r[i]+=r[i-1];
|
||||
}
|
||||
|
||||
float rate = 0.5f;
|
||||
r[0] *= 0.5f;
|
||||
stk[sp++] = rate;
|
||||
for(i=1;i<n;i++)
|
||||
{
|
||||
r[i]-=r[i-1];
|
||||
rate = 1/(4-rate);
|
||||
r[i] *= rate;
|
||||
stk[sp++]=rate;
|
||||
}
|
||||
r[n]-=r[n-1];
|
||||
rate = 1/(2-rate);
|
||||
r[n]*=rate;
|
||||
|
||||
for(i=n-1;i>=0;i--)
|
||||
{
|
||||
r[i] -= stk[--sp] * r[i+1];
|
||||
}
|
||||
|
||||
int base = 0;
|
||||
D3DXVECTOR3 a,b,c,d;
|
||||
D3DXVECTOR3 v3Tmp = Input[base+1].second-Input[base].second;
|
||||
float timebase=0,timenext=h[base], dt=m_fSamplingTime;
|
||||
a = Input[base].second;
|
||||
b = r[base];
|
||||
c = ( 3*v3Tmp - r[base+1]*h[base] - (2*h[base])*r[base] )
|
||||
* (1/(h[base]*h[base]));
|
||||
d = ( -2*v3Tmp + (r[base+1]+r[base])*h[base])
|
||||
* (1/(h[base]*h[base]*h[base]));
|
||||
|
||||
for(float t = 0; t<=length; t+=dt)
|
||||
{
|
||||
while (t>timenext)
|
||||
{
|
||||
timebase = timenext;
|
||||
base++;
|
||||
if (base>=n) break;
|
||||
D3DXVECTOR3 v3Tmp = Input[base+1].second-Input[base].second;
|
||||
a = Input[base].second;
|
||||
b = r[base];
|
||||
c = ( 3*v3Tmp - r[base+1]*h[base] - (2*h[base])*r[base] )
|
||||
* (1/(h[base]*h[base]));
|
||||
d = ( -2*v3Tmp + (r[base+1]+r[base])*h[base])
|
||||
* (1/(h[base]*h[base]*h[base]));
|
||||
|
||||
timenext+=h[base];
|
||||
if (loop)
|
||||
{
|
||||
//Tracef("%f:%f %f %f\n",Input[base].first,Input[base].second.x,Input[base].second.y,Input[base].second.z);
|
||||
}
|
||||
}
|
||||
if (base>n) break;
|
||||
float cc = t - timebase;
|
||||
|
||||
TPDTVertex v;
|
||||
//v.diffuse = D3DXCOLOR(0.3f,0.8f,1.0f, (loop)?max(1.0f-(t/m_fLifeTime),0.0f)/2:0.0f );
|
||||
float ttt = min(max((t+Input[0].first)/m_fLifeTime,0.0f),1.0f);
|
||||
v.diffuse = D3DXCOLOR(0.3f,0.8f,1.0f, (loop)?min(max((1.0f-ttt)*(1.0f-ttt)/2.5-0.1f,0.0f),1.0f):0.0f );
|
||||
//v.diffuse = D3DXCOLOR(0.0f,0.0f,0.0f, (loop)?min(max((1.0f-ttt)*(1.0f-ttt)-0.1f,0.0f),1.0f):0.0f );
|
||||
//v.diffuse = 0xffffffff;
|
||||
v.position = a+cc*(b+cc*(c+cc*d)); // next position
|
||||
v.texCoord.x = t/m_fLifeTime;
|
||||
v.texCoord.y = loop ? 0 : 1;
|
||||
Output.push_back(v);
|
||||
if (loop)
|
||||
{
|
||||
// Tracef("%f %f %f\n", timebase,t,timenext);
|
||||
//Tracef("a:%f %f %f\nb:%f %f %f \nc:%f %f %f \nd:%f %f %f, \n",,a.x,a.y,a.z,b.x,b.y,b.z,c.x,c.y,c.z,d.x,d.y,d.z);
|
||||
|
||||
//Tracef("%f %f %f\n",v.position.x,v.position.y,v.position.z);
|
||||
/*D3DXMATRIX * pBoneMat;
|
||||
m_pInstance->GetBoneMatrix(m_dwModelInstanceIndex, 55, &pBoneMat);
|
||||
D3DXVECTOR3 vbone(m_fx+pBoneMat->_41,m_fy+pBoneMat->_42,m_fz+pBoneMat->_43);
|
||||
float len = D3DXVec3Length(&(v.position-vbone));*/
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// build vertex
|
||||
|
||||
m_PDTVertexVector.clear();
|
||||
|
||||
/*
|
||||
TTimePointList::iterator lit1,lit2, sit1,sit2;
|
||||
|
||||
lit2 = lit1 = m_LongTimePointList.begin();
|
||||
++lit2;
|
||||
|
||||
sit2 = sit1 = m_ShortTimePointList.begin();
|
||||
++sit2;
|
||||
*/
|
||||
std::vector<TPDTVertex>::iterator lit,sit;
|
||||
for(lit = m_LongVertexVector.begin(), sit = m_ShortVertexVector.begin();
|
||||
lit != m_LongVertexVector.end();
|
||||
++lit,++sit)
|
||||
{
|
||||
m_PDTVertexVector.push_back(*lit);
|
||||
m_PDTVertexVector.push_back(*sit);
|
||||
/*float len = D3DXVec3Length(&(lit->position - sit->position));
|
||||
if (len>160)
|
||||
Tracef("dist:%f\n",len);*/
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CWeaponTrace::Render()
|
||||
{
|
||||
//if (!m_isPlaying)
|
||||
// return;
|
||||
//if (m_CurvingTraceVector.size() < 4)
|
||||
// return;
|
||||
|
||||
if (!BuildVertex())
|
||||
return;
|
||||
|
||||
if (m_PDTVertexVector.size()<4)
|
||||
return;
|
||||
|
||||
|
||||
LPDIRECT3DTEXTURE8 lpTexture=NULL;
|
||||
|
||||
// Have to optimize
|
||||
D3DXMATRIX matWorld;
|
||||
D3DXMatrixIdentity(&matWorld);
|
||||
|
||||
STATEMANAGER.SaveTransform(D3DTS_WORLD, &matWorld);
|
||||
STATEMANAGER.SaveVertexShader(D3DFVF_XYZ | D3DFVF_DIFFUSE | D3DFVF_TEX1);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_CULLMODE, D3DCULL_NONE);
|
||||
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
|
||||
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHATESTENABLE, FALSE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHAREF, 0x00000011);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ALPHAFUNC, D3DCMP_GREATER);
|
||||
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ZENABLE, TRUE);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ZFUNC, D3DCMP_LESSEQUAL);
|
||||
STATEMANAGER.SaveRenderState(D3DRS_ZWRITEENABLE, FALSE);
|
||||
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_TEXTURE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, (m_bUseTexture)?D3DTOP_SELECTARG2:D3DTOP_SELECTARG1);
|
||||
//STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
|
||||
//STATEMANAGER.SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_DIFFUSE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_TEXTURE);
|
||||
//STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
|
||||
STATEMANAGER.SetTextureStageState(0, D3DTSS_ALPHAOP, (m_bUseTexture)?D3DTOP_SELECTARG2:D3DTOP_SELECTARG1);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||
STATEMANAGER.SetRenderState(D3DRS_LIGHTING, FALSE);
|
||||
STATEMANAGER.SetTexture(0, lpTexture);
|
||||
STATEMANAGER.SetTexture(1, NULL);
|
||||
STATEMANAGER.DrawPrimitiveUP(D3DPT_TRIANGLESTRIP,
|
||||
int(m_PDTVertexVector.size() - 2),
|
||||
&m_PDTVertexVector[0],
|
||||
sizeof(TPDTVertex));
|
||||
|
||||
STATEMANAGER.SetRenderState(D3DRS_LIGHTING, TRUE);
|
||||
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ZENABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ZFUNC);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ZWRITEENABLE);
|
||||
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHATESTENABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHAREF);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHAFUNC);
|
||||
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_ALPHABLENDENABLE);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_SRCBLEND);
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_DESTBLEND);
|
||||
|
||||
STATEMANAGER.RestoreTransform(D3DTS_WORLD);
|
||||
STATEMANAGER.RestoreVertexShader();
|
||||
STATEMANAGER.RestoreRenderState(D3DRS_CULLMODE);
|
||||
}
|
||||
|
||||
void CWeaponTrace::UseAlpha()
|
||||
{
|
||||
m_bUseTexture = false;
|
||||
}
|
||||
|
||||
void CWeaponTrace::UseTexture()
|
||||
{
|
||||
m_bUseTexture = true;
|
||||
}
|
||||
|
||||
void CWeaponTrace::SetTexture(const char * c_szFileName)
|
||||
{
|
||||
CGraphicImage * pImage = (CGraphicImage *)CResourceManager::Instance().GetResourcePointer("lot_ade10-2.tga");
|
||||
m_ImageInstance.SetImagePointer(pImage);
|
||||
|
||||
//CGraphicTexture * pTexture = m_ImageInstance.GetTexturePointer();
|
||||
//m_lpTexture = pTexture->GetD3DTexture();
|
||||
}
|
||||
|
||||
bool CWeaponTrace::SetWeaponInstance(CGraphicThingInstance * pInstance, DWORD dwModelIndex, const char * c_szBoneName)
|
||||
{
|
||||
pInstance->Update();
|
||||
pInstance->DeformNoSkin();
|
||||
|
||||
D3DXVECTOR3 v3Min;
|
||||
D3DXVECTOR3 v3Max;
|
||||
if (!pInstance->GetBoundBox(dwModelIndex, &v3Min, &v3Max))
|
||||
return false;
|
||||
|
||||
m_iBoneIndex = 0;
|
||||
m_dwModelInstanceIndex = dwModelIndex;
|
||||
|
||||
m_pInstance = pInstance;
|
||||
D3DXMATRIX * pmat;
|
||||
pInstance->GetBoneMatrix(dwModelIndex, 0, &pmat);
|
||||
D3DXVECTOR3 v3Bone(pmat->_41,pmat->_42,pmat->_43);
|
||||
|
||||
const auto vv1 = (v3Bone - v3Min);
|
||||
const auto vv2 = (v3Bone - v3Max);
|
||||
m_fLength =
|
||||
sqrtf(
|
||||
fMAX(
|
||||
D3DXVec3LengthSq(&vv1),
|
||||
D3DXVec3LengthSq(&vv2)
|
||||
)
|
||||
);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CWeaponTrace::SetPosition(float fx, float fy, float fz)
|
||||
{
|
||||
m_fx = fx;
|
||||
m_fy = fy;
|
||||
m_fz = fz;
|
||||
}
|
||||
|
||||
void CWeaponTrace::SetRotation(float fRotation)
|
||||
{
|
||||
m_fRotation = fRotation;
|
||||
}
|
||||
|
||||
void CWeaponTrace::SetLifeTime(float fLifeTime)
|
||||
{
|
||||
m_fLifeTime = fLifeTime;
|
||||
}
|
||||
|
||||
void CWeaponTrace::SetSamplingTime(float fSamplingTime)
|
||||
{
|
||||
m_fSamplingTime = fSamplingTime;
|
||||
}
|
||||
|
||||
void CWeaponTrace::TurnOn()
|
||||
{
|
||||
m_isPlaying = TRUE;
|
||||
}
|
||||
void CWeaponTrace::TurnOff()
|
||||
{
|
||||
m_isPlaying = FALSE;
|
||||
//Clear();
|
||||
}
|
||||
|
||||
void CWeaponTrace::Clear()
|
||||
{
|
||||
//m_PDTVertexVector.clear();
|
||||
//m_CurvingTraceVector.clear();
|
||||
|
||||
m_ShortTimePointList.clear();
|
||||
m_LongTimePointList.clear();
|
||||
Initialize();
|
||||
}
|
||||
|
||||
void CWeaponTrace::Initialize()
|
||||
{
|
||||
m_pInstance = NULL;
|
||||
m_dwModelInstanceIndex = 0;
|
||||
|
||||
m_fx = 0.0f;
|
||||
m_fy = 0.0f;
|
||||
m_fz = 0.0f;
|
||||
m_fRotation = 0.0f;
|
||||
|
||||
m_fLifeTime = 0.18f;
|
||||
//m_fLifeTime = 3.0f;
|
||||
m_fSamplingTime = 0.003f;
|
||||
//m_fLifeTime = 3.0f;
|
||||
//m_fSamplingTime = 0.003f;
|
||||
|
||||
m_isPlaying = FALSE;
|
||||
|
||||
m_bUseTexture = false;
|
||||
|
||||
m_iBoneIndex = 0;
|
||||
|
||||
m_fLastUpdate = CTimer::Instance().GetCurrentSecond();
|
||||
///////////////////////////////////////////////////////////////////////
|
||||
|
||||
//const int c_iSplineCount = 8;
|
||||
//m_SplineValueVector.clear();
|
||||
//m_SplineValueVector.resize(c_iSplineCount);
|
||||
|
||||
//for (int i = 0; i < c_iSplineCount; ++i)
|
||||
//{
|
||||
// float fValue = float(i) / float(c_iSplineCount);
|
||||
// m_SplineValueVector[i].fValue1 = fValue;
|
||||
// m_SplineValueVector[i].fValue2 = fValue * fValue;
|
||||
// m_SplineValueVector[i].fValue3 = fValue * fValue * fValue;
|
||||
//}
|
||||
|
||||
}
|
||||
|
||||
CWeaponTrace::CWeaponTrace()
|
||||
{
|
||||
Initialize();
|
||||
}
|
||||
CWeaponTrace::~CWeaponTrace()
|
||||
{
|
||||
}
|
||||
@@ -0,0 +1,86 @@
|
||||
#pragma once
|
||||
|
||||
// change CatMull to cubic spline
|
||||
#include "../EterGrnLib/ThingInstance.h"
|
||||
|
||||
class CWeaponTrace
|
||||
{
|
||||
/*
|
||||
public:
|
||||
typedef struct SSplineValue
|
||||
{
|
||||
float fValue1;
|
||||
float fValue2;
|
||||
float fValue3;
|
||||
} TSplineValue;
|
||||
*/
|
||||
public:
|
||||
static void DestroySystem();
|
||||
static void Delete(CWeaponTrace* pkWTDel);
|
||||
static CWeaponTrace* New();
|
||||
|
||||
public:
|
||||
CWeaponTrace();
|
||||
virtual ~CWeaponTrace();
|
||||
|
||||
void Clear();
|
||||
|
||||
void TurnOn();
|
||||
void TurnOff();
|
||||
|
||||
void UseAlpha();
|
||||
void UseTexture();
|
||||
|
||||
void SetTexture(const char * c_szFileName);
|
||||
bool SetWeaponInstance(CGraphicThingInstance * pInstance, DWORD dwModelIndex, const char * c_szBoneName);
|
||||
void SetPosition(float fx, float fy, float fz);
|
||||
void SetRotation(float fRotation);
|
||||
|
||||
void SetLifeTime(float fLifeTime);
|
||||
void SetSamplingTime(float fSamplingTime);
|
||||
|
||||
void Update(float fReachScale);
|
||||
void Render();
|
||||
|
||||
void Initialize();
|
||||
|
||||
protected:
|
||||
bool BuildVertex();
|
||||
|
||||
protected:
|
||||
|
||||
float m_fLastUpdate;
|
||||
|
||||
typedef std::pair<float, D3DXVECTOR3> TTimePoint;
|
||||
typedef std::deque<TTimePoint> TTimePointList;
|
||||
TTimePointList m_ShortTimePointList;
|
||||
TTimePointList m_LongTimePointList;
|
||||
|
||||
std::vector<TPDTVertex> m_PDTVertexVector;
|
||||
|
||||
float m_fLifeTime;
|
||||
float m_fSamplingTime;
|
||||
|
||||
//std::vector<TPDTVertex> m_PDTVertexVector;
|
||||
//std::vector<TPDTVertex> m_CurvingTraceVector;
|
||||
//std::vector<TSplineValue> m_SplineValueVector;
|
||||
|
||||
CGraphicThingInstance * m_pInstance;
|
||||
DWORD m_dwModelInstanceIndex;
|
||||
|
||||
CGraphicImageInstance m_ImageInstance;
|
||||
|
||||
float m_fx;
|
||||
float m_fy;
|
||||
float m_fz;
|
||||
float m_fRotation;
|
||||
float m_fLength;
|
||||
|
||||
BOOL m_isPlaying;
|
||||
bool m_bUseTexture;
|
||||
|
||||
int m_iBoneIndex;
|
||||
|
||||
protected:
|
||||
static CDynamicPool<CWeaponTrace> ms_kPool;
|
||||
};
|
||||
@@ -0,0 +1,719 @@
|
||||
#include "StdAfx.h"
|
||||
#include "InstanceBase.h"
|
||||
#include "PythonBackground.h"
|
||||
#include "PythonCharacterManager.h"
|
||||
#include "../PRTerrainLib/Terrain.h"
|
||||
|
||||
float NEW_UnsignedDegreeToSignedDegree(float fUD)
|
||||
{
|
||||
float fSD;
|
||||
if (fUD>180.0f)
|
||||
fSD=-(360.0f-fUD);
|
||||
else if (fUD<-180.0f)
|
||||
fSD=+(360.0f+fUD);
|
||||
else
|
||||
fSD=fUD;
|
||||
|
||||
return fSD;
|
||||
}
|
||||
|
||||
float NEW_GetSignedDegreeFromDirPixelPosition(const TPixelPosition& kPPosDir)
|
||||
{
|
||||
D3DXVECTOR3 vtDir(kPPosDir.x, -kPPosDir.y, kPPosDir.z);
|
||||
D3DXVECTOR3 vtDirNormal;
|
||||
D3DXVec3Normalize(&vtDirNormal, &vtDir);
|
||||
|
||||
D3DXVECTOR3 vtDirNormalStan(0, -1, 0);
|
||||
float fDirRot = D3DXToDegree(acosf(D3DXVec3Dot(&vtDirNormal, &vtDirNormalStan)));
|
||||
|
||||
if (vtDirNormal.x<0.0f)
|
||||
fDirRot=-fDirRot;
|
||||
|
||||
return fDirRot;
|
||||
}
|
||||
|
||||
bool CInstanceBase::IsFlyTargetObject()
|
||||
{
|
||||
return m_GraphicThingInstance.IsFlyTargetObject();
|
||||
}
|
||||
|
||||
float CInstanceBase::GetFlyTargetDistance()
|
||||
{
|
||||
return m_GraphicThingInstance.GetFlyTargetDistance();
|
||||
}
|
||||
|
||||
void CInstanceBase::ClearFlyTargetInstance()
|
||||
{
|
||||
m_GraphicThingInstance.ClearFlyTarget();
|
||||
}
|
||||
|
||||
void CInstanceBase::SetFlyTargetInstance(CInstanceBase& rkInstDst)
|
||||
{
|
||||
// NOTE : NEW_Attack 때 Target을 바꿀때 여기서 리턴 되어버림 - [levites]
|
||||
// if (isLock())
|
||||
// return;
|
||||
|
||||
m_GraphicThingInstance.SetFlyTarget(rkInstDst.GetGraphicThingInstancePtr());
|
||||
}
|
||||
|
||||
void CInstanceBase::AddFlyTargetPosition(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
m_GraphicThingInstance.AddFlyTarget(c_rkPPosDst);
|
||||
}
|
||||
|
||||
void CInstanceBase::AddFlyTargetInstance(CInstanceBase& rkInstDst)
|
||||
{
|
||||
m_GraphicThingInstance.AddFlyTarget(rkInstDst.GetGraphicThingInstancePtr());
|
||||
}
|
||||
|
||||
|
||||
float CInstanceBase::NEW_GetDistanceFromDestInstance(CInstanceBase& rkInstDst)
|
||||
{
|
||||
TPixelPosition kPPosDst;
|
||||
rkInstDst.NEW_GetPixelPosition(&kPPosDst);
|
||||
|
||||
return NEW_GetDistanceFromDestPixelPosition(kPPosDst);
|
||||
}
|
||||
|
||||
float CInstanceBase::NEW_GetDistanceFromDestPixelPosition(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
TPixelPosition kPPosCur;
|
||||
NEW_GetPixelPosition(&kPPosCur);
|
||||
|
||||
TPixelPosition kPPosDir;
|
||||
kPPosDir=c_rkPPosDst-kPPosCur;
|
||||
|
||||
return NEW_GetDistanceFromDirPixelPosition(kPPosDir);
|
||||
}
|
||||
|
||||
float CInstanceBase::NEW_GetDistanceFromDirPixelPosition(const TPixelPosition& c_rkPPosDir)
|
||||
{
|
||||
return sqrtf(c_rkPPosDir.x*c_rkPPosDir.x+c_rkPPosDir.y*c_rkPPosDir.y);
|
||||
}
|
||||
|
||||
float CInstanceBase::NEW_GetRotation()
|
||||
{
|
||||
float fCurRot=GetRotation();
|
||||
return NEW_UnsignedDegreeToSignedDegree(fCurRot);
|
||||
}
|
||||
|
||||
float CInstanceBase::NEW_GetRotationFromDirPixelPosition(const TPixelPosition& c_rkPPosDir)
|
||||
{
|
||||
return NEW_GetSignedDegreeFromDirPixelPosition(c_rkPPosDir);
|
||||
}
|
||||
|
||||
float CInstanceBase::NEW_GetRotationFromDestPixelPosition(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
TPixelPosition kPPosCur;
|
||||
NEW_GetPixelPosition(&kPPosCur);
|
||||
|
||||
TPixelPosition kPPosDir;
|
||||
kPPosDir=c_rkPPosDst-kPPosCur;
|
||||
|
||||
return NEW_GetRotationFromDirPixelPosition(kPPosDir);
|
||||
}
|
||||
|
||||
float CInstanceBase::NEW_GetRotationFromDestInstance(CInstanceBase& rkInstDst)
|
||||
{
|
||||
TPixelPosition kPPosDst;
|
||||
rkInstDst.NEW_GetPixelPosition(&kPPosDst);
|
||||
|
||||
return NEW_GetRotationFromDestPixelPosition(kPPosDst);
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_GetRandomPositionInFanRange(CInstanceBase& rkInstTarget, TPixelPosition* pkPPosDst)
|
||||
{
|
||||
float fDstDirRot=NEW_GetRotationFromDestInstance(rkInstTarget);
|
||||
|
||||
float fRot=frandom(fDstDirRot-10.0f, fDstDirRot+10.0f);
|
||||
|
||||
D3DXMATRIX kMatRot;
|
||||
D3DXMatrixRotationZ(&kMatRot, D3DXToRadian(-fRot));
|
||||
|
||||
D3DXVECTOR3 v3Src(0.0f, 8000.0f, 0.0f);
|
||||
D3DXVECTOR3 v3Pos;
|
||||
D3DXVec3TransformCoord(&v3Pos, &v3Src, &kMatRot);
|
||||
|
||||
const TPixelPosition& c_rkPPosCur=NEW_GetCurPixelPositionRef();
|
||||
//const TPixelPosition& c_rkPPosFront=rkInstTarget.NEW_GetCurPixelPositionRef();
|
||||
|
||||
pkPPosDst->x=c_rkPPosCur.x+v3Pos.x;
|
||||
pkPPosDst->y=c_rkPPosCur.y+v3Pos.y;
|
||||
pkPPosDst->z=__GetBackgroundHeight(c_rkPPosCur.x, c_rkPPosCur.y);
|
||||
}
|
||||
|
||||
bool CInstanceBase::NEW_GetFrontInstance(CInstanceBase ** ppoutTargetInstance, float fDistance)
|
||||
{
|
||||
const float HALF_FAN_ROT_MIN = 10.0f;
|
||||
const float HALF_FAN_ROT_MAX = 50.0f;
|
||||
const float HALF_FAN_ROT_MIN_DISTANCE = 1000.0f;
|
||||
const float RPM = (HALF_FAN_ROT_MAX-HALF_FAN_ROT_MIN)/HALF_FAN_ROT_MIN_DISTANCE;
|
||||
|
||||
float fDstRot=NEW_GetRotation();
|
||||
|
||||
std::multimap<float, CInstanceBase*> kMap_pkInstNear;
|
||||
{
|
||||
CPythonCharacterManager& rkChrMgr=CPythonCharacterManager::Instance();
|
||||
CPythonCharacterManager::CharacterIterator i;
|
||||
for(i = rkChrMgr.CharacterInstanceBegin(); i!=rkChrMgr.CharacterInstanceEnd(); ++i)
|
||||
{
|
||||
CInstanceBase* pkInstEach=*i;
|
||||
if (pkInstEach==this)
|
||||
continue;
|
||||
|
||||
if (!IsAttackableInstance(*pkInstEach))
|
||||
continue;
|
||||
|
||||
if (NEW_GetDistanceFromDestInstance(*pkInstEach) > fDistance)
|
||||
continue;
|
||||
|
||||
float fEachInstDistance=min(NEW_GetDistanceFromDestInstance(*pkInstEach), HALF_FAN_ROT_MIN_DISTANCE);
|
||||
float fEachInstDirRot=NEW_GetRotationFromDestInstance(*pkInstEach);
|
||||
|
||||
float fHalfFanRot=(HALF_FAN_ROT_MAX-HALF_FAN_ROT_MIN)-RPM*fEachInstDistance+HALF_FAN_ROT_MIN;
|
||||
|
||||
float fMinDstDirRot=fDstRot-fHalfFanRot;
|
||||
float fMaxDstDirRot=fDstRot+fHalfFanRot;
|
||||
|
||||
if (fEachInstDirRot>=fMinDstDirRot && fEachInstDirRot<=fMaxDstDirRot)
|
||||
kMap_pkInstNear.insert(std::multimap<float, CInstanceBase*>::value_type(fEachInstDistance, pkInstEach));
|
||||
}
|
||||
}
|
||||
|
||||
if (kMap_pkInstNear.empty())
|
||||
return false;
|
||||
|
||||
*ppoutTargetInstance = kMap_pkInstNear.begin()->second;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// 2004.07.21.levites - 비파부 다중 타겟 지원
|
||||
bool CInstanceBase::NEW_GetInstanceVectorInFanRange(float fSkillDistance, CInstanceBase& rkInstTarget, std::vector<CInstanceBase*>* pkVct_pkInst)
|
||||
{
|
||||
const float HALF_FAN_ROT_MIN = 20.0f;
|
||||
const float HALF_FAN_ROT_MAX = 40.0f;
|
||||
const float HALF_FAN_ROT_MIN_DISTANCE = 1000.0f;
|
||||
const float RPM = (HALF_FAN_ROT_MAX-HALF_FAN_ROT_MIN)/HALF_FAN_ROT_MIN_DISTANCE;
|
||||
|
||||
float fDstDirRot=NEW_GetRotationFromDestInstance(rkInstTarget);
|
||||
|
||||
// 2004.07.24.myevan - 비파부 가까이 있는 적부터 공격
|
||||
std::multimap<float, CInstanceBase*> kMap_pkInstNear;
|
||||
{
|
||||
CPythonCharacterManager& rkChrMgr=CPythonCharacterManager::Instance();
|
||||
CPythonCharacterManager::CharacterIterator i;
|
||||
for(i = rkChrMgr.CharacterInstanceBegin(); i!=rkChrMgr.CharacterInstanceEnd(); ++i)
|
||||
{
|
||||
CInstanceBase* pkInstEach=*i;
|
||||
if (pkInstEach==this)
|
||||
continue;
|
||||
|
||||
// 2004.07.25.myevan - 적인 경우만 추가한다
|
||||
if (!IsAttackableInstance(*pkInstEach))
|
||||
continue;
|
||||
|
||||
// 2004.07.21.levites - 비파부 다중 타겟 지원
|
||||
if (m_GraphicThingInstance.IsClickableDistanceDestInstance(pkInstEach->m_GraphicThingInstance, fSkillDistance))
|
||||
{
|
||||
float fEachInstDistance=min(NEW_GetDistanceFromDestInstance(*pkInstEach), HALF_FAN_ROT_MIN_DISTANCE);
|
||||
float fEachInstDirRot=NEW_GetRotationFromDestInstance(*pkInstEach);
|
||||
|
||||
float fHalfFanRot=(HALF_FAN_ROT_MAX-HALF_FAN_ROT_MIN)-RPM*fEachInstDistance+HALF_FAN_ROT_MIN;
|
||||
|
||||
float fMinDstDirRot=fDstDirRot-fHalfFanRot;
|
||||
float fMaxDstDirRot=fDstDirRot+fHalfFanRot;
|
||||
|
||||
if (fEachInstDirRot>=fMinDstDirRot && fEachInstDirRot<=fMaxDstDirRot)
|
||||
kMap_pkInstNear.insert(std::multimap<float, CInstanceBase*>::value_type(fEachInstDistance, pkInstEach));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
std::multimap<float, CInstanceBase*>::iterator i=kMap_pkInstNear.begin();
|
||||
for (i=kMap_pkInstNear.begin(); i!=kMap_pkInstNear.end(); ++i)
|
||||
pkVct_pkInst->push_back(i->second);
|
||||
}
|
||||
|
||||
if (pkVct_pkInst->empty())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CInstanceBase::NEW_GetInstanceVectorInCircleRange(float fSkillDistance, std::vector<CInstanceBase*>* pkVct_pkInst)
|
||||
{
|
||||
std::multimap<float, CInstanceBase*> kMap_pkInstNear;
|
||||
|
||||
{
|
||||
CPythonCharacterManager& rkChrMgr=CPythonCharacterManager::Instance();
|
||||
CPythonCharacterManager::CharacterIterator i;
|
||||
for(i = rkChrMgr.CharacterInstanceBegin(); i!=rkChrMgr.CharacterInstanceEnd(); ++i)
|
||||
{
|
||||
CInstanceBase* pkInstEach=*i;
|
||||
|
||||
// 자신인 경우 추가하지 않는다
|
||||
if (pkInstEach==this)
|
||||
continue;
|
||||
|
||||
// 적인 경우만 추가한다
|
||||
if (!IsAttackableInstance(*pkInstEach))
|
||||
continue;
|
||||
|
||||
if (m_GraphicThingInstance.IsClickableDistanceDestInstance(pkInstEach->m_GraphicThingInstance, fSkillDistance))
|
||||
{
|
||||
float fEachInstDistance=NEW_GetDistanceFromDestInstance(*pkInstEach);
|
||||
kMap_pkInstNear.insert(std::make_pair(fEachInstDistance, pkInstEach));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
std::multimap<float, CInstanceBase*>::iterator i=kMap_pkInstNear.begin();
|
||||
for (i=kMap_pkInstNear.begin(); i!=kMap_pkInstNear.end(); ++i)
|
||||
pkVct_pkInst->push_back(i->second);
|
||||
}
|
||||
|
||||
if (pkVct_pkInst->empty())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::NEW_IsClickableDistanceDestPixelPosition(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
float fDistance=NEW_GetDistanceFromDestPixelPosition(c_rkPPosDst);
|
||||
|
||||
if (fDistance>150.0f)
|
||||
return FALSE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::NEW_IsClickableDistanceDestInstance(CInstanceBase& rkInstDst)
|
||||
{
|
||||
float fDistance = 150.0f;
|
||||
|
||||
if (IsBowMode())
|
||||
fDistance = __GetBowRange();
|
||||
|
||||
if (rkInstDst.IsNPC())
|
||||
fDistance = 500.0f;
|
||||
|
||||
if (rkInstDst.IsResource())
|
||||
fDistance = 100.0f;
|
||||
|
||||
return m_GraphicThingInstance.IsClickableDistanceDestInstance(rkInstDst.m_GraphicThingInstance, fDistance);
|
||||
}
|
||||
|
||||
bool CInstanceBase::NEW_UseSkill(UINT uSkill, UINT uMot, UINT uMotLoopCount, bool isMovingSkill)
|
||||
{
|
||||
if (IsDead())
|
||||
return false;
|
||||
|
||||
if (IsStun())
|
||||
return false;
|
||||
|
||||
if (IsKnockDown())
|
||||
return false;
|
||||
|
||||
if (isMovingSkill)
|
||||
{
|
||||
if (!IsWalking())
|
||||
StartWalking();
|
||||
|
||||
m_isGoing = TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (IsWalking())
|
||||
EndWalking();
|
||||
|
||||
m_isGoing = FALSE;
|
||||
}
|
||||
|
||||
float fCurRot=m_GraphicThingInstance.GetTargetRotation();
|
||||
SetAdvancingRotation(fCurRot);
|
||||
|
||||
m_GraphicThingInstance.InterceptOnceMotion(CRaceMotionData::NAME_SKILL + uMot, 0.1f, uSkill, 1.0f);
|
||||
|
||||
m_GraphicThingInstance.__OnUseSkill(uMot, uMotLoopCount, isMovingSkill);
|
||||
|
||||
if (uMotLoopCount > 0)
|
||||
m_GraphicThingInstance.SetMotionLoopCount(uMotLoopCount);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_Attack()
|
||||
{
|
||||
float fDirRot=GetRotation();
|
||||
NEW_Attack(fDirRot);
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_Attack(float fDirRot)
|
||||
{
|
||||
if (IsDead())
|
||||
return;
|
||||
|
||||
if (IsStun())
|
||||
return;
|
||||
|
||||
if (IsKnockDown())
|
||||
return;
|
||||
|
||||
if (IsUsingSkill())
|
||||
return;
|
||||
|
||||
if (IsWalking())
|
||||
EndWalking();
|
||||
|
||||
m_isGoing = FALSE;
|
||||
|
||||
if (IsPoly())
|
||||
{
|
||||
InputNormalAttack(fDirRot);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (m_kHorse.IsMounting())
|
||||
{
|
||||
InputComboAttack(fDirRot);
|
||||
}
|
||||
else
|
||||
{
|
||||
InputComboAttack(fDirRot);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void CInstanceBase::NEW_AttackToDestPixelPositionDirection(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
float fDirRot=NEW_GetRotationFromDestPixelPosition(c_rkPPosDst);
|
||||
|
||||
NEW_Attack(fDirRot);
|
||||
}
|
||||
|
||||
bool CInstanceBase::NEW_AttackToDestInstanceDirection(CInstanceBase& rkInstDst, IFlyEventHandler* pkFlyHandler)
|
||||
{
|
||||
return NEW_AttackToDestInstanceDirection(rkInstDst);
|
||||
}
|
||||
|
||||
bool CInstanceBase::NEW_AttackToDestInstanceDirection(CInstanceBase& rkInstDst)
|
||||
{
|
||||
TPixelPosition kPPosDst;
|
||||
rkInstDst.NEW_GetPixelPosition(&kPPosDst);
|
||||
NEW_AttackToDestPixelPositionDirection(kPPosDst);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void CInstanceBase::AttackProcess()
|
||||
{
|
||||
if (!m_GraphicThingInstance.CanCheckAttacking())
|
||||
return;
|
||||
|
||||
CInstanceBase * pkInstLast = NULL;
|
||||
CPythonCharacterManager& rkChrMgr = CPythonCharacterManager::Instance();
|
||||
CPythonCharacterManager::CharacterIterator i = rkChrMgr.CharacterInstanceBegin();
|
||||
while (rkChrMgr.CharacterInstanceEnd()!=i)
|
||||
{
|
||||
CInstanceBase* pkInstEach=*i;
|
||||
++i;
|
||||
|
||||
// 서로간의 InstanceType 비교
|
||||
if (!IsAttackableInstance(*pkInstEach))
|
||||
continue;
|
||||
|
||||
if (pkInstEach!=this)
|
||||
{
|
||||
if (CheckAttacking(*pkInstEach))
|
||||
{
|
||||
pkInstLast=pkInstEach;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (pkInstLast)
|
||||
{
|
||||
m_dwLastDmgActorVID=pkInstLast->GetVirtualID();
|
||||
}
|
||||
}
|
||||
|
||||
void CInstanceBase::InputNormalAttack(float fAtkDirRot)
|
||||
{
|
||||
m_GraphicThingInstance.InputNormalAttackCommand(fAtkDirRot);
|
||||
}
|
||||
|
||||
void CInstanceBase::InputComboAttack(float fAtkDirRot)
|
||||
{
|
||||
m_GraphicThingInstance.InputComboAttackCommand(fAtkDirRot);
|
||||
__ComboProcess();
|
||||
}
|
||||
|
||||
void CInstanceBase::RunNormalAttack(float fAtkDirRot)
|
||||
{
|
||||
EndGoing();
|
||||
m_GraphicThingInstance.NormalAttack(fAtkDirRot);
|
||||
}
|
||||
|
||||
void CInstanceBase::RunComboAttack(float fAtkDirRot, DWORD wMotionIndex)
|
||||
{
|
||||
EndGoing();
|
||||
m_GraphicThingInstance.ComboAttack(wMotionIndex, fAtkDirRot);
|
||||
}
|
||||
|
||||
// 리턴값 TRUE가 무엇인가가 있다
|
||||
BOOL CInstanceBase::CheckAdvancing()
|
||||
{
|
||||
#ifdef __MOVIE_MODE__
|
||||
if (IsMovieMode())
|
||||
return FALSE;
|
||||
#endif
|
||||
if (!__IsMainInstance() && !IsAttacking())
|
||||
{
|
||||
if (IsPC() && IsWalking())
|
||||
{
|
||||
CPythonCharacterManager& rkChrMgr=CPythonCharacterManager::Instance();
|
||||
for(CPythonCharacterManager::CharacterIterator i = rkChrMgr.CharacterInstanceBegin(); i!=rkChrMgr.CharacterInstanceEnd();++i)
|
||||
{
|
||||
CInstanceBase* pkInstEach=*i;
|
||||
if (pkInstEach==this)
|
||||
continue;
|
||||
if (!pkInstEach->IsDoor())
|
||||
continue;
|
||||
|
||||
if (m_GraphicThingInstance.TestActorCollision(pkInstEach->GetGraphicThingInstanceRef()))
|
||||
{
|
||||
BlockMovement();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (m_GraphicThingInstance.CanSkipCollision())
|
||||
{
|
||||
//Tracenf("%x VID %d 충돌 스킵", ELTimer_GetMSec(), GetVirtualID());
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
BOOL bUsingSkill = m_GraphicThingInstance.IsUsingSkill();
|
||||
|
||||
m_dwAdvActorVID = 0;
|
||||
UINT uCollisionCount=0;
|
||||
|
||||
CPythonCharacterManager& rkChrMgr=CPythonCharacterManager::Instance();
|
||||
for(CPythonCharacterManager::CharacterIterator i = rkChrMgr.CharacterInstanceBegin(); i!=rkChrMgr.CharacterInstanceEnd();++i)
|
||||
{
|
||||
CInstanceBase* pkInstEach=*i;
|
||||
if (pkInstEach==this)
|
||||
continue;
|
||||
|
||||
CActorInstance& rkActorSelf=m_GraphicThingInstance;
|
||||
CActorInstance& rkActorEach=pkInstEach->GetGraphicThingInstanceRef();
|
||||
|
||||
//NOTE : Skil을 쓰더라도 Door Type과는 Collision체크 한다.
|
||||
if( bUsingSkill && !rkActorEach.IsDoor() )
|
||||
continue;
|
||||
|
||||
// 앞으로 전진할수 있는가?
|
||||
if (rkActorSelf.TestActorCollision(rkActorEach))
|
||||
{
|
||||
uCollisionCount++;
|
||||
if (uCollisionCount==2)
|
||||
{
|
||||
rkActorSelf.BlockMovement();
|
||||
return TRUE;
|
||||
}
|
||||
rkActorSelf.AdjustDynamicCollisionMovement(&rkActorEach);
|
||||
|
||||
if (rkActorSelf.TestActorCollision(rkActorEach))
|
||||
{
|
||||
rkActorSelf.BlockMovement();
|
||||
return TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
NEW_MoveToDestPixelPositionDirection(NEW_GetDstPixelPositionRef());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 맵속성 체크
|
||||
CPythonBackground& rkBG=CPythonBackground::Instance();
|
||||
const D3DXVECTOR3 & rv3Position = m_GraphicThingInstance.GetPosition();
|
||||
const D3DXVECTOR3 & rv3MoveDirection = m_GraphicThingInstance.GetMovementVectorRef();
|
||||
|
||||
// NOTE : 만약 이동 거리가 크다면 쪼개서 구간 별로 속성을 체크해 본다
|
||||
// 현재 설정해 놓은 10.0f는 임의의 거리 - [levites]
|
||||
int iStep = int(D3DXVec3Length(&rv3MoveDirection) / 10.0f);
|
||||
D3DXVECTOR3 v3CheckStep = rv3MoveDirection / float(iStep);
|
||||
D3DXVECTOR3 v3CheckPosition = rv3Position;
|
||||
for (int j = 0; j < iStep; ++j)
|
||||
{
|
||||
v3CheckPosition += v3CheckStep;
|
||||
|
||||
// Check
|
||||
if (rkBG.isAttrOn(v3CheckPosition.x, -v3CheckPosition.y, CTerrainImpl::ATTRIBUTE_BLOCK))
|
||||
{
|
||||
BlockMovement();
|
||||
//return TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
// Check
|
||||
D3DXVECTOR3 v3NextPosition = rv3Position + rv3MoveDirection;
|
||||
if (rkBG.isAttrOn(v3NextPosition.x, -v3NextPosition.y, CTerrainImpl::ATTRIBUTE_BLOCK))
|
||||
{
|
||||
BlockMovement();
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::CheckAttacking(CInstanceBase& rkInstVictim)
|
||||
{
|
||||
if (IsInSafe())
|
||||
return FALSE;
|
||||
|
||||
if (rkInstVictim.IsInSafe())
|
||||
return FALSE;
|
||||
|
||||
#ifdef __MOVIE_MODE__
|
||||
return FALSE;
|
||||
#endif
|
||||
|
||||
if (!m_GraphicThingInstance.AttackingProcess(rkInstVictim.m_GraphicThingInstance))
|
||||
return FALSE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::isNormalAttacking()
|
||||
{
|
||||
return m_GraphicThingInstance.isNormalAttacking();
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::isComboAttacking()
|
||||
{
|
||||
return m_GraphicThingInstance.isComboAttacking();
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::IsUsingSkill()
|
||||
{
|
||||
return m_GraphicThingInstance.IsUsingSkill();
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::IsUsingMovingSkill()
|
||||
{
|
||||
return m_GraphicThingInstance.IsUsingMovingSkill();
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::CanCancelSkill()
|
||||
{
|
||||
return m_GraphicThingInstance.CanCancelSkill();
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::CanAttackHorseLevel()
|
||||
{
|
||||
if (!IsMountingHorse())
|
||||
return FALSE;
|
||||
|
||||
return m_kHorse.CanAttack();
|
||||
}
|
||||
|
||||
bool CInstanceBase::IsAffect(UINT uAffect)
|
||||
{
|
||||
return m_kAffectFlagContainer.IsSet(uAffect);
|
||||
}
|
||||
|
||||
MOTION_KEY CInstanceBase::GetNormalAttackIndex()
|
||||
{
|
||||
return m_GraphicThingInstance.GetNormalAttackIndex();
|
||||
}
|
||||
|
||||
DWORD CInstanceBase::GetComboIndex()
|
||||
{
|
||||
return m_GraphicThingInstance.GetComboIndex();
|
||||
}
|
||||
|
||||
float CInstanceBase::GetAttackingElapsedTime()
|
||||
{
|
||||
return m_GraphicThingInstance.GetAttackingElapsedTime();
|
||||
}
|
||||
|
||||
void CInstanceBase::ProcessHitting(DWORD dwMotionKey, CInstanceBase * pVictimInstance)
|
||||
{
|
||||
assert(!"-_-" && "CInstanceBase::ProcessHitting");
|
||||
//m_GraphicThingInstance.ProcessSucceedingAttacking(dwMotionKey, pVictimInstance->m_GraphicThingInstance);
|
||||
}
|
||||
|
||||
void CInstanceBase::ProcessHitting(DWORD dwMotionKey, BYTE byEventIndex, CInstanceBase * pVictimInstance)
|
||||
{
|
||||
assert(!"-_-" && "CInstanceBase::ProcessHitting");
|
||||
//m_GraphicThingInstance.ProcessSucceedingAttacking(dwMotionKey, byEventIndex, pVictimInstance->m_GraphicThingInstance);
|
||||
}
|
||||
|
||||
void CInstanceBase::GetBlendingPosition(TPixelPosition * pPixelPosition)
|
||||
{
|
||||
m_GraphicThingInstance.GetBlendingPosition(pPixelPosition);
|
||||
}
|
||||
|
||||
void CInstanceBase::SetBlendingPosition(const TPixelPosition & c_rPixelPosition)
|
||||
{
|
||||
m_GraphicThingInstance.SetBlendingPosition(c_rPixelPosition);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void CInstanceBase::Revive()
|
||||
{
|
||||
m_isGoing=FALSE;
|
||||
m_GraphicThingInstance.Revive();
|
||||
|
||||
__AttachHorseSaddle();
|
||||
}
|
||||
|
||||
void CInstanceBase::Stun()
|
||||
{
|
||||
NEW_Stop();
|
||||
m_GraphicThingInstance.Stun();
|
||||
|
||||
__AttachEffect(EFFECT_STUN);
|
||||
}
|
||||
|
||||
void CInstanceBase::Die()
|
||||
{
|
||||
__DetachHorseSaddle();
|
||||
|
||||
if (IsAffect(AFFECT_SPAWN))
|
||||
__AttachEffect(EFFECT_SPAWN_DISAPPEAR);
|
||||
|
||||
// 2004.07.25.이펙트 안붙는 문제해결
|
||||
////////////////////////////////////////
|
||||
__ClearAffects();
|
||||
////////////////////////////////////////
|
||||
|
||||
OnUnselected();
|
||||
OnUntargeted();
|
||||
|
||||
m_GraphicThingInstance.Die();
|
||||
}
|
||||
|
||||
void CInstanceBase::Hide()
|
||||
{
|
||||
m_GraphicThingInstance.SetAlphaValue(0.0f);
|
||||
m_GraphicThingInstance.BlendAlphaValue(0.0f, 0.1f);
|
||||
}
|
||||
|
||||
void CInstanceBase::Show()
|
||||
{
|
||||
m_GraphicThingInstance.SetAlphaValue(1.0f);
|
||||
m_GraphicThingInstance.BlendAlphaValue(1.0f, 0.1f);
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,17 @@
|
||||
#include "StdAfx.h"
|
||||
#include "InstanceBase.h"
|
||||
|
||||
CActorInstance::IEventHandler& CInstanceBase::GetEventHandlerRef()
|
||||
{
|
||||
return m_GraphicThingInstance.__GetEventHandlerRef();
|
||||
}
|
||||
|
||||
CActorInstance::IEventHandler* CInstanceBase::GetEventHandlerPtr()
|
||||
{
|
||||
return m_GraphicThingInstance.__GetEventHandlerPtr();
|
||||
}
|
||||
|
||||
void CInstanceBase::SetEventHandler(CActorInstance::IEventHandler* pkEventHandler)
|
||||
{
|
||||
m_GraphicThingInstance.SetEventHandler(pkEventHandler);
|
||||
}
|
||||
@@ -0,0 +1,165 @@
|
||||
#include "StdAfx.h"
|
||||
#include "InstanceBase.h"
|
||||
#include "AbstractPlayer.h"
|
||||
#include "../GameLib/ActorInstance.h"
|
||||
|
||||
const int c_iFishingRotStep = 8;
|
||||
const float c_fFishingDistance = 600.0f;
|
||||
|
||||
void CInstanceBase::SetMotionMode(int iMotionMode)
|
||||
{
|
||||
m_GraphicThingInstance.SetMotionMode(iMotionMode);
|
||||
}
|
||||
|
||||
int CInstanceBase::GetMotionMode(DWORD dwMotionIndex)
|
||||
{
|
||||
return m_GraphicThingInstance.GetMotionMode();
|
||||
}
|
||||
|
||||
void CInstanceBase::SetLoopMotion(WORD wMotion, float fBlendTime/* =0.1f */, float fSpeedRatio)
|
||||
{
|
||||
m_GraphicThingInstance.SetLoopMotion(wMotion, fBlendTime, fSpeedRatio);
|
||||
}
|
||||
|
||||
void CInstanceBase::PushOnceMotion(WORD wMotion, float fBlendTime, float fSpeedRatio)
|
||||
{
|
||||
m_GraphicThingInstance.PushOnceMotion(wMotion, fBlendTime, fSpeedRatio);
|
||||
}
|
||||
|
||||
void CInstanceBase::PushLoopMotion(WORD wMotion, float fBlendTime, float fSpeedRatio)
|
||||
{
|
||||
m_GraphicThingInstance.PushLoopMotion(wMotion, fBlendTime, fSpeedRatio);
|
||||
}
|
||||
|
||||
void CInstanceBase::ResetLocalTime()
|
||||
{
|
||||
m_GraphicThingInstance.ResetLocalTime();
|
||||
}
|
||||
|
||||
void CInstanceBase::SetEndStopMotion()
|
||||
{
|
||||
m_GraphicThingInstance.SetEndStopMotion();
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::isLock()
|
||||
{
|
||||
return m_GraphicThingInstance.isLock();
|
||||
}
|
||||
|
||||
void CInstanceBase::StartFishing(float frot)
|
||||
{
|
||||
BlendRotation(frot);
|
||||
|
||||
const TPixelPosition& c_rkPPosCur=m_GraphicThingInstance.NEW_GetCurPixelPositionRef();
|
||||
float fRot = m_GraphicThingInstance.GetTargetRotation();
|
||||
//float fPlainCoordRot=ELRightCoord_ConvertToPlainCoordDegree(fRightCoordRot);
|
||||
|
||||
TPixelPosition kPPosFishing;
|
||||
ELPlainCoord_GetRotatedPixelPosition(c_rkPPosCur.x, c_rkPPosCur.y, c_fFishingDistance, fRot, &kPPosFishing.x, &kPPosFishing.y);
|
||||
if (!__Background_GetWaterHeight(kPPosFishing, &kPPosFishing.z))
|
||||
kPPosFishing.z=c_rkPPosCur.z;
|
||||
|
||||
D3DXVECTOR3 v3Fishing;
|
||||
PixelPositionToD3DXVECTOR3(kPPosFishing, &v3Fishing);
|
||||
m_GraphicThingInstance.SetFishingPosition(v3Fishing);
|
||||
|
||||
PushOnceMotion(CRaceMotionData::NAME_FISHING_THROW);
|
||||
PushLoopMotion(CRaceMotionData::NAME_FISHING_WAIT);
|
||||
}
|
||||
void CInstanceBase::StopFishing()
|
||||
{
|
||||
m_GraphicThingInstance.InterceptOnceMotion(CRaceMotionData::NAME_FISHING_STOP);
|
||||
PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
void CInstanceBase::ReactFishing()
|
||||
{
|
||||
PushOnceMotion(CRaceMotionData::NAME_FISHING_REACT);
|
||||
PushLoopMotion(CRaceMotionData::NAME_FISHING_WAIT);
|
||||
}
|
||||
void CInstanceBase::CatchSuccess()
|
||||
{
|
||||
m_GraphicThingInstance.InterceptOnceMotion(CRaceMotionData::NAME_FISHING_CATCH);
|
||||
PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
void CInstanceBase::CatchFail()
|
||||
{
|
||||
m_GraphicThingInstance.InterceptOnceMotion(CRaceMotionData::NAME_FISHING_FAIL);
|
||||
PushLoopMotion(CRaceMotionData::NAME_WAIT);
|
||||
}
|
||||
|
||||
BOOL CInstanceBase::GetFishingRot(int * pirot)
|
||||
{
|
||||
const TPixelPosition& c_rkPPosCur=m_GraphicThingInstance.NEW_GetCurPixelPositionRef();
|
||||
float fCharacterRot = m_GraphicThingInstance.GetRotation();
|
||||
|
||||
//float frot = fCharacterRot;
|
||||
|
||||
for (float fRot=0.0f; fRot<=180.0f; fRot+=10.0f)
|
||||
{
|
||||
TPixelPosition kPPosFishingRight;
|
||||
ELPlainCoord_GetRotatedPixelPosition(c_rkPPosCur.x, c_rkPPosCur.y, c_fFishingDistance, fCharacterRot+fRot, &kPPosFishingRight.x, &kPPosFishingRight.y);
|
||||
if (__Background_IsWaterPixelPosition(kPPosFishingRight))
|
||||
{
|
||||
*pirot = fCharacterRot+fRot;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
TPixelPosition kPPosFishingLeft;
|
||||
ELPlainCoord_GetRotatedPixelPosition(c_rkPPosCur.x, c_rkPPosCur.y, c_fFishingDistance, fCharacterRot-fRot, &kPPosFishingLeft.x, &kPPosFishingLeft.y);
|
||||
if (__Background_IsWaterPixelPosition(kPPosFishingLeft))
|
||||
{
|
||||
*pirot = fCharacterRot-fRot;
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
void CInstanceBase::__EnableChangingTCPState()
|
||||
{
|
||||
m_bEnableTCPState = TRUE;
|
||||
}
|
||||
|
||||
void CInstanceBase::__DisableChangingTCPState()
|
||||
{
|
||||
m_bEnableTCPState = FALSE;
|
||||
}
|
||||
|
||||
void CInstanceBase::ActDualEmotion(CInstanceBase & rkDstInst, WORD wMotionNumber1, WORD wMotionNumber2)
|
||||
{
|
||||
if (!IsWaiting())
|
||||
{
|
||||
m_GraphicThingInstance.SetLoopMotion(CRaceMotionData::NAME_WAIT, 0.05f);
|
||||
}
|
||||
if (!rkDstInst.IsWaiting())
|
||||
{
|
||||
rkDstInst.m_GraphicThingInstance.SetLoopMotion(CRaceMotionData::NAME_WAIT, 0.05f);
|
||||
}
|
||||
|
||||
const float c_fEmotionDistance = 100.0f;
|
||||
const TPixelPosition & c_rMainPosition = NEW_GetCurPixelPositionRef();
|
||||
const TPixelPosition & c_rTargetPosition = rkDstInst.NEW_GetCurPixelPositionRef();
|
||||
TPixelPosition kDirection = c_rMainPosition - c_rTargetPosition;
|
||||
float fDistance = sqrtf((kDirection.x*kDirection.x) + (kDirection.y*kDirection.y));
|
||||
TPixelPosition kDstPosition;
|
||||
kDstPosition.x = c_rTargetPosition.x + (kDirection.x/fDistance)*c_fEmotionDistance;
|
||||
kDstPosition.y = c_rTargetPosition.y + (kDirection.y/fDistance)*c_fEmotionDistance;
|
||||
|
||||
DWORD dwCurTime = ELTimer_GetServerMSec() + 500;
|
||||
PushTCPStateExpanded(dwCurTime, kDstPosition, 0.0f, FUNC_EMOTION, MAKELONG(wMotionNumber1, wMotionNumber2), rkDstInst.GetVirtualID());
|
||||
|
||||
__DisableChangingTCPState();
|
||||
rkDstInst.__DisableChangingTCPState();
|
||||
|
||||
if (__IsMainInstance() || rkDstInst.__IsMainInstance())
|
||||
{
|
||||
IAbstractPlayer & rPlayer=IAbstractPlayer::GetSingleton();
|
||||
rPlayer.StartEmotionProcess();
|
||||
}
|
||||
}
|
||||
|
||||
void CInstanceBase::ActEmotion(DWORD dwMotionNumber)
|
||||
{
|
||||
PushOnceMotion(dwMotionNumber);
|
||||
}
|
||||
@@ -0,0 +1,93 @@
|
||||
#include "StdAfx.h"
|
||||
#include "InstanceBase.h"
|
||||
#include "PythonBackground.h"
|
||||
|
||||
|
||||
|
||||
|
||||
void CInstanceBase::SCRIPT_SetPixelPosition(float fx, float fy)
|
||||
{
|
||||
float fz = __GetBackgroundHeight(fx, fy);
|
||||
NEW_SetPixelPosition(TPixelPosition(fx, fy, fz));
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_SetPixelPosition(const TPixelPosition & c_rPixelPosition)
|
||||
{
|
||||
m_GraphicThingInstance.SetCurPixelPosition(c_rPixelPosition);
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_GetPixelPosition(TPixelPosition * pPixelPosition)
|
||||
{
|
||||
*pPixelPosition=m_GraphicThingInstance.NEW_GetCurPixelPositionRef();
|
||||
}
|
||||
|
||||
void CInstanceBase::SetRotation(float fRotation)
|
||||
{
|
||||
m_GraphicThingInstance.SetRotation(fRotation);
|
||||
}
|
||||
|
||||
void CInstanceBase::BlendRotation(float fRotation, float fBlendTime)
|
||||
{
|
||||
m_GraphicThingInstance.BlendRotation(fRotation, fBlendTime);
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_LookAtFlyTarget()
|
||||
{
|
||||
m_GraphicThingInstance.LookAtFlyTarget();
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_LookAtDestPixelPosition(const TPixelPosition& c_rkPPosDst)
|
||||
{
|
||||
m_GraphicThingInstance.LookAt(c_rkPPosDst.x, -c_rkPPosDst.y);
|
||||
}
|
||||
|
||||
void CInstanceBase::NEW_LookAtDestInstance(CInstanceBase& rkInstDst)
|
||||
{
|
||||
m_GraphicThingInstance.LookAt(&rkInstDst.m_GraphicThingInstance);
|
||||
// Tracenf("LookAt %f", m_GraphicThingInstance.GetTargetRotation());
|
||||
}
|
||||
|
||||
float CInstanceBase::GetRotation()
|
||||
{
|
||||
return m_GraphicThingInstance.GetRotation();
|
||||
}
|
||||
|
||||
float CInstanceBase::GetAdvancingRotation()
|
||||
{
|
||||
return m_GraphicThingInstance.GetAdvancingRotation();
|
||||
}
|
||||
|
||||
void CInstanceBase::SetDirection(int dir)
|
||||
{
|
||||
float fDegree = GetDegreeFromDirection(dir);
|
||||
SetRotation(fDegree);
|
||||
SetAdvancingRotation(fDegree);
|
||||
}
|
||||
|
||||
void CInstanceBase::BlendDirection(int dir, float blendTime)
|
||||
{
|
||||
m_GraphicThingInstance.BlendRotation(GetDegreeFromDirection(dir), blendTime);
|
||||
}
|
||||
|
||||
float CInstanceBase::GetDegreeFromDirection(int dir)
|
||||
{
|
||||
if (dir < 0)
|
||||
return 0.0f;
|
||||
|
||||
if (dir >= DIR_MAX_NUM)
|
||||
return 0.0f;
|
||||
|
||||
static float s_dirRot[DIR_MAX_NUM]=
|
||||
{
|
||||
+45.0f * 4,
|
||||
+45.0f * 3,
|
||||
+45.0f * 2,
|
||||
+45.0f,
|
||||
+0.0f,
|
||||
360.0f-45.0f,
|
||||
360.0f-45.0f * 2,
|
||||
360.0f-45.0f * 3,
|
||||
};
|
||||
|
||||
return s_dirRot[dir];
|
||||
}
|
||||
@@ -2050,7 +2050,7 @@ typedef struct SPlayerSkill
|
||||
{
|
||||
BYTE bMasterType;
|
||||
BYTE bLevel;
|
||||
time_t tNextRead;
|
||||
LONG tNextRead; // PORT: time_t is 32-bit under 40250's _USE_32BIT_TIME_T; 64-bit on LP64 hosts
|
||||
} TPlayerSkill;
|
||||
|
||||
typedef struct packet_skill_level_new
|
||||
@@ -2058,6 +2058,7 @@ typedef struct packet_skill_level_new
|
||||
BYTE bHeader;
|
||||
TPlayerSkill skills[SKILL_MAX_NUM];
|
||||
} TPacketGCSkillLevelNew;
|
||||
static_assert(sizeof(TPacketGCSkillLevelNew) == 1 + SKILL_MAX_NUM * 6);
|
||||
|
||||
// fly
|
||||
typedef struct packet_fly
|
||||
|
||||
@@ -302,15 +302,84 @@ typedef enum _D3DTEXTURESTAGESTATETYPE
|
||||
D3DTSS_FORCE_DWORD = 0x7fffffff,
|
||||
} D3DTEXTURESTAGESTATETYPE;
|
||||
|
||||
// D3D8 texture-stage arguments and operations used by the character renderer.
|
||||
// D3D8 texture-stage arguments (d3d8types.h D3DTA_*).
|
||||
enum : DWORD {
|
||||
D3DTA_DIFFUSE = 0,
|
||||
D3DTA_CURRENT = 1,
|
||||
D3DTA_TEXTURE = 2,
|
||||
D3DTA_SELECTMASK = 0x0000000f,
|
||||
D3DTA_DIFFUSE = 0x00000000,
|
||||
D3DTA_CURRENT = 0x00000001,
|
||||
D3DTA_TEXTURE = 0x00000002,
|
||||
D3DTA_TFACTOR = 0x00000003,
|
||||
D3DTA_SPECULAR = 0x00000004,
|
||||
D3DTA_TEMP = 0x00000005,
|
||||
D3DTA_COMPLEMENT = 0x00000010,
|
||||
D3DTA_ALPHAREPLICATE = 0x00000020,
|
||||
};
|
||||
|
||||
typedef enum _D3DTEXTUREOP {
|
||||
D3DTOP_DISABLE = 1,
|
||||
D3DTOP_SELECTARG1 = 2,
|
||||
D3DTOP_SELECTARG2 = 3,
|
||||
D3DTOP_MODULATE = 4,
|
||||
};
|
||||
D3DTOP_MODULATE2X = 5,
|
||||
D3DTOP_MODULATE4X = 6,
|
||||
D3DTOP_ADD = 7,
|
||||
D3DTOP_ADDSIGNED = 8,
|
||||
D3DTOP_ADDSIGNED2X = 9,
|
||||
D3DTOP_SUBTRACT = 10,
|
||||
D3DTOP_ADDSMOOTH = 11,
|
||||
D3DTOP_BLENDDIFFUSEALPHA = 12,
|
||||
D3DTOP_BLENDTEXTUREALPHA = 13,
|
||||
D3DTOP_BLENDFACTORALPHA = 14,
|
||||
D3DTOP_BLENDTEXTUREALPHAPM = 15,
|
||||
D3DTOP_BLENDCURRENTALPHA = 16,
|
||||
D3DTOP_PREMODULATE = 17,
|
||||
D3DTOP_MODULATEALPHA_ADDCOLOR = 18,
|
||||
D3DTOP_MODULATECOLOR_ADDALPHA = 19,
|
||||
D3DTOP_MODULATEINVALPHA_ADDCOLOR = 20,
|
||||
D3DTOP_MODULATEINVCOLOR_ADDALPHA = 21,
|
||||
D3DTOP_BUMPENVMAP = 22,
|
||||
D3DTOP_BUMPENVMAPLUMINANCE = 23,
|
||||
D3DTOP_DOTPRODUCT3 = 24,
|
||||
D3DTOP_MULTIPLYADD = 25,
|
||||
D3DTOP_LERP = 26,
|
||||
D3DTOP_FORCE_DWORD = 0x7fffffff,
|
||||
} D3DTEXTUREOP;
|
||||
|
||||
typedef enum _D3DCMPFUNC {
|
||||
D3DCMP_NEVER = 1,
|
||||
D3DCMP_LESS = 2,
|
||||
D3DCMP_EQUAL = 3,
|
||||
D3DCMP_LESSEQUAL = 4,
|
||||
D3DCMP_GREATER = 5,
|
||||
D3DCMP_NOTEQUAL = 6,
|
||||
D3DCMP_GREATEREQUAL = 7,
|
||||
D3DCMP_ALWAYS = 8,
|
||||
D3DCMP_FORCE_DWORD = 0x7fffffff,
|
||||
} D3DCMPFUNC;
|
||||
|
||||
typedef enum _D3DBLEND {
|
||||
D3DBLEND_ZERO = 1,
|
||||
D3DBLEND_ONE = 2,
|
||||
D3DBLEND_SRCCOLOR = 3,
|
||||
D3DBLEND_INVSRCCOLOR = 4,
|
||||
D3DBLEND_SRCALPHA = 5,
|
||||
D3DBLEND_INVSRCALPHA = 6,
|
||||
D3DBLEND_DESTALPHA = 7,
|
||||
D3DBLEND_INVDESTALPHA = 8,
|
||||
D3DBLEND_DESTCOLOR = 9,
|
||||
D3DBLEND_INVDESTCOLOR = 10,
|
||||
D3DBLEND_SRCALPHASAT = 11,
|
||||
D3DBLEND_BOTHSRCALPHA = 12,
|
||||
D3DBLEND_BOTHINVSRCALPHA = 13,
|
||||
D3DBLEND_FORCE_DWORD = 0x7fffffff,
|
||||
} D3DBLEND;
|
||||
|
||||
typedef enum _D3DCULL {
|
||||
D3DCULL_NONE = 1,
|
||||
D3DCULL_CW = 2,
|
||||
D3DCULL_CCW = 3,
|
||||
D3DCULL_FORCE_DWORD = 0x7fffffff,
|
||||
} D3DCULL;
|
||||
|
||||
#define D3DTS_WORLDMATRIX(index) (D3DTRANSFORMSTATETYPE)(index + 256)
|
||||
#define D3DTS_WORLD D3DTS_WORLDMATRIX(0)
|
||||
|
||||
@@ -404,7 +404,8 @@ bool FakeLoginServer::ServeGame(Connection& c, int index)
|
||||
return Fail(name + ": CG_CHARACTER_SELECT picks an empty slot");
|
||||
Event(name + ":select");
|
||||
|
||||
// CInputDB::PlayerLoad: SetPhase(PHASE_LOADING), CHARACTER::MainCharacterPacket, PointsPacket.
|
||||
// CInputDB::PlayerLoad: SetPhase(PHASE_LOADING), CHARACTER::MainCharacterPacket, PointsPacket,
|
||||
// SkillLevelPacket (1531 bytes; guards the client's 32-bit time_t TPlayerSkill layout).
|
||||
auto main = zeroed<GCMainCharacter>();
|
||||
main.header = HDR_GC_MAIN_CHARACTER;
|
||||
main.vid = kMainVID;
|
||||
@@ -416,7 +417,9 @@ bool FakeLoginServer::ServeGame(Connection& c, int index)
|
||||
auto points = zeroed<GCPoints>();
|
||||
points.header = HDR_GC_CHARACTER_POINTS;
|
||||
points.points[1] = 10; // POINT_LEVEL
|
||||
if (!c.Phase(PHASE_LOADING) || !c.Send(main) || !c.Send(points))
|
||||
auto skill = zeroed<GCSkillLevel>();
|
||||
skill.header = HDR_GC_SKILL_LEVEL;
|
||||
if (!c.Phase(PHASE_LOADING) || !c.Send(main) || !c.Send(points) || !c.Send(skill))
|
||||
return Fail(name + ": send loading packets");
|
||||
|
||||
// The client answers the main character with its version (CInputProcessor::Version).
|
||||
@@ -448,7 +451,7 @@ bool FakeLoginServer::ServeGame(Connection& c, int index)
|
||||
actor.vid = kMainVID;
|
||||
actor.x = kX;
|
||||
actor.y = kY;
|
||||
actor.type = 0; // CHAR_TYPE_PC
|
||||
actor.type = 6; // CHAR_TYPE_PC (common/length.h ECharType)
|
||||
actor.race = 0; // warrior male
|
||||
actor.moving_speed = 100;
|
||||
actor.attack_speed = 100;
|
||||
|
||||
@@ -44,6 +44,9 @@
|
||||
#include "GameLib/RaceManager.h"
|
||||
#include "GameLib/RaceData.h"
|
||||
#include "GameLib/RaceMotionData.h"
|
||||
#include "UserInterface/StdAfx.h"
|
||||
#include "UserInterface/PythonCharacterManager.h"
|
||||
#include "UserInterface/InstanceBase.h"
|
||||
#include "port_login_flow_server.h"
|
||||
|
||||
#include <memory>
|
||||
@@ -305,6 +308,13 @@ int main(int argc, char** argv)
|
||||
CHECK(CRaceManager::Instance().GetRaceDataPointer(0, &race) && race &&
|
||||
race->GetMotionVectorPointer(CRaceMotionData::MODE_GENERAL, CRaceMotionData::NAME_WAIT, &waits) &&
|
||||
waits && !waits->empty());
|
||||
// (批次 2V2-d) GC_CHARACTER_ADD for the player's own VID went through RecvCharacterAppendPacket and
|
||||
// CNetworkActorManager into CPythonCharacterManager: the main instance exists and SetRace ran on it
|
||||
// (offline the fake server sends a warrior, race 0), and CHAR_ADDITIONAL_INFO found the actor.
|
||||
CInstanceBase* main_instance = CPythonCharacterManager::Instance().GetMainInstancePtr();
|
||||
CHECK(main_instance != nullptr);
|
||||
CHECK(live || (main_instance && main_instance->GetRace() == 0));
|
||||
CHECK(count_syserr("TPacketGCCharacterAdditionalInfo") == 0);
|
||||
}
|
||||
if (server)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user