ManaPlus
Functions
TmwAthena::BeingRecv Namespace Reference

Functions

void processBeingChangeLook (Net::MessageIn &msg)
 
void processBeingChangeLook2 (Net::MessageIn &msg)
 
void processBeingVisible (Net::MessageIn &msg)
 
void processBeingMove (Net::MessageIn &msg)
 
void processPlayerUpdate1 (Net::MessageIn &msg)
 
void processPlayerUpdate2 (Net::MessageIn &msg)
 
void processPlayerMove (Net::MessageIn &msg)
 
void processBeingSpawn (Net::MessageIn &msg)
 
void processSkillCasting (Net::MessageIn &msg)
 
void processBeingStatusChange (Net::MessageIn &msg)
 
void processBeingMove2 (Net::MessageIn &msg)
 
void processBeingChangeDirection (Net::MessageIn &msg)
 
void processBeingChangeLookContinue (const Net::MessageIn &msg, Being *const dstBeing, const uint8_t type, const int id, const int id2)
 
void processPlayerStatusChange (Net::MessageIn &msg)
 
void processBeingResurrect (Net::MessageIn &msg)
 
void processPlayerGuilPartyInfo (Net::MessageIn &msg)
 
void processBeingSelfEffect (Net::MessageIn &msg)
 
void processSkillCastCancel (Net::MessageIn &msg)
 
void processIpResponse (Net::MessageIn &msg)
 
void processPvpSet (Net::MessageIn &msg)
 
void processSkillDamage (Net::MessageIn &msg)
 
void applyPlayerAction (Net::MessageIn &msg, Being *const being, const uint8_t type)
 
void setServerGender (Being *const being, const uint8_t gender)
 

Function Documentation

◆ applyPlayerAction()

void TmwAthena::BeingRecv::applyPlayerAction ( Net::MessageIn msg,
Being *const  being,
const uint8_t  type 
)

Definition at line 1436 of file beingrecv.cpp.

1439 {
1440  if (being == nullptr)
1441  return;
1442  switch (type)
1443  {
1444  case 0:
1445  being->setAction(BeingAction::STAND, 0);
1447  break;
1448 
1449  case 1:
1450  if (being->getCurrentAction() != BeingAction::DEAD)
1451  {
1452  being->setAction(BeingAction::DEAD, 0);
1453  being->recalcSpritesOrder();
1454  }
1455  break;
1456 
1457  case 2:
1458  being->setAction(BeingAction::SIT, 0);
1460  break;
1461 
1462  default:
1464  break;
1465  }
1466 }
virtual void setAction(const BeingActionT &action, const int attackId)
Definition: being.cpp:1554
void recalcSpritesOrder()
Definition: being.cpp:4359
BeingActionT getCurrentAction() const
Definition: being.h:482
void imitateAction(const Being *const being, const BeingActionT &action)
LocalPlayer * localPlayer
#define UNIMPLEMENTEDPACKETFIELD(field)
Definition: logger.h:59

References BeingAction::DEAD, Being::getCurrentAction(), LocalPlayer::imitateAction(), localPlayer, Being::recalcSpritesOrder(), Being::setAction(), BeingAction::SIT, BeingAction::STAND, and UNIMPLEMENTEDPACKETFIELD.

◆ processBeingChangeDirection()

void TmwAthena::BeingRecv::processBeingChangeDirection ( Net::MessageIn msg)

Definition at line 1215 of file beingrecv.cpp.

1216 {
1217  BLOCK_START("BeingRecv::processBeingChangeDirection")
1218  if (actorManager == nullptr)
1219  {
1220  BLOCK_END("BeingRecv::processBeingChangeDirection")
1221  return;
1222  }
1223 
1224  Being *const dstBeing = actorManager->findBeing(
1225  msg.readBeingId("being id"));
1226 
1227  if (dstBeing == nullptr)
1228  {
1229  DEBUGLOGSTR("invisible player?");
1230  msg.readInt16("unused");
1231  msg.readUInt8("direction");
1232  BLOCK_END("BeingRecv::processBeingChangeDirection");
1233  return;
1234  }
1235 
1236  msg.readInt16("unused");
1237 
1238  const uint8_t dir = Net::MessageIn::fromServerDirection(
1239  CAST_U8(msg.readUInt8("direction") & 0x0FU));
1240  dstBeing->setDirection(dir);
1241  if (localPlayer != nullptr)
1242  localPlayer->imitateDirection(dstBeing, dir);
1243  BLOCK_END("BeingRecv::processBeingChangeDirection")
1244 }
ActorManager * actorManager
#define CAST_U8
Definition: cast.h:27
Definition: being.h:96
void imitateDirection(const Being *const being, const unsigned char dir)
static uint8_t fromServerDirection(const uint8_t serverDir)
Definition: messagein.cpp:266
if(!vert) return
#define DEBUGLOGSTR(str)
Definition: logger.h:45
bool msg(InputEvent &event)
Definition: chat.cpp:39
static Being * findBeing(const std::string &name, const bool npc)
Definition: actions.cpp:212
#define BLOCK_END(name)
Definition: perfomance.h:80
#define BLOCK_START(name)
Definition: perfomance.h:79

References actorManager, BLOCK_END, BLOCK_START, CAST_U8, DEBUGLOGSTR, ActorManager::findBeing(), Net::MessageIn::fromServerDirection(), LocalPlayer::imitateDirection(), localPlayer, Actions::msg(), and Being::setDirection().

◆ processBeingChangeLook()

void TmwAthena::BeingRecv::processBeingChangeLook ( Net::MessageIn msg)

Definition at line 78 of file beingrecv.cpp.

79 {
80  BLOCK_START("BeingRecv::processBeingChangeLook")
81  if (actorManager == nullptr)
82  {
83  BLOCK_END("BeingRecv::processBeingChangeLook")
84  return;
85  }
86 
87  Being *const dstBeing = actorManager->findBeing(
88  msg.readBeingId("being id"));
89 
90  const uint8_t type = msg.readUInt8("type");
91  const int16_t id = CAST_S16(msg.readUInt8("id"));
92  const int id2 = 1;
93 
94  if ((localPlayer == nullptr) || (dstBeing == nullptr))
95  {
96  BLOCK_END("BeingRecv::processBeingChangeLook")
97  return;
98  }
99  processBeingChangeLookContinue(msg, dstBeing, type, id, id2);
100  BLOCK_END("BeingRecv::processBeingChangeLook")
101 }
#define CAST_S16
Definition: cast.h:28
void processBeingChangeLookContinue(const Net::MessageIn &msg, Being *const dstBeing, const uint8_t type, const int id, const int id2, const int *const cards)
Definition: beingrecv.cpp:263
void processBeingChangeLook(Net::MessageIn &msg)
Definition: beingrecv.cpp:78

References actorManager, BLOCK_END, BLOCK_START, CAST_S16, ActorManager::findBeing(), localPlayer, Actions::msg(), and EAthena::BeingRecv::processBeingChangeLookContinue().

◆ processBeingChangeLook2()

void TmwAthena::BeingRecv::processBeingChangeLook2 ( Net::MessageIn msg)

Definition at line 103 of file beingrecv.cpp.

104 {
105  BLOCK_START("BeingRecv::processBeingChangeLook")
106  if (actorManager == nullptr)
107  {
108  BLOCK_END("BeingRecv::processBeingChangeLook")
109  return;
110  }
111 
112  Being *const dstBeing = actorManager->findBeing(
113  msg.readBeingId("being id"));
114 
115  const uint8_t type = msg.readUInt8("type");
116  int id2 = 0;
117 
118  const int16_t id = msg.readInt16("id1");
119  if (type == 2)
120  {
121  id2 = msg.readInt16("id2");
122  }
123  else
124  {
125  msg.readInt16("id2");
126  id2 = 1;
127  }
128 
129  if ((localPlayer == nullptr) || (dstBeing == nullptr))
130  {
131  BLOCK_END("BeingRecv::processBeingChangeLook")
132  return;
133  }
134  processBeingChangeLookContinue(msg, dstBeing, type, id, id2);
135  BLOCK_END("BeingRecv::processBeingChangeLook")
136 }

References actorManager, BLOCK_END, BLOCK_START, ActorManager::findBeing(), localPlayer, Actions::msg(), and EAthena::BeingRecv::processBeingChangeLookContinue().

◆ processBeingChangeLookContinue()

void TmwAthena::BeingRecv::processBeingChangeLookContinue ( const Net::MessageIn msg,
Being *const  dstBeing,
const uint8_t  type,
const int  id,
const int  id2 
)

Definition at line 138 of file beingrecv.cpp.

