diff --git a/src/entity/Entity.php b/src/entity/Entity.php index d49e9c0d5..aa5d51118 100644 --- a/src/entity/Entity.php +++ b/src/entity/Entity.php @@ -55,6 +55,7 @@ use pocketmine\timings\Timings; use pocketmine\timings\TimingsHandler; use pocketmine\world\format\Chunk; use pocketmine\world\Position; +use pocketmine\world\sound\Sound; use pocketmine\world\World; use function abs; use function array_map; @@ -214,6 +215,8 @@ abstract class Entity{ protected $immobile = false; /** @var bool */ protected $invisible = false; + /** @var bool */ + protected $silent = false; /** @var int|null */ protected $ownerId = null; @@ -356,6 +359,14 @@ abstract class Entity{ $this->invisible = $value; } + public function isSilent() : bool{ + return $this->silent; + } + + public function setSilent(bool $value = true) : void{ + $this->silent = $value; + } + /** * Returns whether the entity is able to climb blocks such as ladders or vines. */ @@ -1656,6 +1667,7 @@ abstract class Entity{ $properties->setGenericFlag(EntityMetadataFlags::HAS_COLLISION, true); $properties->setGenericFlag(EntityMetadataFlags::IMMOBILE, $this->immobile); $properties->setGenericFlag(EntityMetadataFlags::INVISIBLE, $this->invisible); + $properties->setGenericFlag(EntityMetadataFlags::SILENT, $this->silent); $properties->setGenericFlag(EntityMetadataFlags::ONFIRE, $this->isOnFire()); $properties->setGenericFlag(EntityMetadataFlags::WALLCLIMBING, $this->canClimbWalls); } @@ -1667,6 +1679,16 @@ abstract class Entity{ $this->server->broadcastPackets($targets ?? $this->getViewers(), $animation->encode()); } + /** + * Broadcasts a sound caused by the entity. If the entity is considered "silent", the sound will be dropped. + * @param Player[]|null $targets + */ + public function broadcastSound(Sound $sound, ?array $targets = null) : void{ + if(!$this->silent){ + $this->server->broadcastPackets($targets ?? $this->getViewers(), $sound->encode($this->location)); + } + } + public function __destruct(){ $this->close(); } diff --git a/src/entity/ExperienceManager.php b/src/entity/ExperienceManager.php index 223ad5ee1..457187745 100644 --- a/src/entity/ExperienceManager.php +++ b/src/entity/ExperienceManager.php @@ -87,7 +87,7 @@ class ExperienceManager{ if($playSound){ $newLevel = $this->getXpLevel(); if((int) ($newLevel / 5) > (int) ($oldLevel / 5)){ - $this->entity->getWorld()->addSound($this->entity->getPosition(), new XpLevelUpSound($newLevel)); + $this->entity->broadcastSound(new XpLevelUpSound($newLevel)); } } @@ -161,9 +161,9 @@ class ExperienceManager{ if($playSound){ $newLevel = $this->getXpLevel(); if((int) ($newLevel / 5) > (int) ($oldLevel / 5)){ - $this->entity->getWorld()->addSound($this->entity->getPosition(), new XpLevelUpSound($newLevel)); + $this->entity->broadcastSound(new XpLevelUpSound($newLevel)); }elseif($this->getCurrentTotalXp() > $oldTotal){ - $this->entity->getWorld()->addSound($this->entity->getPosition(), new XpCollectSound()); + $this->entity->broadcastSound(new XpCollectSound()); } } diff --git a/src/entity/Human.php b/src/entity/Human.php index 39a671e09..daac796a2 100644 --- a/src/entity/Human.php +++ b/src/entity/Human.php @@ -296,7 +296,7 @@ class Human extends Living implements ProjectileSource, InventoryHolder{ $this->effectManager->add(new EffectInstance(VanillaEffects::ABSORPTION(), 5 * 20, 1)); $this->broadcastAnimation(new TotemUseAnimation($this)); - $this->getWorld()->addSound($this->location->add(0, $this->eyeHeight, 0), new TotemUseSound()); + $this->broadcastSound(new TotemUseSound()); $hand = $this->inventory->getItemInHand(); if($hand instanceof Totem){ diff --git a/src/entity/Living.php b/src/entity/Living.php index 2926cce53..18b86fe08 100644 --- a/src/entity/Living.php +++ b/src/entity/Living.php @@ -300,7 +300,7 @@ abstract class Living extends Entity{ $ev = new EntityDamageEvent($this, EntityDamageEvent::CAUSE_FALL, $damage); $this->attack($ev); - $this->getWorld()->addSound($this->location, $damage > 4 ? + $this->broadcastSound($damage > 4 ? new EntityLongFallSound($this) : new EntityShortFallSound($this) ); @@ -312,7 +312,7 @@ abstract class Living extends Entity{ $fallBlock = $this->getWorld()->getBlock($fallBlockPos); } if($fallBlock->getId() !== BlockLegacyIds::AIR){ - $this->getWorld()->addSound($this->location, new EntityLandSound($this, $fallBlock)); + $this->broadcastSound(new EntityLandSound($this, $fallBlock)); } } } @@ -433,7 +433,7 @@ abstract class Living extends Entity{ private function damageItem(Durable $item, int $durabilityRemoved) : void{ $item->applyDamage($durabilityRemoved); if($item->isBroken()){ - $this->getWorld()->addSound($this->location, new ItemBreakSound()); + $this->broadcastSound(new ItemBreakSound()); } } diff --git a/src/entity/object/PrimedTNT.php b/src/entity/object/PrimedTNT.php index 13c4ab850..48affa0ba 100644 --- a/src/entity/object/PrimedTNT.php +++ b/src/entity/object/PrimedTNT.php @@ -74,7 +74,7 @@ class PrimedTNT extends Entity implements Explosive{ $this->fuse = $nbt->getShort("Fuse", 80); - $this->getWorld()->addSound($this->location, new IgniteSound()); + $this->broadcastSound(new IgniteSound()); } public function canCollideWith(Entity $entity) : bool{ diff --git a/src/entity/projectile/Arrow.php b/src/entity/projectile/Arrow.php index 39f62fa91..503f55cf4 100644 --- a/src/entity/projectile/Arrow.php +++ b/src/entity/projectile/Arrow.php @@ -137,7 +137,7 @@ class Arrow extends Projectile{ protected function onHit(ProjectileHitEvent $event) : void{ $this->setCritical(false); - $this->getWorld()->addSound($this->location, new ArrowHitSound()); + $this->broadcastSound(new ArrowHitSound()); } protected function onHitBlock(Block $blockHit, RayTraceResult $hitResult) : void{ diff --git a/src/entity/projectile/ExperienceBottle.php b/src/entity/projectile/ExperienceBottle.php index e6c026af3..eb69b0edf 100644 --- a/src/entity/projectile/ExperienceBottle.php +++ b/src/entity/projectile/ExperienceBottle.php @@ -40,7 +40,7 @@ class ExperienceBottle extends Throwable{ public function onHit(ProjectileHitEvent $event) : void{ $this->getWorld()->addParticle($this->location, new PotionSplashParticle(PotionSplashParticle::DEFAULT_COLOR())); - $this->getWorld()->addSound($this->location, new PotionSplashSound()); + $this->broadcastSound(new PotionSplashSound()); $this->getWorld()->dropExperience($this->location, mt_rand(3, 11)); } diff --git a/src/entity/projectile/SplashPotion.php b/src/entity/projectile/SplashPotion.php index f4f0c1443..a800ee555 100644 --- a/src/entity/projectile/SplashPotion.php +++ b/src/entity/projectile/SplashPotion.php @@ -92,7 +92,7 @@ class SplashPotion extends Throwable{ } $this->getWorld()->addParticle($this->location, $particle); - $this->getWorld()->addSound($this->location, new PotionSplashSound()); + $this->broadcastSound(new PotionSplashSound()); if($hasEffects){ if(!$this->willLinger()){