DragonNest/Server/DNVillageServer/DNPartyManager.cpp
2024-12-19 09:48:26 +08:00

1155 lines
No EOL
30 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "StdAfx.h"
#include "DNPartyManager.h"
#include "DNUserSession.h"
#include "DNUserSendManager.h"
#include "DNMasterConnection.h"
#include "Util.h"
#include "DNDBConnectionManager.h"
#include "DNDBConnection.h"
#ifdef _USE_VOICECHAT
#include "DNVoiceChat.h"
#endif
#if defined( PRE_PARTY_DB )
#include "DNPartySortObject.hpp"
#endif // #if defined( PRE_PARTY_DB )
#include "DNServiceConnection.h"
CDNPartyManager* g_pPartyManager;
extern TVillageConfig g_Config;
CDNPartyManager::CDNPartyManager(void): m_nProcessCount(0)
{
#if defined( PRE_PARTY_DB )
m_pDBCon = NULL;
m_dwGetListPartyTick = 0;
#else
ScopeLock<CSyncLock> Lock(m_Sync);
#endif // #if defined( PRE_PARTY_DB )
m_pMapPartyList.clear();
m_nLastCheckTick = 0;
#if defined( PRE_PARTY_DB )
m_bDeletePartyForServer = false;
#else
m_pVecPartyList.clear();
m_pMultiMapWaitParty.clear();
#endif // #if defined( PRE_PARTY_DB )
#if defined( PRE_WORLDCOMBINE_PARTY )
m_nCreateWorldPartyTick = 0;
m_WorldReqCombineParty.clear();
#endif
}
CDNPartyManager::~CDNPartyManager(void)
{
#if defined( PRE_PARTY_DB )
if( m_pMapPartyList.empty() )
return;
#else
if (m_pVecPartyList.empty() && m_pMapPartyList.empty())
return;
ScopeLock<CSyncLock> Lock(m_Sync);
#endif // #if defined( PRE_PARTY_DB )
#if defined( PRE_PARTY_DB )
for( TMapParty::iterator itor=m_pMapPartyList.begin() ; itor!=m_pMapPartyList.end() ; ++itor )
delete (*itor).second;
m_pMapPartyList.clear();
#else
if (!m_pVecPartyList.empty())
{
std::vector <CDNParty*>::iterator ii;
for (ii = m_pVecPartyList.begin(); ii != m_pVecPartyList.end(); ii++)
SAFE_DELETE((*ii));
}
m_pVecPartyList.clear();
m_pMapPartyList.clear();
m_pMultiMapWaitParty.clear();
#endif // #if defined( PRE_PARTY_DB )
}
void CDNPartyManager::DoUpdate(DWORD CurTick)
{
#if defined( PRE_PARTY_DB )
if( m_nLastCheckTick > 0 && CurTick < (DWORD)m_nLastCheckTick)
return;
m_nLastCheckTick = CurTick + 50;
for( TMapParty::iterator itor=m_pMapPartyList.begin() ; itor!=m_pMapPartyList.end() ; )
{
CDNParty* pParty = (*itor).second;
if( pParty )
{
if( !(pParty->DoUpdate( CurTick )) )
{
itor++;
DestroyParty(pParty->GetPartyID());
}
else
itor++;
}
}
#else
if (m_pVecPartyList.empty()) return;
if (m_nLastCheckTick > 0 && CurTick < (DWORD)m_nLastCheckTick) return;
m_nLastCheckTick = CurTick + 50;
int nCount;
CDNParty *pParty = NULL;
ScopeLock<CSyncLock> Lock(m_Sync);
nCount = (int)m_pVecPartyList.size();
if (nCount > PROCESSCOUNT) nCount = PROCESSCOUNT;
for (int i = 0; i < nCount; i++){
if (m_nProcessCount >= (int)m_pVecPartyList.size())
m_nProcessCount = 0;
pParty = m_pVecPartyList[m_nProcessCount];
if (pParty)
pParty->DoUpdate(CurTick);
m_nProcessCount++;
}
#endif // #if defined( PRE_PARTY_DB )
}
#if defined( PRE_PARTY_DB )
CDNDBConnection* CDNPartyManager::GetDBConnection()
{
if( m_pDBCon == NULL )
{
BYTE cThreadID;
m_pDBCon = g_pDBConnectionManager->GetDBConnection( g_Config.nWorldSetID, cThreadID );
}
return m_pDBCon;
}
void CDNPartyManager::InternalDoUpdate( DWORD dwCurTick )
{
if( m_bDeletePartyForServer == false )
{
QueryDelPartyForServer( g_Config.nManagedID );
m_bDeletePartyForServer = true;
}
const DWORD dwInterval = 3000;
// DelPartyForServer
if( m_DeletePartyForServerList.empty() == false )
{
for( TDELETEPARTYFORSERVERLIST::iterator itor=m_DeletePartyForServerList.begin() ; itor!=m_DeletePartyForServerList.end() ; ++itor )
{
if( (*itor).second+dwInterval < dwCurTick )
QueryDelPartyForServer( (*itor).first, dwCurTick );
}
return;
}
// OutParty
BYTE cThreadID;
CDNDBConnection* pLoopDBCon = g_pDBConnectionManager->GetDBConnection( cThreadID );
for( TOUTPARTYLIST::iterator itor=m_OutPartyList.begin() ; itor!=m_OutPartyList.end() ; )
{
bool bRet = true;
if( (*itor).second+dwInterval < dwCurTick )
bRet = QueryOutParty( GetTupleValue((*itor).first,0), GetTupleValue((*itor).first,1), GetTupleValue((*itor).first,2), GetTupleValue((*itor).first,3), GetTupleValue((*itor).first,4), dwCurTick, pLoopDBCon );
if( bRet == true )
++itor;
else
m_OutPartyList.erase( itor++ );
}
// DelParty
pLoopDBCon = g_pDBConnectionManager->GetDBConnection( cThreadID );
for( TDELETEPARTYLIST::iterator itor=m_DeletePartyList.begin() ; itor!=m_DeletePartyList.end() ; )
{
bool bRet = true;
if( (*itor).second+dwInterval < dwCurTick )
bRet = QueryDelParty( (*itor).first, dwCurTick, pLoopDBCon );
if( bRet == true )
++itor;
else
m_DeletePartyList.erase( itor++ );
}
#if defined( PRE_WORLDCOMBINE_PARTY )
if( m_nCreateWorldPartyTick + 30 * 1000 < dwCurTick )
{
const sChannelInfo* pChannelInfo = g_pMasterConnection->GetChannelInfoFromAttr( GlobalEnum::CHANNEL_ATT_PVPLOBBY );
if( g_Config.nCombinePartyWorld > 0 && g_Config.nWorldSetID == g_Config.nCombinePartyWorld && pChannelInfo &&
pChannelInfo->cVillageID == g_Config.nVillageID )
{
QueryGetListWorldParty();
m_nCreateWorldPartyTick = dwCurTick;
}
}
#endif
// PartyUpdate
DoUpdate( dwCurTick );
// GetListParty
if( m_dwGetListPartyTick+Party::Interval::GetListPartyTick < dwCurTick )
{
QueryGetListParty( dwCurTick );
}
}
#endif // #if defined( PRE_PARTY_DB )
#if defined( PRE_PARTY_DB )
CDNParty* CDNPartyManager::CreateParty( CDNUserSession* pUser, TPARTYID PartyID, const DBCreateParty* pData )
{
if( PartyID == 0 )
return NULL;
CDNParty* pParty = new CDNParty(0);
if( pParty == NULL )
return NULL;
//Set Values
pParty->Create( PartyID, pData );
bool bAdd = true;
UINT uiRandomSeed = pParty->GetRandomSeed();
errno_t err = rand_s(&uiRandomSeed);
if (err == 0)
{
if (m_pMapPartyList.find(PartyID) != m_pMapPartyList.end())
bAdd = false;
if (bAdd)
{
#if defined( PRE_PARTY_DB )
#else
m_pVecPartyList.push_back(pParty);
#endif // #if defined( PRE_PARTY_DB )
m_pMapPartyList[pParty->GetPartyID()] = pParty;
#if defined( PRE_PARTY_DB )
#else
for (TMultiMapParty::iterator ii = m_pMultiMapWaitParty.begin(); ii != m_pMultiMapWaitParty.end(); )
{
if ((*ii).second->GetPartyID() == pParty->GetPartyID() )
{
ii = m_pMultiMapWaitParty.erase(ii);
}
else
ii++;
}
m_pMultiMapWaitParty.insert(std::make_pair(pParty->GetPartyMapIndex(), pParty));
#endif // #if defined( PRE_PARTY_DB )
// <20><>Ƽ <20><><EFBFBD><EFBFBD> <20>α<EFBFBD>(<28><>Ƽ<EFBFBD><C6BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><>Ƽ <20><><EFBFBD><EFBFBD>,<2C><><EFBFBD><EFBFBD><EFBFBD>α<EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD>ƴ޶<C6B4><DEB6><EFBFBD> <20><><EFBFBD>ô<EFBFBD><C3B4><EFBFBD> <20><>û)
//if( pUser && pUser->GetDBConnection() )
//{
// pUser->GetDBConnection()->QueryAddPartyStartLog( pUser, PartyID );
//}
return pParty;
}
}
SAFE_DELETE(pParty);
_DANGER_POINT();
return NULL;
}
void CDNPartyManager::PushParty( const Party::Data& Data )
{
DBCreateParty DBCreateParty;
memset( &DBCreateParty, 0, sizeof(DBCreateParty) );
DBCreateParty.PartyData = Data;
CreateParty( NULL, Data.PartyID, &DBCreateParty );
}
CDNParty * CDNPartyManager::PushParty(MAVIPushParty * pPacket)
{
int iPermitLevel = g_pDataManager->GetMapPermitLevel( g_pMasterConnection->GetChannelMapIndex( pPacket->PartyData.iLocationID ) );
pPacket->PartyData.cMinLevel = (pPacket->PartyData.cMinLevel < iPermitLevel) ? iPermitLevel : pPacket->PartyData.cMinLevel;
Party::AddPartyAndMemberVillage PartyData;
memset(&PartyData, 0, sizeof(Party::AddPartyAndMemberVillage));
PartyData.PartyData = pPacket->PartyData;
memcpy( PartyData.nKickedMemberList, pPacket->nKickedMemberList, sizeof(PartyData.nKickedMemberList) );
PartyData.PartyData.iRoomID = 0;
for( int i=0;i<pPacket->PartyData.iCurMemberCount;i++ )
{
if( pPacket->MemberInfo[i].nAccountDBID > 0 )
{
PartyData.MemberData[i].nAccountDBID = pPacket->MemberInfo[i].nAccountDBID;
PartyData.MemberData[i].biCharacterDBID = pPacket->MemberInfo[i].biCharacterDBID;
PartyData.MemberData[i].cMemberIndex = pPacket->MemberInfo[i].cMemberIndex;
#if defined( PRE_ADD_NEWCOMEBACK )
PartyData.MemberData[i].bCheckComebackAppellation = pPacket->MemberInfo[i].bCheckComebackAppellation;
#endif
PartyData.MemberData[i].cVoiceAvailable = pPacket->MemberInfo[i].VoiceInfo.cVoiceAvailable;
memcpy( PartyData.MemberData[i].nMutedList, pPacket->MemberInfo[i].VoiceInfo.nMutedList, sizeof(PartyData.MemberData[i].nMutedList) );
}
else
break;
}
if( GetDBConnection() )
{
GetDBConnection()->QueryAddPartyAndMemberVillage( g_Config.nWorldSetID, pPacket->nLeaderAccountDBID, g_Config.nManagedID, Party::LocationType::Village, &PartyData );
}
return NULL;
}
CDNParty * CDNPartyManager::PushParty(TAAddPartyAndMemberVillage * pPacket)
{
if (pPacket == NULL) return NULL;
CDNParty * pParty = new CDNParty(timeGetTime());
if (pParty == NULL) return NULL;
pParty->PushParty( pPacket );
for(int i=0;i<pPacket->Data.PartyData.iCurMemberCount;i++)
m_AddPartyMemberList.insert( std::make_pair(pPacket->MemberInfo[i].nAccountDBID, pPacket->Data.PartyData.PartyID ) );
if (m_pMapPartyList.find(pParty->GetPartyID()) == m_pMapPartyList.end())
{
m_pMapPartyList[pParty->GetPartyID()] = pParty;
}
else
{
_DANGER_POINT();
SAFE_DELETE(pParty);
return NULL;
}
#ifdef _USE_VOICECHAT
if (pParty->CreateVoiceChannel(pPacket->nVoiceChannelID))
pParty->SetInitVoiceInfo(pPacket->MemberInfo, pPacket->Data.PartyData.iCurMemberCount);
#endif
return pParty;
}
#else
CDNParty * CDNPartyManager::CreateParty(CDNUserSession * pUser, TPARTYID PartyID, const WCHAR * pPartyName, const WCHAR * pPassWord, int nMemberMax, TPARTYITEMLOOTRULE ItemLootRule, TITEMRANK ItemRank, int nLvLimitMin, int nLvLimitMax, int nTargetMapIdx, TDUNGEONDIFFICULTY Difficulty, BYTE cIsPartyJobDice)
{
if (PartyID == 0) return NULL;
CDNParty * pParty = new CDNParty(0);
if (!pParty) return NULL;
//Set Values
pParty->Create(pUser, PartyID, pPartyName, pPassWord, nMemberMax, ItemLootRule, ItemRank, nLvLimitMin, nLvLimitMax, nTargetMapIdx, Difficulty, cIsPartyJobDice );
bool bAdd = true;
UINT uiRandomSeed = pParty->GetRandomSeed();
errno_t err = rand_s(&uiRandomSeed);
if (err == 0)
{
ScopeLock<CSyncLock> Lock(m_Sync);
if (m_pMapPartyList.find(PartyID) != m_pMapPartyList.end())
bAdd = false;
if (bAdd)
{
m_pVecPartyList.push_back(pParty);
m_pMapPartyList[pParty->GetPartyID()] = pParty;
for (TMultiMapParty::iterator ii = m_pMultiMapWaitParty.begin(); ii != m_pMultiMapWaitParty.end(); )
{
if ((*ii).second->GetPartyID() == pParty->GetPartyID())
{
ii = m_pMultiMapWaitParty.erase(ii);
}
else
ii++;
}
m_pMultiMapWaitParty.insert(std::make_pair(pParty->GetPartyMapIndex(), pParty));
// <20><>Ƽ <20><><EFBFBD><EFBFBD> <20>α<EFBFBD>
if( pUser->GetDBConnection() )
{
pUser->GetDBConnection()->QueryAddPartyStartLog( pUser, PartyID );
}
return pParty;
}
}
SAFE_DELETE(pParty);
_DANGER_POINT();
return NULL;
}
CDNParty * CDNPartyManager::PushParty(MAVIPushParty * pPacket)
{
if (pPacket == NULL) return NULL;
CDNParty * pParty = new CDNParty(timeGetTime());
if (pParty == NULL) return NULL;
pParty->PushParty( pPacket );
ScopeLock<CSyncLock> Lock(m_Sync);
if (m_pMapPartyList.find(pParty->GetPartyID()) == m_pMapPartyList.end())
{
m_pVecPartyList.push_back(pParty);
m_pMapPartyList[pParty->GetPartyID()] = pParty;
}
else
{
_DANGER_POINT();
SAFE_DELETE(pParty);
return NULL;
}
#ifdef _USE_VOICECHAT
if (pParty->CreateVoiceChannel(pPacket->nVoiceChannelID))
pParty->SetInitVoiceInfo(pPacket->MemberInfo, pPacket->cMemberCount);
#endif
return pParty;
}
#endif // #if defined( PRE_PARTY_DB )
bool CDNPartyManager::DestroyParty(TPARTYID PartyID, bool bLog/*=true*/)
{
#if defined( PRE_PARTY_DB )
#else
ScopeLock<CSyncLock> Lock(m_Sync);
#endif // #if defined( PRE_PARTY_DB )
CDNParty * pParty = NULL;
std::map <TPARTYID, CDNParty*>::iterator ii = m_pMapPartyList.find(PartyID);
if (ii != m_pMapPartyList.end())
{
//<2F><EFBFBD><E2BABB><EFBFBD><EFBFBD> <20><>Ȳ<EFBFBD><C8B2> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>˻<EFBFBD><CBBB>ϰ<EFBFBD> <20>;<EFBFBD><CDBE><EFBFBD>
pParty = (*ii).second;
pParty->BanAllPartyMember(pParty->GetLeaderAccountDBID()); //<2F><><EFBFBD><EFBFBD> <20>ִ<EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20>߷ȴٰ<C8B4> <20><><EFBFBD><EFBFBD><EFBFBD>ְ<EFBFBD>
#if defined( PRE_PARTY_DB )
#else
std::vector <CDNParty*>::iterator ih;
for (ih = m_pVecPartyList.begin(); ih != m_pVecPartyList.end(); ih++)
{
if ((*ih)->GetPartyID() == PartyID)
{
m_pVecPartyList.erase(ih);
break;
}
}
#endif // #if defined( PRE_PARTY_DB )
#if defined( PRE_PARTY_DB )
#else
TMultiMapParty::iterator ij;
for (ij = m_pMultiMapWaitParty.begin(); ij != m_pMultiMapWaitParty.end(); )
{
if ((*ij).second->GetPartyID() == PartyID)
{
ij = m_pMultiMapWaitParty.erase(ij);
}
else
ij++;
}
#endif // #if defined( PRE_PARTY_DB )
#ifdef _USE_VOICECHAT
pParty->DestroyVoiceChannel();
#endif
m_pMapPartyList.erase(ii);
SAFE_DELETE(pParty);
#if !defined(PRE_PARTY_DB)
if( bLog )
{
// <20><>Ƽ <20><><EFBFBD><EFBFBD> <20>α<EFBFBD>
BYTE cThreadID;
CDNDBConnection* pDBCon = g_pDBConnectionManager->GetDBConnection( cThreadID );
if( pDBCon )
{
pDBCon->QueryAddPartyEndLog( cThreadID, g_Config.nWorldSetID, 0, PartyID );
}
}
#endif // #if !defined(PRE_PARTY_DB)
#if defined( PRE_PARTY_DB )
QueryDelParty( PartyID );
#endif // #if defined( PRE_PARTY_DB )
return true;
}
_DANGER_POINT();
return false;
}
CDNParty * CDNPartyManager::GetParty(TPARTYID PartyID)
{
if( PartyID <= 0 || m_pMapPartyList.empty())
return NULL;
#if defined( PRE_PARTY_DB )
#else
ScopeLock<CSyncLock> Lock(m_Sync);
#endif // #if defined( PRE_PARTY_DB )
std::map <TPARTYID, CDNParty*>::iterator ii = m_pMapPartyList.find(PartyID);
if (ii != m_pMapPartyList.end())
return (*ii).second;
return NULL;
}
#if defined( PRE_PARTY_DB )
#else
void CDNPartyManager::PushWaitPartyList(CDNParty *pParty)
{
if (!pParty) return;
if (pParty->HasEmptyPlace() == false) return;
if (pParty->GetMemberCount() <= 0) return;
ScopeLock<CSyncLock> Lock(m_Sync);
bool bChecker = false;
for (TMultiMapParty::iterator ii = m_pMultiMapWaitParty.begin(); ii != m_pMultiMapWaitParty.end(); ii++)
{
if ((*ii).second->GetPartyID() == pParty->GetPartyID() || (*ii).second == pParty)
{
bChecker = true;
break;
}
}
if (bChecker == false)
m_pMultiMapWaitParty.insert(std::make_pair(pParty->GetPartyMapIndex(), pParty));
}
bool CDNPartyManager::EraseWaitPartyList(CDNParty *pParty)
{
if (!pParty) return false;
if (m_pMultiMapWaitParty.empty()) return false;
ScopeLock<CSyncLock> Lock(m_Sync);
bool bFlag = false;
for (TMultiMapParty::iterator ii = m_pMultiMapWaitParty.begin(); ii != m_pMultiMapWaitParty.end(); )
{
if ((*ii).second->GetPartyID() == pParty->GetPartyID() || (*ii).second == pParty)
{
ii = m_pMultiMapWaitParty.erase(ii);
bFlag = true;
}
else
ii++;
}
return bFlag;
}
#endif // #if defined( PRE_PARTY_DB )
#if defined( PRE_PARTY_DB )
void CDNPartyManager::GetPartyListInfo(int nMapIdx, int nChannelID, int nChannelMeritID, int nOffSetCount, const CSPartyListInfo* pPacket, std::list<CDNParty*>& PartyList )
{
#if defined( _WORK )
// char szTemp[MAX_PATH];
// sprintf_s( szTemp, MAX_PATH, "GetPartyListInfo() Count:%d", m_pMapPartyList.size() );
// CPerformanceLog Perf( szTemp, 500 ); //rlkt_disabled
#endif // #if defiend( _WORK )
UINT uiTick = timeGetTime();
std::vector <std::pair<int, TPARTYID>> vDelList;
{
for( TMapParty::iterator itor=m_pMapPartyList.begin() ; itor!=m_pMapPartyList.end() ; ++itor )
{
CDNParty* pParty = (*itor).second;
// <20><><EFBFBD><EFBFBD> <20><>Ƽ<EFBFBD><C6BC> <20><><EFBFBD><EFBFBD>Ʈ<EFBFBD><C6AE> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>ʴ´<CAB4>.
if( pParty->HasEmptyPlace() == false )
continue;
// <20>ٸ<EFBFBD> <20><><EFBFBD><EFBFBD> <20><>Ƽ - <20><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>Ʈ <20>˻<EFBFBD>
if( pParty->GetServerID() != g_Config.nManagedID )
{
if( pParty->GetCurMemberCount() >= pParty->GetMemberMax() )
continue;
}
else
{
// <20><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>ϴ<EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD>ϱ<EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD>Ƿ<EFBFBD> 0<≯<EFBFBD> <20>Ѱ<EFBFBD><D1B0>ش<EFBFBD>.
if( pParty->GetMemberCount() == 0 )
continue;
}
// <20><><EFBFBD>Ӽ<EFBFBD><D3BC><EFBFBD><EFBFBD><EFBFBD> <20>ְ<EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>(?)<29><> <20><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD> <20><>Ƽ<EFBFBD><C6BC> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>ʴ´<CAB4>.
if( pParty->bIsInGame() )
{
if( !(pParty->GetBitFlag()&Party::BitFlag::WorldmapAllow) )
continue;
}
// <20><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>ɼ<EFBFBD>
if( pPacket->bOnlySameVillage == true )
{
#if defined( PRE_WORLDCOMBINE_PARTY )
if( !(pParty->bIsInVillage() && pParty->GetPartyMapIndex() == nMapIdx) && !pParty->bIsWorldCombieParty() )
continue;
#else
if( !(pParty->bIsInVillage() && pParty->GetPartyMapIndex() == nMapIdx) )
continue;
#endif
}
Party::CalcSortPoint SortObject(pPacket,nMapIdx);
SortObject.CalcPoint( pParty );
PartyList.push_back( pParty );
}
}
PartyList.sort( Party::SortObject() );
UINT uiGap = timeGetTime()-uiTick;
if( uiGap >= 500 && g_pServiceConnection )
{
WCHAR wszBuf[GAMEDELAYSIZE] = {0,};
wsprintf( wszBuf, L"[%d] CDNPartyManager::GetPartyListInfo Delay=%d PartyCount=%d", g_Config.nManagedID, uiGap, m_pMapPartyList.size() );
g_pServiceConnection->SendVillageDelayedReport(wszBuf);
}
}
#else
int CDNPartyManager::GetPartyListInfo(int nMapIdx, int nChannelID, int nChannelMeritID, int nOffSetCount, int nPageNum, int * nSortMapIdx, TDUNGEONDIFFICULTY Difficulty, int &nRet, std::list<SPartyListInfo> * pPartyList)
{
if (nSortMapIdx == NULL) return 0;
if (m_pMultiMapWaitParty.empty()) return 0;
int nWholeCnt, nCount, nFirst, nLast;
nCount = 0;
std::vector <std::pair<int, TPARTYID>> vDelList;
{
ScopeLock<CSyncLock> Lock(m_Sync);
nWholeCnt = (int)m_pMultiMapWaitParty.count(nMapIdx);
if (nWholeCnt <= 0) return 0;
int nLastPageNum = nWholeCnt/((nOffSetCount <= 0) ? PARTYLISTOFFSET : nOffSetCount);
nPageNum = nLastPageNum < nPageNum ? nLastPageNum : nPageNum;
nFirst = nPageNum * nOffSetCount;
nLast = nFirst + nOffSetCount - 1;
if (nSortMapIdx[0] > 0 || Difficulty > 0)
nRet = ERROR_PARTY_CONDITION_MATCHED_LIST_NOT_FOUND;
SPartyListInfo sPartyInfo;
std::multimap <int, std::pair<CDNParty*, const sChannelInfo *>> SortTemp;
for (TMultiMapParty::iterator ii = m_pMultiMapWaitParty.lower_bound(nMapIdx); ii != m_pMultiMapWaitParty.upper_bound(nMapIdx); ii++)
{
int nKeyCode = -1;
if (nSortMapIdx[0] > 0 || Difficulty > 0)
{
bool bSortMapFlag = false;
bool bIsPrivate = false;
for (int j = 0; j < PARTYSORTCONDITIONMAX; j++)
{
if (nSortMapIdx[j] > 0 && (*ii).second->GetTargetMapIndex() == nSortMapIdx[j])
{
bSortMapFlag = true;
break;
}
}
bIsPrivate = (*ii).second->bIsPasswordParty();
if ((bSortMapFlag) && (bIsPrivate == false) && (Difficulty > 0 && (*ii).second->GetDifficulty() == Difficulty))
{
nRet = ERROR_NONE;
nKeyCode = 0;
}
else if ((bSortMapFlag) && (bIsPrivate == false))
{
nRet = ERROR_NONE;
nKeyCode = 1;
}
else if ((Difficulty > 0 && (*ii).second->GetDifficulty() == Difficulty) && (bIsPrivate == false))
{
nRet = ERROR_NONE;
nKeyCode = 2;
}
else
{
nKeyCode = 3;
}
}
else
{
bool bIsPrivate = (*ii).second->bIsPasswordParty();
if (bIsPrivate == false)
{
nRet = ERROR_NONE;
nKeyCode = 0;
}
else
{
nRet = ERROR_NONE;
nKeyCode = 1;
}
}
const sChannelInfo * pInfo = g_pMasterConnection->GetChannelInfo((*ii).second->GetChannelID());
if (pInfo == NULL || pInfo->bVisibility == false || pInfo->nMapIdx != nMapIdx) continue;
SortTemp.insert(std::make_pair(nKeyCode, std::make_pair((*ii).second, pInfo)));
}
pPartyList->clear();
std::multimap <int, std::pair<CDNParty*, const sChannelInfo *>>::iterator ih;
for (ih = SortTemp.begin(); ih != SortTemp.end(); ih++)
{
if (nCount >= nFirst && nLast >= nCount)
{
memset(&sPartyInfo, 0, sizeof(sPartyInfo));
int nPartyRet = ((*ih).second).first->GetPartyInfo(&sPartyInfo, ((*ih).second).second);
if (nPartyRet != ERROR_NONE)
{
vDelList.push_back(std::make_pair(nPartyRet, ((*ih).second).first->GetPartyID()));
continue;
}
pPartyList->push_back(sPartyInfo);
if (pPartyList->size() >= PARTYLISTOFFSET)
{
AdjustParty(vDelList);
return nWholeCnt;
}
}
nCount++;
}
}
AdjustParty(vDelList);
return nWholeCnt;
}
#endif // #if defined( PRE_PARTY_DB )
void CDNPartyManager::AdjustParty(std::vector <std::pair<int, TPARTYID>> &vList)
{
if (!vList.empty())
{
CDNParty * pEraseParty = NULL;
for (int h = 0; h < (int)vList.size(); h++)
{
#if defined( PRE_PARTY_DB )
if (vList[h].first == -2)
#else
if (vList[h].first == -1)
{
pEraseParty = GetParty(vList[h].second);
if (pEraseParty)
EraseWaitPartyList(pEraseParty);
}
else if (vList[h].first == -2)
#endif // #if defined( PRE_PARTY_DB )
{
DestroyParty(vList[h].second);
}
}
}
}
void CDNPartyManager::SendPartyMemberPart(TPARTYID PartyID, CDNUserSession *pSession)
{
CDNParty *pParty = GetParty(PartyID);
if (!pParty) return;
pParty->SendPartyMemberPart(pSession);
}
void CDNPartyManager::SendPartyUseRadio(TPARTYID PartyID, UINT nSessionID, USHORT nRadioID)
{
CDNParty * pParty = GetParty(PartyID);
if (!pParty) return;
pParty->SendPartyUseRadio(nSessionID, nRadioID);
}
void CDNPartyManager::SendPartyReadyRequest(TPARTYID PartyID, UINT nAccountDBID)
{
CDNParty * pParty = GetParty(PartyID);
if (!pParty) return;
if (pParty->GetLeaderAccountDBID() != nAccountDBID)
{
_DANGER_POINT();
return;
}
pParty->SendPartyReadyRequest();
}
#if defined( PRE_PARTY_DB )
int CDNPartyManager::DelPartyMember( CDNParty* pParty, CDNUserSession* pSession, const TAOutParty* pPacket )
#else
int CDNPartyManager::DelPartyMember( CDNParty* pParty, CDNUserSession* pSession )
#endif // #if defined( PRE_PARTY_DB )
{
int nMemberIdx = pSession->m_nPartyMemberIndex;
char cKickKind = -1;
#if defined( PRE_PARTY_DB )
switch( pPacket->Type )
{
case Party::QueryOutPartyType::Kick:
{
cKickKind = 0;
break;
}
case Party::QueryOutPartyType::EternityKick:
{
cKickKind = 1;
break;
}
}
#endif // #if defined( PRE_PARTY_DB )
if( pParty->DelPartyMember( pSession, cKickKind ) == false )
return ERROR_PARTY_LEAVEFAIL;
#if defined( PRE_PARTY_DB)
if(pPacket->bIsDelParty)
{
if( pParty->GetMemberCount() != 0 )
{
g_Log.Log(LogType::_PARTYERROR, L"[Party] DelPartyError1 - PartyDBID:%I64d MemberCount:%d MemberOutType:%d\r\n", pPacket->PartyID, pParty->GetMemberCount(), pPacket->Type);
DestroyParty( pParty->GetPartyID(), true );
}
else
{
DestroyParty( pParty->GetPartyID(), ((pSession->m_eUserState != STATE_MOVETOVILLAGE) && (pSession->m_eUserState != STATE_MOVETOGAME)) );
}
}
else
{
if( pParty->GetMemberCount() == 0 )
{
DestroyParty( pParty->GetPartyID(), true );
}
else if( pParty->bIsMove() == false )
{
if( cKickKind != -1 )
pParty->SendKickPartyMember( pSession->GetSessionID() );
pParty->SendAllRefreshParty(PARTYREFRESH_NONE);
}
}
#else
if( pParty->GetMemberCount() == 0 )
{
DestroyParty( pParty->GetPartyID(), ((pSession->m_eUserState != STATE_MOVETOVILLAGE) && (pSession->m_eUserState != STATE_MOVETOGAME)) );
}
else
{
if( pParty->bIsMove() == false )
{
pParty->SendAllRefreshParty(PARTYREFRESH_NONE);
PushWaitPartyList( pParty );
}
}
#endif
return ERROR_NONE;
}
#if defined( PRE_PARTY_DB )
TPARTYID CDNPartyManager::GetPartyID( UINT nAccountDBID )
{
TPARTYID PartyID = 0;
TADDPARTYMEMBERLIST::iterator itor = m_AddPartyMemberList.find( nAccountDBID );
if( itor != m_AddPartyMemberList.end() )
{
PartyID = itor->second;
m_AddPartyMemberList.erase( itor );
}
return PartyID;
}
int CDNPartyManager::DelPartyMember( CDNParty* pParty, const TAOutParty* pA )
{
if( pParty->DelPartyMember( pA, -1 ) == false )
return ERROR_PARTY_LEAVEFAIL;
if(pA->bIsDelParty)
{
if( pParty->GetMemberCount() != 0 )
{
g_Log.Log(LogType::_PARTYERROR, L"[Party] DelPartyError3 - PartyDBID:%I64d MemberCount:%d MemberOutType:%d\r\n", pA->PartyID, pParty->GetMemberCount(), pA->Type);
DestroyParty( pParty->GetPartyID(), true );
}
else
{
DestroyParty( pParty->GetPartyID(), true );
}
}
else
{
if( pParty->GetMemberCount() == 0 )
{
DestroyParty( pParty->GetPartyID(), true );
}
else if( pParty->bIsMove() == false )
{
pParty->SendAllRefreshParty(PARTYREFRESH_NONE);
}
}
return ERROR_NONE;
}
void CDNPartyManager::QueryDelPartyForServer( int iServerID, DWORD dwTick/*=0*/ )
{
if( dwTick == 0 )
dwTick = timeGetTime();
m_DeletePartyForServerList[iServerID] = dwTick;
CDNDBConnection* pDBCon = GetDBConnection();
if( pDBCon && pDBCon->GetActive() )
pDBCon->QueryDelPartyForServer( g_Config.nWorldSetID, iServerID );
}
void CDNPartyManager::QueryDelPartyForServerResponse( const TADelPartyForServer* pPacket )
{
if( pPacket->nRetCode != ERROR_NONE )
return;
m_DeletePartyForServerList.erase( pPacket->iServerID );
}
void CDNPartyManager::QueryGetListParty( DWORD dwTick/*=0*/ )
{
if( dwTick == 0 )
dwTick = timeGetTime();
CDNDBConnection* pDBCon = GetDBConnection();
if( pDBCon && pDBCon->GetActive() )
pDBCon->QueryGetListParty( g_Config.nWorldSetID );
m_dwGetListPartyTick = dwTick;
}
void CDNPartyManager::QueryGetListPartyResponse( const TAGetListParty* pPacket )
{
if( pPacket->nRetCode != ERROR_NONE )
return;
if( pPacket->bIsStart == true )
{
// <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>ƴ<EFBFBD> <20><>Ƽ<EFBFBD><C6BC> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.
for( TMapParty::iterator itor=m_pMapPartyList.begin() ; itor!=m_pMapPartyList.end() ; )
{
CDNParty* pParty = (*itor).second;
if( pParty->GetServerID() != g_Config.nManagedID )
{
m_pMapPartyList.erase( itor++ );
SAFE_DELETE( pParty );
}
else
++itor;
}
}
for( int i=0 ; i<pPacket->nCount ; ++i )
{
PushParty( pPacket->DataArr[i] );
}
}
bool CDNPartyManager::QueryDelParty( TPARTYID PartyID, DWORD dwTick/*=0*/, CDNDBConnection* pLoopDBCon/*=NULL*/ )
{
if( dwTick == 0 )
dwTick = timeGetTime();
/*
CDNParty* pParty = GetParty( PartyID );
if( pParty == NULL )
return false;
*/
m_DeletePartyList[PartyID] = dwTick;
if( pLoopDBCon && pLoopDBCon->GetActive() )
{
pLoopDBCon->QueryDelParty( g_Config.nWorldSetID, PartyID );
return true;
}
CDNDBConnection* pDBCon = GetDBConnection();
if( pDBCon && pDBCon->GetActive() )
pDBCon->QueryDelParty( g_Config.nWorldSetID, PartyID );
return true;
}
void CDNPartyManager::QueryDelPartyResponse( const TADelParty* pPacket )
{
if( pPacket->nRetCode != ERROR_NONE )
return;
m_DeletePartyList.erase( pPacket->PartyID );
}
bool CDNPartyManager::QueryOutParty( TPARTYID PartyID, UINT uiAccountDBID, INT64 biCharacterDBID, UINT nSessionID, Party::QueryOutPartyType::eCode Type, DWORD dwTick/*=0*/, CDNDBConnection* pLoopDBCon/*=NULL*/ )
{
if( dwTick == 0 )
dwTick = timeGetTime();
CDNParty* pParty = GetParty( PartyID );
if( pParty == NULL )
return false;
m_OutPartyList[std::tr1::make_tuple(PartyID,uiAccountDBID,biCharacterDBID,nSessionID,Type)] = dwTick;
if( pLoopDBCon && pLoopDBCon->GetActive() )
{
pLoopDBCon->QueryOutParty( g_Config.nWorldSetID, uiAccountDBID, biCharacterDBID, nSessionID, PartyID, Type );
return true;
}
CDNDBConnection* pDBCon = GetDBConnection();
if( pDBCon && pDBCon->GetActive() )
pDBCon->QueryOutParty( g_Config.nWorldSetID, uiAccountDBID, biCharacterDBID, nSessionID, PartyID, Type );
return true;
}
void CDNPartyManager::QueryOutPartyResponse( const TAOutParty* pPacket )
{
if( pPacket->nRetCode != ERROR_NONE )
return;
m_OutPartyList.erase( std::tr1::make_tuple(pPacket->PartyID,pPacket->nAccountDBID,pPacket->biCharacterDBID,pPacket->nSessionID,pPacket->Type) );
}
void CDNPartyManager::ModParty( const TAModParty* pPacket )
{
CDNParty * pParty = GetParty(pPacket->PartyData.PartyID);
if (!pParty)
return;
if( pPacket->nRetCode != ERROR_NONE )
return;
pParty->SetPartyStructData( pPacket->PartyData );
pParty->SendAllRefreshParty(PARTYREFRESH_MODIFY_INFO);
}
#endif // #if defined( PRE_PARTY_DB )
#if defined( PRE_WORLDCOMBINE_PARTY )
bool CDNPartyManager::QueryGetListWorldParty()
{
CDNDBConnection* pDBCon = GetDBConnection();
if( pDBCon && pDBCon->GetActive() )
pDBCon->QueryGetListWorldParty( g_Config.nWorldSetID );
return true;
}
void CDNPartyManager::QueryGetListWorldPartyResponse( const TAGetListParty* pPacket )
{
// Ÿ<>ٸ<EFBFBD><D9B8><EFBFBD> <20>ϳ<EFBFBD><CFB3>̹Ƿ<CCB9> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD>
TWORLDCOBINEPARTY ExistWorldPartyList;
ExistWorldPartyList.clear();
TWORLDCOBINEPARTY::iterator itor;
WorldCombineParty::WrldCombinePartyData WorldCombineData;
memset( &WorldCombineData, 0, sizeof(WorldCombineParty::WrldCombinePartyData));
for(itor = m_WorldReqCombineParty.begin(); itor != m_WorldReqCombineParty.end();itor++)
{
ExistWorldPartyList.insert( make_pair( itor->first, WorldCombineData) );
}
for( int i=0 ; i<pPacket->nCount ; ++i )
{
itor = m_WorldReqCombineParty.find(pPacket->DataArr[i].iTargetMapIndex);
if( itor == m_WorldReqCombineParty.end())
{
ExistWorldPartyList.insert( make_pair(pPacket->DataArr[i].iTargetMapIndex, WorldCombineData) );
}
}
TWORLDCOBINEPARTY CreateCombineParty;
CreateCombineParty.clear();
g_pDataManager->CheckCombinePartyData(ExistWorldPartyList, CreateCombineParty);
if( !CreateCombineParty.empty() )
{
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ƽ<EFBFBD><C6BC> <20><><EFBFBD><EFBFBD>
for( TWORLDCOBINEPARTY::iterator itor = CreateCombineParty.begin();itor != CreateCombineParty.end();itor++ )
{
WorldCombineParty::WrldCombinePartyData Data = itor->second;
ReqAddWorldParty( &Data );
}
}
}
void CDNPartyManager::ReqAddWorldParty( WorldCombineParty::WrldCombinePartyData *Data )
{
CDNParty* pParty = new CDNParty(0);
Party::Data PartyData;
PartyData.Clear();
PartyData.iBitFlag |= Party::BitFlag::WorldmapAllow;
PartyData.iBitFlag |= Party::BitFlag::JobDice;
PartyData.LocationType = Party::LocationType::Worldmap;
PartyData.iTargetMapIndex = Data->nTargetMap;
PartyData.Type = Data->PartyType;
PartyData.nPartyMaxCount = Data->cPartyMemberMax;
PartyData.cMinLevel = Data->cUserLvLimitMin;
PartyData.iLocationID = Data->nWorldMap;
PartyData.LootItemRank = Data->ItemRank;
PartyData.LootRule = Data->ItemLootRule;
PartyData.TargetMapDifficulty = Data->Difficulty;
_wcscpy( PartyData.wszPartyName, _countof(PartyData.wszPartyName), Data->wszPartyName, (int)wcslen(Data->wszPartyName) );
PartyData.iBitFlag = Data->iBitFlag;
PartyData.nWorldSetID = g_Config.nWorldSetID;
PartyData.nPrimaryIndex = Data->nTargetMap;
pParty->SetPartyStructData(PartyData);
pParty->SetPartyID( Data->nTargetMap );
if(g_pMasterConnection && g_pMasterConnection->GetActive())
{
g_pMasterConnection->SendReqGameID( GameTaskType::Normal, REQINFO_TYPE_PARTY, pParty->GetPartyID(), g_Config.nVillageID, pParty->GetRandomSeed(), pParty->GetPartyMapIndex(), 1, pParty->GetDifficulty(), true, pParty ); // GameID<49><44> <20><>û
}
m_WorldReqCombineParty.insert( make_pair(Data->nTargetMap, *Data) );
}
void CDNPartyManager::DelCombinePartyData( int nPrimaryIndex )
{
TWORLDCOBINEPARTY::iterator itor = m_WorldReqCombineParty.find(nPrimaryIndex);
if( itor != m_WorldReqCombineParty.end() )
m_WorldReqCombineParty.erase(itor);
}
void CDNPartyManager::ClearReqWorldParty( )
{
m_WorldReqCombineParty.clear();
}
#endif