Fixed block picking, added PlayerBlockPickEvent

This commit is contained in:
Dylan K. Taylor 2017-09-23 14:42:28 +01:00
parent 826ec90856
commit 178dd1b981
3 changed files with 86 additions and 13 deletions

View File

@ -46,6 +46,7 @@ use pocketmine\event\player\PlayerAchievementAwardedEvent;
use pocketmine\event\player\PlayerAnimationEvent;
use pocketmine\event\player\PlayerBedEnterEvent;
use pocketmine\event\player\PlayerBedLeaveEvent;
use pocketmine\event\player\PlayerBlockPickEvent;
use pocketmine\event\player\PlayerChatEvent;
use pocketmine\event\player\PlayerCommandPreprocessEvent;
use pocketmine\event\player\PlayerDeathEvent;
@ -2521,22 +2522,35 @@ class Player extends Human implements CommandSender, ChunkLoader, IPlayer{
}
public function handleBlockPickRequest(BlockPickRequestPacket $packet) : bool{
if($this->isCreative()){
$tile = $this->getLevel()->getTile($this->temporalVector->setComponents($packet->tileX, $packet->tileY, $packet->tileZ));
if($tile instanceof Tile){ //TODO: check if the held item matches the target tile
$block = $this->level->getBlock($this->temporalVector->setComponents($packet->blockX, $packet->blockY, $packet->blockZ));
//TODO: this doesn't handle crops correctly (need more API work)
$item = Item::get($block->getItemId(), $block->getDamage() & $block->getVariantBitmask());
if($packet->addUserData){
$tile = $this->getLevel()->getTile($block);
if($tile instanceof Tile){
$nbt = $tile->getCleanedNBT();
if($nbt instanceof CompoundTag){
$item = $this->inventory->getItemInHand();
$item->setCustomBlockData($nbt);
$item->setLore(["+(DATA)"]);
$this->inventory->setItemInHand($item);
}
}
}
$ev = new PlayerBlockPickEvent($this, $block, $item);
if(!$this->isCreative(true)){
$this->server->getLogger()->debug("Got block-pick request from " . $this->getName() . " when not in creative mode (gamemode " . $this->getGamemode() . ")");
$ev->setCancelled();
}
$this->server->getPluginManager()->callEvent($ev);
if(!$ev->isCancelled()){
$this->inventory->setItemInHand($ev->getResultItem());
}
return true;
}
}
return false;
}
public function handlePlayerAction(PlayerActionPacket $packet) : bool{

View File

@ -0,0 +1,59 @@
<?php
/*
*
* ____ _ _ __ __ _ __ __ ____
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* @author PocketMine Team
* @link http://www.pocketmine.net/
*
*
*/
declare(strict_types=1);
namespace pocketmine\event\player;
use pocketmine\block\Block;
use pocketmine\event\Cancellable;
use pocketmine\item\Item;
use pocketmine\Player;
/**
* Called when a player middle-clicks on a block to get an item in creative mode.
*/
class PlayerBlockPickEvent extends PlayerEvent implements Cancellable{
public static $handlerList = null;
/** @var Block */
private $blockClicked;
/** @var Item */
private $resultItem;
public function __construct(Player $player, Block $blockClicked, Item $resultItem){
$this->player = $player;
$this->blockClicked = $blockClicked;
$this->resultItem = $resultItem;
}
public function getBlock() : Block{
return $this->blockClicked;
}
public function getResultItem() : Item{
return $this->resultItem;
}
public function setResultItem(Item $item) : void{
$this->resultItem = clone $item;
}
}

View File

@ -33,24 +33,24 @@ class BlockPickRequestPacket extends DataPacket{
const NETWORK_ID = ProtocolInfo::BLOCK_PICK_REQUEST_PACKET;
/** @var int */
public $tileX;
public $blockX;
/** @var int */
public $tileY;
public $blockY;
/** @var int */
public $tileZ;
public $blockZ;
/** @var bool */
public $addUserData = false;
/** @var int */
public $hotbarSlot;
protected function decodePayload(){
$this->getSignedBlockPosition($this->tileX, $this->tileY, $this->tileZ);
$this->getSignedBlockPosition($this->blockX, $this->blockY, $this->blockZ);
$this->addUserData = $this->getBool();
$this->hotbarSlot = $this->getByte();
}
protected function encodePayload(){
$this->putSignedBlockPosition($this->tileX, $this->tileY, $this->tileZ);
$this->putSignedBlockPosition($this->blockX, $this->blockY, $this->blockZ);
$this->putBool($this->addUserData);
$this->putByte($this->hotbarSlot);
}