From 78930916add332ebc58bf6aa7e0be9a7b30fda4d Mon Sep 17 00:00:00 2001 From: CPunch Date: Wed, 23 Sep 2020 14:44:27 -0500 Subject: [PATCH] added support for nano missions --- src/MissionManager.cpp | 77 ++++++++++++++++++++++++++++++++---------- src/MissionManager.hpp | 2 ++ src/MobManager.cpp | 2 ++ src/TableData.cpp | 8 +++++ 4 files changed, 71 insertions(+), 18 deletions(-) diff --git a/src/MissionManager.cpp b/src/MissionManager.cpp index 769283b..e65f325 100644 --- a/src/MissionManager.cpp +++ b/src/MissionManager.cpp @@ -2,12 +2,14 @@ #include "CNStructs.hpp" #include "MissionManager.hpp" #include "PlayerManager.hpp" +#include "NanoManager.hpp" #include "ItemManager.hpp" #include "string.h" std::map MissionManager::Rewards; std::map MissionManager::Tasks; +nlohmann::json MissionManager::AvatarGrowth[36]; void MissionManager::init() { REGISTER_SHARD_PACKET(P_CL2FE_REQ_PC_TASK_START, taskStart); @@ -16,6 +18,31 @@ void MissionManager::init() { REGISTER_SHARD_PACKET(P_CL2FE_REQ_PC_TASK_STOP, quitMission); } +bool startTask(Player* plr, int TaskID) { + if (MissionManager::Tasks.find(TaskID) == MissionManager::Tasks.end()) { + std::cout << "[WARN] Player submitted unknown task!?" << std::endl; + return false; + } + + TaskData& task = *MissionManager::Tasks[TaskID]; + int i; + for (i = 0; i < ACTIVE_MISSION_COUNT; i++) { + if (plr->tasks[i] == 0) { + plr->tasks[i] = TaskID; + for (int j = 0; j < 3; j++) { + plr->RemainingNPCCount[i][j] = (int)task["m_iCSUNumToKill"][j]; + } + break; + } + } + + if (i == ACTIVE_MISSION_COUNT - 1 && plr->tasks[i] != TaskID) { + std::cout << "[WARN] Player has more than 6 active missions!?" << std::endl; + } + + return true; +} + void MissionManager::taskStart(CNSocket* sock, CNPacketData* data) { if (data->size != sizeof(sP_CL2FE_REQ_PC_TASK_START)) return; // malformed packet @@ -24,30 +51,13 @@ void MissionManager::taskStart(CNSocket* sock, CNPacketData* data) { INITSTRUCT(sP_FE2CL_REP_PC_TASK_START_SUCC, response); Player *plr = PlayerManager::getPlayer(sock); - if (Tasks.find(missionData->iTaskNum) == Tasks.end()) { - std::cout << "[WARN] Player submitted unknown task!?" << std::endl; + if (!startTask(plr, missionData->iTaskNum)) { // TODO: TASK_FAIL? response.iTaskNum = missionData->iTaskNum; sock->sendPacket((void*)&response, P_FE2CL_REP_PC_TASK_START_SUCC, sizeof(sP_FE2CL_REP_PC_TASK_START_SUCC)); return; } - TaskData& task = *Tasks[missionData->iTaskNum]; - int i; - for (i = 0; i < ACTIVE_MISSION_COUNT; i++) { - if (plr->tasks[i] == 0) { - plr->tasks[i] = missionData->iTaskNum; - for (int j = 0; j < 3; j++) { - plr->RemainingNPCCount[i][j] = (int)task["m_iCSUNumToKill"][j]; - } - break; - } - } - - if (i == ACTIVE_MISSION_COUNT - 1 && plr->tasks[i] != missionData->iTaskNum) { - std::cout << "[WARN] Player has more than 6 active missions!?" << std::endl; - } - response.iTaskNum = missionData->iTaskNum; sock->sendPacket((void*)&response, P_FE2CL_REP_PC_TASK_START_SUCC, sizeof(sP_FE2CL_REP_PC_TASK_START_SUCC)); } @@ -116,6 +126,12 @@ void MissionManager::taskEnd(CNSocket* sock, CNPacketData* data) { { // save completed mission on player saveMission(plr, (int)(task["m_iHMissionID"])-1); + + // if it's a nano mission, reward the nano. + if (task["m_iSTNanoID"] != 0) { + NanoManager::addNano(sock, task["m_iSTNanoID"], 0); + } + // remove current mission plr->CurrentMissionID = 0; } @@ -306,9 +322,34 @@ int MissionManager::giveMissionReward(CNSocket *sock, int task) { } sock->sendPacket((void*)respbuf, P_FE2CL_REP_REWARD_ITEM, resplen); + + MissionManager::updateFusionMatter(sock); return 0; } +void MissionManager::updateFusionMatter(CNSocket* sock) { + Player *plr = PlayerManager::getPlayer(sock); + + // check if it is over the limit + std::cout << plr->fusionmatter << " > " << AvatarGrowth[plr->level]["m_iReqBlob_NanoCreate"] << std::endl; + if (plr->fusionmatter > AvatarGrowth[plr->level]["m_iReqBlob_NanoCreate"]) { + // check if the nano task is already started + + for (int i = 0; i < ACTIVE_MISSION_COUNT; i++) { + TaskData& task = *Tasks[plr->tasks[i]]; + if (task["m_iSTNanoID"] != 0) + return; // nano mission was already started! + } + + // start the nano mission + startTask(plr, AvatarGrowth[plr->level]["m_iNanoQuestTaskID"]); + + INITSTRUCT(sP_FE2CL_REP_PC_TASK_START_SUCC, response); + response.iTaskNum = AvatarGrowth[plr->level]["m_iNanoQuestTaskID"]; + sock->sendPacket((void*)&response, P_FE2CL_REP_PC_TASK_START_SUCC, sizeof(sP_FE2CL_REP_PC_TASK_START_SUCC)); + } +} + void MissionManager::mobKilled(CNSocket *sock, int mobid) { Player *plr = PlayerManager::getPlayer(sock); bool missionmob = false; diff --git a/src/MissionManager.hpp b/src/MissionManager.hpp index 1d6bed5..df19f0f 100644 --- a/src/MissionManager.hpp +++ b/src/MissionManager.hpp @@ -38,6 +38,7 @@ struct TaskData { namespace MissionManager { extern std::map Rewards; extern std::map Tasks; + extern nlohmann::json AvatarGrowth[36]; void init(); void taskStart(CNSocket* sock, CNPacketData* data); @@ -50,6 +51,7 @@ namespace MissionManager { //checks if player doesn't have n/n quest items bool isQuestItemFull(CNSocket* sock, int itemId, int itemCount); int giveMissionReward(CNSocket *sock, int task); + void updateFusionMatter(CNSocket* sock); void mobKilled(CNSocket *sock, int mobid); diff --git a/src/MobManager.cpp b/src/MobManager.cpp index c0725af..9d87d6a 100644 --- a/src/MobManager.cpp +++ b/src/MobManager.cpp @@ -131,6 +131,8 @@ void MobManager::giveReward(CNSocket *sock) { sock->sendPacket((void*)respbuf, P_FE2CL_REP_REWARD_ITEM, resplen); } + + MissionManager::updateFusionMatter(sock); } void MobManager::killMob(CNSocket *sock, Mob *mob) { diff --git a/src/TableData.cpp b/src/TableData.cpp index fdd2f66..dfc0ae0 100644 --- a/src/TableData.cpp +++ b/src/TableData.cpp @@ -123,6 +123,14 @@ void TableData::init() { std::cout << "[INFO] Loaded " << ItemManager::ItemData.size() << " items" << std::endl; + // load player limits from m_pAvatarTable.m_pAvatarGrowData + + nlohmann::json growth = xdtData["m_pAvatarTable"]["m_pAvatarGrowData"]; + + for (int i = 0; i < 36; i++) { + MissionManager::AvatarGrowth[i] = growth[i]; + } + // load vendor listings nlohmann::json listings = xdtData["m_pVendorTable"]["m_pItemData"];