#include "stdafx.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "ExpTable.h" #include "Character.h" bool CCharacter::CheckRenameWarrant(Item::ItemPos InvenPos, bool bItemAccept) { // °è¸íÇã°¡¼­ È®ÀÎ Item::CItem* lpItem = NULL; if(InvenPos.m_cPos != TakeType::TS_ADMIN) { // ¸Á°¢Àǵ¹ È®ÀÎ lpItem = m_Inventory.GetItem(InvenPos); if (NULL == lpItem) { ERRLOG3(g_Log, "CID:0x%08x À̸§º¯°æ ¿À·ù : ¿äûÇÑ À§Ä¡¿¡ ¾ÆÀÌÅÛÀÌ ¾ø½À´Ï´Ù. Pos:%d, Index:%d", m_dwCID, InvenPos.m_cPos, InvenPos.m_cIndex); return false; } if (Item::EtcItemID::RENAME_WARRANT != lpItem->GetPrototypeID()) { ERRLOG2(g_Log, "CID:0x%08x À̸§º¯°æ ¿À·ù : »ç¿ëÇÏ·Á´Â ¾ÆÀÌÅÛÀÌ °è¸íÇã°¡¼­°¡ ¾Æ´Õ´Ï´Ù. ItemID:%d", m_dwCID, lpItem->GetPrototypeID()); return false; } // °è¸íÇã°¡¼­ÀÇ °³¼ö°¡ ÀÌ»óÇÑÁö È®ÀÎ if(lpItem->GetNumOrDurability() <= 0) { ERRLOG3(g_Log, "CID:0x%08x À̸§º¯°æ ¿À·ù : °è¸íÇã°¡¼­ÀÇ °¹¼ö°¡ ÀÌ»óÇÕ´Ï´Ù. Pos:%d, Index:%d", m_dwCID, InvenPos.m_cPos, InvenPos.m_cIndex); return false; } } if(bItemAccept == true) { // ¿¡·¯¾øÀÌ ¼º°øÇßÀ¸¸é °è¸íÇã°¡¼­ °¨¼Ò if(InvenPos.m_cPos != TakeType::TS_ADMIN) { // °è¸íÇã°¡¼­ °³¼ö 1°³ °¨¼Ò lpItem->SetNumOrDurability(lpItem->GetNumOrDurability() - 1); if (0 == lpItem->GetNumOrDurability()) { if (RemoveItem(InvenPos)) { DELETE_ITEM(lpItem); } else { ERRLOG3(g_Log, "CID:0x%08x ½ºÅ³»èÁ¦ ¿À·ù : °è¸íÇã°¡¼­¸¦ Á¦°ÅÇÒ ¼ö ¾ø½À´Ï´Ù. Pos:%d, Index:%d", m_dwCID, InvenPos.m_cPos, InvenPos.m_cIndex); m_Inventory.DumpItemInfo(); return false; } } } } return true; } bool CCharacter::CalculateAbility(const SKILL& skill) { memset(m_AbilityValue, 0, sizeof(m_AbilityValue)); // ¾îºô¸®Æ¼ ½ºÅ³ È¿°ú for (unsigned char cSlotIndex = 0; cSlotIndex < skill.wSlotNum; ++cSlotIndex) { const SKILLSLOT& SkillSlot = skill.SSlot[cSlotIndex]; unsigned short wSkillID = SkillSlot.SKILLINFO.wSkill; // ¾ÙÅÍ³ÊÆ¼ºê ½ºÅ³ÀÇ °æ¿ì const Skill::ProtoType* lpProtoType = CSkillMgr::GetInstance().GetSkillProtoType(wSkillID); if (NULL == lpProtoType) continue; if(lpProtoType->m_eSkillType != Skill::Type::ABILITY) continue; int cLock = SkillSlot.SKILLINFO.cLockCount; int id = wSkillID-0x1001; m_AbilityValue[Skill::Type::AB_ANIMAL_TALK+id] = static_cast(lpProtoType[cLock].m_fMaxRange); /* AB_ANIMAL_TALK = 0, // µ¿¹°NPC¿Í ´ëÈ­ AB_SOCIALEX = 1, // È®Àå ¼Ò¼È¸ð¼Ç »ç¿ë°¡´É AB_NOFIRSTATK = 2, // ¼±°ø¸÷ °ø°Ý ¾È´çÇÔ AB_MOUNT_SPEEDUP = 3, // Å»°Í ÀÌ¼Ó Áõ°¡ AB_TEMPINVEN_TIMEUP = 4, // ÀÓ½ÃÀκ¥Å丮 ½Ã°£Áõ°¡ AB_GETUP_GOLD = 5, // °ñµå ȹµæ·® Áõ°¡ AB_RESPAWN_EX = 6, // È®Àå ¸®½ºÆù »ç¿ë AB_FOOD_UP = 7, // À½½Ä·ù ´É·ÂÄ¡ Áõ°¡ AB_SHOP_MEMBERSHIP = 8, // »óÁ¡ ¸â¹ö½Ê(±¸¸Å°¡°Ý Ç϶ô, ÆÇ¸Å°¡°Ý »ó½Â) AB_CHEMICAL = 9, // ÀâÅÛÀ» ȸº¹ÅÛÀ¸·Î º¯°æ AB_ENDUR_SHILD = 10, // ³»±¸µµ Ç϶ô °¨¼Ò AB_RECOVERY_UP = 11, // HP,MP ȸº¹µµ Áõ°¡ AB_AWARD_UP = 12, // Äù½ºÆ® º¸»ó Áõ°¡ AB_MYEQUIP_UP = 13, // ÀÚ½ÅÀÇ Àåºñ ȹµæÀ² Áõ°¡ AB_LUCK_UP = 14, // ·°Âù Áõ°¡ AB_EQUIP_LEVELDOWN = 15, // ÀåºñÀÇ Á¦ÇÑ ·¹º§À» ´Ù¿î½ÃŲ´Ù. */ } return true; } bool CCharacter::CalculateStatusData(bool bFullHPandMP) { // ±âº» ½ºÅÈ m_CharacterStatus.Init(m_DBData.m_Info); m_CreatureStatus.m_StatusInfo.m_cCalculateState = FightStatus::CS_NONE; const unsigned char cLevel = static_cast(m_DBData.m_Info.Level); const unsigned char cClass = static_cast(m_DBData.m_Info.Class); m_CreatureStatus.m_StatusInfo.CalculateBaseInfo(m_CharacterStatus, cLevel, cClass); // ¾îºô¸®Æ¼¸¦ °è»êÇØÁØ´Ù CalculateAbility(m_DBData.m_Skill); // ¸®Á¨°ªÀ» Áõ°¡½ÃÄÑÁØ´Ù. if(m_AbilityValue[Skill::Type::AB_RECOVERY_UP]) { int Regen = m_AbilityValue[Skill::Type::AB_RECOVERY_UP]; m_CreatureStatus.m_StatusInfo.m_wHPRegen += Regen; m_CreatureStatus.m_StatusInfo.m_wMPRegen += Regen; } // Àåºñ¿¡ ÀÇÇÑ Ãß°¡ ½ºÅÈ Item::CEquipment* aryEquipList[Item::EquipmentPos::MAX_EQUPMENT_POS]; m_Equipments.GetEquipList(aryEquipList); bool bFirstWeaponSlot = (m_cHandPos == 1) ? false : true; bool bRidesSlot = (m_cRidePos == 0) ? false : true; // ±âº»ÀûÀ¸·Î »ç¿ëµÇ´Â Àåºñ ½ºÅÈ m_CreatureStatus.m_StatusInfo.CalculateEquipInfo(const_cast(aryEquipList), bFirstWeaponSlot, true, bRidesSlot, m_DBData.m_Skill, cLevel, m_AbilityValue[Skill::Type::AB_MOUNT_SPEEDUP], m_AbilityValue[Skill::Type::AB_LUCK_UP], m_AbilityValue[Skill::Type::AB_EQUIP_LEVELDOWN], m_CharacterStatus, cClass, m_EquipStatus); // ±âŸ Ư¼öÇÑ °æ¿ì¿¡ »ç¿ëµÇ´Â ½ºÅȵé m_CreatureStatus.m_StatusInfo.CalculateEquipInfo(const_cast(aryEquipList), bFirstWeaponSlot, false, bRidesSlot, m_DBData.m_Skill, cLevel, m_AbilityValue[Skill::Type::AB_MOUNT_SPEEDUP], m_AbilityValue[Skill::Type::AB_LUCK_UP], m_AbilityValue[Skill::Type::AB_EQUIP_LEVELDOWN], m_CharacterStatus, cClass, m_EtcTypeStatus[Creature::LEFT_PASSIVE_TYPE]); m_CreatureStatus.m_StatusInfo.CalculateEquipInfo(const_cast(aryEquipList), bFirstWeaponSlot, true, bRidesSlot, SKILL(), cLevel, m_AbilityValue[Skill::Type::AB_MOUNT_SPEEDUP], m_AbilityValue[Skill::Type::AB_LUCK_UP], m_AbilityValue[Skill::Type::AB_EQUIP_LEVELDOWN], m_CharacterStatus, cClass, m_EtcTypeStatus[Creature::RIGHT_NON_PASSIVE_TYPE]); m_CreatureStatus.m_StatusInfo.CalculateEquipInfo(const_cast(aryEquipList), bFirstWeaponSlot, false, bRidesSlot, SKILL(), cLevel, m_AbilityValue[Skill::Type::AB_MOUNT_SPEEDUP], m_AbilityValue[Skill::Type::AB_LUCK_UP], m_AbilityValue[Skill::Type::AB_EQUIP_LEVELDOWN], m_CharacterStatus, cClass, m_EtcTypeStatus[Creature::LEFT_NON_PASSIVE_TYPE]); // Äù½ºÆ®¿¡ ÀÇÇØ ¹Þ´Â ¿µÇâÀ» °è»ê CalculateStatusByQuest(); // ÀÎæƮ¿¡ ÀÇÇÑ Ãß°¡ ½ºÅÈ CalculateEnchantStatus(); if (true == bFullHPandMP) { m_CreatureStatus.m_nNowHP = m_CreatureStatus.m_StatusInfo.m_nMaxHP; m_CreatureStatus.m_nNowMP = m_CreatureStatus.m_StatusInfo.m_nMaxMP; } // ÃÖ´ë°ªº¸´Ù ÇöÀç°ªÀÌ ´õ Å« °æ¿ì ÃÖ´ë°ªÀ¸·Î ¼³Á¤ÇØÁØ´Ù. m_CreatureStatus.m_nNowHP = std::min(m_CreatureStatus.m_nNowHP, m_CreatureStatus.m_StatusInfo.m_nMaxHP); m_CreatureStatus.m_nNowMP = std::min(m_CreatureStatus.m_nNowMP, m_CreatureStatus.m_StatusInfo.m_nMaxMP); return true; } // edith 2008.02.13 ÀüÁ÷ ÆÐŶ. bool CCharacter::ChangeClass(unsigned char cClassType) { unsigned short usError = 0; if (cClassType >= CClass::MAX_CLASS) { ERRLOG3(g_Log, "CID:0x%08x Ŭ·¡½º üÀÎÁö ½ÇÆÐ. ÇöÀç ij¸¯ÅÍÀÇ Å¬·¡½º´Â %d, ¹Ù²Ù°íÀÚ Çϴ Ŭ·¡½º´Â %dÀÔ´Ï´Ù.", m_dwCID, m_DBData.m_Info.Class, cClassType); usError = 1; } m_DBData.m_Info.Exp = m_CreatureStatus.m_nExp; if (false == ClassTable[cClassType].JobChange(&m_DBData, cClassType)) { ERRLOG3(g_Log, "CID:0x%08x Ŭ·¡½º üÀÎÁö ½ÇÆÐ. ÇöÀç ij¸¯ÅÍÀÇ Å¬·¡½º´Â %d, ¹Ù²Ù°íÀÚ Çϴ Ŭ·¡½º´Â %dÀÔ´Ï´Ù.", m_dwCID, m_DBData.m_Info.Class, cClassType); usError = 1; } m_CreatureStatus.Init(m_DBData.m_Info); // ±æµå¿ø Á¤º¸ ¾÷µ¥ÀÌÆ® CGuild* lpGuild = Guild::CGuildMgr::GetInstance().GetGuild(GetGID()); if (0 != lpGuild) { lpGuild->UpdateMemberInfo(m_dwCID, cClassType, Guild::TYPE_CLASS); } // ÆÄƼ¿¡ Ŭ·¡½º°¡ º¯°æµÇ¾úÀ½À» º¸³¿ if (0 != m_pParty) { CCharacterParty* lpParty = static_cast(m_pParty); lpParty->SendPartyMemberDataToDBAgent(m_dwCID, 0, cClassType, 0, 0, GetCharacterName(), PktDD::SCmdChangeClassPartyMem); } // Ä£±¸ ¸®½ºÆ®¿¡ Ŭ·¹½º º¯°æ ¸Þ¼¼Áö¸¦ º¸³½´Ù // FriendInfoUpdate(GetUID(), GetCID(), GetGID(), GetClass(), GetLevel(), CServerSetup::GetInstance().GetServerID()); if (0 != m_lpGameClientDispatch && !GameClientSendPacket::SendCharClassUpgrade( m_lpGameClientDispatch->GetSendStream(), m_dwCID, m_DBData, usError) && 0 != usError) { return false; } return CalculateStatusData(true); } // Desc : Admin ¸í·ÉÀ¸·Î ·¹º§À» ´Ù¿î ½Ãų¶§ »ç¿ëÇÏ´Â ÇÔ¼ö // ·¹º§ 1ÀÇ Ãʱâ Ŭ·¡½º·Î ¸¸µé¾î ¹ö¸°´Ù. bool CCharacter::InitLevel1Char(unsigned char cClassType) { if (cClassType >= CClass::MAX_CLASS) { ERRLOG3(g_Log, "CID:0x%08x Ŭ·¡½º üÀÎÁö ½ÇÆÐ. ÇöÀç ij¸¯ÅÍÀÇ Å¬·¡½º´Â %d, ¹Ù²Ù°íÀÚ Çϴ Ŭ·¡½º´Â %dÀÔ´Ï´Ù.", m_dwCID, m_DBData.m_Info.Class, cClassType); return false; } m_DBData.m_Info.Exp = m_CreatureStatus.m_nExp; if (false == ClassTable[cClassType].InitializeClass(&m_DBData, cClassType)) { ERRLOG3(g_Log, "CID:0x%08x Ŭ·¡½º ÃʱâÈ­ ½ÇÆÐ. ÇöÀç ij¸¯ÅÍÀÇ Å¬·¡½º´Â %d, ¹Ù²Ù°íÀÚ Çϴ Ŭ·¡½º´Â %dÀÔ´Ï´Ù.", m_dwCID, m_DBData.m_Info.Class, cClassType); return false; } m_CreatureStatus.Init(m_DBData.m_Info); if (NULL != m_lpGameClientDispatch) { if (false == GameClientSendPacket::SendCharClassUpgrade(m_lpGameClientDispatch->GetSendStream(), m_dwCID, m_DBData, PktBase::NO_SERVER_ERR)) { return false; } } return CalculateStatusData(true); } bool CCharacter::GetHuntingExp(CAggresiveCreature* lpDeadCreature, unsigned long dwExp, unsigned char cMemberNum) { // edith ÆÄƼ°æÇèÄ¡ // ÆÄƼ¿¡ ÀÇÇÑ °æÇèÁ¡ ĸ º¸³Ê½º static const float fExpCapPartyBonus[PARTY::MAX_MEM] = { // 1.0f, 1.1f, 1.2f, 1.3f, 1.4f, 1.5f, 1.6f, 1.7f, 1.8f, 1.9f 1.0f, 1.2f, 1.4f, 1.6f, 1.8f, 2.0f, 2.2f, 2.4f, 2.6f, 2.8f }; float fPartyExpCap = fExpCapPartyBonus[cMemberNum -1]; // edith 2008.06.30 ÆÄƼ¸¦ ¸Î¾úÀ»¶§ º¸³Ê½º °æÇèÄ¡¸¦ ¹Þ´Â´Ù. dwExp = static_cast(dwExp * fPartyExpCap); // °æÇèÁ¡ ĸ Àû¿ë const float fExpCapRevision = EXP::ExpCapTable[m_CreatureStatus.m_nLevel - 1] * (CServerSetup::GetInstance().GetExpDefault() / 100.0f); /* // edith 2008.06.30 // ÆÄƼ ¸ó½ºÅ͸¦ Àâ¾ÒÀ» °æ¿ì¿¡´Â °æÇèÄ¡ º¸»óÀ» ÁØ´Ù. if (NULL != lpDeadCreature->GetParty()) { // ±×·ì(ÆÄƼ)ÀÇ ³­À̵µ¿¡ ´ëÇÑ º¸»ó CMonsterParty* lpParty = reinterpret_cast(lpDeadCreature->GetParty()); switch (lpParty->GetMemberTypeNum()) { case 1: dwExp += static_cast(dwExp * 0.06f); break; case 2: dwExp += static_cast(dwExp * 0.12f); break; case 3: dwExp += static_cast(dwExp * 0.18f); break; case 4: dwExp += static_cast(dwExp * 0.24f); break; case 5: dwExp += static_cast(dwExp * 0.3f); break; } } */ dwExp = std::max(dwExp, static_cast(1)); dwExp = static_cast(dwExp * (CServerSetup::GetInstance().GetExpDefault() / 100.0f)); if (dwExp > fExpCapRevision) { /* RULLOG9(g_Log, "CID:0x%08x ȹµæ °æÇèÄ¡°¡ °æÇèÁ¡ ĸÀ» ÃʰúÇÏ¿´½À´Ï´Ù. ¸â¹ö¼ö:%d " "¹èÀ² : %d%%, ȹµæ °æÇèÄ¡ : %ld, °æÇèÁ¡ ĸ(·¹º§) : %.1f (%d), Ŭ·¡½º : %d, »ìÇØµÈ ³à¼®(·¹º§) : 0x%08x (%d)", m_dwCID, cMemberNum, CServerSetup::GetInstance().GetExpDefault(), dwExp, fExpCapRevision, m_CreatureStatus.m_nLevel, m_DBData.m_Info.Class, lpDeadCreature->GetCID(), lpDeadCreature->GetStatus().m_nLevel); */ dwExp = static_cast(fExpCapRevision); } // ¼­¹ö ¿¤¸®Æ® º¸³Ê½º¿¡ ÀÇÇÑ Ãß°¡ °æÇèÁ¡ (ĸÀÇ ¿µÇâÀ» ¹ÞÁö ¾Ê´Â´Ù) char eliteBonus = GetEliteBonus(); if (0 < eliteBonus) { dwExp = static_cast(dwExp * EliteBonus::usBonusExp[eliteBonus - 1] / 100.0f); } // ¼Òȯ¼ö°¡ ÀÖ´Â °æ¿ì 90%ÀÇ °æÇèÄ¡¸¸À» ¹Þ´Â´Ù. if (NULL != m_lpSummonee) { dwExp = static_cast(dwExp * 0.9f); } unsigned long dwAddExp = 0; float fPt = 0.0f; // '°æÇèÀÇ ¿Àºê' »ç¿ë½Ã if (true == GetEnchantInfo().GetFlag(Skill::SpellID::ExpOrb)) { // ÇöÀç 50% °è»ê fPt += 0.3f; } // ÇÁ¸®¹Ì¾ö ¼­ºñ½º½Ã °æÇèÄ¡ Ãß°¡·ÎÁ÷ if(CheckPremiumTime()) { fPt += GetPremiumPt(); } // '°æÇèÀÇ ¼®»ó' »ç¿ë½Ã. if (true == GetEnchantInfo().GetFlag(Skill::SpellID::ExpStatue)) { unsigned short wLevel = GetEnchantLevel(Skill::SpellID::ExpStatue); fPt += (wLevel*0.01f); } // °ø¼ºÀü º¸»óÀ¸·Î ¼ºÀÇ ¹Ý°æ xxx m ³»¿¡¼­ »ç³É½Ã °æÇèÄ¡ 10%¾¿ ´õ ȹµæ if (true == CServerSetup::GetInstance().UseContents(GameRYL::SIEGE)) { // °ø¼±Àü º¸»óÀ̱⠶§¹®¿¡.. // ¼®¼ºÀü, °ø¼ºÀü ½Ã°£ÀÌ ¾Æ´Ò¶§¸¸, if (!CGameTimeMgr::GetInstance().IsSiegeWarTime()) { int iMyCastleNum = Castle::CCastleMgr::GetInstance().GetCastleNum( GetNation(), CServerSetup::GetInstance().GetServerZone(), GetCurrentPos() ); if (iMyCastleNum > 0) { fPt += (iMyCastleNum*0.01f); } } } // edith 2010.01.02 ±æµå¿ø ¼ö¿Í ±æµå°¡ÀÔÀÚÀÇ ¼ö¿¡ ÀÇÇÑ º¸³Ê½º Æ÷ÀÎÆ® Ãß°¡ CGuild* lpGuild = Guild::CGuildMgr::GetInstance().GetGuild(GetGID()); if (0 != lpGuild) { float fD = lpGuild->GetGuildBonus(GetRealmPoint()); fPt += fD; } if(fPt > 0.0f) dwAddExp = static_cast((float)dwExp*fPt); return IncrementExp(dwExp + dwAddExp); } bool CCharacter::IncrementExp(unsigned long dwExp) { // Áß±¹À̸é float fPt = GetAwardPer(); dwExp = (unsigned long)((float)dwExp*fPt); // ÇöÀç ij¸¯ÅÍ ·¹º§ °ªÀÌ Á¦´ë·Î µÈ °ªÀÎÁö °Ë»ç. if (m_CreatureStatus.m_nLevel > EXP::GetUsingMaxLevel() - 1|| m_CreatureStatus.m_nLevel <= 0) { if (m_CreatureStatus.m_nLevel == EXP::GetUsingMaxLevel()) { return true; } ERRLOG2(g_Log, "CID:0x%08x ·¹º§¾÷À» ÇÒ ¼ö ¾ø½À´Ï´Ù : ÇöÀç ij¸¯ÅÍÀÇ ·¹º§ °ªÀÌ ÀÌ»óÇÕ´Ï´Ù." " ·¹º§ °ªÀº %dÀÔ´Ï´Ù.", m_dwCID, m_CreatureStatus.m_nLevel); return false; } // ÇöÀç Ŭ·¡½º°¡ Á¤»óÀÎÁö È®ÀÎ. if (m_DBData.m_Info.Class >= CClass::MAX_CLASS) { ERRLOG2(g_Log, "CID:0x%08x ·¹º§¾÷À» ÇÒ ¼ö ¾ø½À´Ï´Ù : ÇöÀç ij¸¯ÅÍÀÇ Å¬·¡½º°¡ ÀÌ»óÇÕ´Ï´Ù." " Ŭ·¡½º °ªÀº %dÀÔ´Ï´Ù.", m_dwCID, m_DBData.m_Info.Class); return false; } if (NULL != m_lpGameClientDispatch) { GameClientSendPacket::SendCharAward(m_lpGameClientDispatch->GetSendStream(), m_dwCID, dwExp); } // ÇöÀç Exp·Î ·¹º§¾÷ ÇÒ ¼ö ÀÖ´ÂÁö¸¦ °Ë»ç. m_CreatureStatus.m_nExp += dwExp; if (m_CreatureStatus.m_nExp < EXP::ExpTable[m_CreatureStatus.m_nLevel - 1]) { // ¾ÆÁ÷ °æÇèÄ¡°¡ ¸ðÀÚ¶ó ·¹º§¾÷À» ÇÒ ¼ö ¾ø´Ù. return true; } // ·¹º§¾÷À» Çѹø¿¡ µÎ°³ ÀÌ»ó ÇÏ·Á´ÂÁö È®ÀÎ. if (m_CreatureStatus.m_nExp - EXP::ExpTable[m_CreatureStatus.m_nLevel - 1] >= EXP::ExpTable[m_CreatureStatus.m_nLevel]) { RULLOG2(g_Log, "CID:0x%08x Çѹø¿¡ 2·¹º§ ÀÌ»ó ·¹º§¾÷À» ÇÏ·Á ÇÕ´Ï´Ù. ·¾¾÷ÀüÀÇ ·¹º§:%d", m_dwCID, m_CreatureStatus.m_nLevel); m_DBData.m_Info.Exp = m_CreatureStatus.m_nExp = EXP::ExpTable[m_CreatureStatus.m_nLevel] - 1; } else { m_DBData.m_Info.Exp = m_CreatureStatus.m_nExp = m_CreatureStatus.m_nExp - EXP::ExpTable[m_CreatureStatus.m_nLevel - 1]; } ++m_DBData.m_Info.Level; ++m_CreatureStatus.m_nLevel; // Ŭ·¡½º¿¡ µû¸¥ ½ºÅ×ÀÌÅͽº ÀÚµ¿ Áõ°¡. IP¼ö 2°³ ¿Ã·Á ÁÜ. ClassTable[m_DBData.m_Info.Class].LevelUp(&m_DBData.m_Info); m_DBData.m_Info.HP = m_CreatureStatus.m_nNowHP = m_CreatureStatus.m_StatusInfo.m_nMaxMP; m_DBData.m_Info.MP = m_CreatureStatus.m_nNowMP = m_CreatureStatus.m_StatusInfo.m_nMaxMP; // ±æµå¿ø Á¤º¸ ¾÷µ¥ÀÌÆ® CGuild* lpGuild = Guild::CGuildMgr::GetInstance().GetGuild(GetGID()); if (0 != lpGuild) { lpGuild->UpdateMemberInfo(m_dwCID, m_CreatureStatus.m_nLevel, Guild::TYPE_LEVEL); } // ÆÄƼ¿¡ ·¹º§¾÷ÇßÀ½À» º¸³¿ if (0 != m_pParty) { CCharacterParty* lpParty = static_cast(m_pParty); lpParty->SendPartyMemberDataToDBAgent(m_dwCID, 0, 0, 0, m_CreatureStatus.m_nLevel, GetCharacterName(), PktDD::SCmdLevelUpPartyMem); } // Ä£±¸ ¸®½ºÆ®¿¡ ·¹º§¾÷ ¸Þ¼¼Áö¸¦ º¸³½´Ù // FriendInfoUpdate(GetUID(), GetCID(), GetGID(), GetClass(), GetLevel(), CServerSetup::GetInstance().GetServerID()); // ·¹º§¾÷ À̺¥Æ® // edith 2009.09.05 ½Å±Ô À̺¥Æ® Á¦ÀۺκРif (CServerSetup::GetInstance().GetLevelUpEvent() && 0 != m_CellPos.m_lpCell) { GET_SINGLE_DISPATCH(lpDBAgentDispatch, CDBAgentDispatch, CDBAgentDispatch::GetDispatchTable()); if (0 == lpDBAgentDispatch) { ERRLOG0(g_Log, "À̺¥Æ®·Î±× : ¿¡ÀÌÀüÆ® ¾ò±â ½ÇÆÐ."); } else if(m_DBData.m_Info.Level == 30) // À̺κРÀ̺¥Æ®´Â 30·¹º§¾÷ À̺¥Æ® { // ·¹º§¾÷¿¡ °ü·ÃµÈ À̺¥Æ® Àü¼Û GameClientSendPacket::SendExtraEvent(lpDBAgentDispatch->GetSendStream(), GetUID(), GetCID(), MAKEWPARAM(1,30), 0, 0, 0); } else if(m_DBData.m_Info.Level == 60) // À̺κРÀ̺¥Æ®´Â 30·¹º§¾÷ À̺¥Æ® { // ·¹º§¾÷¿¡ °ü·ÃµÈ À̺¥Æ® Àü¼Û GameClientSendPacket::SendExtraEvent(lpDBAgentDispatch->GetSendStream(), GetUID(), GetCID(), MAKEWPARAM(1,60), 0, 0, 0); } else if(m_DBData.m_Info.Level == 90) // À̺κРÀ̺¥Æ®´Â 30·¹º§¾÷ À̺¥Æ® { // ·¹º§¾÷¿¡ °ü·ÃµÈ À̺¥Æ® Àü¼Û GameClientSendPacket::SendExtraEvent(lpDBAgentDispatch->GetSendStream(), GetUID(), GetCID(), MAKEWPARAM(1,90), 0, 0, 0); } } /* if (CServerSetup::GetInstance().GetLevelUpEvent() && 0 != m_CellPos.m_lpCell) { unsigned short wItemKind = AwardTable::CAward::GetInstance().GetAwardEquipment( Item::EquipType::STANDARD_OPTION, m_DBData.m_Info.Level, this, true); Item::CItem* lpItem = Item::CItemFactory::GetInstance().CreateItem(wItemKind); Item::CEquipment* lpEquip = Item::CEquipment::DowncastToEquipment(lpItem); if (NULL != lpEquip) { lpEquip->AddRandomOption(Item::EquipType::F_GRADE, 0); lpEquip->SetNewEquip(); } GiveItem(lpItem); // GievItem À¸·Î ½ºÅÃµÈ °æ¿ì if (lpItem->IsSet(Item::DetailData::STACKABLE) && 0 == lpItem->GetNumOrDurability()) { DELETE_ITEM(lpItem); } } */ // ij¸¯ÅÍ ·¹º§ ¾÷ ·Î±×¸¦ ³²±ä´Ù. GAMELOG::LogCharLevelUp(*this, m_DBData.m_Info.IP, m_DBData.m_Info.Level, 0); if (0 != m_lpGameClientDispatch) { // ·¹º§¾÷ÇÏ´Â »ç¶÷¿¡°Ô ·¹º§¾÷ À̺¥Æ®¸¦ º¸³½´Ù. GameClientSendPacket::SendCharLevelUp( m_lpGameClientDispatch->GetSendStream(), m_dwCID, m_DBData); } // ÁÖº¯ Àι°µé¿¡°Ô ·¹º§¾÷ À̺¥Æ® Á¤º¸¸¦ º¸³½´Ù. // ¹ÞÀ¸¸é Àû´çÈ÷ ÀÌÆåÆ®¸¦ »Ñ·Á ÁØ´Ù. if(0 != m_CellPos.m_lpCell) { PktLUInfo pktLUInfo; memset(&pktLUInfo, 0, sizeof(PktLUInfo)); pktLUInfo.m_dwCharID = m_dwCID; pktLUInfo.m_cLevel = m_DBData.m_Info.Level; m_CellPos.m_lpCell->SendAllNearCellCharacter( &pktLUInfo, sizeof(PktLUInfo), CmdCharLevelUpInfo); } /* // edith 100·¦ ´Þ¼º ÀÌÆÑÆ® if (true == CServerSetup::GetInstance().UseContents(GameRYL::LEVEL_LIMIT_100)) { if(100 == m_DBData.m_Info.Level) { Skill::CAddSpell(CSpell::Spell_Info(Skill::CProcessTable::ProcessInfo::m_NullProtoType, NULL, Skill::SpellType::ETERNAL_SPELL, Skill::SpellID::HundredLevel, 1, CSpell::INFINITE_DURATION))(this); } } */ DBUpdateForce(DBUpdateData::UPDATE); return CalculateStatusData(true); } bool CCharacter::RegenHPAndMP(unsigned short usAdditionalHP, unsigned short usAdditionalMP, bool bAddDefaultRegenValue) { if (false == CAggresiveCreature::RegenHPAndMP(usAdditionalHP, usAdditionalMP, bAddDefaultRegenValue)) { return false; } if (NULL != m_lpGameClientDispatch) { return GameClientSendPacket::SendCharHPRegen(m_lpGameClientDispatch->GetSendStream(), m_dwCID, m_CreatureStatus.m_nNowHP, m_CreatureStatus.m_nNowMP); } return true; } unsigned short CCharacter::AddState(unsigned char Type_In, ChState& ChState_Out) { unsigned char cDecrementIP = CClass::GetRequiredIP(m_DBData.m_Info.Class, Type_In); if (m_DBData.m_Info.IP < cDecrementIP) { return 2; } switch(Type_In) { case CClass::STR: ++m_DBData.m_Info.STR; break; case CClass::DEX: ++m_DBData.m_Info.DEX; break; case CClass::CON: ++m_DBData.m_Info.CON; break; case CClass::INT: ++m_DBData.m_Info.INT; break; case CClass::WIS: ++m_DBData.m_Info.WIS; break; } m_DBData.m_Info.IP -= cDecrementIP; ChState_Out.m_wIP = m_DBData.m_Info.IP; ChState_Out.m_wSTR = m_DBData.m_Info.STR; ChState_Out.m_wDEX = m_DBData.m_Info.DEX; ChState_Out.m_wCON = m_DBData.m_Info.CON; ChState_Out.m_wINT = m_DBData.m_Info.INT; ChState_Out.m_wWIS = m_DBData.m_Info.WIS; CalculateStatusData(false); return 0; } bool CCharacter::StateRedistribution(ChState& State) { unsigned short usError = PktSRAck::NO_SERVER_ERR; /* if (0 == m_DBData.m_Info.Chance) { usError = PktSRAck::FAIL_NO_CHANCE; } else */ { int CheckStat = State.m_wIP+State.m_wSTR+State.m_wDEX+State.m_wCON+State.m_wINT+State.m_wWIS; if(CheckStat >= 10000) { ERRLOG9(g_Log, "CID:0x%08x ÀçºÐ¹èµÈ ½ºÅÈÀÌ ¿Ã¹Ù¸£Áö ¾Ê½À´Ï´Ù. " "Ŭ·¡½º:%d, ·¹º§:%d, STR:%d, DEX:%d, CON:%d, INT:%d, WIS:%d IP:%d", m_dwCID, m_DBData.m_Info.Class, m_DBData.m_Info.Level, State.m_wSTR, State.m_wDEX, State.m_wCON, State.m_wINT, State.m_wWIS, State.m_wIP); return false; } if (false == ClassTable[m_DBData.m_Info.Class].CheckState(State, m_DBData.m_Info.Level)) { ERRLOG9(g_Log, "CID:0x%08x ÀçºÐ¹èµÈ ½ºÅÈÀÌ ¿Ã¹Ù¸£Áö ¾Ê½À´Ï´Ù. " "Ŭ·¡½º:%d, ·¹º§:%d, STR:%d, DEX:%d, CON:%d, INT:%d, WIS:%d IP:%d", m_dwCID, m_DBData.m_Info.Class, m_DBData.m_Info.Level, State.m_wSTR, State.m_wDEX, State.m_wCON, State.m_wINT, State.m_wWIS, State.m_wIP); return false; } const CHAR_INFOST tempInfoSt = m_DBData.m_Info; m_DBData.m_Info.IP = State.m_wIP; m_DBData.m_Info.STR = State.m_wSTR; m_DBData.m_Info.DEX = State.m_wDEX; m_DBData.m_Info.CON = State.m_wCON; m_DBData.m_Info.INT = State.m_wINT; m_DBData.m_Info.WIS = State.m_wWIS; // ÀçºÐ¹èµÈ ½ºÅÈ¿¡ µû¶ó ½ºÅ³ ÀçÁ¤¸® if (false == RedistributionSkill()) { ERRLOG1(g_Log, "CID:0x%08x ½ºÅ³ ÀçºÐ¹è¿¡ ½ÇÆÐÇÏ¿´½À´Ï´Ù.", m_dwCID); m_DBData.m_Info = tempInfoSt; return false; } // Äü½½·Ô ÃʱâÈ­ m_DBData.m_Quick = QUICK::QUICK(); // m_DBData.m_Info.Chance--; m_DBData.m_Info.Chance = 1; DETLOG2(g_Log, "CID:%u ÀÇ Ä³¸¯ÅͰ¡ ½ºÅÈ ÀçºÐ¹è ±âȸ¸¦ »ç¿ëÇÏ¿´½À´Ï´Ù. (»ç¿ëÈÄ ³²Àº Chance: %d)", m_dwCID, m_DBData.m_Info.Chance); } if (NULL != m_lpGameClientDispatch) { if (false == GameClientSendPacket::SendCharStateRedistribution(m_lpGameClientDispatch->GetSendStream(), m_dwCID, GetState(), GetSkill(), usError)) { return false; } } return CalculateStatusData(true); } // ½ºÅÈÀ» ÀÏÁ¤·® µ¹·Á¹Þ´Â 󸮸¦ ÇÏ´Â ÇÔ¼ö (¸Á°¢ÀÇ µ¹ »ç¿ë) bool CCharacter::StatusRetrain(ChState& State, Item::ItemPos InvenPos) { unsigned short usError = PktSRTAck::NO_SERVER_ERR; if (State.m_wIP - m_DBData.m_Info.IP > PktSRTAck::MAX_STATUS_RETRAIN) { usError = PktSRTAck::FAIL_INVALID_IP; goto SEND_PACKET; } // ºÎȰÀÇ µ¹ Item::CItem* lpItem = m_Inventory.GetItem(InvenPos); if (NULL == lpItem) { ERRLOG2(g_Log, "½ºÅ×ÀÌÅͽº ÀçÈÆ·Ã ¿À·ù : ¿äûÇÑ À§Ä¡¿¡ ¾ÆÀÌÅÛÀÌ ¾ø½À´Ï´Ù. Pos:%d, Index:%d", InvenPos.m_cPos, InvenPos.m_cIndex); usError = PktSRTAck::FAIL_NO_ITEM; goto SEND_PACKET; } if (Item::EtcItemID::REBIRTH_STONE != lpItem->GetPrototypeID()) { ERRLOG1(g_Log, "½ºÅ×ÀÌÅͽº ÀçÈÆ·Ã ¿À·ù : »ç¿ëÇÏ·Á´Â ¾ÆÀÌÅÛÀÌ ºÎȰÀÇ µ¹ÀÌ ¾Æ´Õ´Ï´Ù. ItemID:%d", lpItem->GetPrototypeID()); usError = PktSRTAck::FAIL_INVALID_ITEM; goto SEND_PACKET; } /* unsigned long dwReduceGold = m_CreatureStatus.m_nLevel * 10000; if (dwReduceGold > m_DBData.m_Info.Gold) { ERRLOG2(g_Log, "½ºÅ×ÀÌÅͽº ÀçÈÆ·Ã ¿À·ù : µ·ÀÌ ºÎÁ·ÇÕ´Ï´Ù. ¿ä±¸±Ý¾×:%ld, ¼ÒÁö±Ý:%ld", dwReduceGold, m_DBData.m_Info.Gold); usError = PktSRTAck::FAIL_NOT_ENOUGH_GOLD; goto SEND_PACKET; } */ int CheckStat = State.m_wIP+State.m_wSTR+State.m_wDEX+State.m_wCON+State.m_wINT+State.m_wWIS; if(CheckStat >= 10000) { ERRLOG9(g_Log, "CID:0x%08x ÀçºÐ¹èµÈ ½ºÅÈÀÌ ¿Ã¹Ù¸£Áö ¾Ê½À´Ï´Ù. " "Ŭ·¡½º:%d, ·¹º§:%d, STR:%d, DEX:%d, CON:%d, INT:%d, WIS:%d IP:%d", m_dwCID, m_DBData.m_Info.Class, m_DBData.m_Info.Level, State.m_wSTR, State.m_wDEX, State.m_wCON, State.m_wINT, State.m_wWIS, State.m_wIP); usError = PktSRTAck::FAIL_INVALID_STATUS; goto SEND_PACKET; } // IP ÃÑ ¼öÄ¡°¡ ¿Ã¹Ù¸¥°¡ üũ if (false == ClassTable[m_DBData.m_Info.Class].CheckState(State, m_DBData.m_Info.Level)) { ERRLOG9(g_Log, "CID:0x%08x ÀçºÐ¹èµÈ ½ºÅÈÀÌ ¿Ã¹Ù¸£Áö ¾Ê½À´Ï´Ù. " "Ŭ·¡½º:%d, ·¹º§:%d, STR:%d, DEX:%d, CON:%d, INT:%d, WIS:%d IP:%d", m_dwCID, m_DBData.m_Info.Class, m_DBData.m_Info.Level, State.m_wSTR, State.m_wDEX, State.m_wCON, State.m_wINT, State.m_wWIS, State.m_wIP); usError = PktSRTAck::FAIL_INVALID_STATUS; goto SEND_PACKET; } // ÃÖ¼Ò ½ºÅÈ Ã¼Å© if (false == ClassTable[m_DBData.m_Info.Class].CheckMinState(State, m_DBData.m_Info.Level)) { ERRLOG9(g_Log, "CID:0x%08x ÀçºÐ¹èµÈ ½ºÅÈÀÌ ¿Ã¹Ù¸£Áö ¾Ê½À´Ï´Ù. " "Ŭ·¡½º:%d, ·¹º§:%d, STR:%d, DEX:%d, CON:%d, INT:%d, WIS:%d IP:%d", m_dwCID, m_DBData.m_Info.Class, m_DBData.m_Info.Level, State.m_wSTR, State.m_wDEX, State.m_wCON, State.m_wINT, State.m_wWIS, State.m_wIP); usError = PktSRTAck::FAIL_INVALID_STATUS; goto SEND_PACKET; } if (usError == PktSRTAck::NO_SERVER_ERR) { const CHAR_INFOST tempInfoSt = m_DBData.m_Info; // ½ºÅ×ÀÌÅͽº ÀçÈÆ·Ã ¼º°ø½Ã ¾ÆÀÌÅÛ »èÁ¦ ¹× µ· °¨¼Ò if (0 < lpItem->GetNumOrDurability()) { lpItem->SetNumOrDurability(lpItem->GetNumOrDurability() - 1); } else { ERRLOG2(g_Log, "CID:0x%08x ½ºÅ×ÀÌÅͽº ÀçÈÆ·Ã ¿À·ù : ºÎȰÀÇ µ¹ÀÇ °¹¼ö°¡ ÀÌ»óÇÕ´Ï´Ù. Pos:%d, Index:%d", InvenPos.m_cPos, InvenPos.m_cIndex); usError = PktSRTAck::FAIL_NO_ITEM; goto SEND_PACKET; } if (0 == lpItem->GetNumOrDurability()) { if (RemoveItem(InvenPos)) { DELETE_ITEM(lpItem); } else { ERRLOG2(g_Log, "CID:0x%08x ½ºÅ×ÀÌÅͽº ÀçÈÆ·Ã ¿À·ù : ºÎȰÀÇ µ¹À» Á¦°ÅÇÒ ¼ö ¾ø½À´Ï´Ù. Pos:%d, Index:%d", InvenPos.m_cPos, InvenPos.m_cIndex); m_Inventory.DumpItemInfo(); usError = PktSRTAck::FAIL_NO_ITEM; goto SEND_PACKET; } } // unsigned long dwSrcGold = GetGold(); // DeductGold(dwReduceGold, false); // GAMELOG::LogTakeGold(*this, dwSrcGold, GetGold(), dwReduceGold, // TakeType::TS_INVEN, TakeType::TS_INVEN, GAMELOG::sTakeGoldLogV2::STATE_REDISTRIBUTE, 0); // ¿ø·¡ ½ºÅÝ °Ë»ç int OriStat = tempInfoSt.IP+tempInfoSt.STR+tempInfoSt.DEX+tempInfoSt.CON+tempInfoSt.INT+tempInfoSt.WIS; int NewStat = State.m_wIP+State.m_wSTR+State.m_wDEX+State.m_wCON+State.m_wINT+State.m_wWIS; // ¹Ù²ï ½ºÅÈÀ» Àû¿ë m_DBData.m_Info.IP = State.m_wIP; m_DBData.m_Info.STR = State.m_wSTR; m_DBData.m_Info.DEX = State.m_wDEX; m_DBData.m_Info.CON = State.m_wCON; m_DBData.m_Info.INT = State.m_wINT; m_DBData.m_Info.WIS = State.m_wWIS; // ÀçºÐ¹èµÈ ½ºÅÈ¿¡ µû¶ó ½ºÅ³ ÀçÁ¤¸® if (false == RedistributionSkill()) { ERRLOG1(g_Log, "CID:0x%08x ½ºÅ³ ÀçºÐ¹è¿¡ ½ÇÆÐÇÏ¿´½À´Ï´Ù.", m_dwCID); m_DBData.m_Info = tempInfoSt; return false; } DETLOG7(g_Log, "CID:%u ÀÇ Ä³¸¯ÅͰ¡ ½ºÅÈ ÀçºÐ¹è¸¦ Çß½À´Ï´Ù.(¿À¸®Áö³Î:IP:%d,STR:%d,DEX:%d,CON:%d,INT:%d,WIS:%d)", m_dwCID, tempInfoSt.IP, tempInfoSt.STR, tempInfoSt.DEX, tempInfoSt.CON, tempInfoSt.INT, tempInfoSt.WIS); DETLOG7(g_Log, "CID:%u ÀÇ Ä³¸¯ÅͰ¡ ½ºÅÈ ÀçºÐ¹è¸¦ Çß½À´Ï´Ù.(IP:%d,STR:%d,DEX:%d,CON:%d,INT:%d,WIS:%d)", m_dwCID, State.m_wIP, State.m_wSTR, State.m_wDEX, State.m_wCON, State.m_wINT, State.m_wWIS); // Äü½½·Ô ÃʱâÈ­ m_DBData.m_Quick = QUICK::QUICK(); } SEND_PACKET: if (NULL != m_lpGameClientDispatch) { if (false == GameClientSendPacket::SendCharStatusRetrain(m_lpGameClientDispatch->GetSendStream(), m_dwCID, m_DBData, InvenPos, m_DBData.m_Info.Gold, usError)) { return false; } else { if (false == GameClientSendPacket::SendCharStateRedistribution(m_lpGameClientDispatch->GetSendStream(), m_dwCID, GetState(), GetSkill(), usError)) { return false; } } } if (usError == PktSRTAck::NO_SERVER_ERR) { return CalculateStatusData(true); } // usError °¡ Error °ªÀ» °¡Áö°í ÀÖ´Â ÆÐŶÀ» º¸³Â±â ¶§¹®¿¡ // true ¸¦ ¸®ÅÏÇØ¼­ Ŭ¶óÀ̾ðÆ®ÀÇ Á¢¼ÓÀ» ²÷Áö ¾Ê´Â´Ù. return true; } unsigned char CCharacter::GetCurrentDurability(unsigned char cEquipmentIndex) { if (cEquipmentIndex >= Item::EquipmentPos::MAX_EQUPMENT_POS) { return 0; } Item::ItemPos itemPos(TakeType::TS_EQUIP, cEquipmentIndex); Item::CItem* lpItem = m_Equipments.GetItem(itemPos); if (NULL == lpItem) { return 0; } return lpItem->GetNumOrDurability(); } bool CCharacter::ChangeWeaponAndShield(unsigned char cSelect) { if (cSelect < 0 || cSelect > 1) { ERRLOG2(g_Log, "CID:0x%08x À߸øµÈ À§Ä¡ÀÇ ¹«±â·Î ±³Ã¼ÇÏ·Á ÇÕ´Ï´Ù. Select: %d", m_dwCID, cSelect); return false; } if ((cSelect == 0 && Item::EquipmentPos::WEAPON_HAND1 == m_Equipments.GetRightHandIndex()) || (cSelect == 1 && Item::EquipmentPos::WEAPON_HAND2 == m_Equipments.GetRightHandIndex())) { ERRLOG2(g_Log, "CID:0x%08x ÀÌ¹Ì »ç¿ëÇϰí ÀÖ´Â À§Ä¡ÀÇ ¹«±â·Î ±³Ã¼ÇÏ·Á ÇÕ´Ï´Ù. Select: %d", m_dwCID, cSelect); return false; } m_cHandPos = cSelect; /* if (cSelect <= 0 || cSelect > 2) { ERRLOG2(g_Log, "CID:0x%08x À߸øµÈ À§Ä¡ÀÇ ¹«±â·Î ±³Ã¼ÇÏ·Á ÇÕ´Ï´Ù. Select: %d", m_dwCID, cSelect); return false; } if ((cSelect == 1 && Item::EquipmentPos::WEAPON_HAND1 == m_Equipments.GetRightHandIndex()) || (cSelect == 2 && Item::EquipmentPos::WEAPON_HAND2 == m_Equipments.GetRightHandIndex())) { ERRLOG2(g_Log, "CID:0x%08x ÀÌ¹Ì »ç¿ëÇϰí ÀÖ´Â À§Ä¡ÀÇ ¹«±â·Î ±³Ã¼ÇÏ·Á ÇÕ´Ï´Ù. Select: %d", m_dwCID, cSelect); return false; } m_cHandPos = cSelect - 1; */ m_Equipments.ChangeWeaponAndShield(); CalculateStatusData(false); return true; } bool CCharacter::ChangeRide(unsigned char cSelect) // ¸» Ÿ±â ³»¸®±â { if (cSelect < 0 || cSelect > 1) { ERRLOG2(g_Log, "CID:0x%08x À߸øµÈ À§Ä¡ÀÇ ¸»·Î ±³Ã¼ÇÏ·Á ÇÕ´Ï´Ù. Select: %d", m_dwCID, cSelect); return false; } if (m_cRidePos == cSelect) { ERRLOG2(g_Log, "CID:0x%08x ÀÌ¹Ì °°Àº »óÅ·Π¸»À» »ç¿ëÇϰí ÀÖ½À´Ï´Ù. Select: %d", m_dwCID, cSelect); return false; } m_cRidePos = cSelect; m_Equipments.ChangeRide(m_cRidePos); CalculateStatusData(false); return true; } bool CCharacter::CalculateEquipDurability(unsigned short wAttackType) { Item::CItem* lpEquipment = NULL; unsigned char cEquipIndex = Item::EquipmentPos::MAX_EQUPMENT_POS; unsigned char cEquipValue = 0; int AbValue = m_AbilityValue[Skill::Type::AB_ENDUR_SHILD]; // ÆÛ¼¾Æ®·Î µé¾î°¡ÀÖ´Ù. (100 À̸é 100ÇÁ·Î¸¸Å­ º¸³Ê½º¸¦ ¹Þ´Â´Ù) int AddPer = 0; switch (wAttackType) { // ºí·° case AtType::GUARD: { AddPer = SHIELD_DURABILITY_DECRESE_PERCENTAGE*AbValue/100; if (0 == Math::Random::ComplexRandom(SHIELD_DURABILITY_DECRESE_PERCENTAGE+AddPer)) { lpEquipment = GetEquipments().GetLeftHand(); if (NULL == lpEquipment) { // ¿Þ¼Õ Àåºñ°¡ ¾øÀ¸¸é ¿À¸¥¼ÕÀ¸·Î ºí·° lpEquipment = GetEquipments().GetRightHand(); if (NULL == lpEquipment) { ERRLOG1(g_Log, "CID:0x%08x ºí·°ÇÒ Àåºñ°¡ ¾ø´Â ij¸¯ÅͰ¡ ºí·°ÇÏ¿´½À´Ï´Ù.", m_dwCID); return false; } } } break; } // ¹æ¾î case AtType::DEFENCE: { AddPer = ARMOUR_DURABILITY_DECRESE_PERCENTAGE*AbValue/100; if (0 == Math::Random::ComplexRandom(ARMOUR_DURABILITY_DECRESE_PERCENTAGE+AddPer)) { const unsigned char MAX_ARMOUR_INDEX_NUM = 4; static unsigned char aryArmourShuffleList[MAX_ARMOUR_INDEX_NUM] = { Item::EquipmentPos::HELM, Item::EquipmentPos::BOOTS, Item::EquipmentPos::GLOVE, Item::EquipmentPos::ARMOUR }; std::random_shuffle(aryArmourShuffleList, aryArmourShuffleList + MAX_ARMOUR_INDEX_NUM); lpEquipment = GetEquipments().GetItem(Item::ItemPos(TakeType::TS_EQUIP, aryArmourShuffleList[0])); } break; } // ¿Þ¼Õ °ø°Ý case AtType::LEFT_MELEE: { AddPer = WEAPON_DURABILITY_DECRESE_PERCENTAGE*AbValue/100; if (0 == Math::Random::ComplexRandom(WEAPON_DURABILITY_DECRESE_PERCENTAGE+AddPer)) { lpEquipment = GetEquipments().GetLeftHand(); } break; } // ÀÏ¹Ý °ø°Ý default: { AddPer = WEAPON_DURABILITY_DECRESE_PERCENTAGE*AbValue/100; if (0 == Math::Random::ComplexRandom(WEAPON_DURABILITY_DECRESE_PERCENTAGE+AddPer)) { lpEquipment = GetEquipments().GetRightHand(); } break; } } if (NULL != lpEquipment) { if (0 < lpEquipment->GetNumOrDurability()) { lpEquipment->SetNumOrDurability(lpEquipment->GetNumOrDurability() - 1); } else if (0 == lpEquipment->GetNumOrDurability()) { // edith 2008.01.16 ¾ÆÀÌÅÛ ÃÖ´ë³»±¸µµ °¨¼Ò int idown = STARTAXDURABILITY+Math::Random::ComplexRandom(DOWNMAXDURABILITY); int curDur = lpEquipment->GetMaxNumOrDurability() - idown; if(curDur < 0) curDur = 1; lpEquipment->SetMaxNumOrDurability(curDur); lpEquipment->SetNumOrDurability(0); CalculateStatusData(false); } if (NULL != m_lpGameClientDispatch) { GameClientSendPacket::SendCharEquipDurability(m_lpGameClientDispatch->GetSendStream(), m_dwCID, lpEquipment->GetPos().m_cIndex, lpEquipment->GetNumOrDurability(), lpEquipment->GetMaxNumOrDurability(), PktBase::NO_SERVER_ERR); } } return true; } bool CCharacter::CalculateAllEquipDurability(unsigned char cDecreasePersent) { for (char cIndex = 0; cIndex < Item::EquipmentPos::MAX_EQUPMENT_POS; ++cIndex) { // ³»±¸µµ °¨¼Ò°¡ ¾ø´Â ¾ÆÀÌÅÛÀº Á¦¿Ü if (Item::EquipmentPos::SHIRT == cIndex || Item::EquipmentPos::TUNIC == cIndex || Item::EquipmentPos::NECKLACE == cIndex || Item::EquipmentPos::RINGR == cIndex || Item::EquipmentPos::RINGL == cIndex || Item::EquipmentPos::AVATA == cIndex ) { continue; } Item::ItemPos itemPos(TakeType::TS_EQUIP, cIndex); Item::CItem* lpItem = m_Equipments.GetItem(itemPos); if (NULL == lpItem) { continue; } if (lpItem->GetEnableRepair()) { if (0 < lpItem->GetNumOrDurability()) { const unsigned char cDecreasePoint = static_cast(lpItem->GetMaxNumOrDurability() * cDecreasePersent / 100.0f); if (lpItem->GetNumOrDurability() <= cDecreasePoint) { // edith 2008.01.16 ¾ÆÀÌÅÛ ÃÖ´ë³»±¸µµ °¨¼Ò int idown = STARTAXDURABILITY+Math::Random::ComplexRandom(DOWNMAXDURABILITY)/2; int curDur = lpItem->GetMaxNumOrDurability() - idown; if(curDur < 0) curDur = 1; lpItem->SetMaxNumOrDurability(curDur); lpItem->SetNumOrDurability(0); } else { lpItem->SetNumOrDurability(lpItem->GetNumOrDurability() - cDecreasePoint); } } else if (0 == lpItem->GetNumOrDurability()) { // edith 2008.01.16 ¾ÆÀÌÅÛ ÃÖ´ë³»±¸µµ °¨¼Ò int idown = STARTAXDURABILITY+Math::Random::ComplexRandom(DOWNMAXDURABILITY); int curDur = lpItem->GetMaxNumOrDurability() - idown; if(curDur < 0) curDur = 1; lpItem->SetMaxNumOrDurability(curDur); lpItem->SetNumOrDurability(0); } if (0 == lpItem->GetNumOrDurability()) { CalculateStatusData(false); } if (NULL != m_lpGameClientDispatch) { GameClientSendPacket::SendCharEquipDurability(m_lpGameClientDispatch->GetSendStream(), m_dwCID, lpItem->GetPos().m_cIndex, lpItem->GetNumOrDurability(), lpItem->GetMaxNumOrDurability(), PktBase::NO_SERVER_ERR); } } } return true; } void CCharacter::UpgradeRespawnSpeedByEmblem(unsigned char cUpgradeType, unsigned char cUpgradeStep) { int nKID = Siege::GetKID(Siege::EMBLEM, Siege::COMPLETE, cUpgradeType, cUpgradeStep); const CMonsterMgr::MonsterProtoType* lpProtoType = CMonsterMgr::GetInstance().GetMonsterProtoType(nKID); if (lpProtoType) { m_dwRespawnSpeed -= static_cast(m_dwRespawnSpeed * lpProtoType->m_MonsterInfo.m_fRespawnSpeedUp); } } void CCharacter::DegradeRespawnSpeedByEmblem() { m_dwRespawnSpeed = CCharacter::RESPAWN_PULSE; }