143 {
144  if (dstBeing->getType() == ActorType::Player)
145  dstBeing->setOtherTime();
146 
147  switch (type)
148  {
149  case 0: // change race
150  dstBeing->setSubtype(fromInt(id, BeingTypeId),
151  dstBeing->getLook());
152  break;
153  case 1: // eAthena LOOK_HAIR
154  {
155  const uint16_t look = CAST_U16(id / 256);
156  const int hair = id % 256;
157  dstBeing->setHairStyle(SPRITE_HAIR_COLOR, hair * -1);
158  dstBeing->setLook(look);
159  break;
160  }
161  case 2: // Weapon ID in id, Shield ID in id2
162  dstBeing->setSpriteId(SPRITE_BODY,
163  id);
164  dstBeing->setWeaponId(id);
165  dstBeing->setSpriteId(SPRITE_FLOOR,
166  id2);
168  break;
169  case 3: // Change lower headgear for eAthena, pants for us
170  dstBeing->setSpriteId(SPRITE_WEAPON,
171  id);
173  break;
174  case 4: // Change upper headgear for eAthena, hat for us
176  id);
178  break;
179  case 5: // Change middle headgear for eathena, armor for us
181  id);
183  break;
184  case 6: // eAthena LOOK_HAIR_COLOR
186  fromInt(id, ItemColor));
187  break;
188  case 7: // Clothes color
189  // ignoring it
190  break;
191  case 8: // eAthena LOOK_SHIELD
192  dstBeing->setSpriteId(SPRITE_FLOOR,
193  id);
195  break;
196  case 9: // eAthena LOOK_SHOES
197  dstBeing->setSpriteId(SPRITE_HAIR,
198  id);
200  break;
201  case 10: // LOOK_GLOVES
202  dstBeing->setSpriteId(SPRITE_SHOES,
203  id);
205  break;
206  case 11: // LOOK_CAPE
207  dstBeing->setSpriteId(SPRITE_SHIELD,
208  id);
210  break;
211  case 12:
212  dstBeing->setSpriteId(SPRITE_HEAD_TOP,
213  id);
215  break;
216  case 13:
217  dstBeing->setSpriteId(SPRITE_HEAD_MID,
218  id);
220  break;
221  case 14:
222  dstBeing->setSpriteId(SPRITE_ROBE,
223  id);
225  break;
226  case 15:
227  dstBeing->setSpriteId(SPRITE_EVOL2,
228  id);
230  break;
231  case 16:
232  dstBeing->setLook(CAST_U16(id));
233  break;
234  default:
236  break;
237  }
238 }
int BeingTypeId
Definition: beingtypeid.h:30
#define CAST_U16
Definition: cast.h:29
void setHairStyle(const unsigned int slot, const int id)
Definition: being.cpp:3372
void setWeaponId(const int id)
Definition: being.cpp:3135
void setLook(const uint16_t look)
Definition: being.cpp:5004
void setSubtype(const BeingTypeId subtype, const uint16_t look)
Definition: being.cpp:371
void setOtherTime()
Definition: being.h:718
void setHairColor(const unsigned int slot, const ItemColor color)
Definition: being.cpp:3389
void setSpriteId(const unsigned int slot, const int id)
Definition: being.cpp:2789
uint16_t getLook() const
Definition: being.h:922
ActorTypeT getType() const
Definition: being.h:116
void imitateOutfit(const Being *const player, const int sprite) const
#define fromInt(val, name)
Definition: intdefines.h:46
uint16_t ItemColor
Definition: itemcolor.h:30
@ SPRITE_HAIR_COLOR
Definition: sprite.h:35
@ SPRITE_WEAPON
Definition: sprite.h:31
@ SPRITE_FLOOR
Definition: sprite.h:40
@ SPRITE_HEAD_TOP
Definition: sprite.h:33
@ SPRITE_SHOES
Definition: sprite.h:38
@ SPRITE_SHIELD
Definition: sprite.h:37
@ SPRITE_HEAD_MID
Definition: sprite.h:34
@ SPRITE_EVOL2
Definition: sprite.h:42
@ SPRITE_BODY
Definition: sprite.h:39
@ SPRITE_CLOTHES_COLOR
Definition: sprite.h:36
@ SPRITE_ROBE
Definition: sprite.h:41
@ SPRITE_HEAD_BOTTOM
Definition: sprite.h:32

References CAST_U16, fromInt, Being::getLook(), Being::getType(), LocalPlayer::imitateOutfit(), localPlayer, ActorType::Player, Being::setHairColor(), Being::setHairStyle(), Being::setLook(), Being::setOtherTime(), Being::setSpriteId(), Being::setSubtype(), Being::setWeaponId(), SPRITE_BODY, SPRITE_CLOTHES_COLOR, SPRITE_EVOL2, SPRITE_FLOOR, ItemDbType::SPRITE_HAIR, SPRITE_HAIR_COLOR, SPRITE_HEAD_BOTTOM, SPRITE_HEAD_MID, SPRITE_HEAD_TOP, SPRITE_ROBE, SPRITE_SHIELD, SPRITE_SHOES, SPRITE_WEAPON, and UNIMPLEMENTEDPACKETFIELD.

◆ processBeingMove()

void TmwAthena::BeingRecv::processBeingMove ( Net::MessageIn msg)

Definition at line 918 of file beingrecv.cpp.

