52    public static function getNetworkTypeId() : 
string{ 
return EntityIds::FIREWORKS_ROCKET; }
 
   54    protected int $maxFlightTimeTicks;
 
   57    protected array $explosions = [];
 
   63        if($maxFlightTimeTicks < 0){
 
   64            throw new \InvalidArgumentException(
"Life ticks cannot be negative");
 
   66        $this->maxFlightTimeTicks = $maxFlightTimeTicks;
 
   69        parent::__construct($location, $nbt);
 
 
   82        return $this->maxFlightTimeTicks;
 
 
   91        if($maxFlightTimeTicks < 0){
 
   92            throw new \InvalidArgumentException(
"Max flight time ticks cannot be negative");
 
   94        $this->maxFlightTimeTicks = $maxFlightTimeTicks;
 
 
  102        return $this->explosions;
 
 
  112        $this->explosions = $explosions;
 
 
  117        parent::onFirstUpdate($currentTick);
 
 
  122    protected function entityBaseTick(
int $tickDiff = 1) : bool{
 
  123        $hasUpdate = parent::entityBaseTick($tickDiff);
 
  125        if(!$this->isFlaggedForDespawn()){
 
  129            if($this->ticksLived < 60){
 
  130                $this->addMotion($this->motion->x * 0.15, 0.04, $this->motion->z * 0.15);
 
  133            if($this->ticksLived >= $this->maxFlightTimeTicks){
 
  134                $this->flagForDespawn();
 
  142    public function explode() : void{
 
  143        if(($explosionCount = count($this->explosions)) !== 0){
 
  144            $this->broadcastAnimation(
new FireworkParticlesAnimation($this));
 
  145            foreach($this->explosions as $explosion){
 
  146                $this->broadcastSound($explosion->getType()->getExplosionSound());
 
  147                if($explosion->willTwinkle()){
 
  148                    $this->broadcastSound(
new FireworkCrackleSound());
 
  152            $force = ($explosionCount * 2) + 5;
 
  153            $world = $this->getWorld();
 
  154            foreach($world->getCollidingEntities($this->getBoundingBox()->expandedCopy(5, 5, 5), $this) as $entity){
 
  155                if(!$entity instanceof Living){
 
  159                $position = $entity->getPosition();
 
  160                $distance = $position->distanceSquared($this->location);
 
  167                $height = $entity->getBoundingBox()->getYLength();
 
  168                for($i = 0; $i < 2; $i++){
 
  169                    $target = $position->add(0, 0.5 * $i * $height, 0);
 
  170                    foreach(VoxelRayTrace::betweenPoints($this->location, $target) as $blockPos){
 
  171                        if($world->getBlock($blockPos)->calculateIntercept($this->location, $target) !== 
null){
 
  177                    $damage = $force * sqrt((5 - $position->distance($this->location)) / 5);
 
  178                    $ev = 
new EntityDamageByEntityEvent($this, $entity, EntityDamageEvent::CAUSE_ENTITY_EXPLOSION, $damage);
 
  179                    $entity->attack($ev);
 
  186    public function canBeCollidedWith() : bool{
 
  190    protected function syncNetworkData(EntityMetadataCollection $properties) : void{
 
  191        parent::syncNetworkData($properties);
 
  193        $explosions = 
new ListTag();
 
  194        foreach($this->explosions as $explosion){
 
  195            $explosions->push($explosion->toCompoundTag());
 
  197        $fireworksData = CompoundTag::create()
 
  198            ->setTag(FireworkItem::TAG_FIREWORK_DATA, CompoundTag::create()
 
  199                ->setTag(FireworkItem::TAG_EXPLOSIONS, $explosions)
 
  202        $properties->setCompoundTag(EntityMetadataProperties::FIREWORK_ITEM, 
new CacheableNbt($fireworksData));