mirror of
https://github.com/pmmp/PocketMine-MP.git
synced 2025-10-17 19:50:18 +00:00
Enable various types of interaction to return items to the player, without needing to have a bunch of boilerplate creative mode and held item checks
it became glaringly obvious that this was needed because of #4827 and #4868. this is further needed with the addition of cauldrons.
This commit is contained in:
@@ -1660,9 +1660,10 @@ class World implements ChunkManager{
|
||||
* Tries to break a block using a item, including Player time checks if available
|
||||
* It'll try to lower the durability if Item is a tool, and set it to Air if broken.
|
||||
*
|
||||
* @param Item $item reference parameter (if null, can break anything)
|
||||
* @param Item &$item reference parameter (if null, can break anything)
|
||||
* @param Item[] &$returnedItems Items to be added to the target's inventory (or dropped, if the inventory is full)
|
||||
*/
|
||||
public function useBreakOn(Vector3 $vector, Item &$item = null, ?Player $player = null, bool $createParticles = false) : bool{
|
||||
public function useBreakOn(Vector3 $vector, Item &$item = null, ?Player $player = null, bool $createParticles = false, array &$returnedItems = []) : bool{
|
||||
$vector = $vector->floor();
|
||||
|
||||
$chunkX = $vector->getFloorX() >> Chunk::COORD_BIT_SIZE;
|
||||
@@ -1724,10 +1725,10 @@ class World implements ChunkManager{
|
||||
}
|
||||
|
||||
foreach($affectedBlocks as $t){
|
||||
$this->destroyBlockInternal($t, $item, $player, $createParticles);
|
||||
$this->destroyBlockInternal($t, $item, $player, $createParticles, $returnedItems);
|
||||
}
|
||||
|
||||
$item->onDestroyBlock($target);
|
||||
$item->onDestroyBlock($target, $returnedItems);
|
||||
|
||||
if(count($drops) > 0){
|
||||
$dropPos = $vector->add(0.5, 0.5, 0.5);
|
||||
@@ -1745,12 +1746,15 @@ class World implements ChunkManager{
|
||||
return true;
|
||||
}
|
||||
|
||||
private function destroyBlockInternal(Block $target, Item $item, ?Player $player = null, bool $createParticles = false) : void{
|
||||
/**
|
||||
* @param Item[] &$returnedItems
|
||||
*/
|
||||
private function destroyBlockInternal(Block $target, Item $item, ?Player $player, bool $createParticles, array &$returnedItems) : void{
|
||||
if($createParticles){
|
||||
$this->addParticle($target->getPosition()->add(0.5, 0.5, 0.5), new BlockBreakParticle($target));
|
||||
}
|
||||
|
||||
$target->onBreak($item, $player);
|
||||
$target->onBreak($item, $player, $returnedItems);
|
||||
|
||||
$tile = $this->getTile($target->getPosition());
|
||||
if($tile !== null){
|
||||
@@ -1761,10 +1765,11 @@ class World implements ChunkManager{
|
||||
/**
|
||||
* Uses a item on a position and face, placing it or activating the block
|
||||
*
|
||||
* @param Player|null $player default null
|
||||
* @param bool $playSound Whether to play a block-place sound if the block was placed successfully.
|
||||
* @param Player|null $player default null
|
||||
* @param bool $playSound Whether to play a block-place sound if the block was placed successfully.
|
||||
* @param Item[] &$returnedItems Items to be added to the target's inventory (or dropped if the inventory is full)
|
||||
*/
|
||||
public function useItemOn(Vector3 $vector, Item &$item, int $face, ?Vector3 $clickVector = null, ?Player $player = null, bool $playSound = false) : bool{
|
||||
public function useItemOn(Vector3 $vector, Item &$item, int $face, ?Vector3 $clickVector = null, ?Player $player = null, bool $playSound = false, array &$returnedItems = []) : bool{
|
||||
$blockClicked = $this->getBlock($vector);
|
||||
$blockReplace = $blockClicked->getSide($face);
|
||||
|
||||
@@ -1794,18 +1799,18 @@ class World implements ChunkManager{
|
||||
|
||||
$ev->call();
|
||||
if(!$ev->isCancelled()){
|
||||
if((!$player->isSneaking() || $item->isNull()) && $blockClicked->onInteract($item, $face, $clickVector, $player)){
|
||||
if((!$player->isSneaking() || $item->isNull()) && $blockClicked->onInteract($item, $face, $clickVector, $player, $returnedItems)){
|
||||
return true;
|
||||
}
|
||||
|
||||
$result = $item->onInteractBlock($player, $blockReplace, $blockClicked, $face, $clickVector);
|
||||
$result = $item->onInteractBlock($player, $blockReplace, $blockClicked, $face, $clickVector, $returnedItems);
|
||||
if(!$result->equals(ItemUseResult::NONE())){
|
||||
return $result->equals(ItemUseResult::SUCCESS());
|
||||
}
|
||||
}else{
|
||||
return false;
|
||||
}
|
||||
}elseif($blockClicked->onInteract($item, $face, $clickVector, $player)){
|
||||
}elseif($blockClicked->onInteract($item, $face, $clickVector, $player, $returnedItems)){
|
||||
return true;
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user