919 {
920  BLOCK_START("BeingRecv::processBeingVisibleOrMove")
921  if (actorManager == nullptr)
922  {
923  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
924  return;
925  }
926 
927  BeingId spawnId;
928 
929  // Information about a being in range
930  const BeingId id = msg.readBeingId("being id");
931  if (id == Ea::BeingRecv::mSpawnId)
932  spawnId = Ea::BeingRecv::mSpawnId;
933  else
934  spawnId = BeingId_zero;
935  Ea::BeingRecv::mSpawnId = BeingId_zero;
936  int16_t speed = msg.readInt16("speed");
937  const uint32_t opt1 = msg.readInt16("opt1");
938  const uint32_t opt2 = msg.readInt16("opt2");
939  const uint32_t option = msg.readInt16("option");
940  const int16_t job = msg.readInt16("class");
941  int disguiseId = 0;
942  if (id == localPlayer->getId() && job >= 1000)
943  disguiseId = job;
944 
945  Being *dstBeing = actorManager->findBeing(id);
946 
947  if ((dstBeing != nullptr) && dstBeing->getType() == ActorType::Monster
948  && !dstBeing->isAlive())
949  {
950  actorManager->destroy(dstBeing);
951  actorManager->erase(dstBeing);
952  dstBeing = nullptr;
953  }
954 
955  if (dstBeing == nullptr)
956  {
957  // Being with id >= 110000000 and job 0 are better
958  // known as ghosts, so don't create those.
959  if (job == 0 && toInt(id, int) >= 110000000)
960  {
961  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
962  return;
963  }
964 
965  if (actorManager->isBlocked(id) == true)
966  {
967  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
968  return;
969  }
970 
971  dstBeing = Ea::BeingRecv::createBeing(id, job);
972 
973  if (dstBeing == nullptr)
974  {
975  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
976  return;
977  }
978  }
979  else
980  {
981  if (dstBeing->getType() == ActorType::Npc)
982  {
983  actorManager->undelete(dstBeing);
985  }
986  }
987 
988  if (dstBeing->getType() == ActorType::Player)
989  dstBeing->setMoveTime();
990 
991  if (spawnId != BeingId_zero)
992  dstBeing->setAction(BeingAction::SPAWN, 0);
993 
994  // Prevent division by 0 when calculating frame
995  if (speed == 0)
996  speed = 150;
997 
998  const uint8_t hairStyle = msg.readUInt8("hair style");
999  const uint16_t look = msg.readUInt8("look");
1000  dstBeing->setSubtype(fromInt(job, BeingTypeId), look);
1001  if (dstBeing->getType() == ActorType::Monster && (localPlayer != nullptr))
1002  localPlayer->checkNewName(dstBeing);
1003  dstBeing->setWalkSpeed(speed);
1004  const uint16_t weapon = msg.readInt16("weapon");
1005  const uint16_t headBottom = msg.readInt16("head bottom");
1006 
1007  msg.readInt32("tick");
1008 
1009  const uint16_t shield = msg.readInt16("shield");
1010  const uint16_t headTop = msg.readInt16("head top");
1011  const uint16_t headMid = msg.readInt16("head mid");
1012  const ItemColor hairColor = fromInt(
1013  msg.readUInt8("hair color"), ItemColor);
1014  msg.readUInt8("unused");
1015  const uint16_t shoes = msg.readInt16("shoes / clothes color");
1016 
1017  uint16_t gloves;
1018  if (dstBeing->getType() == ActorType::Monster)
1019  {
1021  {
1022  const int hp = msg.readInt32("hp");
1023  const int maxHP = msg.readInt32("max hp");
1024  if ((hp != 0) && (maxHP != 0))
1025  {
1026  dstBeing->setMaxHP(maxHP);
1027  const int oldHP = dstBeing->getHP();
1028  if ((oldHP == 0) || oldHP > hp)
1029  dstBeing->setHP(hp);
1030  }
1031  }
1032  else
1033  {
1034  msg.readInt32("unused");
1035  msg.readInt32("unused");
1036  }
1037  gloves = 0;
1038  }
1039  else
1040  {
1041  gloves = msg.readInt16("gloves / head dir");
1042  msg.readInt32("guild");
1043  msg.readInt16("guild emblem");
1044  }
1045 
1046  dstBeing->setManner(msg.readInt16("manner"));
1047  const uint32_t opt3 = msg.readInt16("opt3");
1049  && dstBeing->getType() == ActorType::Monster)
1050  {
1051  const int attackRange = CAST_S32(
1052  msg.readUInt8("attack range (was karma)"));
1053  dstBeing->setAttackRange(attackRange);
1054  }
1055  else
1056  {
1057  dstBeing->setKarma(msg.readUInt8("karma"));
1058  }
1059  uint8_t gender = msg.readUInt8("gender");
1060 
1061  if ((disguiseId == 0) && dstBeing->getType() == ActorType::Player)
1062  {
1063  // reserving bits for future usage
1064  gender &= 3;
1065  dstBeing->setGender(Being::intToGender(gender));
1066  // Set these after the gender, as the sprites may be gender-specific
1067  if (hairStyle == 0)
1068  {
1069  dstBeing->updateSprite(SPRITE_HAIR_COLOR, 0, std::string());
1070  }
1071  else
1072  {
1073  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
1074  hairStyle * -1,
1075  ItemDB::get(-hairStyle).getDyeColorsString(hairColor));
1076  }
1077  dstBeing->setHairColor(hairColor);
1078  dstBeing->updateSprite(SPRITE_WEAPON, headBottom, std::string());
1079  dstBeing->updateSprite(SPRITE_HEAD_BOTTOM, headMid, std::string());
1080  dstBeing->updateSprite(SPRITE_CLOTHES_COLOR, headTop, std::string());
1081  dstBeing->updateSprite(SPRITE_HAIR, shoes, std::string());
1082  dstBeing->updateSprite(SPRITE_SHOES, gloves, std::string());
1083  dstBeing->updateSprite(SPRITE_BODY, weapon, std::string());
1084  dstBeing->setWeaponId(weapon);
1085  dstBeing->updateSprite(SPRITE_FLOOR, shield, std::string());
1086  }
1087  else if (dstBeing->getType() == ActorType::Npc
1089  {
1090  setServerGender(dstBeing, gender);
1091  }
1092 
1093  uint16_t srcX;
1094  uint16_t srcY;
1095  uint16_t dstX;
1096  uint16_t dstY;
1097  msg.readCoordinatePair(srcX, srcY, dstX, dstY, "move path");
1098  if (disguiseId == 0)
1099  {
1100  dstBeing->setAction(BeingAction::STAND, 0);
1101  dstBeing->setTileCoords(srcX, srcY);
1102  if (serverFeatures->haveMove3())
1103  dstBeing->setCachedDestination(dstX, dstY);
1104  else
1105  dstBeing->setDestination(dstX, dstY);
1106  }
1107 
1108  msg.readUInt8("unknown");
1109  msg.readUInt8("unknown");
1110  msg.readUInt8("unknown");
1111  msg.readUInt8("unknown");
1112  msg.readUInt8("unknown");
1113 
1114  dstBeing->setStatusEffectOpitons(option,
1115  opt1,
1116  opt2,
1117  opt3);
1118  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
1119 }
Net::BeingHandler * beingHandler
Definition: net.cpp:99
int BeingId
Definition: beingid.h:30
const BeingId BeingId_zero
Definition: beingid.h:30
#define CAST_S32
Definition: cast.h:30
void destroy(ActorSprite *const actor)
void undelete(const ActorSprite *const actor)
void erase(ActorSprite *const actor)
static GenderT intToGender(const uint8_t sex) A_CONST
Definition: being.h:941
void checkNewName(Being *const being)
virtual void requestNameById(const BeingId id) const =0
virtual bool haveNpcGender() const =0
virtual bool haveMove3() const =0
virtual bool haveMonsterAttackRange() const =0
virtual bool haveServerHp() const =0
#define toInt(val, name)
Definition: intdefines.h:47
Being * createBeing(const BeingId id, const int job)
Definition: beingrecv.cpp:507
BeingId mSpawnId
Definition: beingrecv.cpp:58
const ItemInfo & get(const int id)
Definition: itemdb.cpp:792
void setServerGender(Being *const being, const uint8_t gender)
Definition: beingrecv.cpp:1496
Net::ServerFeatures * serverFeatures
Definition: net.cpp:101

References actorManager, beingHandler, BeingId_zero, BLOCK_END, BLOCK_START, CAST_S32, LocalPlayer::checkNewName(), Ea::BeingRecv::createBeing(), ActorManager::destroy(), ActorManager::erase(), ActorManager::findBeing(), fromInt, ItemDB::get(), Being::getHP(), ActorSprite::getId(), Being::getType(), Net::ServerFeatures::haveMonsterAttackRange(), Net::ServerFeatures::haveMove3(), Net::ServerFeatures::haveNpcGender(), Net::ServerFeatures::haveServerHp(), Being::intToGender(), Being::isAlive(), ActorManager::isBlocked(), localPlayer, ActorType::Monster, Actions::msg(), Ea::BeingRecv::mSpawnId, ActorType::Npc, ActorType::Player, Net::BeingHandler::requestNameById(), serverFeatures, Being::setAction(), Being::setAttackRange(), Being::setCachedDestination(), Being::setDestination(), Being::setGender(), Being::setHairColor(), Being::setHP(), Being::setKarma(), Being::setManner(), Being::setMaxHP(), Being::setMoveTime(), setServerGender(), ActorSprite::setStatusEffectOpitons(), Being::setSubtype(), Being::setTileCoords(), Being::setWalkSpeed(), Being::setWeaponId(), BeingAction::SPAWN, SPRITE_BODY, SPRITE_CLOTHES_COLOR, SPRITE_FLOOR, ItemDbType::SPRITE_HAIR, SPRITE_HAIR_COLOR, SPRITE_HEAD_BOTTOM, SPRITE_SHOES, SPRITE_WEAPON, BeingAction::STAND, toInt, ActorManager::undelete(), and Being::updateSprite().

◆ processBeingMove2()

void TmwAthena::BeingRecv::processBeingMove2 ( Net::MessageIn msg)

Definition at line 1171 of file beingrecv.cpp.

1172 {
1173  BLOCK_START("BeingRecv::processBeingMove2")
1174  if (actorManager == nullptr)
1175  {
1176  BLOCK_END("BeingRecv::processBeingMove2")
1177  return;
1178  }
1179 
1180  /*
1181  * A simplified movement packet, used by the
1182  * later versions of eAthena for both mobs and
1183  * players
1184  */
1185  Being *const dstBeing = actorManager->findBeing(
1186  msg.readBeingId("being id"));
1187 
1188  /*
1189  * This packet doesn't have enough info to actually
1190  * create a new being, so if the being isn't found,
1191  * we'll just pretend the packet didn't happen
1192  */
1193 
1194  if (dstBeing == nullptr)
1195  {
1196  BLOCK_END("BeingRecv::processBeingMove2")
1197  return;
1198  }
1199 
1200  uint16_t srcX;
1201  uint16_t srcY;
1202  uint16_t dstX;
1203  uint16_t dstY;
1204  msg.readCoordinatePair(srcX, srcY, dstX, dstY, "move path");
1205  msg.readInt32("tick");
1206 
1207  dstBeing->setAction(BeingAction::STAND, 0);
1208  dstBeing->setTileCoords(srcX, srcY);
1209  dstBeing->setDestination(dstX, dstY);
1210  if (dstBeing->getType() == ActorType::Player)
1211  dstBeing->setMoveTime();
1212  BLOCK_END("BeingRecv::processBeingMove2")
1213 }
bool move(InputEvent &event)
Definition: commands.cpp:44
void processBeingMove2(Net::MessageIn &msg)
Definition: beingrecv.cpp:1189

References actorManager, BLOCK_END, BLOCK_START, ActorManager::findBeing(), Being::getType(), Actions::msg(), ActorType::Player, Being::setAction(), Being::setDestination(), Being::setMoveTime(), Being::setTileCoords(), and BeingAction::STAND.

◆ processBeingResurrect()

void TmwAthena::BeingRecv::processBeingResurrect ( Net::MessageIn msg)

Definition at line 1279 of file beingrecv.cpp.

1280 {
1281  BLOCK_START("BeingRecv::processBeingResurrect")
1282  if (actorManager == nullptr || localPlayer == nullptr)
1283  {
1284  BLOCK_END("BeingRecv::processBeingResurrect")
1285  return;
1286  }
1287 
1288  // A being changed mortality status
1289 
1290  const BeingId id = msg.readBeingId("being id");
1291  Being *const dstBeing = actorManager->findBeing(id);
1292  if (dstBeing == nullptr)
1293  {
1294  DEBUGLOGSTR("insible player?");
1295  msg.readInt16("flag?");
1296  BLOCK_END("BeingRecv::processBeingResurrect")
1297  return;
1298  }
1299 
1300  // If this is player's current target, clear it.
1301  if (dstBeing == localPlayer->getTarget())
1302  localPlayer->stopAttack(false);
1303  if (dstBeing == localPlayer &&
1304  deathNotice != nullptr)
1305  {
1307  deathNotice = nullptr;
1308  }
1309 
1310  if (msg.readInt16("flag?") == 1)
1311  dstBeing->setAction(BeingAction::STAND, 0);
1312  BLOCK_END("BeingRecv::processBeingResurrect")
1313 }
virtual void scheduleDelete()
Definition: window.cpp:831
Window * deathNotice
bool stopAttack(InputEvent &event)
Definition: actions.cpp:56

