Tipologie server(PvM / PvP):-
*Resursă folosită: http://just4metin.ro/sursa/susrsa-t45212.html
*ServerFiles utilizat:clean
*Syserr:
0802 20:37:07254 :: AttributeError
0802 20:37:07255 :: :
0802 20:37:07255 :: '0802 20:37:28959 :: AttributeError
0802 20:37:28960 :: :
0802 20:37:2890802 20:38:38185 :: Unknown Server Command LuaToPython #quest_input# | LuaToPytho0802 20:38:09329 :: CInstanceBase::PushTCPState You can't send move packets to yourself!
0802 20:38:09484 :: CRaceManager::GetRaceDataPointer: cannot load data by dwRaceIndex 20802 20:43:26638 :: CInstanceBase::PushTCPState You can't send move packets to yourself!
0802 20:43:26789 :: CRaceManager::GetRaceDataPointer: cannot load data by dwRaceIndex 20406
0802 20:43:26789 :: CPythonCharacterManager::CreateInstance VID[14691] Race[20406]
0802 20:49:06742 :: CInstanceBase::PushTCPState You can't send move packets to yourself!
0802 20:49:06843 :: CRaceManager::GetRaceDataPointer: cannot load data by dwRaceIndex 20406
0802 20:49:06844 :: CPythonCharacterManager::CreateInstance VID[14691] Race[20406]
0802 20:50:14765 :: Traceback (most recent call last):
0802 20:37:07255 :: :
0802 20:37:07255 :: '0802 20:37:28959 :: AttributeError
0802 20:37:28960 :: :
0802 20:37:2890802 20:38:38185 :: Unknown Server Command LuaToPython #quest_input# | LuaToPytho0802 20:38:09329 :: CInstanceBase::PushTCPState You can't send move packets to yourself!
0802 20:38:09484 :: CRaceManager::GetRaceDataPointer: cannot load data by dwRaceIndex 20802 20:43:26638 :: CInstanceBase::PushTCPState You can't send move packets to yourself!
0802 20:43:26789 :: CRaceManager::GetRaceDataPointer: cannot load data by dwRaceIndex 20406
0802 20:43:26789 :: CPythonCharacterManager::CreateInstance VID[14691] Race[20406]
0802 20:49:06742 :: CInstanceBase::PushTCPState You can't send move packets to yourself!
0802 20:49:06843 :: CRaceManager::GetRaceDataPointer: cannot load data by dwRaceIndex 20406
0802 20:49:06844 :: CPythonCharacterManager::CreateInstance VID[14691] Race[20406]
0802 20:50:14765 :: Traceback (most recent call last):
*Detalii suplimentare:sistemul functioneaza,imi apare 3,2,1,go,win/lose,dar cand incepe duelul imi apare jos ?????!? si la finalul duelului imi apare o casuta pentru a introduce ceva,dupa apas ok dispare.
affect.h
#ifndef __INC_AFFECT_H
#define __INC_AFFECT_H
class CAffect
{
public:
DWORD dwType;
BYTE bApplyOn;
long lApplyValue;
DWORD dwFlag;
long lDuration;
long lSPCost;
static CAffect* Acquire();
static void Release(CAffect* p);
};
enum EAffectTypes
{
AFFECT_NONE,
AFFECT_MOV_SPEED = 200,
AFFECT_ATT_SPEED,
AFFECT_ATT_GRADE,
AFFECT_INVISIBILITY,
AFFECT_STR,
AFFECT_DEX, // 205
AFFECT_CON,
AFFECT_INT,
AFFECT_FISH_MIND_PILL,
AFFECT_POISON,
AFFECT_STUN, // 210
AFFECT_SLOW,
AFFECT_DUNGEON_READY,
AFFECT_DUNGEON_UNIQUE,
AFFECT_BUILDING,
AFFECT_REVIVE_INVISIBLE, // 215
AFFECT_FIRE,
AFFECT_CAST_SPEED,
AFFECT_HP_RECOVER_CONTINUE,
AFFECT_SP_RECOVER_CONTINUE,
AFFECT_POLYMORPH, // 220
AFFECT_MOUNT,
AFFECT_WAR_FLAG, // 222
AFFECT_BLOCK_CHAT, // 223
AFFECT_CHINA_FIREWORK,
AFFECT_BOW_DISTANCE, // 225
AFFECT_DEF_GRADE, // 226
#ifdef ENABLE_WOLFMAN_CHARACTER
AFFECT_BLEEDING, // 227
#endif
AFFECT_PREMIUM_START = 500,
AFFECT_EXP_BONUS = 500, // ??? ??
AFFECT_ITEM_BONUS = 501, // ??? ??
AFFECT_SAFEBOX = 502, // PREMIUM_SAFEBOX,
AFFECT_AUTOLOOT = 503, // PREMIUM_AUTOLOOT,
AFFECT_FISH_MIND = 504, // PREMIUM_FISH_MIND,
AFFECT_MARRIAGE_FAST = 505, // ??? ??
AFFECT_GOLD_BONUS = 506, // ? ???? 50%??
AFFECT_PREMIUM_END = 509,
AFFECT_MALL = 510, // ? ??? ???
AFFECT_NO_DEATH_PENALTY = 511, // ??? ?? (???? ???? ?? ????)
AFFECT_SKILL_BOOK_BONUS = 512, // ??? ?? (? ?? ?? ??? 50% ??)
AFFECT_SKILL_NO_BOOK_DELAY = 513, // ????
AFFECT_HAIR = 514, // ?? ??
AFFECT_COLLECT = 515, //?????
AFFECT_EXP_BONUS_EURO_FREE = 516, // ??? ?? (?? ?? 14 ?? ?? ?? ??)
AFFECT_EXP_BONUS_EURO_FREE_UNDER_15 = 517,
AFFECT_UNIQUE_ABILITY = 518,
AFFECT_CUBE_1,
AFFECT_CUBE_2,
AFFECT_CUBE_3,
AFFECT_CUBE_4,
AFFECT_CUBE_5,
AFFECT_CUBE_6,
AFFECT_CUBE_7,
AFFECT_CUBE_8,
AFFECT_CUBE_9,
AFFECT_CUBE_10,
AFFECT_CUBE_11,
AFFECT_CUBE_12,
AFFECT_BLEND,
AFFECT_HORSE_NAME,
AFFECT_MOUNT_BONUS,
AFFECT_AUTO_HP_RECOVERY = 534,
AFFECT_AUTO_SP_RECOVERY = 535,
AFFECT_DRAGON_SOUL_QUALIFIED = 540,
AFFECT_DRAGON_SOUL_DECK_0 = 541,
AFFECT_DRAGON_SOUL_DECK_1 = 542,
AFFECT_PVP_START = 543,
AFFECT_PVP_WIN = 544,
AFFECT_RAMADAN_ABILITY = 300,
AFFECT_RAMADAN_RING = 301,
AFFECT_NOG_ABILITY = 302,
AFFECT_HOLLY_STONE_POWER = 303,
AFFECT_QUEST_START_IDX = 1000
};
enum EAffectBits
{
AFF_NONE,
AFF_YMIR,
AFF_INVISIBILITY,
AFF_SPAWN,
AFF_POISON,
AFF_SLOW,
AFF_STUN,
AFF_DUNGEON_READY, // ???? ?? ??
AFF_DUNGEON_UNIQUE, // ?? ??? (??????? ??????)
AFF_BUILDING_CONSTRUCTION_SMALL,
AFF_BUILDING_CONSTRUCTION_LARGE,
AFF_BUILDING_UPGRADE,
AFF_MOV_SPEED_POTION,
AFF_ATT_SPEED_POTION,
AFF_FISH_MIND,
AFF_JEONGWIHON, // ???
AFF_GEOMGYEONG, // ??
AFF_CHEONGEUN, // ???
AFF_GYEONGGONG, // ???
AFF_EUNHYUNG, // ???
AFF_GWIGUM, // ??
AFF_TERROR, // ??
AFF_JUMAGAP, // ???
AFF_HOSIN, // ??
AFF_BOHO, // ??
AFF_KWAESOK, // ??
AFF_MANASHIELD, // ????
AFF_MUYEONG, // ??? affect
AFF_REVIVE_INVISIBLE, // ??? ???? ??
AFF_FIRE, // ?? ? ???
AFF_GICHEON, // ????
AFF_JEUNGRYEOK, // ???
AFF_TANHWAN_DASH, // ???? ??????
AFF_PABEOP, // ???
AFF_CHEONGEUN_WITH_FALL, // ???
AFF_POLYMORPH,
AFF_WAR_FLAG1,
AFF_WAR_FLAG2,
AFF_WAR_FLAG3,
AFF_CHINA_FIREWORK,
AFF_HAIR, // ??
AFF_GERMANY, // ??
AFF_RAMADAN_RING,
#ifdef ENABLE_WOLFMAN_CHARACTER
AFF_BLEEDING, // 42
AFF_RED_POSSESSION, // 44
AFF_BLUE_POSSESSION, // 43
#endif
AFF_PVP_START,
AFF_PVP_WIN,
AFF_BITS_MAX
};
extern void SendAffectAddPacket(LPDESC d, CAffect * pkAff);
// AFFECT_DURATION_BUG_FIX
enum AffectVariable
{
// Affect? ???? ??? ??? ? ?? ??.
// ??? ?? ??? ??? ?? ???? ???? ??????.
//// 24??? ???? 25??? ??.
// ... 25?? ????? ???? 29bit ???? ?? ??? ????...
// collect quest?? ?? ??? 60??? ???? ????, ??? 60??? ??.
INFINITE_AFFECT_DURATION = 60 * 365 * 24 * 60 * 60
};
// END_AFFECT_DURATION_BUG_FIX
#endif
#include "stdafx.h"
#include "constants.h"
#include "pvp.h"
#include "crc32.h"
#include "packet.h"
#include "desc.h"
#include "desc_manager.h"
#include "char.h"
#include "char_manager.h"
#include "config.h"
#include "sectree_manager.h"
#include "buffer_manager.h"
#include "locale_service.h"
using namespace std;
CPVP::CPVP(DWORD dwPID1, DWORD dwPID2)
{
if (dwPID1 > dwPID2)
{
m_players[0].dwPID = dwPID1;
m_players[1].dwPID = dwPID2;
m_players[0].bAgree = true;
}
else
{
m_players[0].dwPID = dwPID2;
m_players[1].dwPID = dwPID1;
m_players[1].bAgree = true;
}
DWORD adwID[2];
adwID[0] = m_players[0].dwPID;
adwID[1] = m_players[1].dwPID;
m_dwCRC = GetFastHash((const char *) &adwID, 8);
m_bRevenge = false;
SetLastFightTime();
}
CPVP::CPVP(CPVP & k)
{
m_players[0] = k.m_players[0];
m_players[1] = k.m_players[1];
m_dwCRC = k.m_dwCRC;
m_bRevenge = k.m_bRevenge;
SetLastFightTime();
}
CPVP::~CPVP()
{
}
void CPVP::Packet(bool bDelete)
{
if (!m_players[0].dwVID || !m_players[1].dwVID)
{
if (bDelete)
sys_err("null vid when removing %u %u", m_players[0].dwVID, m_players[0].dwVID);
return;
}
TPacketGCPVP pack;
pack.bHeader = HEADER_GC_PVP;
if (bDelete)
{
pack.bMode = PVP_MODE_NONE;
pack.dwVIDSrc = m_players[0].dwVID;
pack.dwVIDDst = m_players[1].dwVID;
}
else if (IsFight())
{
pack.bMode = PVP_MODE_FIGHT;
pack.dwVIDSrc = m_players[0].dwVID;
pack.dwVIDDst = m_players[1].dwVID;
}
else
{
pack.bMode = m_bRevenge ? PVP_MODE_REVENGE : PVP_MODE_AGREE;
if (m_players[0].bAgree)
{
pack.dwVIDSrc = m_players[0].dwVID;
pack.dwVIDDst = m_players[1].dwVID;
}
else
{
pack.dwVIDSrc = m_players[1].dwVID;
pack.dwVIDDst = m_players[0].dwVID;
}
}
const DESC_MANAGER::DESC_SET & c_rSet = DESC_MANAGER::instance().GetClientSet();
DESC_MANAGER::DESC_SET::const_iterator it = c_rSet.begin();
while (it != c_rSet.end())
{
LPDESC d = *it++;
if (d->IsPhase(PHASE_GAME) || d->IsPhase(PHASE_DEAD))
d->Packet(&pack, sizeof(pack));
}
}
bool CPVP::Agree(DWORD dwPID)
{
m_players[m_players[0].dwPID != dwPID ? 1 : 0].bAgree = true;
if (IsFight())
{
Packet();
return true;
}
return false;
}
bool CPVP::IsFight()
{
return (m_players[0].bAgree == m_players[1].bAgree) && m_players[0].bAgree;
}
void CPVP::Win(DWORD dwPID)
{
int iSlot = m_players[0].dwPID != dwPID ? 1 : 0;
m_bRevenge = true;
m_players[iSlot].bAgree = true; // ÀÚµ¿À¸·Î µ¿ÀÇ
m_players[!iSlot].bCanRevenge = true;
m_players[!iSlot].bAgree = false;
Packet();
}
bool CPVP::CanRevenge(DWORD dwPID)
{
return m_players[m_players[0].dwPID != dwPID ? 1 : 0].bCanRevenge;
}
void CPVP::SetVID(DWORD dwPID, DWORD dwVID)
{
if (m_players[0].dwPID == dwPID)
m_players[0].dwVID = dwVID;
else
m_players[1].dwVID = dwVID;
}
void CPVP::SetLastFightTime()
{
m_dwLastFightTime = get_dword_time();
}
DWORD CPVP::GetLastFightTime()
{
return m_dwLastFightTime;
}
CPVPManager::CPVPManager()
{
}
CPVPManager::~CPVPManager()
{
}
EVENTINFO(start_duel_efect_info)
{
LPCHARACTER ch1;
LPCHARACTER ch2;
CPVP * pkPVP;
BYTE state;
start_duel_efect_info()
: ch1( NULL )
,ch2( NULL )
,pkPVP( NULL )
,state( 0 )
{
}
};
EVENTFUNC(start_duel_efect)
{
start_duel_efect_info * info = dynamic_cast<start_duel_efect_info *>(event->info);
if ((info == NULL) || (info->ch1 == NULL) || (info->ch2 == NULL) || (info->pkPVP == NULL)) return 0;
switch (info->state)
{
case 0:
{
info->ch1->SpecificEffectPacket("d:/ymir work/effect/pvp/3.mse");
info->ch2->SpecificEffectPacket("d:/ymir work/effect/pvp/3.mse");
info->state++;
return PASSES_PER_SEC(1);
break;
}
case 1:
{
info->ch1->SpecificEffectPacket("d:/ymir work/effect/pvp/2.mse");
info->ch2->SpecificEffectPacket("d:/ymir work/effect/pvp/2.mse");
info->state++;
return PASSES_PER_SEC(1);
break;
}
case 2:
{
info->ch1->SpecificEffectPacket("d:/ymir work/effect/pvp/1.mse");
info->ch2->SpecificEffectPacket("d:/ymir work/effect/pvp/1.mse");
info->state++;
return PASSES_PER_SEC(1);
break;
}
case 3:
{
info->ch1->SpecificEffectPacket("d:/ymir work/effect/pvp/go.mse");
info->ch2->SpecificEffectPacket("d:/ymir work/effect/pvp/go.mse");
if (info->pkPVP->Agree(info->ch1->GetPlayerID()))
{
info->ch2->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%s??? ?? ??!"), info->ch1->GetName());
info->ch1->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%s??? ?? ??!"), info->ch2->GetName());
}
return 0;
break;
}
}
return 0;
}
void CPVPManager::Insert(LPCHARACTER pkChr, LPCHARACTER pkVictim)
{
if (pkChr->IsDead() || pkVictim->IsDead())
return;
CPVP kPVP(pkChr->GetPlayerID(), pkVictim->GetPlayerID());
CPVP * pkPVP;
if (pkPVP = Find(kPVP.m_dwCRC))
{
start_duel_efect_info * info = AllocEventInfo<start_duel_efect_info>();
info->ch1 = pkChr;
info->ch2 = pkVictim;
info->pkPVP = pkPVP;
info->state = 0;
pkChr->AddAffect(AFFECT_PVP_START, APPLY_NONE, 0, 0, 5, 0, false);
event_create(start_duel_efect, info, 0);
return;
}
pkPVP = M2_NEW CPVP(kPVP);
pkPVP->SetVID(pkChr->GetPlayerID(), pkChr->GetVID());
pkPVP->SetVID(pkVictim->GetPlayerID(), pkVictim->GetVID());
m_map_pkPVP.insert(map<DWORD, CPVP *>::value_type(pkPVP->m_dwCRC, pkPVP));
m_map_pkPVPSetByID[pkChr->GetPlayerID()].insert(pkPVP);
m_map_pkPVPSetByID[pkVictim->GetPlayerID()].insert(pkPVP);
pkPVP->Packet();
char msg[CHAT_MAX_LEN + 1];
snprintf(msg, sizeof(msg), LC_TEXT("%s´ÔÀÌ ´ë°á½ÅûÀ» Çß½À´Ï´Ù. ½Â³«ÇÏ·Á¸é ´ë°áµ¿ÀǸ¦ Çϼ¼¿ä."), pkChr->GetName());
pkVictim->ChatPacket(CHAT_TYPE_INFO, msg);
pkChr->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%s¿¡°Ô ´ë°á½ÅûÀ» Çß½À´Ï´Ù."), pkVictim->GetName());
// NOTIFY_PVP_MESSAGE
LPDESC pkVictimDesc = pkVictim->GetDesc();
if (pkVictimDesc)
{
TPacketGCWhisper pack;
int len = MIN(CHAT_MAX_LEN, strlen(msg) + 1);
pack.bHeader = HEADER_GC_WHISPER;
pack.wSize = sizeof(TPacketGCWhisper) + len;
pack.bType = WHISPER_TYPE_SYSTEM;
strlcpy(pack.szNameFrom, pkChr->GetName(), sizeof(pack.szNameFrom));
TEMP_BUFFER buf;
buf.write(&pack, sizeof(TPacketGCWhisper));
buf.write(msg, len);
pkVictimDesc->Packet(buf.read_peek(), buf.size());
}
// END_OF_NOTIFY_PVP_MESSAGE
}
void CPVPManager::ConnectEx(LPCHARACTER pkChr, bool bDisconnect)
{
CPVPSetMap::iterator it = m_map_pkPVPSetByID.find(pkChr->GetPlayerID());
if (it == m_map_pkPVPSetByID.end())
return;
DWORD dwVID = bDisconnect ? 0 : pkChr->GetVID();
TR1_NS::unordered_set<CPVP*>::iterator it2 = it->second.begin();
while (it2 != it->second.end())
{
CPVP * pkPVP = *it2++;
pkPVP->SetVID(pkChr->GetPlayerID(), dwVID);
}
}
void CPVPManager::Connect(LPCHARACTER pkChr)
{
ConnectEx(pkChr, false);
}
void CPVPManager::Disconnect(LPCHARACTER pkChr)
{
//ConnectEx(pkChr, true);
}
void CPVPManager::GiveUp(LPCHARACTER pkChr, DWORD dwKillerPID) // This method is calling from no where yet.
{
CPVPSetMap::iterator it = m_map_pkPVPSetByID.find(pkChr->GetPlayerID());
if (it == m_map_pkPVPSetByID.end())
return;
sys_log(1, "PVPManager::Dead %d", pkChr->GetPlayerID());
TR1_NS::unordered_set<CPVP*>::iterator it2 = it->second.begin();
while (it2 != it->second.end())
{
CPVP * pkPVP = *it2++;
DWORD dwCompanionPID;
if (pkPVP->m_players[0].dwPID == pkChr->GetPlayerID())
dwCompanionPID = pkPVP->m_players[1].dwPID;
else
dwCompanionPID = pkPVP->m_players[0].dwPID;
if (dwCompanionPID != dwKillerPID)
continue;
pkPVP->SetVID(pkChr->GetPlayerID(), 0);
m_map_pkPVPSetByID.erase(dwCompanionPID);
it->second.erase(pkPVP);
if (it->second.empty())
m_map_pkPVPSetByID.erase(it);
m_map_pkPVP.erase(pkPVP->m_dwCRC);
pkPVP->Packet(true);
M2_DELETE(pkPVP);
break;
}
}
// ¸®Åϰª: 0 = PK, 1 = PVP
// PVP¸¦ ¸®ÅÏÇÏ¸é °æÇèÄ¡³ª ¾ÆÀÌÅÛÀ» ¶³±¸°í PK¸é ¶³±¸Áö ¾Ê´Â´Ù.
bool CPVPManager::Dead(LPCHARACTER pkChr, DWORD dwKillerPID)
{
CPVPSetMap::iterator it = m_map_pkPVPSetByID.find(pkChr->GetPlayerID());
if (it == m_map_pkPVPSetByID.end())
return false;
bool found = false;
sys_log(1, "PVPManager::Dead %d", pkChr->GetPlayerID());
TR1_NS::unordered_set<CPVP*>::iterator it2 = it->second.begin();
while (it2 != it->second.end())
{
CPVP * pkPVP = *it2++;
DWORD dwCompanionPID;
if (pkPVP->m_players[0].dwPID == pkChr->GetPlayerID())
dwCompanionPID = pkPVP->m_players[1].dwPID;
else
dwCompanionPID = pkPVP->m_players[0].dwPID;
if (dwCompanionPID == dwKillerPID)
{
if (pkPVP->IsFight())
{
pkPVP->SetLastFightTime();
pkPVP->Win(dwKillerPID);
found = true;
break;
}
else if (get_dword_time() - pkPVP->GetLastFightTime() <= 15000)
{
found = true;
break;
}
}
}
LPCHARACTER pkChrW = CHARACTER_MANAGER::instance().FindByPID(dwKillerPID);
pkChrW->SpecificEffectPacket("d:/ymir work/effect/pvp/win.mse");
return found;
}
bool CPVPManager::CanAttack(LPCHARACTER pkChr, LPCHARACTER pkVictim)
{
switch (pkVictim->GetCharType())
{
case CHAR_TYPE_NPC:
case CHAR_TYPE_WARP:
case CHAR_TYPE_GOTO:
return false;
}
if (pkChr == pkVictim) // ³»°¡ ³¯ Ä¥¶ó°í ÇÏ³× -_-
return false;
if (pkVictim->IsNPC() && pkChr->IsNPC() && !pkChr->IsGuardNPC())
return false;
if( true == pkChr->IsHorseRiding() )
{
if( pkChr->GetHorseLevel() > 0 && 1 == pkChr->GetHorseGrade() )
return false;
}
else
{
int iIsMount = __MountAtkSkill(pkChr->GetMountVnum(), false);
switch (iIsMount)
{
case MOUNT_TYPE_NONE:
case MOUNT_TYPE_COMBAT:
case MOUNT_TYPE_MILITARY:
break;
case MOUNT_TYPE_NORMAL:
default:
if (test_server)
sys_log(0, "CanUseSkill: Mount can't attack. vnum(%u) type(%d)", pkChr->GetMountVnum(), iIsMount);
return false;
break;
}
}
if (pkVictim->IsNPC() || pkChr->IsNPC())
{
return true;
}
if (pkVictim->IsObserverMode() || pkChr->IsObserverMode())
return false;
{
BYTE bMapEmpire = SECTREE_MANAGER::instance().GetEmpireFromMapIndex(pkChr->GetMapIndex());
if ( ((pkChr->GetPKMode() == PK_MODE_PROTECT) && (pkChr->GetEmpire() == bMapEmpire)) ||
((pkVictim->GetPKMode() == PK_MODE_PROTECT) && (pkVictim->GetEmpire() == bMapEmpire)) )
{
return false;
}
}
if (pkChr->GetEmpire() != pkVictim->GetEmpire())
{
// @warme005
{
if ( pkChr->GetPKMode() == PK_MODE_PROTECT || pkVictim->GetPKMode() == PK_MODE_PROTECT )
{
return false;
}
}
return true;
}
bool beKillerMode = false;
if (pkVictim->GetParty() && pkVictim->GetParty() == pkChr->GetParty())
{
return false;
// Cannot attack same party on any pvp model
}
else
{
if (pkVictim->IsKillerMode())
{
return true;
}
if (pkChr->GetAlignment() < 0 && pkVictim->GetAlignment() >= 0)
{
if (g_protectNormalPlayer)
{
// ¹ü¹ýÀÚ´Â ÆòȸðµåÀÎ ÂøÇÑ»ç¶÷À» °ø°ÝÇÒ ¼ö ¾ø´Ù.
if (PK_MODE_PEACE == pkVictim->GetPKMode())
return false;
}
}
switch (pkChr->GetPKMode())
{
case PK_MODE_PEACE:
case PK_MODE_REVENGE:
// Cannot attack same guild
if (pkVictim->GetGuild() && pkVictim->GetGuild() == pkChr->GetGuild())
break;
if (pkChr->GetPKMode() == PK_MODE_REVENGE)
{
if (pkChr->GetAlignment() < 0 && pkVictim->GetAlignment() >= 0)
{
pkChr->SetKillerMode(true);
return true;
}
else if (pkChr->GetAlignment() >= 0 && pkVictim->GetAlignment() < 0)
return true;
}
break;
case PK_MODE_GUILD:
// Same implementation from PK_MODE_FREE except for attacking same guild
if (!pkChr->GetGuild() || (pkVictim->GetGuild() != pkChr->GetGuild()))
{
if (pkVictim->GetAlignment() >= 0)
pkChr->SetKillerMode(true);
else if (pkChr->GetAlignment() < 0 && pkVictim->GetAlignment() < 0)
pkChr->SetKillerMode(true);
return true;
}
break;
case PK_MODE_FREE:
if (pkVictim->GetAlignment() >= 0)
pkChr->SetKillerMode(true);
else if (pkChr->GetAlignment() < 0 && pkVictim->GetAlignment() < 0)
pkChr->SetKillerMode(true);
return true;
break;
}
}
CPVP kPVP(pkChr->GetPlayerID(), pkVictim->GetPlayerID());
CPVP * pkPVP = Find(kPVP.m_dwCRC);
if (!pkPVP || !pkPVP->IsFight())
{
if (beKillerMode)
pkChr->SetKillerMode(true);
return (beKillerMode);
}
pkPVP->SetLastFightTime();
return true;
}
CPVP * CPVPManager::Find(DWORD dwCRC)
{
map<DWORD, CPVP *>::iterator it = m_map_pkPVP.find(dwCRC);
if (it == m_map_pkPVP.end())
return NULL;
return it->second;
}
void CPVPManager::Delete(CPVP * pkPVP)
{
map<DWORD, CPVP *>::iterator it = m_map_pkPVP.find(pkPVP->m_dwCRC);
if (it == m_map_pkPVP.end())
return;
m_map_pkPVP.erase(it);
m_map_pkPVPSetByID[pkPVP->m_players[0].dwPID].erase(pkPVP);
m_map_pkPVPSetByID[pkPVP->m_players[1].dwPID].erase(pkPVP);
M2_DELETE(pkPVP);
}
void CPVPManager::SendList(LPDESC d)
{
map<DWORD, CPVP *>::iterator it = m_map_pkPVP.begin();
DWORD dwVID = d->GetCharacter()->GetVID();
TPacketGCPVP pack;
pack.bHeader = HEADER_GC_PVP;
while (it != m_map_pkPVP.end())
{
CPVP * pkPVP = (it++)->second;
if (!pkPVP->m_players[0].dwVID || !pkPVP->m_players[1].dwVID)
continue;
// VID°¡ µÑ´Ù ÀÖÀ» °æ¿ì¿¡¸¸ º¸³½´Ù.
if (pkPVP->IsFight())
{
pack.bMode = PVP_MODE_FIGHT;
pack.dwVIDSrc = pkPVP->m_players[0].dwVID;
pack.dwVIDDst = pkPVP->m_players[1].dwVID;
}
else
{
pack.bMode = pkPVP->m_bRevenge ? PVP_MODE_REVENGE : PVP_MODE_AGREE;
if (pkPVP->m_players[0].bAgree)
{
pack.dwVIDSrc = pkPVP->m_players[0].dwVID;
pack.dwVIDDst = pkPVP->m_players[1].dwVID;
}
else
{
pack.dwVIDSrc = pkPVP->m_players[1].dwVID;
pack.dwVIDDst = pkPVP->m_players[0].dwVID;
}
}
d->Packet(&pack, sizeof(pack));
sys_log(1, "PVPManager::SendList %d %d", pack.dwVIDSrc, pack.dwVIDDst);
if (pkPVP->m_players[0].dwVID == dwVID)
{
LPCHARACTER ch = CHARACTER_MANAGER::instance().Find(pkPVP->m_players[1].dwVID);
if (ch && ch->GetDesc())
{
LPDESC d = ch->GetDesc();
d->Packet(&pack, sizeof(pack));
}
}
else if (pkPVP->m_players[1].dwVID == dwVID)
{
LPCHARACTER ch = CHARACTER_MANAGER::instance().Find(pkPVP->m_players[0].dwVID);
if (ch && ch->GetDesc())
{
LPDESC d = ch->GetDesc();
d->Packet(&pack, sizeof(pack));
}
}
}
}
void CPVPManager::Process()
{
map<DWORD, CPVP *>::iterator it = m_map_pkPVP.begin();
while (it != m_map_pkPVP.end())
{
CPVP * pvp = (it++)->second;
if (get_dword_time() - pvp->GetLastFightTime() > 600000) // 10ºÐ ÀÌ»ó ½Î¿òÀÌ ¾ø¾úÀ¸¸é
{
pvp->Packet(true);
Delete(pvp);
}
}
}





