Permalink
Browse files

add MoveHandlersBinder class that binds specifiec opcode to Client's …

…hander and holds that info. Cleanup Client's interface
  • Loading branch information...
1 parent 0298748 commit 877525e7ddb29a940fcd8f3d75bd9068cdecba3b @SilverIce committed Oct 20, 2011
View
@@ -7,6 +7,7 @@
*/
#pragma once
+#include <vector>
class WorldPacket;
@@ -24,22 +25,17 @@ namespace Movement
Client& operator = (const Client&);
public:
- /** Client's lifetime bounded to WorldSession lifetime */
static Client* create(void * socket);
~Client();
- ClientImpl& Impl() { return m;}
-
void LostControl();
void SetControl(UnitMovement * mov);
- void HandleResponse(WorldPacket& data);
-
- /** Handles messages from another clients */
- void SendMoveMessage(MovementMessage& msg) const;
- /** Handles messages from that client */
- void HandleOutcomingMessage(WorldPacket& recv_data);
+ /** Receives movemet messages from all visible clients */
+ void SendMoveMessage(MovementMessage& message) const;
+ /** Handles messages from this client */
+ void OnMovementMessage(WorldPacket& message);
- void HandleMoveTimeSkipped(WorldPacket & recv_data);
+ static void FillSubscribeList(std::vector<uint16>& opcodes);
};
}
View
@@ -7,7 +7,6 @@
*/
#pragma once
-#include <list>
class ByteBuffer;
class WorldPacket;
@@ -90,14 +89,56 @@ namespace Movement
void LostControl();
void SetControl(UnitMovementImpl * mov);
- void HandleResponse(WorldPacket& data);
-
- /** Handles messages from another clients */
void SendMoveMessage(MovementMessage& msg) const;
- /** Handles messages from that client */
- void HandleOutcomingMessage(WorldPacket& recv_data);
- void HandleMoveTimeSkipped(WorldPacket & recv_data);
+ public:
+
+ void OnCommonMoveMessage(WorldPacket& recv_data);
+ void OnResponse(WorldPacket& data);
+ void OnMoveTimeSkipped(WorldPacket & recv_data);
+ void OnNotImplementedMessage(WorldPacket& data);
+ };
+
+ class MoveHandlersBinder
+ {
+ public:
+ typedef void (ClientImpl::*Handler)(WorldPacket& msg);
+ typedef stdext::hash_map<uint16/*Opcode*/, Handler> HandlerMap;
+
+ static void InvokeHander(ClientImpl * client, WorldPacket& msg)
+ {
+ HandlerMap::const_iterator it = instance().handlers.find(msg.GetOpcode());
+ assert_state_msg(it != instance().handlers.end(), "no handlers for %s", LookupOpcodeName(msg.GetOpcode()));
+ (client->*(it->second)) (msg);
+ }
+
+ static void FillSubscribeList(std::vector<uint16>& opcodes)
+ {
+ for (HandlerMap::const_iterator it = instance().handlers.begin(); it != instance().handlers.end(); ++it)
+ opcodes.push_back(it->first);
+ }
+
+ private:
+
+ explicit MoveHandlersBinder();
+
+ static MoveHandlersBinder& instance() {
+ static MoveHandlersBinder _instance;
+ return _instance;
+ }
+
+ HandlerMap handlers;
+
+ void assignHandler(Handler hdl, uint16 opcode) {
+ HandlerMap::const_iterator it = handlers.find(opcode);
+ assert_state(it == handlers.end());
+ handlers.insert(HandlerMap::value_type(opcode,hdl));
+ }
+
+ void assignHandler(Handler hdl, const uint16 * opcodes, uint32 count) {
+ for (uint32 i = 0; i < count; ++i)
+ assignHandler(hdl, opcodes[i]);
+ }
};
class RespHandler : public Executor<RespHandler,true>
View
@@ -48,7 +48,7 @@ namespace Movement
};
};
- void ClientImpl::HandleOutcomingMessage(WorldPacket& recv_data)
+ void ClientImpl::OnCommonMoveMessage(WorldPacket& recv_data)
{
if (!m_controlled){
log_function("no controlled object");
@@ -134,7 +134,7 @@ namespace Movement
{
}
- void ClientImpl::HandleMoveTimeSkipped(WorldPacket & recv_data)
+ void ClientImpl::OnMoveTimeSkipped(WorldPacket & recv_data)
{
if (!m_controlled){
log_function("no controlled object");
@@ -161,7 +161,7 @@ namespace Movement
return str.str();
}
- void ClientImpl::HandleResponse(WorldPacket& data)
+ void ClientImpl::OnResponse(WorldPacket& data)
{
assert_state(m_controlled); // wrong state
@@ -189,6 +189,13 @@ namespace Movement
m_resp_handlers.remove(handler);
}
+ void ClientImpl::OnNotImplementedMessage( WorldPacket& data )
+ {
+ log_function("Unimplemented message handler called: %s", LookupOpcodeName(data.GetOpcode()));
+ }
+
+ //////////////////////////////////////////////////////////////////////////
+
void Client::LostControl()
{
m.LostControl();
@@ -199,24 +206,14 @@ namespace Movement
m.SetControl(&mov->Impl());
}
- void Client::HandleResponse( WorldPacket& data )
- {
- m.HandleResponse(data);
- }
-
void Client::SendMoveMessage( MovementMessage& msg ) const
{
m.SendMoveMessage(msg);
}
- void Client::HandleOutcomingMessage(WorldPacket& recv_data)
+ void Client::OnMovementMessage(WorldPacket& message)
{
- m.HandleOutcomingMessage(recv_data);
- }
-
- void Client::HandleMoveTimeSkipped(WorldPacket & recv_data)
- {
- m.HandleMoveTimeSkipped(recv_data);
+ MoveHandlersBinder::InvokeHander(&m, message);
}
Client* Client::create(void * socket)
@@ -231,4 +228,9 @@ namespace Movement
{
m.~ClientImpl();
}
+
+ void Client::FillSubscribeList(std::vector<uint16>& opcodes)
+ {
+ MoveHandlersBinder::FillSubscribeList(opcodes);
+ }
}
@@ -43,6 +43,10 @@ namespace Movement
PacketBuilder::WriteClientStatus(state, m_packet);
}
+ void operator << (const ClientMoveStateChange& state) {
+ *this << static_cast<const ClientMoveState&>(state);
+ }
+
/* Message's source. It might be deleted: unsafe to call his functions, access to his fields */
MessageSource Source() const { return m_source;}
const WorldPacket& Packet() const { return m_packet;}
@@ -337,4 +337,62 @@ namespace Movement
{
TeleportRequest::Launch(this, loc);
}
+
+ //////////////////////////////////////////////////////////////////////////
+
+ MoveHandlersBinder::MoveHandlersBinder()
+ {
+
+#define ASSIGN_HANDLER(MessageHanger, ... ) { \
+ uint16 opcodes[] = {__VA_ARGS__}; \
+ assignHandler(MessageHanger, opcodes, CountOf(opcodes)); \
+ }
+ assignHandler(&ClientImpl::OnMoveTimeSkipped, CMSG_MOVE_TIME_SKIPPED);
+
+ for (uint32 i = 0; i < CountOf(ValueChange2Opc_table); ++i)
+ assignHandler(&ClientImpl::OnResponse, ValueChange2Opc_table[i].cmsg_response);
+
+ for (uint32 i = 0; i < CountOf(modeInfo); ++i)
+ assignHandler(&ClientImpl::OnResponse, modeInfo[i].cmsg_ack);
+
+ ASSIGN_HANDLER(&ClientImpl::OnResponse,
+ CMSG_TIME_SYNC_RESP,
+ MSG_MOVE_TELEPORT_ACK);
+
+ ASSIGN_HANDLER(&ClientImpl::OnCommonMoveMessage,
+ MSG_MOVE_START_FORWARD,
+ MSG_MOVE_START_BACKWARD,
+ MSG_MOVE_STOP,
+ MSG_MOVE_START_STRAFE_LEFT,
+ MSG_MOVE_START_STRAFE_RIGHT,
+ MSG_MOVE_STOP_STRAFE,
+ MSG_MOVE_JUMP,
+ MSG_MOVE_START_TURN_LEFT,
+ MSG_MOVE_START_TURN_RIGHT,
+ MSG_MOVE_STOP_TURN,
+ MSG_MOVE_START_PITCH_UP,
+ MSG_MOVE_START_PITCH_DOWN,
+ MSG_MOVE_STOP_PITCH,
+ MSG_MOVE_SET_RUN_MODE,
+ MSG_MOVE_SET_WALK_MODE,
+ MSG_MOVE_FALL_LAND,
+ MSG_MOVE_START_SWIM,
+ MSG_MOVE_STOP_SWIM,
+ MSG_MOVE_SET_FACING,
+ MSG_MOVE_SET_PITCH,
+ MSG_MOVE_HEARTBEAT,
+ CMSG_MOVE_FALL_RESET,
+ CMSG_MOVE_SET_FLY,
+ MSG_MOVE_START_ASCEND,
+ MSG_MOVE_STOP_ASCEND,
+ CMSG_MOVE_CHNG_TRANSPORT,
+ MSG_MOVE_START_DESCEND);
+
+ // TODO:
+ //assignHandler(&ClientImpl::OnNotImplementedMessage, CMSG_MOVE_SPLINE_DONE);
+ //assignHandler(&ClientImpl::OnNotImplementedMessage, CMSG_MOVE_KNOCK_BACK_ACK);
+ //ASSIGN_HANDLER(&ClientImpl::OnNotImplementedMessage, CMSG_MOVE_NOT_ACTIVE_MOVER, CMSG_SET_ACTIVE_MOVER);
+
+#undef ASSIGN_HANDLER
+ }
}
@@ -1,11 +1,13 @@
-#include "typedefs_p.h"
-#include <sstream>
-
#include "UnitMovement.h"
#include "Client.h"
#include "MoveSplineInit.h"
+#include <sstream>
+#include <list>
+#include <hash_map>
+#include "typedefs_p.h"
+
#include "Object.h"
#include "opcodes.h"
#include "MaNGOS_API.h"
View
@@ -26,6 +26,14 @@ namespace Movement
/** Use it to validate object state */
#define assert_state(expr) mov_assert(expr)
+/** Use it to validate object state */
+#define assert_state_msg(expr, msg, ...) \
+ if (bool(expr) == false) { \
+ log_write("In "__FUNCTION__":%i assertion '"#expr"' failed:", __LINE__); \
+ log_write(" " msg, __VA_ARGS__); \
+ __debugbreak(); \
+ }
+
#define log_function(msg, ...) log_write(__FUNCTION__ ": " msg, __VA_ARGS__) \
#define log_fatal(msg, ...) { \

0 comments on commit 877525e

Please sign in to comment.