References actorManager, BLOCK_END, BLOCK_START, deathNotice, DEBUGLOGSTR, ActorManager::findBeing(), LocalPlayer::getTarget(), localPlayer, Actions::msg(), Window::scheduleDelete(), Being::setAction(), BeingAction::STAND, and LocalPlayer::stopAttack().

◆ processBeingSelfEffect()

void TmwAthena::BeingRecv::processBeingSelfEffect ( Net::MessageIn msg)

Definition at line 1353 of file beingrecv.cpp.

1354 {
1355  BLOCK_START("BeingRecv::processBeingSelfEffect")
1356  if ((effectManager == nullptr) || (actorManager == nullptr))
1357  {
1358  BLOCK_END("BeingRecv::processBeingSelfEffect")
1359  return;
1360  }
1361 
1362  const BeingId id = msg.readBeingId("being id");
1363  Being *const being = actorManager->findBeing(id);
1364  if (being == nullptr)
1365  {
1366  DEBUGLOGSTR("insible player?");
1367  msg.readInt32("effect type");
1368  BLOCK_END("BeingRecv::processBeingSelfEffect")
1369  return;
1370  }
1371 
1372  const int effectType = msg.readInt32("effect type");
1373 
1374  if (ParticleEngine::enabled)
1375  effectManager->trigger(effectType, being, 0);
1376 
1377  // +++ need dehard code effectType == 3
1378  if (effectType == 3 && being->getType() == ActorType::Player
1379  && (socialWindow != nullptr))
1380  { // reset received damage
1381  socialWindow->resetDamage(being->getName());
1382  }
1383  BLOCK_END("BeingRecv::processBeingSelfEffect")
1384 }
void resetDamage(const std::string &name)
EffectManager * effectManager
SocialWindow * socialWindow

References actorManager, BLOCK_END, BLOCK_START, DEBUGLOGSTR, effectManager, ParticleEngine::enabled, ActorManager::findBeing(), Being::getName(), Being::getType(), Actions::msg(), ActorType::Player, SocialWindow::resetDamage(), socialWindow, and EffectManager::trigger().

◆ processBeingSpawn()

void TmwAthena::BeingRecv::processBeingSpawn ( Net::MessageIn msg)

Definition at line 1121 of file beingrecv.cpp.

1122 {
1123  BLOCK_START("BeingRecv::processBeingSpawn")
1124  // skipping this packet
1125  Ea::BeingRecv::mSpawnId = msg.readBeingId("being id");
1126  msg.readInt16("speed");
1127  msg.readInt16("opt1");
1128  msg.readInt16("opt2");
1129  msg.readInt16("option");
1130  msg.readInt16("disguise");
1131  msg.skip(25, "unused");
1132  BLOCK_END("BeingRecv::processBeingSpawn")
1133 }
void processBeingSpawn(Net::MessageIn &msg)
Definition: beingrecv.cpp:803

References BLOCK_END, BLOCK_START, Actions::msg(), and Ea::BeingRecv::mSpawnId.

◆ processBeingStatusChange()

void TmwAthena::BeingRecv::processBeingStatusChange ( Net::MessageIn msg)

Definition at line 1146 of file beingrecv.cpp.

1147 {
1148  BLOCK_START("BeingRecv::processBeingStatusChange")
1149  if (actorManager == nullptr)
1150  {
1151  BLOCK_END("BeingRecv::processBeingStatusChange")
1152  return;
1153  }
1154 
1155  // Status change
1156  const uint16_t status = msg.readInt16("status");
1157  const BeingId id = msg.readBeingId("being id");
1158  const Enable flag = fromBool(
1159  msg.readUInt8("flag: 0: stop, 1: start"), Enable);
1160 
1161  Being *const dstBeing = actorManager->findBeing(id);
1162  if (dstBeing != nullptr)
1163  {
1164  // dont know on legacy servers is effect really started
1165  // or not. Because this always sending IsStart_true
1166  dstBeing->setStatusEffect(status, flag, IsStart_true);
1167  }
1168  BLOCK_END("BeingRecv::processBeingStatusChange")
1169 }
#define fromBool(val, name)
Definition: booldefines.h:49
bool Enable
Definition: enable.h:30
const bool IsStart_true
Definition: isstart.h:30

References actorManager, BLOCK_END, BLOCK_START, ActorManager::findBeing(), fromBool, IsStart_true, Actions::msg(), and ActorSprite::setStatusEffect().

◆ processBeingVisible()

void TmwAthena::BeingRecv::processBeingVisible ( Net::MessageIn msg)

Definition at line 702 of file beingrecv.cpp.

703 {
704  BLOCK_START("BeingRecv::processBeingVisibleOrMove")
705  if (actorManager == nullptr)
706  {
707  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
708  return;
709  }
710 
711  BeingId spawnId;
712 
713  // Information about a being in range
714  const BeingId id = msg.readBeingId("being id");
715  if (id == Ea::BeingRecv::mSpawnId)
716  spawnId = Ea::BeingRecv::mSpawnId;
717  else
718  spawnId = BeingId_zero;
719  Ea::BeingRecv::mSpawnId = BeingId_zero;
720  int16_t speed = msg.readInt16("speed");
721  const uint32_t opt1 = msg.readInt16("opt1");
722  const uint32_t opt2 = msg.readInt16("opt2");
723  const uint32_t option = msg.readInt16("option");
724  const int16_t job = msg.readInt16("class");
725  int disguiseId = 0;
726  if (id == localPlayer->getId() && job >= 1000)
727  disguiseId = job;
728 
729  Being *dstBeing = actorManager->findBeing(id);
730 
731  if ((dstBeing != nullptr) && dstBeing->getType() == ActorType::Monster
732  && !dstBeing->isAlive())
733  {
734  actorManager->destroy(dstBeing);
735  actorManager->erase(dstBeing);
736  dstBeing = nullptr;
737  }
738 
739  if (dstBeing == nullptr)
740  {
741  // Being with id >= 110000000 and job 0 are better
742  // known as ghosts, so don't create those.
743  if (job == 0 && toInt(id, int) >= 110000000)
744  {
745  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
746  return;
747  }
748 
749  if (actorManager->isBlocked(id) == true)
750  {
751  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
752  return;
753  }
754 
755  dstBeing = Ea::BeingRecv::createBeing(id, job);
756 
757  if (dstBeing == nullptr)
758  {
759  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
760  return;
761  }
762  }
763  else
764  {
765  if (dstBeing->getType() == ActorType::Npc)
766  {
767  actorManager->undelete(dstBeing);
769  }
770  }
771 
772  if (dstBeing->getType() == ActorType::Player)
773  dstBeing->setMoveTime();
774 
775  if (spawnId != BeingId_zero)
776  {
777  dstBeing->setAction(BeingAction::SPAWN, 0);
778  }
779  else
780  {
781  dstBeing->clearPath();
782  dstBeing->setActionTime(tick_time);
783  dstBeing->setAction(BeingAction::STAND, 0);
784  }
785 
786  // Prevent division by 0 when calculating frame
787  if (speed == 0)
788  speed = 150;
789 
790  const uint8_t hairStyle = msg.readUInt8("hair style");
791  const uint16_t look = msg.readUInt8("look");
792  dstBeing->setSubtype(fromInt(job, BeingTypeId), look);
793  if (dstBeing->getType() == ActorType::Monster && (localPlayer != nullptr))
794  localPlayer->checkNewName(dstBeing);
795  dstBeing->setWalkSpeed(speed);
796  const uint16_t weapon = msg.readInt16("weapon");
797  const uint16_t headBottom = msg.readInt16("head bottom");
798 
799  const uint16_t shield = msg.readInt16("shield");
800  const uint16_t headTop = msg.readInt16("head top");
801  const uint16_t headMid = msg.readInt16("head mid");
802  const ItemColor hairColor = fromInt(msg.readUInt8("hair color"),
803  ItemColor);
804  msg.readUInt8("unused");
805  const uint16_t shoes = msg.readInt16("shoes / clothes color");
806 
807  uint16_t gloves;
808  if (dstBeing->getType() == ActorType::Monster)
809  {
811  {
812  const int hp = msg.readInt32("hp");
813  const int maxHP = msg.readInt32("max hp");
814  if ((hp != 0) && (maxHP != 0))
815  {
816  dstBeing->setMaxHP(maxHP);
817  const int oldHP = dstBeing->getHP();
818  if ((oldHP == 0) || oldHP > hp)
819  dstBeing->setHP(hp);
820  }
821  }
822  else
823  {
824  msg.readInt32("unused");
825  msg.readInt32("unused");
826  }
827  gloves = 0;
828  }
829  else
830  {
831  gloves = msg.readInt16("gloves / head dir");
832  msg.readInt32("guild");
833  msg.readInt16("guild emblem");
834  }
835 
836  dstBeing->setManner(msg.readInt16("manner"));
837  const uint32_t opt3 = msg.readInt16("opt3");
839  && dstBeing->getType() == ActorType::Monster)
840  {
841  const int attackRange = CAST_S32(
842  msg.readUInt8("attack range (was karma)"));
843  dstBeing->setAttackRange(attackRange);
844  }
845  else
846  {
847  dstBeing->setKarma(msg.readUInt8("karma"));
848  }
849  uint8_t gender = msg.readUInt8("gender");
850 
851  if ((disguiseId == 0) && dstBeing->getType() == ActorType::Player)
852  {
853  // reserving bits for future usage
854  gender &= 3;
855  dstBeing->setGender(Being::intToGender(gender));
856  // Set these after the gender, as the sprites may be gender-specific
857  if (hairStyle == 0)
858  {
859  dstBeing->updateSprite(SPRITE_HAIR_COLOR, 0, std::string());
860  }
861  else
862  {
863  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
864  hairStyle * -1,
865  ItemDB::get(-hairStyle).getDyeColorsString(hairColor));
866  }
867  dstBeing->setHairColor(hairColor);
868  dstBeing->updateSprite(SPRITE_WEAPON, headBottom, std::string());
869  dstBeing->updateSprite(SPRITE_HEAD_BOTTOM, headMid, std::string());
870  dstBeing->updateSprite(SPRITE_CLOTHES_COLOR, headTop, std::string());
871  dstBeing->updateSprite(SPRITE_HAIR, shoes, std::string());
872  dstBeing->updateSprite(SPRITE_SHOES, gloves, std::string());
873  dstBeing->updateSprite(SPRITE_BODY, weapon, std::string());
874  dstBeing->setWeaponId(weapon);
875  dstBeing->updateSprite(SPRITE_FLOOR, shield, std::string());
876  }
877  else if (dstBeing->getType() == ActorType::Npc
879  {
880  setServerGender(dstBeing, gender);
881  }
882 
883  uint8_t dir;
884  uint16_t x;
885  uint16_t y;
886  msg.readCoordinates(x, y, dir, "position");
887  dstBeing->setTileCoords(x, y);
888 
889  if (job == 45 && (socialWindow != nullptr) && (outfitWindow != nullptr))
890  {
891  const int num = socialWindow->getPortalIndex(x, y);
892  if (num >= 0)
893  {
894  dstBeing->setName(KeyboardConfig::getKeyShortString(
895  OutfitWindow::keyName(num)));
896  }
897  else
898  {
899  dstBeing->setName("");
900  }
901  }
902 
903  dstBeing->setDirection(dir);
904 
905  msg.readUInt8("unknown");
906  msg.readUInt8("unknown");
907  msg.readUInt8("unknown");
908  msg.readUInt8("unknown");
909  msg.readUInt8("unknown");
910 
911  dstBeing->setStatusEffectOpitons(option,
912  opt1,
913  opt2,
914  opt3);
915  BLOCK_END("BeingRecv::processBeingVisibleOrMove")
916 }
static std::string getKeyShortString(const std::string &key)
static std::string keyName(const int number)
int getPortalIndex(const int x, const int y)
volatile int tick_time
Definition: timer.cpp:53
OutfitWindow * outfitWindow

