Fixed sprinting in 1.6.1, made speeds available through API; fixed messages containing quotes.

Fixes FS #415

git-svn-id: http://mc-server.googlecode.com/svn/trunk@1660 0a769ca7-a7f5-676a-18bf-c427514a06d6
master
madmaxoft@gmail.com 2013-07-07 14:13:43 +00:00
parent b1d05b0f57
commit 0224a4f7fc
10 changed files with 448 additions and 26 deletions

View File

@ -27,6 +27,8 @@ function Initialize(Plugin)
PluginManager:BindCommand("/wool", "debuggers", HandleWoolCmd, "Sets all your armor to blue wool");
PluginManager:BindCommand("/testwnd", "debuggers", HandleTestWndCmd, "Opens up a window using plugin API");
PluginManager:BindCommand("/gc", "debuggers", HandleGCCmd, "Activates the Lua garbage collector");
PluginManager:BindCommand("/fast", "debuggers", HandleFastCmd, "Switches between fast and normal movement speed");
PluginManager:BindCommand("/dash", "debuggers", HandleDashCmd, "Switches between fast and normal sprinting speed");
-- Enable the following line for BlockArea / Generator interface testing:
-- PluginManager:AddHook(Plugin, cPluginManager.HOOK_CHUNK_GENERATED);
@ -633,6 +635,40 @@ end
function HandleFastCmd(a_Split, a_Player)
if (a_Player:GetNormalMaxSpeed() <= 0.11) then
-- The player has normal speed, set double speed:
a_Player:SetNormalMaxSpeed(0.2);
a_Player:SendMessage("You are now fast");
else
-- The player has fast speed, set normal speed:
a_Player:SetNormalMaxSpeed(0.1);
a_Player:SendMessage("Back to normal speed");
end
return true;
end
function HandleDashCmd(a_Split, a_Player)
if (a_Player:GetSprintingMaxSpeed() <= 0.14) then
-- The player has normal sprinting speed, set double Sprintingspeed:
a_Player:SetSprintingMaxSpeed(0.4);
a_Player:SendMessage("You can now sprint very fast");
else
-- The player has fast sprinting speed, set normal sprinting speed:
a_Player:SetSprintingMaxSpeed(0.13);
a_Player:SendMessage("Back to normal sprinting");
end
return true;
end;
function OnChat(a_Player, a_Message)
return false, "blabla " .. a_Message;
end

View File

