diff --git a/src/pocketmine/block/BlockFactory.php b/src/pocketmine/block/BlockFactory.php index e9a2f3c47..ac892a91d 100644 --- a/src/pocketmine/block/BlockFactory.php +++ b/src/pocketmine/block/BlockFactory.php @@ -26,6 +26,7 @@ namespace pocketmine\block; use pocketmine\block\utils\DyeColor; use pocketmine\block\utils\InvalidBlockStateException; use pocketmine\block\utils\PillarRotationTrait; +use pocketmine\block\utils\SlabType; use pocketmine\block\utils\TreeType; use pocketmine\item\Item; use pocketmine\level\Position; @@ -374,7 +375,7 @@ class BlockFactory{ } foreach($slabTypes as $type){ self::registerBlock($type); - self::registerBlock(new DoubleSlab($type->getDoubleSlabId(), $type->getId(), $type->getVariant())); + self::registerBlock((clone $type)->setSlabType(SlabType::double())); //flattening hack } static $wallTypes = [ diff --git a/src/pocketmine/block/DoubleSlab.php b/src/pocketmine/block/DoubleSlab.php deleted file mode 100644 index 41ad6a0d7..000000000 --- a/src/pocketmine/block/DoubleSlab.php +++ /dev/null @@ -1,79 +0,0 @@ -singleId = $singleId; - } - - protected function getSingle() : Block{ - return BlockFactory::get($this->singleId, $this->variant); - } - - public function getHardness() : float{ - return $this->getSingle()->getHardness(); - } - - public function getToolType() : int{ - return $this->getSingle()->getToolType(); - } - - public function getToolHarvestLevel() : int{ - return $this->getSingle()->getToolHarvestLevel(); - } - - public function getFlameEncouragement() : int{ - return $this->getSingle()->getFlameEncouragement(); - } - - public function getFlammability() : int{ - return $this->getSingle()->getFlammability(); - } - - public function getName() : string{ - return "Double " . $this->getSingle()->getName(); - } - - public function getDropsForCompatibleTool(Item $item) : array{ - return [ - ItemFactory::get($this->singleId, $this->variant, 2) - ]; - } - - public function isAffectedBySilkTouch() : bool{ - return false; - } - - public function getPickedItem() : Item{ - return ItemFactory::get($this->singleId, $this->getVariant()); - } -} diff --git a/src/pocketmine/block/Slab.php b/src/pocketmine/block/Slab.php index d293c2768..1b34e5f5d 100644 --- a/src/pocketmine/block/Slab.php +++ b/src/pocketmine/block/Slab.php @@ -23,6 +23,7 @@ declare(strict_types=1); namespace pocketmine\block; +use pocketmine\block\utils\SlabType; use pocketmine\item\Item; use pocketmine\math\AxisAlignedBB; use pocketmine\math\Facing; @@ -33,32 +34,57 @@ abstract class Slab extends Transparent{ /** @var int */ protected $doubleId; - /** @var bool */ - protected $top = false; + /** @var SlabType */ + protected $slabType; public function __construct(int $id, int $doubleId, int $variant = 0, ?string $name = null){ - parent::__construct($id, $variant, $name . " Slab"); + parent::__construct($id, $variant, $name . " Slab", $id); $this->doubleId = $doubleId; + $this->slabType = SlabType::bottom(); + } + + public function getId() : int{ + return $this->slabType === SlabType::double() ? $this->doubleId : parent::getId(); } protected function writeStateToMeta() : int{ - return ($this->top ? 0x08 : 0); + if($this->slabType !== SlabType::double()){ + return ($this->slabType === SlabType::top() ? 0x08 : 0); + } + return 0; } public function readStateFromMeta(int $meta) : void{ - $this->top = ($meta & 0x08) !== 0; + if($this->slabType !== SlabType::double()){ + $this->slabType = ($meta & 0x08) !== 0 ? SlabType::top() : SlabType::bottom(); + } } public function getStateBitmask() : int{ return 0b1000; } - public function getDoubleSlabId() : int{ - return $this->doubleId; + public function isTransparent() : bool{ + return $this->slabType !== SlabType::double(); } - protected function getDouble() : Block{ - return BlockFactory::get($this->doubleId, $this->variant); + /** + * Returns the type of slab block. + * + * @return SlabType + */ + public function getSlabType() : SlabType{ + return $this->slabType; + } + + /** + * @param SlabType $slabType + * + * @return $this + */ + public function setSlabType(SlabType $slabType) : self{ + $this->slabType = $slabType; + return $this; } public function canBePlacedAt(Block $blockReplace, Vector3 $clickVector, int $face, bool $isClickedBlock) : bool{ @@ -66,8 +92,8 @@ abstract class Slab extends Transparent{ return true; } - if($blockReplace instanceof Slab and $blockReplace->isSameType($this)){ - if($blockReplace->top){ //Trying to combine with top slab + if($blockReplace instanceof Slab and $blockReplace->slabType !== SlabType::double() and $blockReplace->isSameType($this)){ + if($blockReplace->slabType === SlabType::top()){ //Trying to combine with top slab return $clickVector->y <= 0.5 or (!$isClickedBlock and $face === Facing::UP); }else{ return $clickVector->y >= 0.5 or (!$isClickedBlock and $face === Facing::DOWN); @@ -80,27 +106,35 @@ abstract class Slab extends Transparent{ public function place(Item $item, Block $blockReplace, Block $blockClicked, int $face, Vector3 $clickVector, Player $player = null) : bool{ /* note these conditions can't be merged, since one targets clicked and the other replace */ - if($blockClicked instanceof Slab and $blockClicked->isSameType($this) and ( - ($face === Facing::DOWN and $blockClicked->top) or //Bottom face of top slab - ($face === Facing::UP and !$blockClicked->top) //Top face of bottom slab + if($blockClicked instanceof Slab and $blockClicked->slabType !== SlabType::double() and $blockClicked->isSameType($this) and ( + ($face === Facing::DOWN and $blockClicked->slabType === SlabType::top()) or + ($face === Facing::UP and $blockClicked->slabType === SlabType::bottom()) )){ - return $this->level->setBlock($blockClicked, $this->getDouble()); + $this->slabType = SlabType::double(); + return $this->level->setBlock($blockClicked, $this); } - if($blockReplace instanceof Slab and $blockReplace->isSameType($this) and ( - ($blockReplace->top and ($clickVector->y <= 0.5 or $face === Facing::UP)) or - (!$blockReplace->top and ($clickVector->y >= 0.5 or $face === Facing::DOWN)) + if($blockReplace instanceof Slab and $blockReplace->slabType !== SlabType::double() and $blockReplace->isSameType($this) and ( + ($blockReplace->slabType === SlabType::top() and ($clickVector->y <= 0.5 or $face === Facing::UP)) or + ($blockReplace->slabType === SlabType::bottom() and ($clickVector->y >= 0.5 or $face === Facing::DOWN)) )){ //Clicked in empty half of existing slab - return $this->level->setBlock($blockReplace, $this->getDouble()); + $this->slabType = SlabType::double(); + }else{ + $this->slabType = (($face !== Facing::UP && $clickVector->y > 0.5) || $face === Facing::DOWN) ? SlabType::top() : SlabType::bottom(); } - $this->top = ($face !== Facing::UP && $clickVector->y > 0.5) || $face === Facing::DOWN; - return parent::place($item, $blockReplace, $blockClicked, $face, $clickVector, $player); } protected function recalculateBoundingBox() : ?AxisAlignedBB{ - return AxisAlignedBB::one()->trim($this->top ? Facing::DOWN : Facing::UP, 0.5); + if($this->slabType === SlabType::double()){ + return parent::recalculateBoundingBox(); + } + return AxisAlignedBB::one()->trim($this->slabType === SlabType::top() ? Facing::DOWN : Facing::UP, 0.5); + } + + public function getDropsForCompatibleTool(Item $item) : array{ + return [$this->getItem()->setCount($this->slabType === SlabType::double() ? 2 : 1)]; } } diff --git a/src/pocketmine/block/utils/SlabType.php b/src/pocketmine/block/utils/SlabType.php new file mode 100644 index 000000000..e3ba9d040 --- /dev/null +++ b/src/pocketmine/block/utils/SlabType.php @@ -0,0 +1,58 @@ +name = $name; + } + + public function getName() : string{ + return $this->name; + } +}