References actorManager, beingHandler, BeingId_zero, BLOCK_END, BLOCK_START, CAST_S32, LocalPlayer::checkNewName(), Being::clearPath(), Ea::BeingRecv::createBeing(), ActorManager::destroy(), ActorManager::erase(), ActorManager::findBeing(), fromInt, ItemDB::get(), Being::getHP(), ActorSprite::getId(), KeyboardConfig::getKeyShortString(), SocialWindow::getPortalIndex(), Being::getType(), Net::ServerFeatures::haveMonsterAttackRange(), Net::ServerFeatures::haveNpcGender(), Net::ServerFeatures::haveServerHp(), Being::intToGender(), Being::isAlive(), ActorManager::isBlocked(), OutfitWindow::keyName(), localPlayer, ActorType::Monster, Actions::msg(), Ea::BeingRecv::mSpawnId, ActorType::Npc, outfitWindow, ActorType::Player, Net::BeingHandler::requestNameById(), serverFeatures, Being::setAction(), Being::setActionTime(), Being::setAttackRange(), Being::setDirection(), Being::setGender(), Being::setHairColor(), Being::setHP(), Being::setKarma(), Being::setManner(), Being::setMaxHP(), Being::setMoveTime(), Being::setName(), setServerGender(), ActorSprite::setStatusEffectOpitons(), Being::setSubtype(), Being::setTileCoords(), Being::setWalkSpeed(), Being::setWeaponId(), socialWindow, BeingAction::SPAWN, SPRITE_BODY, SPRITE_CLOTHES_COLOR, SPRITE_FLOOR, ItemDbType::SPRITE_HAIR, SPRITE_HAIR_COLOR, SPRITE_HEAD_BOTTOM, SPRITE_SHOES, SPRITE_WEAPON, BeingAction::STAND, tick_time, toInt, ActorManager::undelete(), Being::updateSprite(), x, and y.

◆ processIpResponse()

void TmwAthena::BeingRecv::processIpResponse ( Net::MessageIn msg)

Definition at line 1391 of file beingrecv.cpp.

1392 {
1393  BLOCK_START("BeingRecv::processIpResponse")
1394  if (actorManager == nullptr)
1395  {
1396  BLOCK_END("BeingRecv::processIpResponse")
1397  return;
1398  }
1399 
1400  Being *const dstBeing = actorManager->findBeing(
1401  msg.readBeingId("being id"));
1402  if (dstBeing != nullptr)
1403  {
1404  const std::string ip = ipToString(msg.readInt32("ip address"));
1405  dstBeing->setIp(ip);
1406  }
1407  else
1408  {
1409  msg.readInt32("ip address");
1410  DEBUGLOGSTR("invisible player?");
1411  }
1412 
1413  BLOCK_END("BeingRecv::processIpResponse")
1414 }
const char * ipToString(const uint32_t address)
Definition: stringutils.cpp:86

References actorManager, BLOCK_END, BLOCK_START, DEBUGLOGSTR, ActorManager::findBeing(), ipToString(), Actions::msg(), and Being::setIp().

◆ processPlayerGuilPartyInfo()

void TmwAthena::BeingRecv::processPlayerGuilPartyInfo ( Net::MessageIn msg)

Definition at line 1315 of file beingrecv.cpp.

1316 {
1317  BLOCK_START("BeingRecv::processPlayerGuilPartyInfo")
1318  if (actorManager == nullptr)
1319  {
1320  BLOCK_END("BeingRecv::processPlayerGuilPartyInfo")
1321  return;
1322  }
1323 
1324  Being *const dstBeing = actorManager->findBeing(
1325  msg.readBeingId("being id"));
1326 
1327  if (dstBeing != nullptr)
1328  {
1329  dstBeing->setPartyName(msg.readString(24, "party name"));
1330  if ((guildManager == nullptr) || !GuildManager::getEnableGuildBot())
1331  {
1332  dstBeing->setGuildName(msg.readString(24, "guild name"));
1333  dstBeing->setGuildPos(msg.readString(24, "guild pos"));
1334  }
1335  else
1336  {
1337  msg.readString(24, "guild name");
1338  msg.readString(24, "guild pos");
1339  }
1340  dstBeing->addToCache();
1341  msg.readString(24, "?");
1342  }
1343  else
1344  {
1345  msg.readString(24, "party name");
1346  msg.readString(24, "guild name");
1347  msg.readString(24, "guild pos");
1348  msg.readString(24, "?");
1349  }
1350  BLOCK_END("BeingRecv::processPlayerGuilPartyInfo")
1351 }
static bool getEnableGuildBot()
Definition: guildmanager.h:56
GuildManager * guildManager

References actorManager, Being::addToCache(), BLOCK_END, BLOCK_START, ActorManager::findBeing(), GuildManager::getEnableGuildBot(), guildManager, Actions::msg(), Being::setGuildName(), Being::setGuildPos(), and Being::setPartyName().

◆ processPlayerMove()

void TmwAthena::BeingRecv::processPlayerMove ( Net::MessageIn msg)

Definition at line 528 of file beingrecv.cpp.

