mirror of
https://foundry.openuru.org/gitblit/r/CWE-ou-minkata.git
synced 2025-07-21 04:39:45 +00:00
Hoist MOULOpenSourceClientPlugin/Plasma20/* to top level
to match H'uru layout and make patching/cherry-picking easier.
This commit is contained in:
610
Sources/Plasma/PubUtilLib/plNetClient/plLinkEffectsMgr.cpp
Normal file
610
Sources/Plasma/PubUtilLib/plNetClient/plLinkEffectsMgr.cpp
Normal file
@ -0,0 +1,610 @@
|
||||
/*==LICENSE==*
|
||||
|
||||
CyanWorlds.com Engine - MMOG client, server and tools
|
||||
Copyright (C) 2011 Cyan Worlds, Inc.
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Additional permissions under GNU GPL version 3 section 7
|
||||
|
||||
If you modify this Program, or any covered work, by linking or
|
||||
combining it with any of RAD Game Tools Bink SDK, Autodesk 3ds Max SDK,
|
||||
NVIDIA PhysX SDK, Microsoft DirectX SDK, OpenSSL library, Independent
|
||||
JPEG Group JPEG library, Microsoft Windows Media SDK, or Apple QuickTime SDK
|
||||
(or a modified version of those libraries),
|
||||
containing parts covered by the terms of the Bink SDK EULA, 3ds Max EULA,
|
||||
PhysX SDK EULA, DirectX SDK EULA, OpenSSL and SSLeay licenses, IJG
|
||||
JPEG Library README, Windows Media SDK EULA, or QuickTime SDK EULA, the
|
||||
licensors of this Program grant you additional
|
||||
permission to convey the resulting work. Corresponding Source for a
|
||||
non-source form of such a combination shall include the source code for
|
||||
the parts of OpenSSL and IJG JPEG Library used as well as that of the covered
|
||||
work.
|
||||
|
||||
You can contact Cyan Worlds, Inc. by email legal@cyan.com
|
||||
or by snail mail at:
|
||||
Cyan Worlds, Inc.
|
||||
14617 N Newport Hwy
|
||||
Mead, WA 99021
|
||||
|
||||
*==LICENSE==*/
|
||||
#include "hsTypes.h"
|
||||
#include "../pnKeyedObject/plKey.h"
|
||||
#include "hsTemplates.h"
|
||||
#include "hsStream.h"
|
||||
#include "plLinkEffectsMgr.h"
|
||||
#include "../pnMessage/plEventCallbackMsg.h"
|
||||
#include "../pnMessage/plTimeMsg.h"
|
||||
#include "../pnMessage/plPlayerPageMsg.h"
|
||||
#include "../plMessage/plLinkToAgeMsg.h"
|
||||
#include "../plMessage/plTransitionMsg.h"
|
||||
#include "plgDispatch.h"
|
||||
#include "hsResMgr.h"
|
||||
#include "hsTimer.h"
|
||||
#include "../pnNetCommon/plNetApp.h"
|
||||
#include "../plNetClient/plNetClientMgr.h"
|
||||
#include "../pnSceneObject/plSceneObject.h"
|
||||
#include "../plNetTransport/plNetTransportMember.h"
|
||||
#include "../plVault/plVault.h"
|
||||
#include "../plNetClient/plNetLinkingMgr.h"
|
||||
#include "../plAgeLoader/plAgeLoader.h"
|
||||
#include "../pnSceneObject/plCoordinateInterface.h"
|
||||
#include "../pnMessage/plWarpMsg.h"
|
||||
#include "../pnKeyedObject/plFixedKey.h"
|
||||
|
||||
// chronicle var
|
||||
#define kCleftSolved L"CleftSolved"
|
||||
|
||||
#include "../plAvatar/plArmatureMod.h"
|
||||
#include "../plAvatar/plAvatarTasks.h"
|
||||
#include "../plAvatar/plAGAnim.h"
|
||||
#include "../plMessage/plAvatarMsg.h"
|
||||
#include "../plMessage/plLoadAgeMsg.h"
|
||||
|
||||
plLinkEffectsMgr::plLinkEffectsMgr()
|
||||
{
|
||||
}
|
||||
|
||||
plLinkEffectsMgr::~plLinkEffectsMgr()
|
||||
{
|
||||
int i;
|
||||
for( i = 0; i < fLinks.GetCount(); i++ )
|
||||
{
|
||||
hsRefCnt_SafeUnRef(fLinks[i]);
|
||||
}
|
||||
for( i = 0; i < fWaitlist.GetCount(); i++ )
|
||||
{
|
||||
hsRefCnt_SafeUnRef(fWaitlist[i]);
|
||||
}
|
||||
for( i = 0; i < fDeadlist.GetCount(); i++ )
|
||||
{
|
||||
hsRefCnt_SafeUnRef(fDeadlist[i]);
|
||||
}
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::Init()
|
||||
{
|
||||
plgDispatch::Dispatch()->RegisterForExactType(plPlayerPageMsg::Index(), GetKey());
|
||||
plgDispatch::Dispatch()->RegisterForExactType(plPseudoLinkEffectMsg::Index(), GetKey());
|
||||
}
|
||||
|
||||
plLinkEffectsTriggerMsg *plLinkEffectsMgr::IFindLinkTriggerMsg(plKey linkKey)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < fLinks.GetCount(); i++)
|
||||
{
|
||||
if (fLinks[i]->GetLinkKey() == linkKey)
|
||||
return fLinks[i];
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::IAddLink(plLinkEffectsTriggerMsg *msg)
|
||||
{
|
||||
hsRefCnt_SafeRef(msg);
|
||||
fLinks.Append(msg);
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::IAddWait(plLinkEffectsTriggerMsg *msg)
|
||||
{
|
||||
hsRefCnt_SafeRef(msg);
|
||||
fWaitlist.Append(msg);
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::IAddDead(plLinkEffectsTriggerMsg *msg)
|
||||
{
|
||||
hsRefCnt_SafeRef(msg);
|
||||
fDeadlist.Append(msg);
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::IAddPsuedo(plPseudoLinkEffectMsg *msg)
|
||||
{
|
||||
hsRefCnt_SafeRef(msg);
|
||||
fPseudolist.Append(msg);
|
||||
}
|
||||
|
||||
hsBool plLinkEffectsMgr::IHuntWaitlist(plLinkEffectsTriggerMsg *msg)
|
||||
{
|
||||
int i;
|
||||
hsBool found = false;
|
||||
for (i = fWaitlist.GetCount() - 1; i >= 0; i--)
|
||||
{
|
||||
if (fWaitlist[i] == msg)
|
||||
{
|
||||
found = true;
|
||||
hsRefCnt_SafeUnRef(fWaitlist[i]);
|
||||
fWaitlist.Remove(i);
|
||||
plNetApp::GetInstance()->DebugMsg("Received backup LinkEffectsTriggerMsg. Never got remote trigger!\n");
|
||||
}
|
||||
}
|
||||
|
||||
return found || IHuntWaitlist(msg->GetLinkKey());
|
||||
}
|
||||
|
||||
hsBool plLinkEffectsMgr::IHuntWaitlist(plKey linkKey)
|
||||
{
|
||||
int i;
|
||||
hsBool found = false;
|
||||
for (i = fWaitlist.GetCount() - 1; i >= 0; i--)
|
||||
{
|
||||
if (fWaitlist[i]->GetLinkKey() == linkKey)
|
||||
{
|
||||
found = true;
|
||||
IAddDead(fWaitlist[i]);
|
||||
|
||||
hsRefCnt_SafeUnRef(fWaitlist[i]);
|
||||
fWaitlist.Remove(i);
|
||||
plNetApp::GetInstance()->DebugMsg("Received remote LinkEffectsTriggerMsg. Awaiting backup.\n");
|
||||
}
|
||||
}
|
||||
|
||||
return found;
|
||||
}
|
||||
|
||||
hsBool plLinkEffectsMgr::IHuntDeadlist(plLinkEffectsTriggerMsg *msg)
|
||||
{
|
||||
int i;
|
||||
hsBool found = false;
|
||||
for (i = fDeadlist.GetCount() - 1; i >= 0; i--)
|
||||
{
|
||||
if (fDeadlist[i] == msg)
|
||||
{
|
||||
found = true;
|
||||
hsRefCnt_SafeUnRef(fDeadlist[i]);
|
||||
fDeadlist.Remove(i);
|
||||
plNetApp::GetInstance()->DebugMsg("Received backup LinkEffectsTriggerMsg. Cleanly ignoring since we received remote trigger.\n");
|
||||
}
|
||||
}
|
||||
|
||||
return found;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void plLinkEffectsMgr::ISendAllReadyCallbacks()
|
||||
{
|
||||
int i;
|
||||
for (i = fLinks.GetCount() - 1; i >= 0; i--)
|
||||
{
|
||||
if (fLinks[i]->fEffects <= 0)
|
||||
{
|
||||
if (fLinks[i]->IsLeavingAge())
|
||||
{
|
||||
if (fLinks[i]->GetLinkKey() == plNetClientApp::GetInstance()->GetLocalPlayerKey())
|
||||
{
|
||||
plLinkOutUnloadMsg* lam = TRACKED_NEW plLinkOutUnloadMsg; // derived from LoadAgeMsg
|
||||
lam->SetAgeFilename( NetCommGetAge()->ageDatasetName );
|
||||
lam->AddReceiver(plNetClientMgr::GetInstance()->GetKey());
|
||||
lam->SetPlayerID(plNetClientMgr::GetInstance()->GetPlayerID());
|
||||
lam->Send();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
plLinkInDoneMsg* lid = TRACKED_NEW plLinkInDoneMsg;
|
||||
lid->AddReceiver(fLinks[i]->GetLinkKey());
|
||||
lid->SetBCastFlag(plMessage::kPropagateToModifiers);
|
||||
lid->Send();
|
||||
|
||||
if (fLinks[i]->GetLinkKey() == plNetClientApp::GetInstance()->GetLocalPlayerKey())
|
||||
{
|
||||
plLinkInDoneMsg* lid = TRACKED_NEW plLinkInDoneMsg;
|
||||
lid->AddReceiver(plNetClientMgr::GetInstance()->GetKey());
|
||||
lid->Send();
|
||||
}
|
||||
}
|
||||
|
||||
hsRefCnt_SafeUnRef(fLinks[i]);
|
||||
fLinks.Remove(i);
|
||||
|
||||
hsStatusMessage("Done - removing link FX msg\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
hsBool plLinkEffectsMgr::MsgReceive(plMessage *msg)
|
||||
{
|
||||
plNetClientMgr* nc = plNetClientMgr::GetInstance();
|
||||
plNetLinkingMgr* lm = plNetLinkingMgr::GetInstance();
|
||||
|
||||
plPseudoLinkEffectMsg* pSeudoMsg = plPseudoLinkEffectMsg::ConvertNoRef(msg);
|
||||
if (pSeudoMsg)
|
||||
{
|
||||
// verify valid avatar and "link" objects
|
||||
if (!pSeudoMsg->fAvatarKey)
|
||||
return true;
|
||||
if (!pSeudoMsg->fLinkObjKey)
|
||||
return true;
|
||||
if (!pSeudoMsg->fLinkObjKey->ObjectIsLoaded())
|
||||
return true;
|
||||
if (!plNetClientMgr::GetInstance()->IsAPlayerKey(pSeudoMsg->fAvatarKey))
|
||||
return true;
|
||||
// send the trigger message to the avatar...
|
||||
plPseudoLinkAnimTriggerMsg* pMsg = TRACKED_NEW plPseudoLinkAnimTriggerMsg(true, pSeudoMsg->fAvatarKey);
|
||||
pMsg->SetSender(GetKey());
|
||||
pMsg->Send();
|
||||
IAddPsuedo(pSeudoMsg);
|
||||
}
|
||||
|
||||
plPseudoLinkAnimCallbackMsg* pSeudoCallback = plPseudoLinkAnimCallbackMsg::ConvertNoRef(msg);
|
||||
if (pSeudoCallback)
|
||||
{
|
||||
// warp the avatar to his new position
|
||||
plPseudoLinkEffectMsg* pMsg = IFindPseudo(pSeudoCallback->fAvatarKey);
|
||||
if (pMsg)
|
||||
{
|
||||
plSceneObject* pObj = plSceneObject::ConvertNoRef(pMsg->fLinkObjKey->ObjectIsLoaded());
|
||||
if (pObj && pObj->GetCoordinateInterface())
|
||||
{
|
||||
hsMatrix44 mat = pObj->GetCoordinateInterface()->GetLocalToWorld();
|
||||
// create message
|
||||
plWarpMsg* pMsg = TRACKED_NEW plWarpMsg(mat);
|
||||
pMsg->SetWarpFlags(plWarpMsg::kFlushTransform);
|
||||
pMsg->AddReceiver(pSeudoCallback->fAvatarKey);
|
||||
plUoid U(kVirtualCamera1_KEY);
|
||||
plKey pCamKey = hsgResMgr::ResMgr()->FindKey(U);
|
||||
if (pCamKey)
|
||||
{
|
||||
pMsg->AddReceiver(pCamKey);
|
||||
}
|
||||
plgDispatch::MsgSend( pMsg ); // whoosh... off it goes
|
||||
// now make him re-appear
|
||||
plPseudoLinkAnimTriggerMsg* pTrigMsg = TRACKED_NEW plPseudoLinkAnimTriggerMsg(false, pSeudoCallback->fAvatarKey);
|
||||
pTrigMsg->SetSender(GetKey());
|
||||
pTrigMsg->Send();
|
||||
IRemovePseudo(pSeudoCallback->fAvatarKey);
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
plLinkEffectsTriggerPrepMsg *tpMsg = plLinkEffectsTriggerPrepMsg::ConvertNoRef(msg);
|
||||
if (tpMsg)
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("Received LinkEffectsTriggerPREPMsg\n");
|
||||
IAddWait(tpMsg->GetTrigger());
|
||||
plLinkEffectPrepBCMsg *bcpMsg = TRACKED_NEW plLinkEffectPrepBCMsg;
|
||||
bcpMsg->fLeavingAge = tpMsg->fLeavingAge;
|
||||
bcpMsg->fLinkKey = tpMsg->fLinkKey;
|
||||
bcpMsg->Send();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
plLinkEffectsTriggerMsg* pTriggerMsg = plLinkEffectsTriggerMsg::ConvertNoRef(msg);
|
||||
if (pTriggerMsg)
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("Received LinkEffectsTriggerMsg, local=%d, linkingIn=%d, stealth=%d",
|
||||
!msg->HasBCastFlag(plMessage::kNetNonLocal),
|
||||
!pTriggerMsg->IsLeavingAge(), pTriggerMsg->GetInvisLevel());
|
||||
|
||||
plKey linkKey = pTriggerMsg->GetLinkKey();
|
||||
if (linkKey == nil)
|
||||
return true;
|
||||
|
||||
if ((linkKey != nc->GetLocalPlayerKey()) &&
|
||||
(!pTriggerMsg->IsLeavingAge()))
|
||||
{
|
||||
if (IHuntDeadlist(pTriggerMsg)) // Just an obselete safety trigger
|
||||
return true;
|
||||
|
||||
if (!IHuntWaitlist(pTriggerMsg))
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("Unexpected linkEffectsTriggerMsg. Ignoring\n");
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
plSceneObject *avatar = plSceneObject::ConvertNoRef(linkKey->ObjectIsLoaded());
|
||||
if (avatar == nil)
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("Can't find avatar, mod=%s\n", linkKey->GetName());
|
||||
return true;
|
||||
}
|
||||
|
||||
// This is not the right place to catch this problem.
|
||||
// if (IFindLinkTriggerMsg(linkKey) != nil)
|
||||
// {
|
||||
// hsAssert(false, "Trying to link an Avatar already in the process of linking.");
|
||||
// return true;
|
||||
// }
|
||||
|
||||
if (pTriggerMsg->GetInvisLevel() && linkKey != nc->GetLocalPlayerKey())
|
||||
{
|
||||
#ifdef PLASMA_EXTERNAL_RELEASE
|
||||
// Verify that the server told us that the invisible avatar is a CCR
|
||||
plNetTransportMember* mbr=nc->TransportMgr().GetMember(nc->TransportMgr().FindMember(linkKey));
|
||||
if (!mbr || mbr->GetCCRLevel()<pTriggerMsg->GetInvisLevel())
|
||||
{
|
||||
plNetApp::StaticErrorMsg("Remote Avatar trying to be stealthy - REJECTING since he's not a CCR");
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
plNetApp::StaticDebugMsg("Remote Avatar is in stealth mode - making invisible");
|
||||
nc->MakeCCRInvisible(pTriggerMsg->GetLinkKey(), pTriggerMsg->GetInvisLevel());
|
||||
}
|
||||
}
|
||||
|
||||
if (pTriggerMsg->IsLeavingAge())
|
||||
hsStatusMessage("Starting LinkOut FX\n");
|
||||
else
|
||||
hsStatusMessage("Starting LinkIn FX\n");
|
||||
|
||||
plLinkEffectBCMsg *BCMsg = TRACKED_NEW plLinkEffectBCMsg();
|
||||
BCMsg->fLinkKey = linkKey;
|
||||
BCMsg->SetLinkFlag(plLinkEffectBCMsg::kLeavingAge, pTriggerMsg->IsLeavingAge());
|
||||
BCMsg->SetLinkFlag(plLinkEffectBCMsg::kSendCallback, true);
|
||||
|
||||
// Check if you have a Yeesha book, and mute sound if you don't.
|
||||
// 'CleftSolved' gets set when you click on the linking panel in the cleft,
|
||||
// so we use that instead of checking KILevel.
|
||||
// Also, check if you're going to/from the ACA, or through the fissure, and mute sound if you are.
|
||||
if (linkKey == nc->GetLocalPlayerKey())
|
||||
{
|
||||
if(lm) {
|
||||
const char *ageName = lm->GetAgeLink()->GetAgeInfo()->GetAgeFilename();
|
||||
const char *prevAgeName = lm->GetPrevAgeLink()->GetAgeInfo()->GetAgeFilename();
|
||||
|
||||
bool linkToStartup = ageName && !stricmp(ageName, kStartUpAgeFilename ); // To Startup
|
||||
bool linkFromStartup = prevAgeName && !stricmp(prevAgeName, kStartUpAgeFilename); // Leaving Startup
|
||||
|
||||
bool cleftSolved = VaultHasChronicleEntry( kCleftSolved );
|
||||
|
||||
bool linkToACA = ageName && !stricmp(ageName, kAvCustomizationFilename);
|
||||
bool linkFromACA = prevAgeName && !stricmp(prevAgeName, kAvCustomizationFilename);
|
||||
|
||||
bool linkToFissureDrop = lm &&
|
||||
lm->GetAgeLink()->HasSpawnPt() &&
|
||||
lm->GetAgeLink()->SpawnPoint().GetName() &&
|
||||
!stricmp(lm->GetAgeLink()->SpawnPoint().GetName(), kCleftAgeLinkInPointFissureDrop);
|
||||
bool linkToDsntFromShell = lm &&
|
||||
lm->GetAgeLink()->HasSpawnPt() &&
|
||||
lm->GetAgeLink()->SpawnPoint().GetTitle() &&
|
||||
!stricmp(lm->GetAgeLink()->SpawnPoint().GetTitle(), kDescentLinkFromShell);
|
||||
if ( linkToACA || linkFromACA || linkToStartup || linkFromStartup || linkToFissureDrop || linkToDsntFromShell)
|
||||
{
|
||||
BCMsg->SetLinkFlag(plLinkEffectBCMsg::kMute);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
BCMsg->SetSender(GetKey());
|
||||
if (msg->HasBCastFlag(plMessage::kNetNonLocal))
|
||||
// terminate the remote cascade and start a new (local) cascade, since the rcvr is localOnly and will reject remote msgs
|
||||
BCMsg->SetBCastFlag(plMessage::kNetStartCascade);
|
||||
plgDispatch::MsgSend(BCMsg);
|
||||
|
||||
if (!pTriggerMsg->IsLeavingAge()) // Avatar is currently entering a new age
|
||||
{
|
||||
plATCAnim *linkInAnim = nil;
|
||||
plKey linkInAnimKey = nil;
|
||||
const plArmatureMod *avMod = plArmatureMod::ConvertNoRef(avatar->GetModifierByType(plArmatureMod::Index()));
|
||||
if (pTriggerMsg->HasBCastFlag(plMessage::kNetNonLocal))
|
||||
{
|
||||
// Remote trigger, they should tell us how they linked in.
|
||||
linkInAnimKey = pTriggerMsg->GetLinkInAnimKey();
|
||||
}
|
||||
else
|
||||
{
|
||||
// this is our backup trigger we send ourselves. We've already received the remote player's SDL.
|
||||
linkInAnimKey = avMod ? avMod->GetLinkInAnimKey() : nil;
|
||||
}
|
||||
linkInAnim = plATCAnim::ConvertNoRef(linkInAnimKey ? linkInAnimKey->ObjectIsLoaded() : nil);
|
||||
|
||||
if (avMod && linkInAnim)
|
||||
{
|
||||
plAvOneShotTask *task = TRACKED_NEW plAvOneShotTask(linkInAnim->GetName(), false, false, nil);
|
||||
task->fBackwards = true;
|
||||
task->fDisableLooping = true;
|
||||
task->fDisablePhysics = false;
|
||||
(TRACKED_NEW plAvTaskMsg(GetKey(), avMod->GetKey(), task))->Send();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
IAddLink(pTriggerMsg); // refs the avatarMod
|
||||
|
||||
// Dummy msg sent after the broadcast. This guarantees we have a callback to actually trigger the
|
||||
// link, plus we know any effect broadcast messages will have processed before this (and therefore
|
||||
// have told us to wait for them.)
|
||||
pTriggerMsg->fEffects++;
|
||||
plLinkCallbackMsg *dummyMsg = TRACKED_NEW plLinkCallbackMsg();
|
||||
dummyMsg->AddReceiver(GetKey());
|
||||
dummyMsg->fLinkKey = linkKey;
|
||||
plgDispatch::MsgSend(dummyMsg);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// callbacks from linkout events
|
||||
plLinkCallbackMsg* pLinkCallbackMsg = plLinkCallbackMsg::ConvertNoRef(msg);
|
||||
if (pLinkCallbackMsg)
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("Received pLinkCallbackMsg, localmsg=%d\n",
|
||||
!msg->HasBCastFlag(plMessage::kNetNonLocal));
|
||||
|
||||
static char str[ 128 ];
|
||||
plLinkEffectsTriggerMsg *pTriggerMsg = IFindLinkTriggerMsg(pLinkCallbackMsg->fLinkKey);
|
||||
if (pTriggerMsg == nil)
|
||||
{
|
||||
hsAssert(true, "Received a callback for an avatar that isn't linking.");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (--pTriggerMsg->fEffects == 0)
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("All link callbacks received.\n" );
|
||||
plgDispatch::Dispatch()->RegisterForExactType(plTimeMsg::Index(), GetKey());
|
||||
}
|
||||
else if (pTriggerMsg->fEffects < 0 )
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("Too many link callbacks received for avatar %s. Ignoring extras.\n",
|
||||
pTriggerMsg->GetLinkKey()->GetName());
|
||||
}
|
||||
else
|
||||
{
|
||||
plNetApp::GetInstance()->DebugMsg("%d link callbacks left until avatar %s links...\n",
|
||||
pTriggerMsg->fEffects, pTriggerMsg->GetLinkKey()->GetName());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
plTimeMsg *time = plTimeMsg::ConvertNoRef(msg);
|
||||
if (time) // This is how we know we're out of the render function, and it's safe to pageIn/Out nodes
|
||||
{
|
||||
plgDispatch::Dispatch()->UnRegisterForExactType(plTimeMsg::Index(), GetKey());
|
||||
ISendAllReadyCallbacks();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
plPlayerPageMsg *pageMsg = plPlayerPageMsg::ConvertNoRef(msg);
|
||||
if (pageMsg)
|
||||
{
|
||||
if (pageMsg->fUnload)
|
||||
{
|
||||
IHuntWaitlist(pageMsg->fPlayer);
|
||||
return true;
|
||||
}
|
||||
|
||||
const hsScalar kMaxTimeForLinkTrigger = 30.f;
|
||||
|
||||
// If we're not loading state, we're in the age. So this avatar coming in must be linking in.
|
||||
// If the player is us, no prep is necessary.
|
||||
if (!plNetClientApp::GetInstance()->IsLoadingInitialAgeState() &&
|
||||
(pageMsg->fPlayer != nc->GetLocalPlayerKey()))
|
||||
{
|
||||
plLinkEffectsTriggerMsg *trigMsg = TRACKED_NEW plLinkEffectsTriggerMsg;
|
||||
trigMsg->SetLeavingAge(false);
|
||||
trigMsg->SetLinkKey(pageMsg->fPlayer);
|
||||
|
||||
// Send off the prep message right away
|
||||
plLinkEffectsTriggerPrepMsg *trigPrepMsg = TRACKED_NEW plLinkEffectsTriggerPrepMsg;
|
||||
trigPrepMsg->fLinkKey = pageMsg->fPlayer;
|
||||
trigPrepMsg->SetTrigger(trigMsg);
|
||||
trigPrepMsg->Send(GetKey());
|
||||
|
||||
// Send off a delayed safety trigger. If things are going along properly,
|
||||
// we'll get a trigger from the player linking in before this message is
|
||||
// received, and we'll ignore it.
|
||||
double timeToDeliver = hsTimer::GetSysSeconds() + kMaxTimeForLinkTrigger;
|
||||
trigMsg->SetTimeStamp(timeToDeliver);
|
||||
trigMsg->Send(GetKey());
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return hsKeyedObject::MsgReceive(msg);
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::WaitForEffect(plKey linkKey, hsScalar time)
|
||||
{
|
||||
plLinkEffectsTriggerMsg *msg = IFindLinkTriggerMsg(linkKey);
|
||||
if (msg == nil)
|
||||
{
|
||||
hsAssert(true, "Request to wait on an effect for an avatar that isn't linking.");
|
||||
return;
|
||||
}
|
||||
|
||||
msg->fEffects++;
|
||||
plLinkCallbackMsg *callback = TRACKED_NEW plLinkCallbackMsg();
|
||||
callback->fEvent = kStop;
|
||||
callback->fRepeats = 0;
|
||||
callback->fLinkKey = linkKey;
|
||||
double timeToDeliver = hsTimer::GetSysSeconds() + time;
|
||||
callback->SetTimeStamp( timeToDeliver );
|
||||
callback->Send( GetKey() );
|
||||
}
|
||||
|
||||
plMessage *plLinkEffectsMgr::WaitForEffect(plKey linkKey)
|
||||
{
|
||||
plLinkEffectsTriggerMsg *msg = IFindLinkTriggerMsg(linkKey);
|
||||
if (msg == nil)
|
||||
{
|
||||
hsAssert(true, "Request to wait on an effect for an avatar that isn't linking.");
|
||||
return nil;
|
||||
}
|
||||
|
||||
msg->fEffects++;
|
||||
|
||||
plLinkCallbackMsg *callback = TRACKED_NEW plLinkCallbackMsg();
|
||||
callback->fEvent = kStop;
|
||||
callback->fRepeats = 0;
|
||||
callback->fLinkKey = linkKey;
|
||||
callback->AddReceiver( GetKey() );
|
||||
return callback;
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::WaitForPseudoEffect(plKey linkKey, hsScalar time)
|
||||
{
|
||||
plPseudoLinkEffectMsg* msg = IFindPseudo(linkKey);
|
||||
if (msg == nil)
|
||||
{
|
||||
hsAssert(true, "Request to wait on an fake effect for an avatar that isn't fake linking.");
|
||||
return;
|
||||
}
|
||||
|
||||
plPseudoLinkAnimCallbackMsg* callback = TRACKED_NEW plPseudoLinkAnimCallbackMsg();
|
||||
callback->fAvatarKey = linkKey;
|
||||
double timeToDeliver = hsTimer::GetSysSeconds() + time;
|
||||
callback->SetTimeStamp( timeToDeliver );
|
||||
callback->Send( GetKey() );
|
||||
}
|
||||
|
||||
plPseudoLinkEffectMsg* plLinkEffectsMgr::IFindPseudo(plKey avatarKey)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < fPseudolist.GetCount(); i++)
|
||||
{
|
||||
if (fPseudolist[i]->fAvatarKey == avatarKey)
|
||||
return fPseudolist[i];
|
||||
}
|
||||
return nil;
|
||||
|
||||
}
|
||||
|
||||
void plLinkEffectsMgr::IRemovePseudo(plKey avatarKey)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < fPseudolist.GetCount(); i++)
|
||||
{
|
||||
if (fPseudolist[i]->fAvatarKey == avatarKey)
|
||||
{
|
||||
fPseudolist.Remove(i);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
Reference in New Issue
Block a user