summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorErik Schilling <ablu.erikschilling@googlemail.com>2013-04-24 15:42:23 +0200
committerErik Schilling <ablu.erikschilling@googlemail.com>2013-05-08 14:02:51 +0200
commit4d6abb9b40ee1b0a4642a208f314b4dbb41bbac8 (patch)
tree93eccf625249b2db8519dd3b57953b97cbb76849
parent1758acc8e845524071db8996f3dd5d1935a059e1 (diff)
downloadmanaserv-4d6abb9b40ee1b0a4642a208f314b4dbb41bbac8.tar.gz
manaserv-4d6abb9b40ee1b0a4642a208f314b4dbb41bbac8.tar.xz
manaserv-4d6abb9b40ee1b0a4642a208f314b4dbb41bbac8.zip
[Abilities] Inform other players about ability uses
-rw-r--r--src/common/manaserv_protocol.h2
-rw-r--r--src/game-server/abilitycomponent.cpp22
-rw-r--r--src/game-server/abilitycomponent.h27
-rw-r--r--src/game-server/actor.h6
-rw-r--r--src/game-server/state.cpp24
5 files changed, 77 insertions, 4 deletions
diff --git a/src/common/manaserv_protocol.h b/src/common/manaserv_protocol.h
index 498e35f..73837b1 100644
--- a/src/common/manaserv_protocol.h
+++ b/src/common/manaserv_protocol.h
@@ -143,6 +143,8 @@ enum {
GPMSG_BEING_HEALTH_CHANGE = 0x0274, // W being id, W hp, W max hp
GPMSG_BEINGS_MOVE = 0x0280, // { W being id, B flags [, [W*2 position,] W*2 destination, B speed] }*
GPMSG_ITEMS = 0x0281, // { W item id, W*2 position }*
+ GPMSG_BEING_ABILITY_POINT = 0x0282, // W being id, B abilityId, W*2 point
+ GPMSG_BEING_ABILITY_BEING = 0x0283, // W being id, B abilityId, W target being id
PGMSG_ATTACK = 0x0290, // W being id
GPMSG_BEING_ATTACK = 0x0291, // W being id, B direction, B attack Id
PGMSG_USE_ABILITY_ON_BEING = 0x0292, // B abilityID, W being id
diff --git a/src/game-server/abilitycomponent.cpp b/src/game-server/abilitycomponent.cpp
index 5b27be1..60c9b86 100644
--- a/src/game-server/abilitycomponent.cpp
+++ b/src/game-server/abilitycomponent.cpp
@@ -27,7 +27,9 @@
#include "utils/logger.h"
-AbilityComponent::AbilityComponent(Entity &entity)
+AbilityComponent::AbilityComponent(Entity &entity):
+ mLastUsedAbilityId(0),
+ mLastTargetBeingId(0)
{
entity.getComponent<BeingComponent>()->signal_attribute_changed.connect(
sigc::mem_fun(this, &AbilityComponent::attributeChanged));
@@ -136,6 +138,14 @@ void AbilityComponent::useAbilityOnBeing(Entity &user, int id, Entity *b)
script->push(b);
script->push(ability.abilityInfo->id);
script->execute(user.getMap());
+
+ mLastUsedAbilityId = id;
+ if (b)
+ mLastTargetBeingId = b->getComponent<ActorComponent>()->getPublicID();
+ else
+ mLastTargetBeingId = 0;
+ user.getComponent<ActorComponent>()->raiseUpdateFlags(
+ UPDATEFLAG_ABILITY_ON_BEING);
}
/**
@@ -166,6 +176,11 @@ void AbilityComponent::useAbilityOnPoint(Entity &user, int id, int x, int y)
script->push(y);
script->push(ability.abilityInfo->id);
script->execute(user.getMap());
+
+ mLastUsedAbilityId = id;
+ mLastTargetPoint = Point(x, y);
+ user.getComponent<ActorComponent>()->raiseUpdateFlags(
+ UPDATEFLAG_ABILITY_ON_POINT);
}
/**
@@ -211,7 +226,10 @@ void AbilityComponent::startCooldown(
{
unsigned cooldownAttribute = abilityInfo->cooldownAttribute;
auto *bc = entity.getComponent<BeingComponent>();
- mCooldown.set((int)bc->getModifiedAttribute(cooldownAttribute));
+ int cooldown = (int)bc->getModifiedAttribute(cooldownAttribute);
+ // Enforce a minimum cooldown of 1 tick to prevent syncing issues
+ cooldown = std::max(cooldown, 1);
+ mCooldown.set(cooldown);
signal_cooldown_activated.emit();
}
diff --git a/src/game-server/abilitycomponent.h b/src/game-server/abilitycomponent.h
index c44dcb7..def3e00 100644
--- a/src/game-server/abilitycomponent.h
+++ b/src/game-server/abilitycomponent.h
@@ -25,6 +25,8 @@
#include "game-server/component.h"
#include "game-server/timeout.h"
+#include "utils/point.h"
+
#include <sigc++/signal.h>
struct AbilityValue
@@ -73,6 +75,11 @@ public:
sigc::signal<void, int> signal_ability_changed;
sigc::signal<void, int> signal_ability_took;
sigc::signal<void> signal_cooldown_activated;
+
+ // For informing clients
+ int getLastUsedAbilityId() const;
+ const Point &getLastTargetPoint() const;
+ int getLastTargetBeingId() const;
private:
bool abilityUseCheck(AbilityMap::iterator it);
void attributeChanged(Entity *entity, unsigned attr);
@@ -80,6 +87,11 @@ private:
Timeout mCooldown;
AbilityMap mAbilities;
+
+ // Variables required for informing clients
+ int mLastUsedAbilityId;
+ Point mLastTargetPoint;
+ int mLastTargetBeingId;
};
@@ -117,4 +129,19 @@ inline int AbilityComponent::remainingCooldown() const
return mCooldown.remaining();
}
+inline int AbilityComponent::getLastUsedAbilityId() const
+{
+ return mLastUsedAbilityId;
+}
+
+inline const Point &AbilityComponent::getLastTargetPoint() const
+{
+ return mLastTargetPoint;
+}
+
+inline int AbilityComponent::getLastTargetBeingId() const
+{
+ return mLastTargetBeingId;
+}
+
#endif /* ABILITYCOMPONENT_H_ */
diff --git a/src/game-server/actor.h b/src/game-server/actor.h
index 2950d51..d1201aa 100644
--- a/src/game-server/actor.h
+++ b/src/game-server/actor.h
@@ -38,7 +38,9 @@ enum
UPDATEFLAG_LOOKSCHANGE = 16,
UPDATEFLAG_DIRCHANGE = 32,
UPDATEFLAG_HEALTHCHANGE = 64,
- UPDATEFLAG_EMOTE = 128
+ UPDATEFLAG_EMOTE = 128,
+ UPDATEFLAG_ABILITY_ON_POINT = 256,
+ UPDATEFLAG_ABILITY_ON_BEING = 512
};
/**
@@ -143,7 +145,7 @@ class ActorComponent : public Component
unsigned short mMoveTime;
private:
- char mUpdateFlags; /**< Changes in actor status. */
+ int mUpdateFlags; /**< Changes in actor status. */
/** Actor ID sent to clients (unique with respect to the map). */
unsigned short mPublicID;
diff --git a/src/game-server/state.cpp b/src/game-server/state.cpp
index 0b97ec0..6efeb14 100644
--- a/src/game-server/state.cpp
+++ b/src/game-server/state.cpp
@@ -228,6 +228,30 @@ static void informPlayer(MapComposite *map, Entity *p)
gameHandler->sendTo(p, DirMsg);
}
+ // Send ability uses
+ if (oflags & UPDATEFLAG_ABILITY_ON_POINT)
+ {
+ MessageOut abilityMsg(GPMSG_BEING_ABILITY_POINT);
+ abilityMsg.writeInt16(oid);
+ auto *abilityComponent = o->getComponent<AbilityComponent>();
+ const Point &point = abilityComponent->getLastTargetPoint();
+ abilityMsg.writeInt8(abilityComponent->getLastUsedAbilityId());
+ abilityMsg.writeInt16(point.x);
+ abilityMsg.writeInt16(point.y);
+ gameHandler->sendTo(p, abilityMsg);
+ }
+
+ if (oflags & UPDATEFLAG_ABILITY_ON_BEING)
+ {
+ MessageOut abilityMsg(GPMSG_BEING_ABILITY_POINT);
+ abilityMsg.writeInt16(oid);
+ auto *abilityComponent = o->getComponent<AbilityComponent>();
+ abilityMsg.writeInt8(abilityComponent->getLastUsedAbilityId());
+ abilityMsg.writeInt16(
+ abilityComponent->getLastTargetBeingId());
+ gameHandler->sendTo(p, abilityMsg);
+ }
+
// Send damage messages.
if (o->canFight())
{