DragonNest/Server/DNGameServer/DnFarmGameTask.cpp
Cussrro 47f7895977 Revert "修复编码问题"
This reverts commit 9e69c01767.
2024-12-21 10:04:04 +08:00

980 lines
28 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 "DnFarmGameTask.h"
#include "DnActor.h"
#include "DNUserSession.h"
#include "EtWorldSector.h"
#include "EtWorldEventControl.h"
#include "GrowingArea.h"
#include "GrowingAreaStateGrowing.h"
#include "DNDBConnection.h"
#include "FishingArea.h"
#include "DNGameDataManager.h"
#include "DNFarmUserSession.h"
#include "DNFishingStatus.h"
#if defined( PRE_ADD_VIP_FARM )
#include "DNFarmGameRoom.h"
#endif // #if defined( PRE_ADD_VIP_FARM )
#include "TimeSet.h"
CDnFarmGameTask::CDnFarmGameTask( CDNGameRoom* pRoom )
:CDnGameTask( pRoom ),m_bPause(false)
{
m_nGameTaskType = GameTaskType::Farm;
m_vUpdateAreaIndex.reserve( Farm::Max::FIELDCOUNT );
m_vUpdateElapsedTimeSec.reserve( Farm::Max::FIELDCOUNT );
}
CDnFarmGameTask::~CDnFarmGameTask()
{
for( std::map<int,CGrowingArea*>::iterator itor=m_mGrowingArea.begin() ; itor!=m_mGrowingArea.end() ; ++itor )
{
SAFE_DELETE( (*itor).second );
}
m_mGrowingArea.clear();
}
bool CDnFarmGameTask::InitializeStage( int nCurrentMapIndex, int nGateIndex, TDUNGEONDIFFICULTY StageDifficulty, int nRandomSeed, bool bContinueStage, bool bDirectConnect, int nGateSelect )
{
bool bResult = CDnGameTask::InitializeStage( nCurrentMapIndex, nGateIndex, StageDifficulty, nRandomSeed, bContinueStage, bDirectConnect, nGateSelect );
if( !bResult )
return false;
InitializeGrowingArea();
InitializeFishingArea();
return true;
}
void CDnFarmGameTask::InitializeGrowingArea()
{
CEtWorldEventControl* pControl = NULL;
CEtWorldSector* pSector = NULL;
CEtWorldEventArea* pArea = NULL;
std::vector<CEtWorldEventArea*> vRespawnArea;
for( DWORD i=0; i<m_pWorld->GetGrid()->GetActiveSectorCount(); i++ )
{
pSector = m_pWorld->GetGrid()->GetActiveSector(i);
pControl = pSector->GetControlFromUniqueID( ETE_FarmGrowingArea );
if( !pControl )
continue;
for( DWORD j=0; j<pControl->GetAreaCount(); j++ )
{
pArea = pControl->GetAreaFromIndex(j);
if( pArea )
{
std::string strString(pArea->GetName());
std::vector<std::string> vSplit;
boost::algorithm::split( vSplit, strString, boost::algorithm::is_any_of("-") );
_ASSERT( vSplit.size() == 2 );
if( vSplit.size() < 2 )
continue;
boost::trim( vSplit[1] );
int iAreaIndex = boost::lexical_cast<int>( vSplit[1] );
FarmGrowingAreaStruct* pData = reinterpret_cast<FarmGrowingAreaStruct*>(pArea->GetData());
if( pData == NULL )
{
_ASSERT(0);
continue;
}
if( pData->nFarmType == Farm::AreaType::Private )
{
if( bIsPrivateArea( iAreaIndex ) == true )
{
_ASSERT(0);
continue;
}
m_mPrivateGrowingAreaInfo.insert( std::make_pair(iAreaIndex,pArea->GetOBB()) );
continue;
}
if( GetGrowingArea( iAreaIndex) )
{
_ASSERT(0);
continue;
}
CGrowingArea* pGrowingArea = new CGrowingArea( reinterpret_cast<CDNFarmGameRoom*>(GetRoom()), iAreaIndex, pArea->GetOBB() );
_ASSERT(pGrowingArea);
if( pGrowingArea == NULL )
continue;
std::pair<std::map<int,CGrowingArea*>::iterator,bool> Ret = m_mGrowingArea.insert( std::make_pair(iAreaIndex,pGrowingArea) );
if( Ret.second == false )
{
_ASSERT(0);
}
}
}
}
}
void CDnFarmGameTask::InitializeSeed( TAGetListField* pPacket )
{
if( pPacket->nRetCode != ERROR_NONE )
{
_ASSERT(0);
return;
}
for( int i=0 ; i<pPacket->cCount ; ++i )
{
CGrowingArea* pArea = GetGrowingArea( pPacket->Fields[i].nFieldIndex );
if( pArea == NULL )
{
_ASSERT(0);
continue;
}
pArea->InitializeSeed( &pPacket->Fields[i] );
}
}
void CDnFarmGameTask::InitializeFishingArea()
{
std::vector <TFishingAreaTableData> vFishingArea;
g_pDataManager->GetFishingAreaTableDataByMapID(GetMapTableID(), vFishingArea);
CEtWorldEventControl* pControl = NULL;
CEtWorldSector* pSector = NULL;
CEtWorldEventArea* pArea = NULL;
for( DWORD i=0; i<m_pWorld->GetGrid()->GetActiveSectorCount(); i++ )
{
pSector = m_pWorld->GetGrid()->GetActiveSector(i);
pControl = pSector->GetControlFromUniqueID( ETE_FarmFishingArea );
if( !pControl )
continue;
for( DWORD j=0; j<pControl->GetAreaCount(); j++ )
{
pArea = pControl->GetAreaFromIndex(j);
if( pArea )
{
int nFishingPointID = -1;
int nFishingAreaID = -1;
std::vector <TFishingAreaTableData>::iterator ii;
for (ii = vFishingArea.begin(); ii != vFishingArea.end(); ii++)
{
if (pArea->GetCreateUniqueID() == (*ii).nMatchedFishingAreaID)
{
nFishingPointID = (*ii).nFishingPointID;
nFishingAreaID = (*ii).nMatchedFishingAreaID;
break;
}
}
if (nFishingPointID == -1)
continue;
TFishingPointTableData * pFishingPoint = g_pDataManager->GetFishingPointTableData(nFishingPointID);
if (pFishingPoint == NULL)
{
_ASSERT(0);
continue;
}
if (GetFishingArea(nFishingAreaID))
{
_ASSERT_EXPR(0, L"Check Fishing Area Index Duplicated");
continue;
}
CFishingArea * pFishingArea = new CFishingArea(reinterpret_cast<CDNFarmGameRoom*>(GetRoom()), nFishingAreaID, pArea->GetOBB(), pFishingPoint);
_ASSERT(pFishingArea);
if(pFishingArea == NULL)
continue;
std::pair<std::map<int,CFishingArea*>::iterator,bool> Ret = m_mFishingArea.insert(std::make_pair(nFishingAreaID, pFishingArea));
if(Ret.second == false)
{
_ASSERT(0);
}
}
}
}
}
bool CDnFarmGameTask::OnInitializeBreakIntoActor( CDNUserSession* pSession, const int iVectorIndex )
{
if( !CDnGameTask::OnInitializeBreakIntoActor( pSession, iVectorIndex ) )
return false;
return true;
}
void CDnFarmGameTask::OnInitializeStartPosition( CDNUserSession* pSession, const int iPartyIndex )
{
DnActorHandle hActor = pSession->GetActorHandle();
OnInitializeRespawnPosition( hActor, true );
}
void CDnFarmGameTask::OnInitializeRespawnPosition( DnActorHandle hActor, const bool bIsStartPosition/*=false*/ )
{
if( hActor )
{
CEtWorldEventControl* pControl = NULL;
CEtWorldSector* pSector = NULL;
CEtWorldEventArea* pArea = NULL;
std::vector<CEtWorldEventArea*> vRespawnArea;
if( bIsStartPosition )
{
for( DWORD i=0; i<m_pWorld->GetGrid()->GetActiveSectorCount(); i++ )
{
pSector = m_pWorld->GetGrid()->GetActiveSector(i);
pControl = pSector->GetControlFromUniqueID( ETE_EventArea );
if( !pControl )
continue;
for( DWORD j=0; j<pControl->GetAreaCount(); j++ )
{
pArea = pControl->GetAreaFromIndex(j);
if( pArea )
{
if( strstr( pArea->GetName(), Farm::StartPositionStr.c_str() ) == pArea->GetName() )
{
PvPRespawnAreaStruct* pStruct = reinterpret_cast<PvPRespawnAreaStruct*>(pArea->GetData());
if( pStruct )
vRespawnArea.push_back( pArea );
}
}
}
}
}
if( !vRespawnArea.empty() )
{
_srand( GetRoom(), hActor->GetSessionID() );
CEtWorldEventArea* pRespawnArea = vRespawnArea[_rand(GetRoom())%vRespawnArea.size()];
EtVector3 vRandPos = GetGenerationRandomPosition( pRespawnArea->GetOBB() );
float fRotate = pRespawnArea->GetRotate();
EtVector2 vStartPos( vRandPos.x,vRandPos.z );
// <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><>ǥ/LOOK <20><><EFBFBD><EFBFBD>
hActor->SetPosition( EtVector3( vStartPos.x, m_pWorld->GetHeight( vStartPos.x, vStartPos.y ), vStartPos.y ) );
EtVector2 vDir;
vDir.x = sin( EtToRadian( fRotate ) );
vDir.y = cos( EtToRadian( fRotate ) );
hActor->Look( vDir );
if( hActor->GetObjectHandle() )
hActor->GetObjectHandle()->Update( *hActor->GetMatEx() );
}
}
}
int CDnFarmGameTask::OnDispatchMessage(CDNUserSession * pSession, int nMainCmd, int nSubCmd, char *pData, int nLen)
{
CGameServerSession::OnDispatchMessage( pSession, nMainCmd, nSubCmd, pData, nLen );
switch( nMainCmd )
{
case CS_FARM:
return OnRecvFarmMessage( pSession, nSubCmd, pData, nLen );
// <20>ϴ<EFBFBD> <20><><EFBFBD><EFBFBD> <20>½<EFBFBD>ũ<EFBFBD><C5A9> <20><><EFBFBD>´<EFBFBD>.
case CS_FISHING:
return OnRecvFishingMessage( pSession, nSubCmd, pData, nLen );
}
return ERROR_NONE;
}
int CDnFarmGameTask::OnRecvFarmMessage(CDNUserSession * pSession, int nSubCmd, char *pData, int nLen)
{
switch( nSubCmd )
{
case eFarm::CS_PLANT:
{
CSFarmPlant* pPacket = reinterpret_cast<CSFarmPlant*>(pData);
if( sizeof(CSFarmPlant)-sizeof(pPacket->AttachItems)+(pPacket->cCount*sizeof(pPacket->AttachItems[0])) != nLen )
return ERROR_INVALIDPACKET;
CGrowingArea* pArea = GetGrowingArea( pPacket->iAreaIndex, pSession );
if( pArea == NULL )
{
_ASSERT(0);
return ERROR_INVALIDPACKET;
}
switch( pPacket->ActionType )
{
case Farm::ActionType::START:
{
pArea->ProcessStartPlant( pSession, pPacket );
break;
}
case Farm::ActionType::CANCEL:
{
pArea->ProcessCancelPlant( pSession, pPacket );
break;
}
case Farm::ActionType::COMPLETE:
{
pArea->QueryCompletePlant( pSession, pPacket );
break;
}
default:
{
_ASSERT(0);
return ERROR_INVALIDPACKET;
}
}
return ERROR_NONE;
}
case eFarm::CS_HARVEST:
{
if( sizeof(CSFarmHarvest) != nLen )
return ERROR_INVALIDPACKET;
CSFarmHarvest* pPacket = reinterpret_cast<CSFarmHarvest*>(pData);
CGrowingArea* pArea = GetGrowingArea( pPacket->iAreaIndex, pSession );
if( pArea == NULL )
{
_ASSERT(0);
return ERROR_INVALIDPACKET;
}
switch( pPacket->ActionType )
{
case Farm::ActionType::START:
{
pArea->ProcessStartHarvest( pSession, pPacket );
break;
}
case Farm::ActionType::CANCEL:
{
pArea->ProcessCancelHarvest( pSession, pPacket );
break;
}
case Farm::ActionType::COMPLETE:
{
pArea->QueryCompleteHarvest( pSession, pPacket );
break;
}
default:
{
_ASSERT(0);
return ERROR_INVALIDPACKET;
}
}
return ERROR_NONE;
}
case eFarm::CS_ADD_WATER:
{
#if defined( PRE_REMOVE_FARM_WATER )
return ERROR_INVALIDPACKET;
#endif // #if defined( PRE_REMOVE_FARM_WATER )
if( sizeof(CSFarmAddWater) != nLen )
return ERROR_INVALIDPACKET;
const CSFarmAddWater* pPacket = reinterpret_cast<CSFarmAddWater*>(pData);
CGrowingArea* pArea = GetGrowingArea( pPacket->iAreaIndex, pSession );
if( pArea == NULL )
{
_ASSERT(0);
return ERROR_INVALIDPACKET;
}
switch( pPacket->ActionType )
{
case Farm::ActionType::START:
{
pArea->ProcessStartAddWater( pSession, pPacket );
break;
}
case Farm::ActionType::CANCEL:
{
pArea->ProcessCancelAddWater( pSession, pPacket );
break;
}
case Farm::ActionType::COMPLETE:
{
pArea->QueryCompleteAddWater( pSession, pPacket );
break;
}
default:
{
_ASSERT(0);
return ERROR_INVALIDPACKET;
}
}
return ERROR_NONE;
}
case eFarm::CS_WAREHOUSE_LIST:
{
if( 0 != nLen )
return ERROR_INVALIDPACKET;
GetRoom()->GetDBConnection()->QueryGetListHarvestDepotItem( GetRoom()->GetDBThreadID(), GetRoom()->GetWorldSetID(), pSession->GetAccountDBID(), pSession->GetCharacterDBID(), static_cast<CDNFarmUserSession*>(pSession)->GetLastWareHouseItemUniqueID() );
return ERROR_NONE;
}
case eFarm::CS_TAKE_WAREHOUSE_ITEM:
{
if( sizeof(CSFarmTakeWareHouseItem) != nLen )
return ERROR_INVALIDPACKET;
const CSFarmTakeWareHouseItem* pPacket = reinterpret_cast<CSFarmTakeWareHouseItem*>(pData);
const TItem* pItem = static_cast<CDNFarmUserSession*>(pSession)->GetFarmWareHouseItem( pPacket->biUniqueID );
if( pItem == NULL )
{
pSession->SendFarmTakeWareHouseItem( ERROR_ITEM_NOTFOUND, pPacket->biUniqueID );
return ERROR_NONE;
}
int iEmptyIndex = pSession->GetItem()->FindBlankInventorySlot();
if( iEmptyIndex == -1 )
{
pSession->SendFarmTakeWareHouseItem( ERROR_ITEM_INVENTORY_NOTENOUGH, pPacket->biUniqueID );
return ERROR_NONE;
}
pSession->GetItem()->CreateInvenWholeItemByIndex( iEmptyIndex, *const_cast<TItem*>(pItem) );
pSession->SendFarmTakeWareHouseItem( ERROR_NONE, pPacket->biUniqueID );
pSession->GetDBConnection()->QueryChangeItemLocation( pSession, pItem->nSerial, 0, pItem->nItemID, DBDNWorldDef::ItemLocation::Inventory, iEmptyIndex, pItem->wCount, false, 0, false );
pSession->GetDBConnection()->QueryGetCountHarvestDepotItem( pSession );
static_cast<CDNFarmUserSession*>(pSession)->DeleteFarmWareHouseItem( pPacket->biUniqueID );
return ERROR_NONE;
}
}
return ERROR_UNKNOWN_HEADER;
}
int CDnFarmGameTask::OnRecvFishingMessage(CDNUserSession * pSession, int nSubCmd, char *pData, int nLen)
{
switch (nSubCmd)
{
case eFishing::CS_READYFISHING:
{
if (sizeof(CSFishingReady) != nLen)
return ERROR_INVALIDPACKET;
//<2F><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>ִ<EFBFBD><D6B4><EFBFBD> Ȯ<><C8AE><EFBFBD>ϰ<EFBFBD> <20>κ<EFBFBD><CEBA><EFBFBD> <20><><EFBFBD>õ<EFBFBD><C3B5><EFBFBD><EFBFBD><EFBFBD> <20>ִ<EFBFBD><D6B4><EFBFBD> Ȯ<><C8AE><EFBFBD><EFBFBD> <20><> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>, <20><><EFBFBD>۽<EFBFBD><DBBD><EFBFBD><EFBFBD>ش<EFBFBD>.
if (static_cast<CDNFarmUserSession*>(pSession)->GetIsFishing())
return ERROR_NONE;
#if defined( PRE_ADD_VIP_FARM )
#if defined( PRE_ADD_FARM_DOWNSCALE )
if( static_cast<CDNFarmGameRoom*>(GetRoom())->GetAttr()&Farm::Attr::Vip )
#else
if( static_cast<CDNFarmGameRoom*>(GetRoom())->GetAttr() == Farm::Attr::Vip )
#endif // #if defined( PRE_ADD_FARM_DOWNSCALE )
{
if( pSession->bIsFarmVip() == false )
{
pSession->SendFishingReadyResult(ERROR_FARM_INVALID_VIP);
return ERROR_NONE;
}
}
#endif // #if defined( PRE_ADD_VIP_FARM )
CSFishingReady * pPacket = (CSFishingReady*)pData;
CFishingArea * pFishing = GetFishingArea(pSession->GetActorHandle()->GetPosition());
if (pFishing)
{
#ifdef PRE_ADD_CASHFISHINGITEM
TFishingMeritInfo FishingMerit;
memset(&FishingMerit, 0, sizeof(TFishingMeritInfo));
int nRet = pFishing->CheckFishingRequirement(static_cast<CDNFarmUserSession*>(pSession), pPacket->ToolInfo, FishingMerit);
#else //#ifdef PRE_ADD_CASHFISHINGITEM
INT64 nBaitSerial = 0;
int nRet = pFishing->CheckFishingRequirement(static_cast<CDNFarmUserSession*>(pSession), pPacket->nFishingRodInvenIdx, pPacket->nFishingBaitInvenIdx, nBaitSerial);
#endif //#ifdef PRE_ADD_CASHFISHINGITEM
if (nRet != ERROR_NONE)
{
pSession->SendFishingReadyResult(nRet);
return ERROR_NONE;
}
//<2F>⺻ȯ<E2BABB>οϷ<CEBF> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><20><><EFBFBD><EFBFBD> <20><><EFBFBD>¸<EFBFBD> <20><><EFBFBD>ǿ<EFBFBD> <20>߰<EFBFBD>
if (static_cast<CDNFarmUserSession*>(pSession)->SetFishingStatus(pFishing))
{
pSession->SendFishingReadyResult(ERROR_NONE);
return ERROR_NONE;
}
}
pSession->SendFishingReadyResult(ERROR_FISHING_FAIL);
return ERROR_NONE;
}
case eFishing::CS_CASTBAIT:
{
if (sizeof(CSCastBait) != nLen)
return ERROR_INVALIDPACKET;
if (static_cast<CDNFarmUserSession*>(pSession)->GetIsFishing())
return ERROR_NONE;
#if defined( PRE_ADD_VIP_FARM )
#if defined( PRE_ADD_FARM_DOWNSCALE )
if( static_cast<CDNFarmGameRoom*>(GetRoom())->GetAttr()&Farm::Attr::Vip )
#else
if( static_cast<CDNFarmGameRoom*>(GetRoom())->GetAttr() == Farm::Attr::Vip )
#endif // #if defined( PRE_ADD_FARM_DOWNSCALE )
{
if( pSession->bIsFarmVip() == false )
{
pSession->SendFishingCastBaitResult(ERROR_FARM_INVALID_VIP);
return ERROR_NONE;
}
}
#endif // #if defined( PRE_ADD_VIP_FARM )
CSCastBait * pPacket = (CSCastBait*)pData;
CDNFishingStatus * pStatus = static_cast<CDNFarmUserSession*>(pSession)->GetFishingStatus();
if (pStatus)
{
CFishingArea * pArea = pStatus->GetFishingArea();
if (pArea)
{
#ifdef PRE_ADD_CASHFISHINGITEM
TFishingMeritInfo FishingMerit;
memset(&FishingMerit, 0, sizeof(TFishingMeritInfo));
int nRet = pArea->CheckFishingRequirement(static_cast<CDNFarmUserSession*>(pSession), pPacket->ToolInfo, FishingMerit);
#else //#ifdef PRE_ADD_CASHFISHINGITEM
INT64 nBaitSerial = 0;
int nRet = pArea->CheckFishingRequirement(static_cast<CDNFarmUserSession*>(pSession), pPacket->nFishingRodInvenIdx, pPacket->nFishingBaitInvenIdx, nBaitSerial);
#endif //#ifdef PRE_ADD_CASHFISHINGITEM
if (nRet != ERROR_NONE)
{
pSession->SendFishingCastBaitResult(nRet);
return ERROR_NONE;
}
//<2F><><EFBFBD><EFBFBD><EFBFBD>̶<EFBFBD><CCB6><EFBFBD> <20><><EFBFBD><EFBFBD>!
#ifdef PRE_ADD_CASHFISHINGITEM
if (pStatus->StartFishing(pPacket->eCastType, FishingMerit))
#else //#ifdef PRE_ADD_CASHFISHINGITEM
if (pStatus->StartFishing(pPacket->eCastType, pPacket->nFishingBaitInvenIdx, nBaitSerial))
#endif //#ifdef PRE_ADD_CASHFISHINGITEM
return ERROR_NONE;
}
}
pSession->SendFishingCastBaitResult(ERROR_FISHING_CASTBAIT_FAIL);
return ERROR_NONE;
}
case eFishing::CS_STOPFISHING:
{
if (0 != nLen)
return ERROR_INVALIDPACKET;
if (static_cast<CDNFarmUserSession*>(pSession)->GetIsFishing() == false)
return ERROR_NONE;
CDNFishingStatus * pStatus = static_cast<CDNFarmUserSession*>(pSession)->GetFishingStatus();
if (pStatus)
{
if (pStatus->StopFishing())
return ERROR_NONE;
}
pSession->SendFishingStopFishingResult(ERROR_FISHING_STOPFISHING_FAIL);
return ERROR_NONE;
}
case eFishing::CS_PULLINGROD:
{
if (sizeof(CSPullingRod) != nLen)
return ERROR_INVALIDPACKET;
if (static_cast<CDNFarmUserSession*>(pSession)->GetIsFishing() == false)
return ERROR_NONE;
CSPullingRod * pPacket = (CSPullingRod*)pData;
CDNFishingStatus * pStatus = static_cast<CDNFarmUserSession*>(pSession)->GetFishingStatus();
if (pStatus)
pStatus->FishingControl(pPacket->ePullingControl);
return ERROR_NONE;
}
case eFishing::CS_FISHINGREWARD:
{
if (nLen != 0)
return ERROR_INVALIDPACKET;
CDNFishingStatus * pStatus = static_cast<CDNFarmUserSession*>(pSession)->GetFishingStatus();
if (pStatus)
pStatus->CheckAndRewardItem();
return ERROR_NONE;
}
}
return ERROR_UNKNOWN_HEADER;
}
void CDnFarmGameTask::Process( LOCAL_TIME LocalTime, float fDelta )
{
CDnGameTask::Process( LocalTime, fDelta );
ProcessGrowingArea( fDelta );
//ProcessFishingArea(fDelta);
}
void CDnFarmGameTask::ProcessGrowingArea( float fDelta )
{
if( m_bPause )
return;
m_vUpdateAreaIndex.clear();
m_vUpdateElapsedTimeSec.clear();
for( std::map<int,CGrowingArea*>::iterator itor=m_mGrowingArea.begin() ; itor!=m_mGrowingArea.end() ; ++itor )
{
CGrowingArea* pArea = (*itor).second;
pArea->Process( fDelta );
// DB Update <20>˻<EFBFBD>
if( pArea->CanDBUpdate() )
{
m_vUpdateAreaIndex.push_back( pArea->GetIndex() );
m_vUpdateElapsedTimeSec.push_back( pArea->GetPlantSeed()->GetElapsedTimeSec() );
}
}
if( m_vUpdateAreaIndex.size() )
{
GetRoom()->GetDBConnection()->QueryModFieldElapsedTime( GetRoom()->GetDBThreadID(), GetRoom()->GetWorldSetID(), 0, GetRoom()->GetFarmIndex(), m_vUpdateAreaIndex, m_vUpdateElapsedTimeSec );
}
for( std::map<INT64,std::vector<CGrowingArea*>>::iterator itor=m_mPrivateGrowingArea.begin() ; itor!=m_mPrivateGrowingArea.end() ; ++itor )
{
m_vUpdateAreaIndex.clear();
m_vUpdateElapsedTimeSec.clear();
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
{
CGrowingArea* pArea = (*itor).second[i];
pArea->Process( fDelta );
// DB Update <20>˻<EFBFBD>
if( pArea->CanDBUpdate() )
{
m_vUpdateAreaIndex.push_back( pArea->GetIndex() );
m_vUpdateElapsedTimeSec.push_back( pArea->GetPlantSeed()->GetElapsedTimeSec() );
}
}
if( m_vUpdateAreaIndex.size() )
GetRoom()->GetDBConnection()->QueryModFieldForCharacterElapsedTime( GetRoom()->GetDBThreadID(), GetRoom()->GetWorldSetID(), 0, (*itor).first, m_vUpdateAreaIndex, m_vUpdateElapsedTimeSec );
}
}
CGrowingArea* CDnFarmGameTask::GetGrowingArea( const int iIndex, CDNUserSession* pSession/*=NULL*/ )
{
if( bIsPrivateArea(iIndex) == true )
{
if( pSession == NULL )
return NULL;
std::map<INT64,std::vector<CGrowingArea*>>::iterator itor= m_mPrivateGrowingArea.find( pSession->GetCharacterDBID() );
if( itor == m_mPrivateGrowingArea.end() )
return NULL;
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
{
if( (*itor).second[i]->GetIndex() == iIndex )
return (*itor).second[i];
}
return NULL;
}
std::map<int,CGrowingArea*>::iterator itor = m_mGrowingArea.find( iIndex );
if( itor != m_mGrowingArea.end() )
return (*itor).second;
return NULL;
}
CFishingArea * CDnFarmGameTask::GetFishingArea(int nIdx)
{
std::map <int, CFishingArea*>::iterator ii = m_mFishingArea.find(nIdx);
return ii != m_mFishingArea.end() ? (*ii).second : NULL;
}
CFishingArea * CDnFarmGameTask::GetFishingArea(EtVector3 * pPosition)
{
CFishingArea * pFishingArea = NULL;
std::map <int, CFishingArea*>::iterator ii;
for (ii = m_mFishingArea.begin(); ii != m_mFishingArea.end(); ii++)
{
if ((*ii).second->CheckInside(*pPosition))
{
pFishingArea = (*ii).second;
break;
}
}
return pFishingArea;
}
CFishingArea * CDnFarmGameTask::GetFishingArea(CDNUserSession * pSession)
{
if (!pSession || !pSession->GetActorHandle())
return NULL;
std::map <int, CFishingArea*>::iterator ii;
for (ii = m_mFishingArea.begin(); ii != m_mFishingArea.end(); ii++)
{
if ((*ii).second->CheckInside(*pSession->GetActorHandle()->GetPosition()))
return (*ii).second;
}
return NULL;
}
void CDnFarmGameTask::SyncArea( CDNUserSession* pBreakIntoGameSession )
{
if( pBreakIntoGameSession == NULL )
{
_ASSERT(0);
return;
}
SCAreaInfoList TxPacket;
memset( &TxPacket, 0, sizeof(TxPacket) );
for( std::map<int,CGrowingArea*>::iterator itor=m_mGrowingArea.begin() ; itor!=m_mGrowingArea.end() ; ++itor )
{
CGrowingArea* pArea = (*itor).second;
CPlantSeed* pSeed = pArea->GetPlantSeed();
if( pSeed == NULL )
continue;
pArea->MakeAreaInfo( TxPacket.AreaInfos[TxPacket.unCount] );
++TxPacket.unCount;
}
std::map<INT64,std::vector<CGrowingArea*>>::iterator itor = m_mPrivateGrowingArea.find( pBreakIntoGameSession->GetCharacterDBID() );
if( itor != m_mPrivateGrowingArea.end() )
{
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
{
CGrowingArea* pArea = (*itor).second[i];
CPlantSeed* pSeed = pArea->GetPlantSeed();
if( pSeed == NULL )
continue;
pArea->MakeAreaInfo( TxPacket.AreaInfos[TxPacket.unCount] );
// <20><><EFBFBD><EFBFBD> <20><><EFBFBD>۹<EFBFBD><DBB9><EFBFBD> <20≯<EFBFBD><CCB8><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20>־<EFBFBD><D6BE>ش<EFBFBD>.
_wcscpy( TxPacket.AreaInfos[TxPacket.unCount].wszCharName, NAMELENMAX, pBreakIntoGameSession->GetCharacterName(), static_cast<int>(wcslen(pBreakIntoGameSession->GetCharacterName())));
++TxPacket.unCount;
}
}
int iSize = sizeof(TxPacket)-sizeof(TxPacket.AreaInfos)+TxPacket.unCount*sizeof(TxPacket.AreaInfos[0]);
pBreakIntoGameSession->AddSendData( SC_FARM, eFarm::SC_AREAINFO_LIST, reinterpret_cast<char*>(&TxPacket), iSize );
}
void CDnFarmGameTask::SyncFishing( CDNUserSession* pBreakIntoGameSession )
{
if( pBreakIntoGameSession == NULL )
{
_ASSERT(0);
return;
}
SCFishingPlayer TxPacket;
memset( &TxPacket, 0, sizeof(TxPacket) );
for( UINT i=0 ; i<GetUserCount() ; ++i )
{
CDNFarmUserSession* pSession = static_cast<CDNFarmUserSession*>(GetUserData(i));
if( pSession && pSession->GetIsFishingReward() )
{
TxPacket.nSessionID = pSession->GetSessionID();
#ifdef PRE_ADD_CASHFISHINGITEM
TxPacket.nRodItemID = pSession->GetFishingRodItemID();
#endif //#ifdef PRE_ADD_CASHFISHINGITEM
pBreakIntoGameSession->AddSendData( SC_FISHING, eFishing::SC_FISHINGPLAYER, reinterpret_cast<char*>(&TxPacket), sizeof(TxPacket) );
}
}
}
bool CDnFarmGameTask::UpdateCharacterName( MAChangeCharacterName* pPacket )
{
bool bBroadcast = false;
for( std::map<int,CGrowingArea*>::iterator itor=m_mGrowingArea.begin() ; itor!=m_mGrowingArea.end() ; ++itor )
{
CGrowingArea* pArea = (*itor).second;
if (!pArea)
continue;
CPlantSeed* pSeed = pArea->GetPlantSeed();
if (!pSeed)
continue;
if (pSeed->UpdateOwnerCharacterName(pPacket))
bBroadcast = true;
}
return bBroadcast;
}
void CDnFarmGameTask::InitializePrivateGrowingArea( TAGetListFieldForCharacter* pPacket )
{
if( pPacket->nRetCode != ERROR_NONE )
return;
std::map<INT64,std::vector<CGrowingArea*>>::iterator itor = m_mPrivateGrowingArea.find( pPacket->biCharacterDBID );
if( itor != m_mPrivateGrowingArea.end() )
{
_DANGER_POINT();
// <20><><EFBFBD>α<EFBFBD><CEB1><EFBFBD><EFBFBD><EFBFBD> <20>ߺ<EFBFBD> <20><> <20><> <20><><EFBFBD><EFBFBD>. <20><> <20><><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>.
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
{
SAFE_DELETE( (*itor).second[i] );
}
m_mPrivateGrowingArea.erase( itor );
}
m_mPrivateGrowingArea.insert( std::make_pair(pPacket->biCharacterDBID, std::vector<CGrowingArea*>()) );
std::map<INT64,std::vector<CGrowingArea*>>::iterator PrivateItor = m_mPrivateGrowingArea.find( pPacket->biCharacterDBID );
if( m_mPrivateGrowingArea.find( pPacket->biCharacterDBID ) == m_mPrivateGrowingArea.end() )
{
_DANGER_POINT();
return;
}
// PrivateArea <20><><EFBFBD><EFBFBD>
for( std::map<int,SOBB*>::iterator itor=m_mPrivateGrowingAreaInfo.begin() ; itor!=m_mPrivateGrowingAreaInfo.end() ; ++itor )
{
CGrowingArea* pGrowingArea = new CGrowingArea( reinterpret_cast<CDNFarmGameRoom*>(GetRoom()), (*itor).first, (*itor).second, true, pPacket->biCharacterDBID );
_ASSERT(pGrowingArea);
if( pGrowingArea == NULL )
continue;
(*PrivateItor).second.push_back( pGrowingArea );
}
// Seed <20><><EFBFBD><EFBFBD>
for( int i=0 ; i<pPacket->cCount ; ++i )
{
CTimeSet CurTime;
CTimeSet UpdateTime( pPacket->Fields[i].tUpdateDate, true );
INT64 biElapsedSec = CurTime-UpdateTime;
TFarmField Field;
memset( &Field, 0, sizeof(Field) );
Field.nFieldIndex = pPacket->Fields[i].nFieldIndex;
Field.biCharacterDBID = pPacket->biCharacterDBID;
Field.iItemID = pPacket->Fields[i].iItemID;
Field.iElapsedTimeSec = pPacket->Fields[i].iElapsedTimeSec;
memcpy( Field.AttachItems, pPacket->Fields[i].AttachItems, sizeof(pPacket->Fields[i].AttachItems) );
// <20>ð<EFBFBD> Update
if( biElapsedSec > 0 )
{
Field.iElapsedTimeSec += static_cast<int>(biElapsedSec);
}
for( UINT j=0 ; j<(*PrivateItor).second.size() ; ++j )
{
if( (*PrivateItor).second[j]->GetIndex() == Field.nFieldIndex )
{
(*PrivateItor).second[j]->InitializeSeed( &Field, biElapsedSec > 0 ? true : false );
}
}
}
}
void CDnFarmGameTask::OnLeaveUser( UINT uiSessionID )
{
CDNUserSession* pSession = GetRoom()->GetUserSession( uiSessionID );
if( pSession == NULL )
return;
std::map<INT64,std::vector<CGrowingArea*>>::iterator itor = m_mPrivateGrowingArea.find( pSession->GetCharacterDBID() );
if( itor != m_mPrivateGrowingArea.end() )
{
// ElapsedUpdate
std::vector<int> vUpdateAreaIndex;
std::vector<int> vUpdateElapsedTimeSec;
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
{
CGrowingArea* pArea = (*itor).second[i];
if( pArea && pArea->GetPlantSeed() )
{
vUpdateAreaIndex.push_back( pArea->GetIndex() );
vUpdateElapsedTimeSec.push_back( pArea->GetPlantSeed()->GetElapsedTimeSec() );
}
}
if( vUpdateAreaIndex.size() )
GetRoom()->GetDBConnection()->QueryModFieldForCharacterElapsedTime( GetRoom()->GetDBThreadID(), GetRoom()->GetWorldSetID(), 0, (*itor).first, vUpdateAreaIndex, vUpdateElapsedTimeSec );
// Delete
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
SAFE_DELETE( (*itor).second[i] );
m_mPrivateGrowingArea.erase( itor );
}
}
void CDnFarmGameTask::OnStartGuildWarFinal()
{
for( std::map<int,CGrowingArea*>::iterator itor=m_mGrowingArea.begin() ; itor!=m_mGrowingArea.end() ; ++itor )
{
CGrowingArea* pArea = (*itor).second;
if( pArea->GetState() == Farm::AreaState::GROWING )
{
CPlantSeed* pSeed = pArea->GetPlantSeed();
if( pSeed )
pSeed->ForceComplete();
}
else if( pArea->GetState() == Farm::AreaState::COMPLETED )
{
pArea->QueryCompleteHarvest( NULL, NULL, true );
}
}
}
bool CDnFarmGameTask::bIsPrivateArea( int iAreaIndex )
{
std::map<int,SOBB*>::iterator itor = m_mPrivateGrowingAreaInfo.find( iAreaIndex );
if( itor == m_mPrivateGrowingAreaInfo.end() )
return false;
return true;
}
bool CDnFarmGameTask::CheckActivePrivateFieldCount( CDNUserSession* pSession )
{
std::map<INT64,std::vector<CGrowingArea*>>::iterator itor = m_mPrivateGrowingArea.find( pSession->GetCharacterDBID() );
if( itor == m_mPrivateGrowingArea.end() )
return false;
int iPrivateSeedCount = 0;
for( UINT i=0 ; i<(*itor).second.size() ; ++i )
{
if( (*itor).second[i]->GetPlantSeed() )
++iPrivateSeedCount;
}
int iAvailCount = Farm::Max::PRIVATEPLANTCOUNT+pSession->GetItem()->GetExtendPrivateFarmFieldCount();
return iAvailCount > iPrivateSeedCount;
}