@ -1,6 +1,6 @@
/*
** Lua binding: AllToLua
** Generated automatically by tolua++-1.0.92 on 07/01/13 20:42:05.
** Generated automatically by tolua++-1.0.92 on 07/07/13 15:41:32.
*/
#ifndef __cplusplus
@ -9308,6 +9308,234 @@ static int tolua_AllToLua_cPlayer_LoadPermissionsFromDisk00(lua_State* tolua_S)
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: GetMaxSpeed of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_GetMaxSpeed00
static int tolua_AllToLua_cPlayer_GetMaxSpeed00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"const cPlayer",0,&tolua_err) ||
!tolua_isnoobj(tolua_S,2,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
const cPlayer* self = (const cPlayer*) tolua_tousertype(tolua_S,1,0);
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'GetMaxSpeed'", NULL);
#endif
{
double tolua_ret = (double) self->GetMaxSpeed();
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
return 1;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'GetMaxSpeed'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: GetNormalMaxSpeed of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_GetNormalMaxSpeed00
static int tolua_AllToLua_cPlayer_GetNormalMaxSpeed00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"const cPlayer",0,&tolua_err) ||
!tolua_isnoobj(tolua_S,2,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
const cPlayer* self = (const cPlayer*) tolua_tousertype(tolua_S,1,0);
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'GetNormalMaxSpeed'", NULL);
#endif
{
double tolua_ret = (double) self->GetNormalMaxSpeed();
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
return 1;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'GetNormalMaxSpeed'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: GetSprintingMaxSpeed of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_GetSprintingMaxSpeed00
static int tolua_AllToLua_cPlayer_GetSprintingMaxSpeed00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"const cPlayer",0,&tolua_err) ||
!tolua_isnoobj(tolua_S,2,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
const cPlayer* self = (const cPlayer*) tolua_tousertype(tolua_S,1,0);
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'GetSprintingMaxSpeed'", NULL);
#endif
{
double tolua_ret = (double) self->GetSprintingMaxSpeed();
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
return 1;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'GetSprintingMaxSpeed'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: SetNormalMaxSpeed of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_SetNormalMaxSpeed00
static int tolua_AllToLua_cPlayer_SetNormalMaxSpeed00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"cPlayer",0,&tolua_err) ||
!tolua_isnumber(tolua_S,2,0,&tolua_err) ||
!tolua_isnoobj(tolua_S,3,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
cPlayer* self = (cPlayer*) tolua_tousertype(tolua_S,1,0);
double a_Speed = ((double) tolua_tonumber(tolua_S,2,0));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'SetNormalMaxSpeed'", NULL);
#endif
{
self->SetNormalMaxSpeed(a_Speed);
}
}
return 0;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'SetNormalMaxSpeed'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: SetSprintingMaxSpeed of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_SetSprintingMaxSpeed00
static int tolua_AllToLua_cPlayer_SetSprintingMaxSpeed00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"cPlayer",0,&tolua_err) ||
!tolua_isnumber(tolua_S,2,0,&tolua_err) ||
!tolua_isnoobj(tolua_S,3,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
cPlayer* self = (cPlayer*) tolua_tousertype(tolua_S,1,0);
double a_Speed = ((double) tolua_tonumber(tolua_S,2,0));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'SetSprintingMaxSpeed'", NULL);
#endif
{
self->SetSprintingMaxSpeed(a_Speed);
}
}
return 0;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'SetSprintingMaxSpeed'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: SetCrouch of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_SetCrouch00
static int tolua_AllToLua_cPlayer_SetCrouch00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"cPlayer",0,&tolua_err) ||
!tolua_isboolean(tolua_S,2,0,&tolua_err) ||
!tolua_isnoobj(tolua_S,3,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
cPlayer* self = (cPlayer*) tolua_tousertype(tolua_S,1,0);
bool a_IsCrouched = ((bool) tolua_toboolean(tolua_S,2,0));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'SetCrouch'", NULL);
#endif
{
self->SetCrouch(a_IsCrouched);
}
}
return 0;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'SetCrouch'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
/* method: SetSprint of class cPlayer */
#ifndef TOLUA_DISABLE_tolua_AllToLua_cPlayer_SetSprint00
static int tolua_AllToLua_cPlayer_SetSprint00(lua_State* tolua_S)
{
#ifndef TOLUA_RELEASE
tolua_Error tolua_err;
if (
!tolua_isusertype(tolua_S,1,"cPlayer",0,&tolua_err) ||
!tolua_isboolean(tolua_S,2,0,&tolua_err) ||
!tolua_isnoobj(tolua_S,3,&tolua_err)
)
goto tolua_lerror;
else
#endif
{
cPlayer* self = (cPlayer*) tolua_tousertype(tolua_S,1,0);
bool a_IsSprinting = ((bool) tolua_toboolean(tolua_S,2,0));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'SetSprint'", NULL);
#endif
{
self->SetSprint(a_IsSprinting);
}
}
return 0;
#ifndef TOLUA_RELEASE
tolua_lerror:
tolua_error(tolua_S,"#ferror in function 'SetSprint'.",&tolua_err);
return 0;
#endif
}
#endif //#ifndef TOLUA_DISABLE
class Lua__cPlayer : public cPlayer, public ToluaBase {
@ -12929,7 +13157,8 @@ static int tolua_AllToLua_cInventory_AddItem00(lua_State* tolua_S)
!tolua_isusertype(tolua_S,1,"cInventory",0,&tolua_err) ||
(tolua_isvaluenil(tolua_S,2,&tolua_err) || !tolua_isusertype(tolua_S,2,"const cItem",0,&tolua_err)) ||
!tolua_isboolean(tolua_S,3,1,&tolua_err) ||
!tolua_isnoobj(tolua_S,4,&tolua_err)
!tolua_isboolean(tolua_S,4,1,&tolua_err) ||
!tolua_isnoobj(tolua_S,5,&tolua_err)
)
goto tolua_lerror;
else
@ -12938,11 +13167,12 @@ static int tolua_AllToLua_cInventory_AddItem00(lua_State* tolua_S)
cInventory* self = (cInventory*) tolua_tousertype(tolua_S,1,0);
const cItem* a_ItemStack = ((const cItem*) tolua_tousertype(tolua_S,2,0));
bool a_AllowNewStacks = ((bool) tolua_toboolean(tolua_S,3,true));
bool a_tryToFillEquippedFirst = ((bool) tolua_toboolean(tolua_S,4,false));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'AddItem'", NULL);
#endif
{
int tolua_ret = (int) self->AddItem(*a_ItemStack,a_AllowNewStacks);
int tolua_ret = (int) self->AddItem(*a_ItemStack,a_AllowNewStacks,a_tryToFillEquippedFirst);
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
@ -12965,7 +13195,8 @@ static int tolua_AllToLua_cInventory_AddItems00(lua_State* tolua_S)
!tolua_isusertype(tolua_S,1,"cInventory",0,&tolua_err) ||
(tolua_isvaluenil(tolua_S,2,&tolua_err) || !tolua_isusertype(tolua_S,2,"cItems",0,&tolua_err)) ||
!tolua_isboolean(tolua_S,3,0,&tolua_err) ||
!tolua_isnoobj(tolua_S,4,&tolua_err)
!tolua_isboolean(tolua_S,4,0,&tolua_err) ||
!tolua_isnoobj(tolua_S,5,&tolua_err)
)
goto tolua_lerror;
else
@ -12974,11 +13205,12 @@ static int tolua_AllToLua_cInventory_AddItems00(lua_State* tolua_S)
cInventory* self = (cInventory*) tolua_tousertype(tolua_S,1,0);
cItems* a_ItemStackList = ((cItems*) tolua_tousertype(tolua_S,2,0));
bool a_AllowNewStacks = ((bool) tolua_toboolean(tolua_S,3,0));
bool a_tryToFillEquippedFirst = ((bool) tolua_toboolean(tolua_S,4,0));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'AddItems'", NULL);
#endif
{
int tolua_ret = (int) self->AddItems(*a_ItemStackList,a_AllowNewStacks,false);
int tolua_ret = (int) self->AddItems(*a_ItemStackList,a_AllowNewStacks,a_tryToFillEquippedFirst);
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
@ -15808,7 +16040,8 @@ static int tolua_AllToLua_cItemGrid_AddItem00(lua_State* tolua_S)
!tolua_isusertype(tolua_S,1,"cItemGrid",0,&tolua_err) ||
(tolua_isvaluenil(tolua_S,2,&tolua_err) || !tolua_isusertype(tolua_S,2,"cItem",0,&tolua_err)) ||
!tolua_isboolean(tolua_S,3,1,&tolua_err) ||
!tolua_isnoobj(tolua_S,4,&tolua_err)
!tolua_isnumber(tolua_S,4,1,&tolua_err) ||
!tolua_isnoobj(tolua_S,5,&tolua_err)
)
goto tolua_lerror;
else
@ -15817,11 +16050,12 @@ static int tolua_AllToLua_cItemGrid_AddItem00(lua_State* tolua_S)
cItemGrid* self = (cItemGrid*) tolua_tousertype(tolua_S,1,0);
cItem* a_ItemStack = ((cItem*) tolua_tousertype(tolua_S,2,0));
bool a_AllowNewStacks = ((bool) tolua_toboolean(tolua_S,3,true));
int a_PrioritarySlot = ((int) tolua_tonumber(tolua_S,4,-1));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'AddItem'", NULL);
#endif
{
int tolua_ret = (int) self->AddItem(*a_ItemStack,a_AllowNewStacks, false);
int tolua_ret = (int) self->AddItem(*a_ItemStack,a_AllowNewStacks,a_PrioritarySlot);
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
@ -15844,7 +16078,8 @@ static int tolua_AllToLua_cItemGrid_AddItems00(lua_State* tolua_S)
!tolua_isusertype(tolua_S,1,"cItemGrid",0,&tolua_err) ||
(tolua_isvaluenil(tolua_S,2,&tolua_err) || !tolua_isusertype(tolua_S,2,"cItems",0,&tolua_err)) ||
!tolua_isboolean(tolua_S,3,1,&tolua_err) ||
!tolua_isnoobj(tolua_S,4,&tolua_err)
!tolua_isnumber(tolua_S,4,1,&tolua_err) ||
!tolua_isnoobj(tolua_S,5,&tolua_err)
)
goto tolua_lerror;
else
@ -15853,11 +16088,12 @@ static int tolua_AllToLua_cItemGrid_AddItems00(lua_State* tolua_S)
cItemGrid* self = (cItemGrid*) tolua_tousertype(tolua_S,1,0);
cItems* a_ItemStackList = ((cItems*) tolua_tousertype(tolua_S,2,0));
bool a_AllowNewStacks = ((bool) tolua_toboolean(tolua_S,3,true));
int a_PrioritarySlot = ((int) tolua_tonumber(tolua_S,4,-1));
#ifndef TOLUA_RELEASE
if (!self) tolua_error(tolua_S,"invalid 'self' in function 'AddItems'", NULL);
#endif
{
int tolua_ret = (int) self->AddItems(*a_ItemStackList,a_AllowNewStacks);
int tolua_ret = (int) self->AddItems(*a_ItemStackList,a_AllowNewStacks,a_PrioritarySlot);
tolua_pushnumber(tolua_S,(lua_Number)tolua_ret);
}
}
@ -28201,6 +28437,13 @@ TOLUA_API int tolua_AllToLua_open (lua_State* tolua_S)
tolua_function(tolua_S,"IsVisible",tolua_AllToLua_cPlayer_IsVisible00);
tolua_function(tolua_S,"MoveToWorld",tolua_AllToLua_cPlayer_MoveToWorld00);
tolua_function(tolua_S,"LoadPermissionsFromDisk",tolua_AllToLua_cPlayer_LoadPermissionsFromDisk00);
tolua_function(tolua_S,"GetMaxSpeed",tolua_AllToLua_cPlayer_GetMaxSpeed00);
tolua_function(tolua_S,"GetNormalMaxSpeed",tolua_AllToLua_cPlayer_GetNormalMaxSpeed00);
tolua_function(tolua_S,"GetSprintingMaxSpeed",tolua_AllToLua_cPlayer_GetSprintingMaxSpeed00);
tolua_function(tolua_S,"SetNormalMaxSpeed",tolua_AllToLua_cPlayer_SetNormalMaxSpeed00);
tolua_function(tolua_S,"SetSprintingMaxSpeed",tolua_AllToLua_cPlayer_SetSprintingMaxSpeed00);
tolua_function(tolua_S,"SetCrouch",tolua_AllToLua_cPlayer_SetCrouch00);
tolua_function(tolua_S,"SetSprint",tolua_AllToLua_cPlayer_SetSprint00);
tolua_endmodule(tolua_S);
tolua_cclass(tolua_S,"Lua__cPlayer","Lua__cPlayer","cPlayer",NULL);
tolua_beginmodule(tolua_S,"Lua__cPlayer");