529 {
530  BLOCK_START("BeingRecv::processPlayerMoveUpdate")
531  if ((actorManager == nullptr) || (localPlayer == nullptr))
532  {
533  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
534  return;
535  }
536 
537  // An update about a player, potentially including movement.
538  const BeingId id = msg.readBeingId("account id");
539  const int16_t speed = msg.readInt16("speed");
540  const uint32_t opt1 = msg.readInt16("opt1");
541  const uint32_t opt2 = msg.readInt16("opt2");
542  const uint32_t option = msg.readInt16("option");
543  const int16_t job = msg.readInt16("job");
544  int disguiseId = 0;
545  if (toInt(id, int) < 110000000 && job >= 1000)
546  disguiseId = job;
547 
548  Being *dstBeing = actorManager->findBeing(id);
549  if (dstBeing == nullptr)
550  {
551  if (actorManager->isBlocked(id) == true)
552  {
553  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
554  return;
555  }
556 
557  dstBeing = Ea::BeingRecv::createBeing(id, job);
558 
559  if (dstBeing == nullptr)
560  {
561  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
562  return;
563  }
564  }
565  else if (disguiseId != 0)
566  {
567  actorManager->undelete(dstBeing);
569  }
570 
571  const uint8_t dir = dstBeing->getDirectionDelayed();
572  if (dir != 0U)
573  {
574  if (dir != dstBeing->getDirection())
575  dstBeing->setDirection(dir);
576  }
577 
578  if (Party *const party = localPlayer->getParty())
579  {
580  if (party->isMember(id))
581  dstBeing->setParty(party);
582  }
583 
584  dstBeing->setWalkSpeed(speed);
585 
586  const uint8_t hairStyle = msg.readUInt8("hair style");
587  const uint16_t look = msg.readUInt8("look");
588  dstBeing->setSubtype(fromInt(job, BeingTypeId), look);
589  const uint16_t weapon = msg.readInt16("weapon");
590  const uint16_t shield = msg.readInt16("shield");
591  const uint16_t headBottom = msg.readInt16("head bottom");
592 
593  msg.readInt32("tick");
594 
595  const uint16_t headTop = msg.readInt16("head top");
596  const uint16_t headMid = msg.readInt16("head mid");
597  const ItemColor hairColor = fromInt(
598  msg.readUInt8("hair color"), ItemColor);
599  msg.readUInt8("unused");
600  msg.readInt32("unused");
601 
602  const int guild = msg.readInt32("guild");
603 
604  if ((guildManager == nullptr) || !GuildManager::getEnableGuildBot())
605  {
606  if (guild == 0)
607  dstBeing->clearGuilds();
608  else
609  dstBeing->setGuild(Guild::getGuild(CAST_S16(guild)));
610  }
611 
612  msg.readInt16("emblem");
613  dstBeing->setManner(msg.readInt16("manner"));
614  const uint32_t opt3 = msg.readInt16("opt3");
615  dstBeing->setKarma(msg.readUInt8("karma"));
616  // reserving bit for future usage
617  dstBeing->setGender(Being::intToGender(
618  CAST_U8(msg.readUInt8("gender") & 3)));
619 
620  if (disguiseId == 0)
621  {
622  // Set these after the gender, as the sprites may be gender-specific
623  dstBeing->updateSprite(SPRITE_BODY,
624  weapon,
625  std::string());
626  dstBeing->setWeaponId(weapon);
627  dstBeing->updateSprite(SPRITE_FLOOR, shield, std::string());
628  dstBeing->updateSprite(SPRITE_WEAPON, headBottom, std::string());
629  dstBeing->updateSprite(SPRITE_HEAD_BOTTOM, headMid, std::string());
630  dstBeing->updateSprite(SPRITE_CLOTHES_COLOR, headTop, std::string());
631  if (hairStyle == 0)
632  {
633  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
634  0,
635  std::string());
636  }
637  else
638  {
639  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
640  hairStyle * -1,
641  ItemDB::get(-hairStyle).getDyeColorsString(hairColor));
642  }
643  dstBeing->setHairColor(hairColor);
644  }
645  localPlayer->imitateOutfit(dstBeing, -1);
646 
647  uint16_t srcX;
648  uint16_t srcY;
649  uint16_t dstX;
650  uint16_t dstY;
651  msg.readCoordinatePair(srcX, srcY, dstX, dstY, "moving path");
652 
653  localPlayer->followMoveTo(dstBeing, srcX, srcY, dstX, dstY);
654 
655  dstBeing->setTileCoords(srcX, srcY);
656  dstBeing->setDestination(dstX, dstY);
657 
658  // because server don't send direction in move packet,
659  // we fixing it
660 
661  if (srcX != dstX || srcY != dstY)
662  {
663  const int d = dstBeing->calcDirection(dstX, dstY);
664 
665  if ((d != 0) && dstBeing->getDirection() != d)
666  dstBeing->setDirectionDelayed(CAST_U8(d));
667  }
668 
671  if (localPlayer->getDirection() != dstBeing->getDirection())
672  {
673  localPlayer->imitateDirection(dstBeing,
674  dstBeing->getDirection());
675  }
676 
677  const uint16_t gmstatus = msg.readInt16("gm status");
678 
679  setGm(dstBeing, gmstatus);
680 
681  msg.readUInt8("unused");
682 
683  const int level = CAST_S32(msg.readUInt8("level"));
684  if (level != 0)
685  dstBeing->setLevel(level);
686 
687  msg.readUInt8("unused");
688 
689  if (dstBeing->getType() != ActorType::Player)
690  dstBeing->setActionTime(tick_time);
691 
692  dstBeing->setStatusEffectOpitons(option,
693  opt1,
694  opt2,
695  opt3);
696 
697  if (dstBeing->getType() == ActorType::Player)
698  dstBeing->setMoveTime();
699  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
700 }
bool isBlocked(const BeingId id) const
Party * getParty() const
Definition: being.h:330
uint8_t getDirection() const
Definition: being.h:494
static Guild * getGuild(const int16_t id)
Definition: guild.cpp:374
void followMoveTo(const Being *const being, const int x, const int y)
Definition: party.h:63
uint32_t guild
uint32_t party
static void setGm(Being *const dstBeing, const uint16_t gmstatus)
Definition: beingrecv.cpp:64

References actorManager, beingHandler, BLOCK_END, BLOCK_START, Being::calcDirection(), CAST_S16, CAST_S32, CAST_U8, Being::clearGuilds(), Ea::BeingRecv::createBeing(), ActorManager::findBeing(), LocalPlayer::followMoveTo(), fromInt, ItemDB::get(), Being::getCurrentAction(), Being::getDirection(), Being::getDirectionDelayed(), GuildManager::getEnableGuildBot(), Guild::getGuild(), Being::getParty(), Being::getType(), guild, guildManager, LocalPlayer::imitateAction(), LocalPlayer::imitateDirection(), LocalPlayer::imitateOutfit(), Being::intToGender(), ActorManager::isBlocked(), localPlayer, Actions::msg(), party, ActorType::Player, Net::BeingHandler::requestNameById(), Being::setActionTime(), Being::setDestination(), Being::setDirection(), Being::setDirectionDelayed(), Being::setGender(), TmwAthena::setGm(), Being::setGuild(), Being::setHairColor(), Being::setKarma(), Being::setLevel(), Being::setManner(), Being::setMoveTime(), Being::setParty(), ActorSprite::setStatusEffectOpitons(), Being::setSubtype(), Being::setTileCoords(), Being::setWalkSpeed(), Being::setWeaponId(), SPRITE_BODY, SPRITE_CLOTHES_COLOR, SPRITE_FLOOR, SPRITE_HAIR_COLOR, SPRITE_HEAD_BOTTOM, SPRITE_WEAPON, BeingAction::STAND, tick_time, toInt, ActorManager::undelete(), and Being::updateSprite().

◆ processPlayerStatusChange()

void TmwAthena::BeingRecv::processPlayerStatusChange ( Net::MessageIn msg)

Definition at line 1246 of file beingrecv.cpp.

1247 {
1248  BLOCK_START("BeingRecv::processPlayerStop")
1249  if (actorManager == nullptr)
1250  {
1251  BLOCK_END("BeingRecv::processPlayerStop")
1252  return;
1253  }
1254 
1255  // Change in players' flags
1256  const BeingId id = msg.readBeingId("account id");
1257  Being *const dstBeing = actorManager->findBeing(id);
1258  if (dstBeing == nullptr)
1259  {
1260  DEBUGLOGSTR("invisible player?");
1261  msg.readInt16("stun mode");
1262  msg.readInt16("status effect");
1263  msg.readInt16("opt?");
1264  msg.readUInt8("Unused?");
1265  return;
1266  }
1267 
1268  const uint32_t opt1 = msg.readInt16("opt1");
1269  const uint32_t opt2 = msg.readInt16("opt2");
1270  const uint32_t option = msg.readInt16("option");
1271  msg.readUInt8("Unused?");
1272 
1273  dstBeing->setStatusEffectOpitons(option,
1274  opt1,
1275  opt2);
1276  BLOCK_END("BeingRecv::processPlayerStop")
1277 }

