summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTycho <work.tycho+git@gmail.com>2014-03-09 19:02:30 +0100
committerTycho <work.tycho+git@gmail.com>2014-03-09 19:02:30 +0100
commitb5e33c5424c0b148a7076bb0f3019cfb0ef9c824 (patch)
treedabb3041abd9b8513570111310903992254d8063
parentFix IsThread destructor (diff)
parentFixed #778 - stack overflow.com (diff)
downloadcuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.tar
cuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.tar.gz
cuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.tar.bz2
cuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.tar.lz
cuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.tar.xz
cuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.tar.zst
cuberite-b5e33c5424c0b148a7076bb0f3019cfb0ef9c824.zip
-rw-r--r--CONTRIBUTING.md2
m---------MCServer/Plugins/Core0
-rw-r--r--src/Blocks/BlockBed.h5
-rw-r--r--src/Blocks/BlockButton.h5
-rw-r--r--src/Blocks/BlockChest.h5
-rw-r--r--src/Blocks/BlockComparator.h5
-rw-r--r--src/Blocks/BlockDoor.cpp2
-rw-r--r--src/Blocks/BlockDoor.h58
-rw-r--r--src/Blocks/BlockDropSpenser.h19
-rw-r--r--src/Blocks/BlockEnderchest.h6
-rw-r--r--src/Blocks/BlockFenceGate.h6
-rw-r--r--src/Blocks/BlockStairs.h68
-rw-r--r--src/Blocks/BlockTorch.h67
-rw-r--r--src/Blocks/BlockVine.h8
-rw-r--r--src/Blocks/MetaRotater.h120
-rw-r--r--src/ClientHandle.cpp71
-rw-r--r--src/ClientHandle.h4
-rw-r--r--src/Entities/Floater.h2
-rw-r--r--src/Protocol/Protocol125.cpp11
-rw-r--r--src/Protocol/Protocol125.h1
-rw-r--r--src/Protocol/Protocol16x.cpp11
-rw-r--r--src/Protocol/Protocol17x.cpp10
22 files changed, 302 insertions, 184 deletions
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index a0a332f30..7ec7058ae 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -22,8 +22,10 @@ Code Stuff
- This helps prevent mistakes such as `if (a & 1 == 0)`
* White space is free, so use it freely
- "freely" as in "plentifully", not "arbitrarily"
+ * All `case` statements inside a `switch` need an extra indent.
* Each and every control statement deserves its braces. This helps maintainability later on when the file is edited, lines added or removed - the control logic doesn't break so easily.
- The only exception: a `switch` statement with all `case` statements being a single short statement is allowed to use the short brace-less form.
+ - These two rules really mean that indent is governed by braces
* Add an empty last line in all source files (GCC and GIT can complain otherwise)
* Use doxy-comments for functions in the header file, format as `/** Description */`
* Use spaces after the comment markers: `// Comment` instead of `//Comment`
diff --git a/MCServer/Plugins/Core b/MCServer/Plugins/Core
-Subproject 3b416b07a339b3abcbc127070d56eea05b05373
+Subproject 013a32a7fb3c8a6cfe0aef892d4c7394d4e1be5
diff --git a/src/Blocks/BlockBed.h b/src/Blocks/BlockBed.h
index caec2b56f..6daa94730 100644
--- a/src/Blocks/BlockBed.h
+++ b/src/Blocks/BlockBed.h
@@ -4,6 +4,7 @@
#include "BlockHandler.h"
#include "ChunkInterface.h"
#include "WorldInterface.h"
+#include "MetaRotater.h"
#include "../Entities/Player.h"
@@ -11,11 +12,11 @@
class cBlockBedHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x3, 0x02, 0x03, 0x00, 0x01, true>
{
public:
cBlockBedHandler(BLOCKTYPE a_BlockType)
- : cBlockHandler(a_BlockType)
+ : cMetaRotater<cBlockHandler, 0x3, 0x02, 0x03, 0x00, 0x01,true>(a_BlockType)
{
}
diff --git a/src/Blocks/BlockButton.h b/src/Blocks/BlockButton.h
index 2db9b7ec7..740cbe3c4 100644
--- a/src/Blocks/BlockButton.h
+++ b/src/Blocks/BlockButton.h
@@ -2,16 +2,17 @@
#include "BlockHandler.h"
#include "Chunk.h"
+#include "MetaRotater.h"
class cBlockButtonHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x07, 0x04, 0x01, 0x03, 0x02, true>
{
public:
cBlockButtonHandler(BLOCKTYPE a_BlockType)
- : cBlockHandler(a_BlockType)
+ : cMetaRotater<cBlockHandler, 0x07, 0x04, 0x01, 0x03, 0x02, true>(a_BlockType)
{
}
diff --git a/src/Blocks/BlockChest.h b/src/Blocks/BlockChest.h
index 02ecc4346..30588d8fc 100644
--- a/src/Blocks/BlockChest.h
+++ b/src/Blocks/BlockChest.h
@@ -4,17 +4,18 @@
#include "BlockEntity.h"
#include "../BlockArea.h"
#include "../Entities/Player.h"
+#include "MetaRotater.h"
class cBlockChestHandler :
- public cBlockEntityHandler
+ public cMetaRotater<cBlockEntityHandler, 0x07, 0x04, 0x01, 0x03, 0x02, true>
{
public:
cBlockChestHandler(BLOCKTYPE a_BlockType)
- : cBlockEntityHandler(a_BlockType)
+ : cMetaRotater<cBlockEntityHandler, 0x07, 0x04, 0x01, 0x03, 0x02, true>(a_BlockType)
{
}
diff --git a/src/Blocks/BlockComparator.h b/src/Blocks/BlockComparator.h
index cea35a864..e570ff302 100644
--- a/src/Blocks/BlockComparator.h
+++ b/src/Blocks/BlockComparator.h
@@ -3,17 +3,18 @@
#include "BlockHandler.h"
#include "BlockRedstoneRepeater.h"
+#include "MetaRotater.h"
class cBlockComparatorHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x03, 0x00, 0x01, 0x02, 0x03, true>
{
public:
cBlockComparatorHandler(BLOCKTYPE a_BlockType)
- : cBlockHandler(a_BlockType)
+ : cMetaRotater<cBlockHandler, 0x03, 0x00, 0x01, 0x02, 0x03, true>(a_BlockType)
{
}
diff --git a/src/Blocks/BlockDoor.cpp b/src/Blocks/BlockDoor.cpp
index 0acf04852..4e38ef334 100644
--- a/src/Blocks/BlockDoor.cpp
+++ b/src/Blocks/BlockDoor.cpp
@@ -9,7 +9,7 @@
cBlockDoorHandler::cBlockDoorHandler(BLOCKTYPE a_BlockType)
- : cBlockHandler(a_BlockType)
+ : super(a_BlockType)
{
}
diff --git a/src/Blocks/BlockDoor.h b/src/Blocks/BlockDoor.h
index 68be2c658..981774c17 100644
--- a/src/Blocks/BlockDoor.h
+++ b/src/Blocks/BlockDoor.h
@@ -4,13 +4,15 @@
#include "BlockHandler.h"
#include "../Entities/Player.h"
#include "Chunk.h"
+#include "MetaRotater.h"
class cBlockDoorHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x03, 0x01, 0x02, 0x03, 0x00, true>
{
+ typedef cMetaRotater<cBlockHandler, 0x03, 0x01, 0x02, 0x03, 0x00, true> super;
public:
cBlockDoorHandler(BLOCKTYPE a_BlockType);
@@ -168,6 +170,60 @@ public:
}
+ virtual NIBBLETYPE MetaRotateCCW(NIBBLETYPE a_Meta) override
+ {
+ if (a_Meta & 0x08)
+ {
+ return a_Meta;
+ }
+ else
+ {
+ return super::MetaRotateCCW(a_Meta);
+ }
+ }
+
+
+
+ virtual NIBBLETYPE MetaRotateCW(NIBBLETYPE a_Meta) override
+ {
+ if (a_Meta & 0x08)
+ {
+ return a_Meta;
+ }
+ else
+ {
+ return super::MetaRotateCW(a_Meta);
+ }
+ }
+
+
+
+ virtual NIBBLETYPE MetaMirrorXY(NIBBLETYPE a_Meta) override
+ {
+ if (a_Meta & 0x08)
+ {
+ return a_Meta;
+ }
+ else
+ {
+ return super::MetaMirrorXY(a_Meta);
+ }
+ }
+
+
+
+ virtual NIBBLETYPE MetaMirrorYZ(NIBBLETYPE a_Meta) override
+ {
+ if (a_Meta & 0x08)
+ {
+ return a_Meta;
+ }
+ else
+ {
+ return super::MetaMirrorYZ(a_Meta);
+ }
+ }
+
} ;
diff --git a/src/Blocks/BlockDropSpenser.h b/src/Blocks/BlockDropSpenser.h
index 30d347ec9..7e0ad0e55 100644
--- a/src/Blocks/BlockDropSpenser.h
+++ b/src/Blocks/BlockDropSpenser.h
@@ -6,17 +6,18 @@
#pragma once
#include "../Piston.h"
+#include "MetaRotater.h"
class cBlockDropSpenserHandler :
- public cBlockEntityHandler
+ public cMetaRotater<cBlockEntityHandler, 0x07, 0x02, 0x05, 0x03, 0x04>
{
public:
cBlockDropSpenserHandler(BLOCKTYPE a_BlockType) :
- cBlockEntityHandler(a_BlockType)
+ cMetaRotater<cBlockEntityHandler, 0x07, 0x02, 0x05, 0x03, 0x04>(a_BlockType)
{
}
@@ -34,6 +35,20 @@ public:
a_BlockMeta = cPiston::RotationPitchToMetaData(a_Player->GetYaw(), a_Player->GetPitch());
return true;
}
+
+ virtual NIBBLETYPE MetaMirrorXZ(NIBBLETYPE a_Meta) override
+ {
+ // Bit 0x08 is a flag. Lowest three bits are position. 0x08 == 1000
+ NIBBLETYPE OtherMeta = a_Meta & 0x08;
+ // Mirrors defined by by a table. (Source, mincraft.gamepedia.com) 0x07 == 0111
+ switch (a_Meta & 0x07)
+ {
+ case 0x00: return 0x01 + OtherMeta; // Down -> Up
+ case 0x01: return 0x00 + OtherMeta; // Up -> Down
+ }
+ // Not Facing Up or Down; No change.
+ return a_Meta;
+ }
} ;
diff --git a/src/Blocks/BlockEnderchest.h b/src/Blocks/BlockEnderchest.h
index b4b0b995d..97cf484fb 100644
--- a/src/Blocks/BlockEnderchest.h
+++ b/src/Blocks/BlockEnderchest.h
@@ -2,17 +2,17 @@
#pragma once
#include "BlockEntity.h"
-
+#include "MetaRotater.h"
class cBlockEnderchestHandler :
- public cBlockEntityHandler
+ public cMetaRotater<cBlockEntityHandler, 0x07, 0x02, 0x05, 0x03, 0x04>
{
public:
cBlockEnderchestHandler(BLOCKTYPE a_BlockType)
- : cBlockEntityHandler(a_BlockType)
+ : cMetaRotater<cBlockEntityHandler, 0x07, 0x02, 0x05, 0x03, 0x04>(a_BlockType)
{
}
diff --git a/src/Blocks/BlockFenceGate.h b/src/Blocks/BlockFenceGate.h
index 1abe1eecf..e3162bbd6 100644
--- a/src/Blocks/BlockFenceGate.h
+++ b/src/Blocks/BlockFenceGate.h
@@ -2,17 +2,17 @@
#pragma once
#include "BlockHandler.h"
-
+#include "MetaRotater.h"
class cBlockFenceGateHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x03, 0x02, 0x03, 0x00, 0x01, true>
{
public:
cBlockFenceGateHandler(BLOCKTYPE a_BlockType) :
- cBlockHandler(a_BlockType)
+ cMetaRotater<cBlockHandler, 0x03, 0x02, 0x03, 0x00, 0x01, true>(a_BlockType)
{
}
diff --git a/src/Blocks/BlockStairs.h b/src/Blocks/BlockStairs.h
index 93035b3b1..ea8405597 100644
--- a/src/Blocks/BlockStairs.h
+++ b/src/Blocks/BlockStairs.h
@@ -2,17 +2,17 @@
#pragma once
#include "BlockHandler.h"
-
+#include "MetaRotater.h"
class cBlockStairsHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x03, 0x03, 0x00, 0x02, 0x01, true>
{
public:
cBlockStairsHandler(BLOCKTYPE a_BlockType) :
- cBlockHandler(a_BlockType)
+ cMetaRotater<cBlockHandler, 0x03, 0x03, 0x00, 0x02, 0x01, true>(a_BlockType)
{
}
@@ -104,54 +104,6 @@ public:
}
- virtual NIBBLETYPE MetaRotateCCW(NIBBLETYPE a_Meta) override
- {
- // Bits 3 and 4 stay, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x0c);
- switch (a_Meta & 0x03)
- {
- case 0x00: return TopBits | 0x03; // East -> North
- case 0x01: return TopBits | 0x02; // West -> South
- case 0x02: return TopBits | 0x00; // South -> East
- case 0x03: return TopBits | 0x01; // North -> West
- }
- // Not reachable, but to avoid a compiler warning:
- return 0;
- }
-
-
- virtual NIBBLETYPE MetaRotateCW(NIBBLETYPE a_Meta) override
- {
- // Bits 3 and 4 stay, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x0c);
- switch (a_Meta & 0x03)
- {
- case 0x00: return TopBits | 0x02; // East -> South
- case 0x01: return TopBits | 0x03; // West -> North
- case 0x02: return TopBits | 0x01; // South -> West
- case 0x03: return TopBits | 0x00; // North -> East
- }
- // Not reachable, but to avoid a compiler warning:
- return 0;
- }
-
-
- virtual NIBBLETYPE MetaMirrorXY(NIBBLETYPE a_Meta) override
- {
- // Bits 3 and 4 stay, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x0c);
- switch (a_Meta & 0x03)
- {
- case 0x00: return TopBits | 0x00; // East -> East
- case 0x01: return TopBits | 0x01; // West -> West
- case 0x02: return TopBits | 0x03; // South -> North
- case 0x03: return TopBits | 0x02; // North -> South
- }
- // Not reachable, but to avoid a compiler warning:
- return 0;
- }
-
-
virtual NIBBLETYPE MetaMirrorXZ(NIBBLETYPE a_Meta) override
{
// Toggle bit 3:
@@ -159,20 +111,6 @@ public:
}
- virtual NIBBLETYPE MetaMirrorYZ(NIBBLETYPE a_Meta) override
- {
- // Bits 3 and 4 stay, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x0c);
- switch (a_Meta & 0x03)
- {
- case 0x00: return TopBits | 0x01; // East -> West
- case 0x01: return TopBits | 0x00; // West -> East
- case 0x02: return TopBits | 0x02; // South -> South
- case 0x03: return TopBits | 0x03; // North -> North
- }
- // Not reachable, but to avoid a compiler warning:
- return 0;
- }
} ;
diff --git a/src/Blocks/BlockTorch.h b/src/Blocks/BlockTorch.h
index 84bbb37ec..d32c77629 100644
--- a/src/Blocks/BlockTorch.h
+++ b/src/Blocks/BlockTorch.h
@@ -2,17 +2,17 @@
#include "BlockHandler.h"
#include "../Chunk.h"
-
+#include "MetaRotater.h"
class cBlockTorchHandler :
- public cBlockHandler
+ public cMetaRotater<cBlockHandler, 0x7, 0x4, 0x1, 0x3, 0x2>
{
public:
cBlockTorchHandler(BLOCKTYPE a_BlockType)
- : cBlockHandler(a_BlockType)
+ : cMetaRotater<cBlockHandler, 0x7, 0x4, 0x1, 0x3, 0x2>(a_BlockType)
{
}
@@ -185,67 +185,6 @@ public:
{
return "step.wood";
}
-
-
- virtual NIBBLETYPE MetaRotateCCW(NIBBLETYPE a_Meta) override
- {
- // Bit 4 stays, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x08);
- switch (a_Meta & 0x07)
- {
- case 0x01: return TopBits | 0x04; // East -> North
- case 0x02: return TopBits | 0x03; // West -> South
- case 0x03: return TopBits | 0x01; // South -> East
- case 0x04: return TopBits | 0x02; // North -> West
- default: return a_Meta; // Floor -> Floor
- }
- }
-
-
- virtual NIBBLETYPE MetaRotateCW(NIBBLETYPE a_Meta) override
- {
- // Bit 4 stays, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x08);
- switch (a_Meta & 0x07)
- {
- case 0x01: return TopBits | 0x03; // East -> South
- case 0x02: return TopBits | 0x04; // West -> North
- case 0x03: return TopBits | 0x02; // South -> West
- case 0x04: return TopBits | 0x01; // North -> East
- default: return a_Meta; // Floor -> Floor
- }
- }
-
-
- virtual NIBBLETYPE MetaMirrorXY(NIBBLETYPE a_Meta) override
- {
- // Bit 4 stays, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x08);
- switch (a_Meta & 0x07)
- {
- case 0x03: return TopBits | 0x04; // South -> North
- case 0x04: return TopBits | 0x03; // North -> South
- default: return a_Meta; // Keep the rest
- }
- }
-
-
- // Mirroring around the XZ plane doesn't make sense for floor torches,
- // the others stay the same, so let's keep all the metas the same.
- // The base class does tht for us, no need to override MetaMirrorXZ()
-
-
- virtual NIBBLETYPE MetaMirrorYZ(NIBBLETYPE a_Meta) override
- {
- // Bit 4 stays, the rest is swapped around according to a table:
- NIBBLETYPE TopBits = (a_Meta & 0x08);
- switch (a_Meta & 0x07)
- {
- case 0x01: return TopBits | 0x02; // East -> West
- case 0x02: return TopBits | 0x01; // West -> East
- default: return a_Meta; // Keep the rest
- }
- }
} ;
diff --git a/src/Blocks/BlockVine.h b/src/Blocks/BlockVine.h
index 0934a451b..708583e70 100644
--- a/src/Blocks/BlockVine.h
+++ b/src/Blocks/BlockVine.h
@@ -1,8 +1,7 @@
-
#pragma once
#include "BlockHandler.h"
-
+#include "MetaRotater.h"
@@ -190,8 +189,8 @@ public:
{
return ((a_Meta << 1) | (a_Meta >> 3)) & 0x0f; // Rotate bits to the left
}
-
-
+
+
virtual NIBBLETYPE MetaMirrorXY(NIBBLETYPE a_Meta) override
{
// Bits 2 and 4 stay, bits 1 and 3 swap
@@ -204,6 +203,7 @@ public:
// Bits 1 and 3 stay, bits 2 and 4 swap
return ((a_Meta & 0x05) | ((a_Meta & 0x02) << 2) | ((a_Meta & 0x08) >> 2));
}
+
} ;
diff --git a/src/Blocks/MetaRotater.h b/src/Blocks/MetaRotater.h
new file mode 100644
index 000000000..dde88e6db
--- /dev/null
+++ b/src/Blocks/MetaRotater.h
@@ -0,0 +1,120 @@
+// MetaRotater.h
+
+// Provides a mixin for rotations and reflections
+
+#pragma once
+
+// MSVC generates warnings for the templated AssertIfNotMatched parameter conditions, so disable it:
+#ifdef _MSC_VER
+ #pragma warning(disable: 4127) // Conditional expression is constant
+#endif
+
+
+
+
+
+/*
+Provides a mixin for rotations and reflections following the standard pattern of apply mask then use case.
+
+Usage:
+Inherit from this class providing your base class as Base, the BitMask for the direction bits in bitmask and the masked value for the directions in North, East, South, West. There is also an aptional parameter AssertIfNotMatched. Set this if it is invalid for a block to exist in any other state.
+*/
+
+template<class Base, NIBBLETYPE BitMask, NIBBLETYPE North, NIBBLETYPE East, NIBBLETYPE South, NIBBLETYPE West, bool AssertIfNotMatched = false>
+class cMetaRotater : public Base
+{
+public:
+
+ cMetaRotater(BLOCKTYPE a_BlockType) :
+ Base(a_BlockType)
+ {}
+
+ virtual ~cMetaRotater() {}
+
+ virtual NIBBLETYPE MetaRotateCCW(NIBBLETYPE a_Meta) override;
+ virtual NIBBLETYPE MetaRotateCW(NIBBLETYPE a_Meta) override;
+ virtual NIBBLETYPE MetaMirrorXY(NIBBLETYPE a_Meta) override;
+ virtual NIBBLETYPE MetaMirrorYZ(NIBBLETYPE a_Meta) override;
+};
+
+
+
+
+
+template<class Base, NIBBLETYPE BitMask, NIBBLETYPE North, NIBBLETYPE East, NIBBLETYPE South, NIBBLETYPE West, bool AssertIfNotMatched>
+NIBBLETYPE cMetaRotater<Base, BitMask, North, East, South, West, AssertIfNotMatched>::MetaRotateCW(NIBBLETYPE a_Meta)
+{
+ NIBBLETYPE OtherMeta = a_Meta & (~BitMask);
+ switch (a_Meta & BitMask)
+ {
+ case South: return West | OtherMeta;
+ case West: return North | OtherMeta;
+ case North: return East | OtherMeta;
+ case East: return South | OtherMeta;
+ }
+ if (AssertIfNotMatched)
+ {
+ ASSERT(!"Invalid Meta value");
+ }
+ return a_Meta;
+}
+
+
+
+
+
+template<class Base, NIBBLETYPE BitMask, NIBBLETYPE North, NIBBLETYPE East, NIBBLETYPE South, NIBBLETYPE West, bool AssertIfNotMatched>
+NIBBLETYPE cMetaRotater<Base, BitMask, North, East, South, West, AssertIfNotMatched>::MetaRotateCCW(NIBBLETYPE a_Meta)
+{
+ NIBBLETYPE OtherMeta = a_Meta & (~BitMask);
+ switch (a_Meta & BitMask)
+ {
+ case South: return East | OtherMeta;
+ case East: return North | OtherMeta;
+ case North: return West | OtherMeta;
+ case West: return South | OtherMeta;
+ }
+ if (AssertIfNotMatched)
+ {
+ ASSERT(!"Invalid Meta value");
+ }
+ return a_Meta;
+}
+
+
+
+
+
+template<class Base, NIBBLETYPE BitMask, NIBBLETYPE North, NIBBLETYPE East, NIBBLETYPE South, NIBBLETYPE West, bool AssertIfNotMatched>
+NIBBLETYPE cMetaRotater<Base, BitMask, North, East, South, West, AssertIfNotMatched>::MetaMirrorXY(NIBBLETYPE a_Meta)
+{
+ NIBBLETYPE OtherMeta = a_Meta & (~BitMask);
+ switch (a_Meta & BitMask)
+ {
+ case South: return North | OtherMeta;
+ case North: return South | OtherMeta;
+ }
+ // Not Facing North or South; No change.
+ return a_Meta;
+}
+
+
+
+
+
+template<class Base, NIBBLETYPE BitMask, NIBBLETYPE North, NIBBLETYPE East, NIBBLETYPE South, NIBBLETYPE West, bool AssertIfNotMatched>
+NIBBLETYPE cMetaRotater<Base, BitMask, North, East, South, West, AssertIfNotMatched>::MetaMirrorYZ(NIBBLETYPE a_Meta)
+{
+ NIBBLETYPE OtherMeta = a_Meta & (~BitMask);
+ switch (a_Meta & BitMask)
+ {
+ case West: return East | OtherMeta;
+ case East: return West | OtherMeta;
+ }
+ // Not Facing East or West; No change.
+ return a_Meta;
+}
+
+
+
+
diff --git a/src/ClientHandle.cpp b/src/ClientHandle.cpp
index 53c859721..b08c029c0 100644
--- a/src/ClientHandle.cpp
+++ b/src/ClientHandle.cpp
@@ -555,12 +555,25 @@ void cClientHandle::HandlePluginMessage(const AString & a_Channel, const AString
}
else if (a_Channel == "REGISTER")
{
+ if (HasPluginChannel(a_Channel))
+ {
+ SendPluginMessage("UNREGISTER", a_Channel);
+ return; // Can't register again if already taken - kinda defeats the point of plugin messaging!
+ }
+
RegisterPluginChannels(BreakApartPluginChannels(a_Message));
}
else if (a_Channel == "UNREGISTER")
{
UnregisterPluginChannels(BreakApartPluginChannels(a_Message));
}
+ else if (!HasPluginChannel(a_Channel))
+ {
+ // Ignore if client sent something but didn't register the channel first
+ LOGD("Player %s sent a plugin message on channel \"%s\", but didn't REGISTER it first", GetUsername().c_str(), a_Channel.c_str());
+ SendPluginMessage("UNREGISTER", a_Channel);
+ return;
+ }
cPluginManager::Get()->CallHookPluginMessage(*this, a_Channel, a_Message);
}
@@ -1453,7 +1466,7 @@ bool cClientHandle::HandleHandshake(const AString & a_Username)
-void cClientHandle::HandleEntityAction(int a_EntityID, char a_ActionID)
+void cClientHandle::HandleEntityCrouch(int a_EntityID, bool a_IsCrouching)
{
if (a_EntityID != m_Player->GetUniqueID())
{
@@ -1461,35 +1474,37 @@ void cClientHandle::HandleEntityAction(int a_EntityID, char a_ActionID)
return;
}
- switch (a_ActionID)
+ m_Player->SetCrouch(a_IsCrouching);
+}
+
+
+
+
+
+void cClientHandle::HandleEntityLeaveBed(int a_EntityID)
+{
+ if (a_EntityID != m_Player->GetUniqueID())
{
- case 1: // Crouch
- {
- m_Player->SetCrouch(true);
- break;
- }
- case 2: // Uncrouch
- {
- m_Player->SetCrouch(false);
- break;
- }
- case 3: // Leave bed
- {
- m_Player->GetWorld()->BroadcastEntityAnimation(*m_Player, 2);
- break;
- }
- case 4: // Start sprinting
- {
- m_Player->SetSprint(true);
- break;
- }
- case 5: // Stop sprinting
- {
- m_Player->SetSprint(false);
- SendPlayerMaxSpeed();
- break;
- }
+ // We should only receive entity actions from the entity that is performing the action
+ return;
+ }
+
+ m_Player->GetWorld()->BroadcastEntityAnimation(*m_Player, 2);
+}
+
+
+
+
+
+void cClientHandle::HandleEntitySprinting(int a_EntityID, bool a_IsSprinting)
+{
+ if (a_EntityID != m_Player->GetUniqueID())
+ {
+ // We should only receive entity actions from the entity that is performing the action
+ return;
}
+
+ m_Player->SetSprint(a_IsSprinting);
}
diff --git a/src/ClientHandle.h b/src/ClientHandle.h
index 194533402..035fadfe4 100644
--- a/src/ClientHandle.h
+++ b/src/ClientHandle.h
@@ -188,7 +188,9 @@ public:
void HandleChat (const AString & a_Message);
void HandleCreativeInventory(short a_SlotNum, const cItem & a_HeldItem);
void HandleDisconnect (const AString & a_Reason);
- void HandleEntityAction (int a_EntityID, char a_ActionID);
+ void HandleEntityCrouch (int a_EntityID, bool a_IsCrouching);
+ void HandleEntityLeaveBed (int a_EntityID);
+ void HandleEntitySprinting (int a_EntityID, bool a_IsSprinting);
/** Called when the protocol handshake has been received (for protocol versions that support it;
otherwise the first instant when a username is received).
diff --git a/src/Entities/Floater.h b/src/Entities/Floater.h
index 865d6dc50..f3b51d77b 100644
--- a/src/Entities/Floater.h
+++ b/src/Entities/Floater.h
@@ -11,7 +11,7 @@
class cFloater :
public cEntity
{
- typedef cFloater super;
+ typedef cEntity super;
public:
//tolua_end
diff --git a/src/Protocol/Protocol125.cpp b/src/Protocol/Protocol125.cpp
index e032e4050..50ebb6d43 100644
--- a/src/Protocol/Protocol125.cpp
+++ b/src/Protocol/Protocol125.cpp
@@ -1375,7 +1375,16 @@ int cProtocol125::ParseEntityAction(void)
{
HANDLE_PACKET_READ(ReadBEInt, int, EntityID);
HANDLE_PACKET_READ(ReadChar, char, ActionID);
- m_Client->HandleEntityAction(EntityID, ActionID);
+
+ switch (ActionID)
+ {
+ case 1: m_Client->HandleEntityCrouch(EntityID, true); break; // Crouch
+ case 2: m_Client->HandleEntityCrouch(EntityID, false); break; // Uncrouch
+ case 3: m_Client->HandleEntityLeaveBed(EntityID); break; // Leave Bed
+ case 4: m_Client->HandleEntitySprinting(EntityID, true); break; // Start sprinting
+ case 5: m_Client->HandleEntitySprinting(EntityID, false); break; // Stop sprinting
+ }
+
return PARSE_OK;
}
diff --git a/src/Protocol/Protocol125.h b/src/Protocol/Protocol125.h
index 66f3227b0..aca24c03a 100644
--- a/src/Protocol/Protocol125.h
+++ b/src/Protocol/Protocol125.h
@@ -11,6 +11,7 @@
#include "Protocol.h"
#include "../ByteBuffer.h"
+#include "../Entities/Painting.h"
diff --git a/src/Protocol/Protocol16x.cpp b/src/Protocol/Protocol16x.cpp
index cfa27b3c4..f6ec0a199 100644
--- a/src/Protocol/Protocol16x.cpp
+++ b/src/Protocol/Protocol16x.cpp
@@ -184,7 +184,16 @@ int cProtocol161::ParseEntityAction(void)
HANDLE_PACKET_READ(ReadBEInt, int, EntityID);
HANDLE_PACKET_READ(ReadChar, char, ActionID);
HANDLE_PACKET_READ(ReadBEInt, int, UnknownHorseVal);
- m_Client->HandleEntityAction(EntityID, ActionID);
+
+ switch (ActionID)
+ {
+ case 1: m_Client->HandleEntityCrouch(EntityID, true); break; // Crouch
+ case 2: m_Client->HandleEntityCrouch(EntityID, false); break; // Uncrouch
+ case 3: m_Client->HandleEntityLeaveBed(EntityID); break; // Leave Bed
+ case 4: m_Client->HandleEntitySprinting(EntityID, true); break; // Start sprinting
+ case 5: m_Client->HandleEntitySprinting(EntityID, false); break; // Stop sprinting
+ }
+
return PARSE_OK;
}
diff --git a/src/Protocol/Protocol17x.cpp b/src/Protocol/Protocol17x.cpp
index 8e0d33227..a72da776d 100644
--- a/src/Protocol/Protocol17x.cpp
+++ b/src/Protocol/Protocol17x.cpp
@@ -1732,7 +1732,15 @@ void cProtocol172::HandlePacketEntityAction(cByteBuffer & a_ByteBuffer)
HANDLE_READ(a_ByteBuffer, ReadBEInt, int, PlayerID);
HANDLE_READ(a_ByteBuffer, ReadByte, Byte, Action);
HANDLE_READ(a_ByteBuffer, ReadBEInt, int, JumpBoost);
- m_Client->HandleEntityAction(PlayerID, Action);
+
+ switch (Action)
+ {
+ case 1: m_Client->HandleEntityCrouch(PlayerID, true); break; // Crouch
+ case 2: m_Client->HandleEntityCrouch(PlayerID, false); break; // Uncrouch
+ case 3: m_Client->HandleEntityLeaveBed(PlayerID); break; // Leave Bed
+ case 4: m_Client->HandleEntitySprinting(PlayerID, true); break; // Start sprinting
+ case 5: m_Client->HandleEntitySprinting(PlayerID, false); break; // Stop sprinting
+ }
}