pocketmine\entity\Projectile::onUpdate PHP Method

onUpdate() public method

public onUpdate ( $currentTick )
    public function onUpdate($currentTick)
    {
        if ($this->closed) {
            return false;
        }
        $tickDiff = $currentTick - $this->lastUpdate;
        if ($tickDiff <= 0 and !$this->justCreated) {
            return true;
        }
        $this->lastUpdate = $currentTick;
        $hasUpdate = $this->entityBaseTick($tickDiff);
        if ($this->isAlive()) {
            $movingObjectPosition = null;
            if (!$this->isCollided) {
                $this->motionY -= $this->gravity;
            }
            $moveVector = new Vector3($this->x + $this->motionX, $this->y + $this->motionY, $this->z + $this->motionZ);
            $list = $this->getLevel()->getCollidingEntities($this->boundingBox->addCoord($this->motionX, $this->motionY, $this->motionZ)->expand(1, 1, 1), $this);
            $nearDistance = PHP_INT_MAX;
            $nearEntity = null;
            foreach ($list as $entity) {
                if ($entity === $this->shootingEntity and $this->ticksLived < 5) {
                    continue;
                }
                $axisalignedbb = $entity->boundingBox->grow(0.3, 0.3, 0.3);
                $ob = $axisalignedbb->calculateIntercept($this, $moveVector);
                if ($ob === null) {
                    continue;
                }
                $distance = $this->distanceSquared($ob->hitVector);
                if ($distance < $nearDistance) {
                    $nearDistance = $distance;
                    $nearEntity = $entity;
                }
            }
            if ($nearEntity !== null) {
                $movingObjectPosition = MovingObjectPosition::fromEntity($nearEntity);
            }
            if ($movingObjectPosition !== null) {
                if ($movingObjectPosition->entityHit !== null) {
                    $this->server->getPluginManager()->callEvent(new ProjectileHitEvent($this));
                    $motion = sqrt($this->motionX ** 2 + $this->motionY ** 2 + $this->motionZ ** 2);
                    $damage = ceil($motion * $this->damage);
                    if ($this instanceof Arrow and $this->isCritical) {
                        $damage += mt_rand(0, (int) ($damage / 2) + 1);
                    }
                    if ($this->shootingEntity === null) {
                        $ev = new EntityDamageByEntityEvent($this, $movingObjectPosition->entityHit, EntityDamageEvent::CAUSE_PROJECTILE, $damage);
                    } else {
                        $ev = new EntityDamageByChildEntityEvent($this->shootingEntity, $this, $movingObjectPosition->entityHit, EntityDamageEvent::CAUSE_PROJECTILE, $damage);
                    }
                    if ($movingObjectPosition->entityHit->attack($ev->getFinalDamage(), $ev) === true) {
                        if ($this instanceof Arrow and $this->getPotionId() != 0) {
                            foreach (Potion::getEffectsById($this->potionId - 1) as $effect) {
                                $movingObjectPosition->entityHit->addEffect($effect->setDuration($effect->getDuration() / 8));
                            }
                        }
                        $ev->useArmors();
                    }
                    $this->hadCollision = true;
                    if ($this->fireTicks > 0) {
                        $ev = new EntityCombustByEntityEvent($this, $movingObjectPosition->entityHit, 5);
                        $this->server->getPluginManager()->callEvent($ev);
                        if (!$ev->isCancelled()) {
                            $movingObjectPosition->entityHit->setOnFire($ev->getDuration());
                        }
                    }
                    $this->kill();
                    return true;
                }
            }
            $this->move($this->motionX, $this->motionY, $this->motionZ);
            if ($this->isCollided and !$this->hadCollision) {
                $this->hadCollision = true;
                $this->motionX = 0;
                $this->motionY = 0;
                $this->motionZ = 0;
                $this->server->getPluginManager()->callEvent(new ProjectileHitEvent($this));
            } elseif (!$this->isCollided and $this->hadCollision) {
                $this->hadCollision = false;
            }
            if (!$this->onGround or abs($this->motionX) > 1.0E-5 or abs($this->motionY) > 1.0E-5 or abs($this->motionZ) > 1.0E-5) {
                $f = sqrt($this->motionX ** 2 + $this->motionZ ** 2);
                $this->yaw = atan2($this->motionX, $this->motionZ) * 180 / M_PI;
                $this->pitch = atan2($this->motionY, $f) * 180 / M_PI;
                $hasUpdate = true;
            }
            $this->updateMovement();
        }
        return $hasUpdate;
    }

Usage Example

示例#1
0
 public function onUpdate($currentTick)
 {
     if ($this->closed) {
         return false;
     }
     $this->timings->startTiming();
     $hasUpdate = parent::onUpdate($currentTick);
     if ($this->isCollidedVertically && $this->isInsideOfWater()) {
         $this->motionX = 0;
         $this->motionY += 0.01;
         $this->motionZ = 0;
         $this->motionChanged = true;
         $hasUpdate = true;
     } elseif ($this->isCollided && $this->keepMovement === true) {
         $this->motionX = 0;
         $this->motionY = 0;
         $this->motionZ = 0;
         $this->motionChanged = true;
         $this->keepMovement = false;
         $hasUpdate = true;
     }
     if ($this->attractTimer === 0 && mt_rand(0, 100) <= 0.1 * 100) {
         // chance, that a fish bites
         $this->attractTimer = mt_rand(5, 10) * 20;
         // random delay when a fish bites (5-10 seconds)
     } else {
         $this->attractFish();
         $this->attractTimer--;
     }
     $this->timings->stopTiming();
     return $hasUpdate;
 }
All Usage Examples Of pocketmine\entity\Projectile::onUpdate