References actorManager, BLOCK_END, BLOCK_START, DEBUGLOGSTR, ActorManager::findBeing(), Actions::msg(), and ActorSprite::setStatusEffectOpitons().

◆ processPlayerUpdate1()

void TmwAthena::BeingRecv::processPlayerUpdate1 ( Net::MessageIn msg)

Definition at line 240 of file beingrecv.cpp.

241 {
242  BLOCK_START("BeingRecv::processPlayerMoveUpdate")
243  if ((actorManager == nullptr) || (localPlayer == nullptr))
244  {
245  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
246  return;
247  }
248 
249  // An update about a player, potentially including movement.
250  const BeingId id = msg.readBeingId("account id");
251  const int16_t speed = msg.readInt16("speed");
252  const uint32_t opt1 = msg.readInt16("opt1");
253  const uint32_t opt2 = msg.readInt16("opt2");
254  const uint32_t option = msg.readInt16("option");
255  const int16_t job = msg.readInt16("job");
256  int disguiseId = 0;
257  if (toInt(id, int) < 110000000 && job >= 1000)
258  disguiseId = job;
259 
260  Being *dstBeing = actorManager->findBeing(id);
261  if (dstBeing == nullptr)
262  {
263  if (actorManager->isBlocked(id) == true)
264  {
265  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
266  return;
267  }
268 
269  dstBeing = Ea::BeingRecv::createBeing(id, job);
270 
271  if (dstBeing == nullptr)
272  {
273  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
274  return;
275  }
276  }
277  else if (disguiseId != 0)
278  {
279  actorManager->undelete(dstBeing);
281  }
282 
283  uint8_t dir = dstBeing->getDirectionDelayed();
284  if (dir != 0U)
285  {
286  if (dir != dstBeing->getDirection())
287  dstBeing->setDirection(dir);
288  }
289 
290  if (Party *const party = localPlayer->getParty())
291  {
292  if (party->isMember(id))
293  dstBeing->setParty(party);
294  }
295 
296  dstBeing->setWalkSpeed(speed);
297 
298  const uint8_t hairStyle = msg.readUInt8("hair style");
299  const uint16_t look = msg.readUInt8("look");
300  dstBeing->setSubtype(fromInt(job, BeingTypeId), look);
301  const uint16_t weapon = msg.readInt16("weapon");
302  const uint16_t shield = msg.readInt16("shield");
303  const uint16_t headBottom = msg.readInt16("head bottom");
304 
305  const uint16_t headTop = msg.readInt16("head top");
306  const uint16_t headMid = msg.readInt16("head mid");
307  const ItemColor hairColor = fromInt(
308  msg.readUInt8("hair color"), ItemColor);
309  msg.readUInt8("unused");
310  msg.readInt32("unused");
311 
312  const int guild = msg.readInt32("guild");
313 
314  if ((guildManager == nullptr) || !GuildManager::getEnableGuildBot())
315  {
316  if (guild == 0)
317  dstBeing->clearGuilds();
318  else
319  dstBeing->setGuild(Guild::getGuild(CAST_S16(guild)));
320  }
321 
322  msg.readInt16("emblem");
323  dstBeing->setManner(msg.readInt16("manner"));
324  const uint32_t opt3 = msg.readInt16("opt3");
325  dstBeing->setKarma(msg.readUInt8("karma"));
326  // reserving bit for future usage
327  dstBeing->setGender(Being::intToGender(
328  CAST_U8(msg.readUInt8("gender") & 3)));
329 
330  if (disguiseId == 0)
331  {
332  // Set these after the gender, as the sprites may be gender-specific
333  dstBeing->updateSprite(SPRITE_BODY,
334  weapon,
335  std::string());
336  dstBeing->setWeaponId(weapon);
337  dstBeing->updateSprite(SPRITE_FLOOR, shield, std::string());
338  dstBeing->updateSprite(SPRITE_WEAPON, headBottom, std::string());
339  dstBeing->updateSprite(SPRITE_HEAD_BOTTOM, headMid, std::string());
340  dstBeing->updateSprite(SPRITE_CLOTHES_COLOR, headTop, std::string());
341  if (hairStyle == 0)
342  {
343  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
344  0,
345  std::string());
346  }
347  else
348  {
349  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
350  hairStyle * -1,
351  ItemDB::get(-hairStyle).getDyeColorsString(hairColor));
352  }
353  dstBeing->setHairColor(hairColor);
354  }
355  localPlayer->imitateOutfit(dstBeing, -1);
356 
357  uint16_t x;
358  uint16_t y;
359  msg.readCoordinates(x, y, dir, "position");
360  dstBeing->setTileCoords(x, y);
361  dstBeing->setDirection(dir);
362 
363  localPlayer->imitateDirection(dstBeing, dir);
364 
365  const uint16_t gmstatus = msg.readInt16("gm status");
366 
367  setGm(dstBeing, gmstatus);
368 
369  applyPlayerAction(msg, dstBeing, msg.readUInt8("action type"));
370  const int level = CAST_S32(msg.readUInt8("level"));
371  if (level != 0)
372  dstBeing->setLevel(level);
373 
374  msg.readUInt8("unused");
375 
376  dstBeing->setActionTime(tick_time);
377 
378  dstBeing->setStatusEffectOpitons(option,
379  opt1,
380  opt2,
381  opt3);
382 
383  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
384 }
void applyPlayerAction(Net::MessageIn &msg, Being *const being, const uint8_t type)
Definition: beingrecv.cpp:2397

References actorManager, EAthena::BeingRecv::applyPlayerAction(), beingHandler, BLOCK_END, BLOCK_START, CAST_S16, CAST_S32, CAST_U8, Being::clearGuilds(), Ea::BeingRecv::createBeing(), ActorManager::findBeing(), fromInt, ItemDB::get(), Being::getDirection(), Being::getDirectionDelayed(), GuildManager::getEnableGuildBot(), Guild::getGuild(), Being::getParty(), guild, guildManager, LocalPlayer::imitateDirection(), LocalPlayer::imitateOutfit(), Being::intToGender(), ActorManager::isBlocked(), localPlayer, Actions::msg(), party, Net::BeingHandler::requestNameById(), Being::setActionTime(), Being::setDirection(), Being::setGender(), TmwAthena::setGm(), Being::setGuild(), Being::setHairColor(), Being::setKarma(), Being::setLevel(), Being::setManner(), Being::setParty(), ActorSprite::setStatusEffectOpitons(), Being::setSubtype(), Being::setTileCoords(), Being::setWalkSpeed(), Being::setWeaponId(), SPRITE_BODY, SPRITE_CLOTHES_COLOR, SPRITE_FLOOR, SPRITE_HAIR_COLOR, SPRITE_HEAD_BOTTOM, SPRITE_WEAPON, tick_time, toInt, ActorManager::undelete(), Being::updateSprite(), x, and y.

◆ processPlayerUpdate2()

void TmwAthena::BeingRecv::processPlayerUpdate2 ( Net::MessageIn msg)

Definition at line 386 of file beingrecv.cpp.

