Advertisement
Guest User

party.cpp

a guest
Jun 10th, 2016
102
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 12.40 KB | None | 0 0
  1. ////////////////////////////////////////////////////////////////////////
  2. // OpenTibia - an opensource roleplaying game
  3. ////////////////////////////////////////////////////////////////////////
  4. // This program is free software: you can redistribute it and/or modify
  5. // it under the terms of the GNU General Public License as published by
  6. // the Free Software Foundation, either version 3 of the License, or
  7. // (at your option) any later version.
  8. //
  9. // This program is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. // GNU General Public License for more details.
  13. //
  14. // You should have received a copy of the GNU General Public License
  15. // along with this program.  If not, see <http://www.gnu.org/licenses/>.
  16. ////////////////////////////////////////////////////////////////////////
  17. #include "otpch.h"
  18. #include "party.h"
  19.  
  20. #include "player.h"
  21. #include "chat.h"
  22. #include "game.h"
  23. #include "configmanager.h"
  24.  
  25. extern Game g_game;
  26. extern Chat g_chat;
  27. extern ConfigManager g_config;
  28.  
  29. Party::Party(Player* _leader)
  30. {
  31.     sharedExpActive = sharedExpEnabled = false;
  32.     if(_leader)
  33.     {
  34.         leader = _leader;
  35.         leader->setParty(this);
  36.         leader->sendPlayerIcons(leader);
  37.     }
  38. }
  39.  
  40. void Party::disband()
  41. {
  42.     leader->sendClosePrivate(CHANNEL_PARTY);
  43.     leader->setParty(NULL);
  44.     leader->sendTextMessage(MSG_INFO_DESCR, "Your party has been disbanded.");
  45.  
  46.     leader->sendPlayerIcons(leader);
  47.     for(PlayerVector::iterator it = inviteList.begin(); it != inviteList.end(); ++it)
  48.     {
  49.         (*it)->removePartyInvitation(this);
  50.         (*it)->sendPlayerIcons(leader);
  51.         (*it)->sendPlayerIcons(*it);
  52.         leader->sendPlayerIcons(*it);
  53.     }
  54.  
  55.     inviteList.clear();
  56.     for(PlayerVector::iterator it = memberList.begin(); it != memberList.end(); ++it)
  57.     {
  58.         (*it)->sendClosePrivate(CHANNEL_PARTY);
  59.         (*it)->setParty(NULL);
  60.         (*it)->sendTextMessage(MSG_INFO_DESCR, "Your party has been disbanded.");
  61.  
  62.         (*it)->sendPlayerIcons(*it);
  63.         (*it)->sendPlayerIcons(leader);
  64.         leader->sendPlayerIcons(*it);
  65.     }
  66.  
  67.     memberList.clear();
  68.     leader = NULL;
  69.     delete this;
  70. }
  71.  
  72. bool Party::leave(Player* player)
  73. {
  74.     if(!isPlayerMember(player) && player != leader)
  75.         return false;
  76.  
  77.     bool missingLeader = false;
  78.     if(leader == player)
  79.     {
  80.         if(!memberList.empty())
  81.         {
  82.             if(memberList.size() == 1 && inviteList.empty())
  83.                 missingLeader = true;
  84.             else
  85.                 passLeadership(memberList.front());
  86.         }
  87.         else
  88.             missingLeader = true;
  89.     }
  90.  
  91.     //since we already passed the leadership, we remove the player from the list
  92.     PlayerVector::iterator it = std::find(memberList.begin(), memberList.end(), player);
  93.     if(it != memberList.end())
  94.         memberList.erase(it);
  95.  
  96.     it = std::find(inviteList.begin(), inviteList.end(), player);
  97.     if(it != inviteList.end())
  98.         inviteList.erase(it);
  99.  
  100.     player->setParty(NULL);
  101.     player->sendClosePrivate(CHANNEL_PARTY);
  102.  
  103.     player->sendTextMessage(MSG_INFO_DESCR, "You have left the party.");
  104.     player->sendPlayerIcons(player);
  105.  
  106.     updateSharedExperience();
  107.     updateIcons(player);
  108.     clearPlayerPoints(player);
  109.  
  110.     char buffer[105];
  111.     sprintf(buffer, "%s has left the party.", player->getName().c_str());
  112.  
  113.     broadcastMessage(MSG_INFO_DESCR, buffer);
  114.     if(missingLeader || canDisband())
  115.         disband();
  116.  
  117.     return true;
  118. }
  119.  
  120. bool Party::passLeadership(Player* player)
  121. {
  122.     if(!isPlayerMember(player) || player == leader)
  123.         return false;
  124.  
  125.     //Remove it before to broadcast the message correctly
  126.     PlayerVector::iterator it = std::find(memberList.begin(), memberList.end(), player);
  127.     if(it != memberList.end())
  128.         memberList.erase(it);
  129.  
  130.     Player* oldLeader = leader;
  131.     leader = player;
  132.     memberList.insert(memberList.begin(), oldLeader);
  133.  
  134.     char buffer[125];
  135.     sprintf(buffer, "%s is now the leader of the party.", player->getName().c_str());
  136.     broadcastMessage(MSG_INFO_DESCR, buffer, true);
  137.  
  138.     player->sendTextMessage(MSG_INFO_DESCR, "You are now the leader of the party.");
  139.     updateSharedExperience();
  140.  
  141.     updateIcons(oldLeader);
  142.     updateIcons(player);
  143.     return true;
  144. }
  145.  
  146. bool Party::join(Player* player)
  147. {
  148.     if(isPlayerMember(player) || !isPlayerInvited(player))
  149.         return false;
  150.  
  151.     memberList.push_back(player);
  152.     player->setParty(this);
  153.  
  154.     player->removePartyInvitation(this);
  155.     PlayerVector::iterator it = std::find(inviteList.begin(), inviteList.end(), player);
  156.     if(it != inviteList.end())
  157.         inviteList.erase(it);
  158.  
  159.     char buffer[200];
  160.     sprintf(buffer, "%s has joined the party.", player->getName().c_str());
  161.     broadcastMessage(MSG_INFO_DESCR, buffer);
  162.  
  163.     sprintf(buffer, "You have joined %s'%s party. Open the party channel to communicate with your companions.", leader->getName().c_str(), (leader->getName()[leader->getName().length() - 1] == 's' ? "" : "s"));
  164.     player->sendTextMessage(MSG_INFO_DESCR, buffer);
  165.  
  166.     updateSharedExperience();
  167.     updateIcons(player);
  168.     return true;
  169. }
  170.  
  171. bool Party::removeInvite(Player* player)
  172. {
  173.     if(!isPlayerInvited(player))
  174.         return false;
  175.  
  176.     PlayerVector::iterator it = std::find(inviteList.begin(), inviteList.end(), player);
  177.     if(it != inviteList.end())
  178.         inviteList.erase(it);
  179.  
  180.     leader->sendPlayerIcons(player);
  181.     player->sendPlayerIcons(leader);
  182.  
  183.     player->removePartyInvitation(this);
  184.     if(canDisband())
  185.         disband();
  186.  
  187.     return true;
  188. }
  189.  
  190. void Party::revokeInvitation(Player* player)
  191. {
  192.     if(!player || player->isRemoved())
  193.         return;
  194.  
  195.     char buffer[150];
  196.     sprintf(buffer, "%s has revoked %s invitation.", leader->getName().c_str(), (leader->getSex(false) ? "his" : "her"));
  197.     player->sendTextMessage(MSG_INFO_DESCR, buffer);
  198.  
  199.     sprintf(buffer, "Invitation for %s has been revoked.", player->getName().c_str());
  200.     leader->sendTextMessage(MSG_INFO_DESCR, buffer);
  201.     removeInvite(player);
  202. }
  203.  
  204. bool Party::invitePlayer(Player* player)
  205. {
  206.     if(isPlayerInvited(player, true))
  207.         return false;
  208.  
  209.     inviteList.push_back(player);
  210.     player->addPartyInvitation(this);
  211.  
  212.     char buffer[150];
  213.     sprintf(buffer, "%s has been invited.%s", player->getName().c_str(), (!memberList.size() ? " Open the party channel to communicate with your members." : ""));
  214.     leader->sendTextMessage(MSG_INFO_DESCR, buffer);
  215.  
  216.     sprintf(buffer, "%s has invited you to %s party.", leader->getName().c_str(), (leader->getSex(false) ? "his" : "her"));
  217.     player->sendTextMessage(MSG_INFO_DESCR, buffer);
  218.  
  219.     leader->sendPlayerIcons(player);
  220.     player->sendPlayerIcons(leader);
  221.     return true;
  222. }
  223.  
  224. void Party::updateIcons(Player* player)
  225. {
  226.     if(!player || player->isRemoved())
  227.         return;
  228.  
  229.     PlayerVector::iterator it;
  230.     for(it = memberList.begin(); it != memberList.end(); ++it)
  231.     {
  232.         (*it)->sendPlayerIcons(player);
  233.         player->sendPlayerIcons((*it));
  234.     }
  235.  
  236.     for(it = inviteList.begin(); it != inviteList.end(); ++it)
  237.     {
  238.         (*it)->sendPlayerIcons(player);
  239.         player->sendPlayerIcons((*it));
  240.     }
  241.  
  242.     leader->sendPlayerIcons(player);
  243.     player->sendPlayerIcons(leader);
  244. }
  245.  
  246. void Party::updateAllIcons()
  247. {
  248.     PlayerVector::iterator it;
  249.     for(it = memberList.begin(); it != memberList.end(); ++it)
  250.     {
  251.         for(PlayerVector::iterator iit = memberList.begin(); iit != memberList.end(); ++iit)
  252.             (*it)->sendPlayerIcons((*iit));
  253.  
  254.         (*it)->sendPlayerIcons(leader);
  255.         leader->sendPlayerIcons((*it));
  256.     }
  257.  
  258.     leader->sendPlayerIcons(leader);
  259.     for(it = inviteList.begin(); it != inviteList.end(); ++it)
  260.         (*it)->sendPlayerIcons(leader);
  261. }
  262.  
  263. void Party::broadcastMessage(MessageClasses messageClass, const std::string& text, bool sendToInvitations/* = false*/)
  264. {
  265.     PlayerVector::iterator it;
  266.     if(!memberList.empty())
  267.     {
  268.         for(it = memberList.begin(); it != memberList.end(); ++it)
  269.             (*it)->sendTextMessage(messageClass, text);
  270.     }
  271.  
  272.     leader->sendTextMessage(messageClass, text);
  273.     if(!sendToInvitations || inviteList.empty())
  274.         return;
  275.  
  276.     for(it = inviteList.begin(); it != inviteList.end(); ++it)
  277.         (*it)->sendTextMessage(messageClass, text);
  278. }
  279.  
  280. void Party::updateSharedExperience()
  281. {
  282.     if(!sharedExpActive)
  283.         return;
  284.  
  285.     bool result = canEnableSharedExperience();
  286.     if(result == sharedExpEnabled)
  287.         return;
  288.  
  289.     sharedExpEnabled = result;
  290.     updateAllIcons();
  291. }
  292.  
  293. bool Party::setSharedExperience(Player* player, bool _sharedExpActive)
  294. {
  295.     if(!player || player->isRemoved() || player != leader)
  296.         return false;
  297.  
  298.     if(sharedExpActive == _sharedExpActive)
  299.         return true;
  300.  
  301.     sharedExpActive = _sharedExpActive;
  302.     if(sharedExpActive)
  303.     {
  304.         sharedExpEnabled = canEnableSharedExperience();
  305.         if(sharedExpEnabled)
  306.             leader->sendTextMessage(MSG_INFO_DESCR, "Shared Experience is now active.");
  307.         else
  308.             leader->sendTextMessage(MSG_INFO_DESCR, "Shared Experience has been activated, but some members of your party are inactive.");
  309.     }
  310.     else
  311.         leader->sendTextMessage(MSG_INFO_DESCR, "Shared Experience has been deactivated.");
  312.  
  313.     updateAllIcons();
  314.     return true;
  315. }
  316.  
  317. void Party::shareExperience(double experience, bool fromMonster, bool multiplied)
  318. {
  319.     double shareExperience = experience;
  320.     if(experience >= (double)g_config.getNumber(ConfigManager::EXTRA_PARTY_LIMIT))
  321.         shareExperience += (experience * ((double)g_config.getNumber(ConfigManager::EXTRA_PARTY_PERCENT) / 100));
  322.  
  323.     shareExperience /= memberList.size() + 1;
  324.     double tmpExperience = shareExperience; //we need this, as onGainSharedExperience increases the value
  325.  
  326.     leader->onGainSharedExperience(tmpExperience, fromMonster, multiplied);
  327.     for(PlayerVector::iterator it = memberList.begin(); it != memberList.end(); ++it)
  328.     {
  329.         tmpExperience = shareExperience;
  330.         (*it)->onGainSharedExperience(tmpExperience, fromMonster, multiplied);
  331.     }
  332. }
  333.  
  334. bool Party::canUseSharedExperience(const Player* player, uint32_t highestLevel/* = 0*/) const
  335. {
  336.     if(!player || player->isRemoved())
  337.         return false;
  338.  
  339.     if(!highestLevel)
  340.     {
  341.         highestLevel = leader->getLevel();
  342.         for(PlayerVector::const_iterator it = memberList.begin(); it != memberList.end(); ++it)
  343.         {
  344.             if((*it)->getLevel() > highestLevel)
  345.                 highestLevel = (*it)->getLevel();
  346.         }
  347.     }
  348.  
  349.     if(player->getLevel() < (uint32_t)std::ceil((double)highestLevel * g_config.getDouble(
  350.         ConfigManager::PARTY_DIFFERENCE)) || !Position::areInRange(Position(
  351.         g_config.getNumber(ConfigManager::PARTY_RADIUS_X), g_config.getNumber(
  352.         ConfigManager::PARTY_RADIUS_Y), g_config.getNumber(ConfigManager::PARTY_RADIUS_Z)),
  353.         leader->getPosition(), player->getPosition()))
  354.         return false;
  355.  
  356.     CountMap::const_iterator it = pointMap.find(player->getID());
  357.     return it != pointMap.end() && (OTSYS_TIME() - it->second.ticks) <= g_config.getNumber(
  358.         ConfigManager::EXPERIENCE_SHARE_ACTIVITY);
  359. }
  360.  
  361. bool Party::canEnableSharedExperience()
  362. {
  363.     if(!memberList.size())
  364.         return false;
  365.  
  366.     uint32_t highestLevel = leader->getLevel();
  367.     for(PlayerVector::iterator it = memberList.begin(); it != memberList.end(); ++it)
  368.     {
  369.         if((*it)->getLevel() > highestLevel)
  370.             highestLevel = (*it)->getLevel();
  371.     }
  372.  
  373.     for(PlayerVector::iterator it = memberList.begin(); it != memberList.end(); ++it)
  374.     {
  375.         if(!canUseSharedExperience((*it), highestLevel))
  376.             return false;
  377.     }
  378.  
  379.     return canUseSharedExperience(leader, highestLevel);
  380. }
  381.  
  382. void Party::addPlayerHealedMember(Player* player, uint32_t points)
  383. {
  384.     if(points <= 0)
  385.         return;
  386.  
  387.     CountMap::iterator it = pointMap.find(player->getID());
  388.     if(it != pointMap.end())
  389.     {
  390.         it->second.totalHeal += points;
  391.         it->second.ticks = OTSYS_TIME();
  392.     }
  393.     else
  394.         pointMap[player->getID()] = CountBlock_t(points, 0);
  395.  
  396.     updateSharedExperience();
  397. }
  398.  
  399. void Party::addPlayerDamageMonster(Player* player, uint32_t points)
  400. {
  401.     if(points <= 0)
  402.         return;
  403.  
  404.     CountMap::iterator it = pointMap.find(player->getID());
  405.     if(it != pointMap.end())
  406.     {
  407.         it->second.totalDamage += points;
  408.         it->second.ticks = OTSYS_TIME();
  409.     }
  410.     else
  411.         pointMap[player->getID()] = CountBlock_t(0, points);
  412.  
  413.     updateSharedExperience();
  414. }
  415.  
  416. void Party::clearPlayerPoints(Player* player)
  417. {
  418.     CountMap::iterator it = pointMap.find(player->getID());
  419.     if(it == pointMap.end())
  420.         return;
  421.  
  422.     pointMap.erase(it);
  423.     updateSharedExperience();
  424. }
  425.  
  426. bool Party::isPlayerMember(const Player* player, bool result/* = false*/) const
  427. {
  428.     if(!player || player->isRemoved())
  429.         return result;
  430.  
  431.     return std::find(memberList.begin(), memberList.end(), player) != memberList.end();
  432. }
  433.  
  434. bool Party::isPlayerInvited(const Player* player, bool result/* = false*/) const
  435. {
  436.     if(!player || player->isRemoved())
  437.         return result;
  438.  
  439.     return std::find(inviteList.begin(), inviteList.end(), player) != inviteList.end();
  440. }
  441.  
  442. bool Party::canOpenCorpse(uint32_t ownerId)
  443. {
  444.     return leader->getGUID() == ownerId || isPlayerMember(g_game.getPlayerByGuid(ownerId));
  445. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement