diff --git a/src/block/tile/BrewingStand.php b/src/block/tile/BrewingStand.php index 9e5c5dd16..d6571f630 100644 --- a/src/block/tile/BrewingStand.php +++ b/src/block/tile/BrewingStand.php @@ -54,7 +54,7 @@ class BrewingStand extends Spawnable implements Container, Nameable{ public function __construct(World $world, Vector3 $pos){ parent::__construct($world, $pos); $this->inventory = new BrewingStandInventory($this->pos); - $this->inventory->addListeners(CallbackInventoryListener::onAnyChange(function(Inventory $unused) : void{ + $this->inventory->getListeners()->add(CallbackInventoryListener::onAnyChange(function(Inventory $unused) : void{ $this->pos->getWorldNonNull()->scheduleDelayedBlockUpdate($this->pos, 1); })); } diff --git a/src/block/tile/ContainerTrait.php b/src/block/tile/ContainerTrait.php index 45711b596..76ebacf31 100644 --- a/src/block/tile/ContainerTrait.php +++ b/src/block/tile/ContainerTrait.php @@ -48,14 +48,14 @@ trait ContainerTrait{ $inventoryTag = $tag->getListTag(Container::TAG_ITEMS); $inventory = $this->getRealInventory(); - $listeners = $inventory->getListeners(); - $inventory->removeListeners(...$listeners); //prevent any events being fired by initialization + $listeners = $inventory->getListeners()->toArray(); + $inventory->getListeners()->remove(...$listeners); //prevent any events being fired by initialization $inventory->clearAll(); /** @var CompoundTag $itemNBT */ foreach($inventoryTag as $itemNBT){ $inventory->setItem($itemNBT->getByte("Slot"), Item::nbtDeserialize($itemNBT)); } - $inventory->addListeners(...$listeners); + $inventory->getListeners()->add(...$listeners); } if($tag->hasTag(Container::TAG_LOCK, StringTag::class)){ diff --git a/src/block/tile/Furnace.php b/src/block/tile/Furnace.php index 2fccc2d5d..ce67b83fc 100644 --- a/src/block/tile/Furnace.php +++ b/src/block/tile/Furnace.php @@ -58,7 +58,7 @@ class Furnace extends Spawnable implements Container, Nameable{ public function __construct(World $world, Vector3 $pos){ parent::__construct($world, $pos); $this->inventory = new FurnaceInventory($this->pos); - $this->inventory->addListeners(CallbackInventoryListener::onAnyChange( + $this->inventory->getListeners()->add(CallbackInventoryListener::onAnyChange( function(Inventory $unused) : void{ $this->pos->getWorldNonNull()->scheduleDelayedBlockUpdate($this->pos, 1); }) diff --git a/src/entity/Human.php b/src/entity/Human.php index ff0a843c7..55518fcf4 100644 --- a/src/entity/Human.php +++ b/src/entity/Human.php @@ -221,8 +221,8 @@ class Human extends Living implements ProjectileSource, InventoryHolder{ $inventoryTag = $nbt->getListTag("Inventory"); if($inventoryTag !== null){ - $armorListeners = $this->armorInventory->getListeners(); - $this->armorInventory->removeListeners(...$armorListeners); + $armorListeners = $this->armorInventory->getListeners()->toArray(); + $this->armorInventory->getListeners()->clear(); /** @var CompoundTag $item */ foreach($inventoryTag as $i => $item){ @@ -236,7 +236,7 @@ class Human extends Living implements ProjectileSource, InventoryHolder{ } } - $this->armorInventory->addListeners(...$armorListeners); + $this->armorInventory->getListeners()->add(...$armorListeners); } $enderChestInventoryTag = $nbt->getListTag("EnderChestInventory"); diff --git a/src/entity/Living.php b/src/entity/Living.php index daa2a69c4..c5cbf8949 100644 --- a/src/entity/Living.php +++ b/src/entity/Living.php @@ -110,7 +110,7 @@ abstract class Living extends Entity{ $this->armorInventory = new ArmorInventory($this); //TODO: load/save armor inventory contents - $this->armorInventory->addListeners(CallbackInventoryListener::onAnyChange( + $this->armorInventory->getListeners()->add(CallbackInventoryListener::onAnyChange( function(Inventory $unused) : void{ foreach($this->getViewers() as $viewer){ $viewer->getNetworkSession()->onMobArmorChange($this); diff --git a/src/inventory/BaseInventory.php b/src/inventory/BaseInventory.php index 63ecb4d8f..38bc601d3 100644 --- a/src/inventory/BaseInventory.php +++ b/src/inventory/BaseInventory.php @@ -23,6 +23,7 @@ declare(strict_types=1); namespace pocketmine\inventory; +use Ds\Set; use pocketmine\item\Item; use pocketmine\item\ItemFactory; use pocketmine\player\Player; @@ -43,11 +44,15 @@ abstract class BaseInventory implements Inventory{ protected $slots; /** @var Player[] */ protected $viewers = []; - /** @var InventoryListener[] */ - protected $listeners = []; + /** + * @var InventoryListener[]|Set + * @phpstan-var Set + */ + protected $listeners; public function __construct(int $size){ $this->slots = new \SplFixedArray($size); + $this->listeners = new Set(); } /** @@ -92,8 +97,8 @@ abstract class BaseInventory implements Inventory{ $oldContents = $this->slots->toArray(); - $listeners = $this->listeners; - $this->listeners = []; + $listeners = $this->listeners->toArray(); + $this->listeners->clear(); $viewers = $this->viewers; $this->viewers = []; @@ -105,7 +110,7 @@ abstract class BaseInventory implements Inventory{ } } - $this->addListeners(...$listeners); //don't directly write, in case listeners were added while operation was in progress + $this->listeners->add(...$listeners); //don't directly write, in case listeners were added while operation was in progress foreach($viewers as $id => $viewer){ $this->viewers[$id] = $viewer; } @@ -372,23 +377,7 @@ abstract class BaseInventory implements Inventory{ return $slot >= 0 and $slot < $this->slots->getSize(); } - public function addListeners(InventoryListener ...$listeners) : void{ - foreach($listeners as $listener){ - $this->listeners[spl_object_id($listener)] = $listener; - } - } - - public function removeListeners(InventoryListener ...$listeners) : void{ - foreach($listeners as $listener){ - unset($this->listeners[spl_object_id($listener)]); - } - } - - public function removeAllListeners() : void{ - $this->listeners = []; - } - - public function getListeners() : array{ + public function getListeners() : Set{ return $this->listeners; } } diff --git a/src/inventory/Inventory.php b/src/inventory/Inventory.php index 95ea5001a..e2226f82f 100644 --- a/src/inventory/Inventory.php +++ b/src/inventory/Inventory.php @@ -26,6 +26,7 @@ declare(strict_types=1); */ namespace pocketmine\inventory; +use Ds\Set; use pocketmine\item\Item; use pocketmine\player\Player; @@ -155,19 +156,8 @@ interface Inventory{ public function slotExists(int $slot) : bool; /** - * @param InventoryListener ...$listeners + * @return InventoryListener[]|Set + * @phpstan-return Set */ - public function addListeners(InventoryListener ...$listeners) : void; - - /** - * @param InventoryListener ...$listeners - */ - public function removeListeners(InventoryListener ...$listeners) : void; - - public function removeAllListeners() : void; - - /** - * @return InventoryListener[] - */ - public function getListeners() : array; + public function getListeners() : Set; } diff --git a/src/inventory/InventoryListener.php b/src/inventory/InventoryListener.php index da8274661..c5040993f 100644 --- a/src/inventory/InventoryListener.php +++ b/src/inventory/InventoryListener.php @@ -29,8 +29,7 @@ use pocketmine\item\Item; * Classes implementing this interface can be injected into inventories to receive notifications when content changes * occur. * @see CallbackInventoryListener for a closure-based listener - * @see Inventory::addListeners() - * @see Inventory::removeListeners() + * @see Inventory::getListeners() */ interface InventoryListener{