387 {
388  BLOCK_START("BeingRecv::processPlayerMoveUpdate")
389  if ((actorManager == nullptr) || (localPlayer == nullptr))
390  {
391  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
392  return;
393  }
394 
395  // An update about a player, potentially including movement.
396  const BeingId id = msg.readBeingId("account id");
397  const int16_t speed = msg.readInt16("speed");
398  const uint32_t opt1 = msg.readInt16("opt1");
399  const uint32_t opt2 = msg.readInt16("opt2");
400  const uint32_t option = msg.readInt16("option");
401  const int16_t job = msg.readInt16("job");
402  int disguiseId = 0;
403  if (toInt(id, int) < 110000000 && job >= 1000)
404  disguiseId = job;
405 
406  Being *dstBeing = actorManager->findBeing(id);
407  if (dstBeing == nullptr)
408  {
409  if (actorManager->isBlocked(id) == true)
410  {
411  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
412  return;
413  }
414 
415  dstBeing = Ea::BeingRecv::createBeing(id, job);
416 
417  if (dstBeing == nullptr)
418  {
419  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
420  return;
421  }
422  }
423  else if (disguiseId != 0)
424  {
425  actorManager->undelete(dstBeing);
427  }
428 
429  uint8_t dir = dstBeing->getDirectionDelayed();
430  if (dir != 0U)
431  {
432  if (dir != dstBeing->getDirection())
433  dstBeing->setDirection(dir);
434  }
435 
436  if (Party *const party = localPlayer->getParty())
437  {
438  if (party->isMember(id))
439  dstBeing->setParty(party);
440  }
441 
442  dstBeing->setWalkSpeed(speed);
443 
444  const uint8_t hairStyle = msg.readUInt8("hair style");
445  const uint16_t look = msg.readUInt8("look");
446  dstBeing->setSubtype(fromInt(job, BeingTypeId), look);
447  const uint16_t weapon = msg.readInt16("weapon");
448  const uint16_t shield = msg.readInt16("shield");
449  const uint16_t headBottom = msg.readInt16("head bottom");
450  const uint16_t headTop = msg.readInt16("head top");
451  const uint16_t headMid = msg.readInt16("head mid");
452  const ItemColor hairColor = fromInt(
453  msg.readUInt8("hair color"), ItemColor);
454  msg.readUInt8("unused");
455  msg.readInt32("unused");
456 
457  const int guild = msg.readInt32("guild");
458 
459  if ((guildManager == nullptr) || !GuildManager::getEnableGuildBot())
460  {
461  if (guild == 0)
462  dstBeing->clearGuilds();
463  else
464  dstBeing->setGuild(Guild::getGuild(CAST_S16(guild)));
465  }
466 
467  msg.readInt16("emblem");
468  dstBeing->setManner(msg.readInt16("manner"));
469  const uint32_t opt3 = msg.readInt16("opt3");
470  dstBeing->setKarma(msg.readUInt8("karma"));
471  // reserving bit for future usage
472  dstBeing->setGender(Being::intToGender(
473  CAST_U8(msg.readUInt8("gender") & 3)));
474 
475  if (disguiseId == 0)
476  {
477  // Set these after the gender, as the sprites may be gender-specific
478  dstBeing->updateSprite(SPRITE_BODY,
479  weapon,
480  std::string());
481  dstBeing->setWeaponId(weapon);
482  dstBeing->updateSprite(SPRITE_FLOOR, shield, std::string());
483  dstBeing->updateSprite(SPRITE_WEAPON, headBottom, std::string());
484  dstBeing->updateSprite(SPRITE_HEAD_BOTTOM, headMid, std::string());
485  dstBeing->updateSprite(SPRITE_CLOTHES_COLOR, headTop, std::string());
486  if (hairStyle == 0)
487  {
488  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
489  0,
490  std::string());
491  }
492  else
493  {
494  dstBeing->updateSprite(SPRITE_HAIR_COLOR,
495  hairStyle * -1,
496  ItemDB::get(-hairStyle).getDyeColorsString(hairColor));
497  }
498  dstBeing->setHairColor(hairColor);
499  }
500  localPlayer->imitateOutfit(dstBeing, -1);
501 
502  uint16_t x;
503  uint16_t y;
504  msg.readCoordinates(x, y, dir, "position");
505  dstBeing->setTileCoords(x, y);
506  dstBeing->setDirection(dir);
507 
508  localPlayer->imitateDirection(dstBeing, dir);
509 
510  const uint16_t gmstatus = msg.readInt16("gm status");
511 
512  setGm(dstBeing, gmstatus);
513 
514  applyPlayerAction(msg, dstBeing, msg.readUInt8("action type"));
515  const int level = CAST_S32(msg.readUInt8("level"));
516  if (level != 0)
517  dstBeing->setLevel(level);
518 
519  dstBeing->setActionTime(tick_time);
520  dstBeing->setStatusEffectOpitons(option,
521  opt1,
522  opt2,
523  opt3);
524 
525  BLOCK_END("BeingRecv::processPlayerMoveUpdate")
526 }

References actorManager, EAthena::BeingRecv::applyPlayerAction(), beingHandler, BLOCK_END, BLOCK_START, CAST_S16, CAST_S32, CAST_U8, Being::clearGuilds(), Ea::BeingRecv::createBeing(), ActorManager::findBeing(), fromInt, ItemDB::get(), Being::getDirection(), Being::getDirectionDelayed(), GuildManager::getEnableGuildBot(), Guild::getGuild(), Being::getParty(), guild, guildManager, LocalPlayer::imitateDirection(), LocalPlayer::imitateOutfit(), Being::intToGender(), ActorManager::isBlocked(), localPlayer, Actions::msg(), party, Net::BeingHandler::requestNameById(), Being::setActionTime(), Being::setDirection(), Being::setGender(), TmwAthena::setGm(), Being::setGuild(), Being::setHairColor(), Being::setKarma(), Being::setLevel(), Being::setManner(), Being::setParty(), ActorSprite::setStatusEffectOpitons(), Being::setSubtype(), Being::setTileCoords(), Being::setWalkSpeed(), Being::setWeaponId(), SPRITE_BODY, SPRITE_CLOTHES_COLOR, SPRITE_FLOOR, SPRITE_HAIR_COLOR, SPRITE_HEAD_BOTTOM, SPRITE_WEAPON, tick_time, toInt, ActorManager::undelete(), Being::updateSprite(), x, and y.

◆ processPvpSet()

void TmwAthena::BeingRecv::processPvpSet ( Net::MessageIn msg)

Definition at line 1416 of file beingrecv.cpp.

1417 {
1418  BLOCK_START("BeingRecv::processPvpSet")
1419  const BeingId id = msg.readBeingId("being id");
1420  const int rank = msg.readInt32("rank");
1421  int teamId = 0;
1422  teamId = msg.readInt32("team");
1423  if (actorManager != nullptr)
1424  {
1425  Being *const dstBeing = actorManager->findBeing(id);
1426  if (dstBeing != nullptr)
1427  {
1428  dstBeing->setPvpRank(rank);
1429  dstBeing->setTeamId(CAST_U16(teamId));
1430  dstBeing->addToCache();
1431  }
1432  }
1433  BLOCK_END("BeingRecv::processPvpSet")
1434 }
Being * findBeing(const BeingId id) const
void setPvpRank(const unsigned int rank)
Definition: being.h:752
void setTeamId(const uint16_t teamId)
Definition: being.cpp:5187
void addToCache() const
Definition: being.cpp:3513

References actorManager, Being::addToCache(), BLOCK_END, BLOCK_START, CAST_U16, ActorManager::findBeing(), Actions::msg(), Being::setPvpRank(), and Being::setTeamId().

◆ processSkillCastCancel()

void TmwAthena::BeingRecv::processSkillCastCancel ( Net::MessageIn msg)

Definition at line 1386 of file beingrecv.cpp.

1387 {
1388  msg.readInt32("skill id");
1389 }

References Actions::msg().

◆ processSkillCasting()

void TmwAthena::BeingRecv::processSkillCasting ( Net::MessageIn msg)

Definition at line 1135 of file beingrecv.cpp.

1136 {
1137  msg.readInt32("src id");
1138  msg.readInt32("dst id");
1139  msg.readInt16("dst x");
1140  msg.readInt16("dst y");
1141  msg.readInt16("skill num");
1142  msg.readInt32("skill get p1");
1143  msg.readInt32("cast time");
1144 }

References Actions::msg().

◆ processSkillDamage()

void TmwAthena::BeingRecv::processSkillDamage ( Net::MessageIn msg)

Definition at line 1468 of file beingrecv.cpp.

1469 {
1470  BLOCK_START("BeingRecv::processSkillDamage")
1471  if (actorManager == nullptr)
1472  {
1473  BLOCK_END("BeingRecv::processSkillDamage")
1474  return;
1475  }
1476 
1477  const int id = msg.readInt16("skill id");
1478  Being *const srcBeing = actorManager->findBeing(
1479  msg.readBeingId("src being id"));
1480  Being *const dstBeing = actorManager->findBeing(
1481  msg.readBeingId("dst being id"));
1482  msg.readInt32("tick");
1483  msg.readInt32("src speed");
1484  msg.readInt32("dst speed");
1485  const int param1 = msg.readInt32("damage");
1486  const int level = msg.readInt16("skill level");
1487  msg.readInt16("div");
1488  msg.readUInt8("skill hit/type?");
1489  if (srcBeing != nullptr)
1490  srcBeing->handleSkill(dstBeing, param1, id, level);
1491  if (dstBeing != nullptr)
1492  dstBeing->takeDamage(srcBeing, param1, AttackType::SKILL, id, level);
1493  BLOCK_END("BeingRecv::processSkillDamage")
1494 }
bool skill(InputEvent &event)
Definition: commands.cpp:97
void processSkillDamage(Net::MessageIn &msg)
Definition: beingrecv.cpp:2350

References actorManager, BLOCK_END, BLOCK_START, ActorManager::findBeing(), Being::handleSkill(), Actions::msg(), AttackType::SKILL, and Being::takeDamage().

◆ setServerGender()

void TmwAthena::BeingRecv::setServerGender ( Being *const  being,
const uint8_t  gender 
)

Definition at line 1496 of file beingrecv.cpp.

1498 {
1499  if (being == nullptr)
1500  return;
1501  switch (gender)
1502  {
1503  case 2:
1504  being->setGender(Gender::FEMALE);
1505  break;
1506  case 3:
1507  being->setGender(Gender::MALE);
1508  break;
1509  default:
1511  break;
1512  }
1513 }
virtual void setGender(const GenderT gender)
Definition: being.cpp:3581
@ UNSPECIFIED
Definition: gender.h:33
@ MALE
Definition: gender.h:31
@ FEMALE
Definition: gender.h:32

References Gender::FEMALE, Gender::MALE, Being::setGender(), and Gender::UNSPECIFIED.

Referenced by processBeingMove(), and processBeingVisible().