View File

@ -1,6 +1,6 @@
/*
** Lua binding: AllToLua
** Generated automatically by tolua++-1.0.92 on 07/01/13 20:42:05.
** Generated automatically by tolua++-1.0.92 on 07/07/13 15:41:32.
*/
/* Exported function */

View File

@ -1193,6 +1193,17 @@ void cClientHandle::HandleEntityAction(int a_EntityID, char a_ActionID)
m_Player->GetWorld()->BroadcastPlayerAnimation(*m_Player, 3);
break;
}
case 4: // Start sprinting
{
m_Player->SetSprint(true);
break;
}
case 5: // Stop sprinting
{
m_Player->SetSprint(false);
SendPlayerMaxSpeed();
break;
}
}
}

View File

@ -50,7 +50,10 @@ cPlayer::cPlayer(cClientHandle* a_Client, const AString & a_PlayerName)
, m_ClientHandle( a_Client )
, m_FoodExhaustionLevel(0.f)
, m_FoodTickTimer(0)
, m_NormalMaxSpeed(0.1)
, m_SprintingMaxSpeed(0.13)
, m_IsCrouched(false)
, m_IsSprinting(false)
{
LOGD("Created a player object for \"%s\" @ \"%s\" at %p, ID %d",
a_PlayerName.c_str(), a_Client->GetIPString().c_str(),
@ -356,6 +359,41 @@ const cSlotNums & cPlayer::GetInventoryPaintSlots(void) const
double cPlayer::GetMaxSpeed(void) const
{
return m_IsSprinting ? m_SprintingMaxSpeed : m_NormalMaxSpeed;
}
void cPlayer::SetNormalMaxSpeed(double a_Speed)
{
m_NormalMaxSpeed = a_Speed;
if (!m_IsSprinting)
{
m_ClientHandle->SendPlayerMaxSpeed();
}
}
void cPlayer::SetSprintingMaxSpeed(double a_Speed)
{
m_SprintingMaxSpeed = a_Speed;
if (m_IsSprinting)
{
m_ClientHandle->SendPlayerMaxSpeed();
}
}
void cPlayer::SetCrouch(bool a_IsCrouched)
{
// Set the crouch status, broadcast to all visible players
@ -373,6 +411,22 @@ void cPlayer::SetCrouch(bool a_IsCrouched)
void cPlayer::SetSprint(bool a_IsSprinting)
{
if (a_IsSprinting == m_IsSprinting)
{
// No change
return;
}
m_IsSprinting = a_IsSprinting;
m_ClientHandle->SendPlayerMaxSpeed();
}
void cPlayer::DoTakeDamage(TakeDamageInfo & a_TDI)
{
if (m_GameMode == eGameMode_Creative)

View File

@ -171,11 +171,34 @@ public:
/// Returns the list of slots currently stored for inventory painting. To be used by cWindow only
const cSlotNums & GetInventoryPaintSlots(void) const;
// tolua_begin
/// Returns the current maximum speed, as reported in the 1.6.1+ protocol (takes current sprinting state into account)
double GetMaxSpeed(void) const;
/// Gets the normal maximum speed, as reported in the 1.6.1+ protocol, in the protocol units
double GetNormalMaxSpeed(void) const { return m_NormalMaxSpeed; }
/// Gets the sprinting maximum speed, as reported in the 1.6.1+ protocol, in the protocol units
double GetSprintingMaxSpeed(void) const { return m_SprintingMaxSpeed; }
/// Sets the normal maximum speed, as reported in the 1.6.1+ protocol. Sends the update to player, if needed.
void SetNormalMaxSpeed(double a_Speed);
/// Sets the sprinting maximum speed, as reported in the 1.6.1+ protocol. Sends the update to player, if needed.
void SetSprintingMaxSpeed(double a_Speed);
/// Sets the crouch status, broadcasts to all visible players
void SetCrouch(bool a_IsCrouched);
/// Starts or stops sprinting, sends the max speed update to the client, if needed
void SetSprint(bool a_IsSprinting);
// tolua_end
// cEntity overrides:
virtual bool IsCrouched (void) const { return m_IsCrouched; }
virtual bool IsSprinting(void) const { return m_IsSprinting; }
protected:
typedef std::map< std::string, bool > PermissionMap;
@ -226,7 +249,14 @@ protected:
cSlotNums m_InventoryPaintSlots;
/// Max speed, in ENTITY_PROPERTIES packet's units, when the player is walking. 0.1 by default
double m_NormalMaxSpeed;
/// Max speed, in ENTITY_PROPERTIES packet's units, when the player is sprinting. 0.13 by default
double m_SprintingMaxSpeed;
bool m_IsCrouched;
bool m_IsSprinting;
virtual void Destroyed(void);

View File

@ -74,7 +74,7 @@ void cProtocol161::SendAttachEntity(const cEntity & a_Entity, const cEntity * a_
void cProtocol161::SendChat(const AString & a_Message)
{
super::SendChat(Printf("{\"text\":\"%s\"}", a_Message.c_str()));
super::SendChat(Printf("{\"text\":\"%s\"}", EscapeString(a_Message).c_str()));
}
@ -83,15 +83,7 @@ void cProtocol161::SendChat(const AString & a_Message)
void cProtocol161::SendGameMode(eGameMode a_GameMode)
{
super::SendGameMode(a_GameMode);
// Also send the EntityProperties packet specifying the movementSpeed:
cCSLock Lock(m_CSPacket);
WriteByte(PACKET_ENTITY_PROPERTIES);
WriteInt(m_Client->GetPlayer()->GetUniqueID());
WriteInt(1);
WriteString("generic.movementSpeed");
WriteDouble(0.1);
Flush();
SendPlayerMaxSpeed();
}
@ -112,6 +104,21 @@ void cProtocol161::SendHealth(void)
void cProtocol161::SendPlayerMaxSpeed(void)
{
cCSLock Lock(m_CSPacket);
WriteByte(PACKET_ENTITY_PROPERTIES);
WriteInt(m_Client->GetPlayer()->GetUniqueID());
WriteInt(1);
WriteString("generic.movementSpeed");
WriteDouble(m_Client->GetPlayer()->GetMaxSpeed());
Flush();
}
void cProtocol161::SendWindowOpen(char a_WindowID, char a_WindowType, const AString & a_WindowTitle, char a_NumSlots)
{
if (a_WindowType < 0)

View File

@ -33,6 +33,7 @@ public:
virtual void SendChat (const AString & a_Message) override;
virtual void SendGameMode (eGameMode a_GameMode) override;
virtual void SendHealth (void) override;
virtual void SendPlayerMaxSpeed(void) override;
virtual void SendWindowOpen (char a_WindowID, char a_WindowType, const AString & a_WindowTitle, char a_NumSlots) override;
virtual int ParseEntityAction (void) override;

View File

@ -569,3 +569,40 @@ AString & CreateHexDump(AString & a_Out, const void * a_Data, int a_Size, int a_
AString EscapeString(const AString & a_Message)
{
AString EscapedMsg;
size_t len = a_Message.size();
size_t last = 0;
EscapedMsg.reserve(len);
for (size_t i = 0; i < len; i++)
{
char ch = a_Message[i];
switch (ch)
{
case '\'':
case '\"':
case '\\':
{
if (i > last)
{
EscapedMsg.append(a_Message, last, i - last);
}
EscapedMsg.push_back('\\');
EscapedMsg.push_back(ch);
last = i + 1;
break;
}
}
}
if (len > last)
{
EscapedMsg.append(a_Message, last, len - last);
}
return EscapedMsg;
}

View File

@ -66,6 +66,9 @@ extern AString & UTF8ToRawBEUTF16(const char * a_UTF8, size_t a_UTF8Length, AStr
/// Creates a nicely formatted HEX dump of the given memory block. Max a_BytesPerLine is 120
extern AString & CreateHexDump(AString & a_Out, const void * a_Data, int a_Size, int a_BytesPerLine);
/// Returns a copy of a_Message with all quotes and backslashes escaped by a backslash
extern AString EscapeString(const AString & a_Message);
// If you have any other string helper functions, declare them here