package net.minecraft.server; import com.google.common.collect.Lists; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import java.util.UUID; import javax.annotation.Nullable; public class EntityShulkerBullet extends Entity { private EntityLiving shooter; private Entity target; @Nullable private EnumDirection c; private int d; private double e; private double f; private double g; @Nullable private UUID h; private BlockPosition at; @Nullable private UUID au; private BlockPosition av; public EntityShulkerBullet(World world) { super(world); this.setSize(0.3125F, 0.3125F); this.noclip = true; } public SoundCategory bC() { return SoundCategory.HOSTILE; } public EntityShulkerBullet(World world, EntityLiving entityliving, Entity entity, EnumDirection.EnumAxis enumdirection_enumaxis) { this(world); this.shooter = entityliving; BlockPosition blockposition = new BlockPosition(entityliving); double d0 = (double) blockposition.getX() + 0.5D; double d1 = (double) blockposition.getY() + 0.5D; double d2 = (double) blockposition.getZ() + 0.5D; this.setPositionRotation(d0, d1, d2, this.yaw, this.pitch); this.target = entity; this.c = EnumDirection.UP; this.a(enumdirection_enumaxis); projectileSource = (org.bukkit.entity.LivingEntity) entityliving.getBukkitEntity(); // CraftBukkit } // CraftBukkit start public EntityLiving getShooter() { return this.shooter; } public void setShooter(EntityLiving e) { this.shooter = e; } public Entity getTarget() { return this.target; } public void setTarget(Entity e) { this.target = e; this.c = EnumDirection.UP; this.a(EnumDirection.EnumAxis.X); } // CraftBukkit end protected void b(NBTTagCompound nbttagcompound) { BlockPosition blockposition; NBTTagCompound nbttagcompound1; if (this.shooter != null) { blockposition = new BlockPosition(this.shooter); nbttagcompound1 = GameProfileSerializer.a(this.shooter.getUniqueID()); nbttagcompound1.setInt("X", blockposition.getX()); nbttagcompound1.setInt("Y", blockposition.getY()); nbttagcompound1.setInt("Z", blockposition.getZ()); nbttagcompound.set("Owner", nbttagcompound1); } if (this.target != null) { blockposition = new BlockPosition(this.target); nbttagcompound1 = GameProfileSerializer.a(this.target.getUniqueID()); nbttagcompound1.setInt("X", blockposition.getX()); nbttagcompound1.setInt("Y", blockposition.getY()); nbttagcompound1.setInt("Z", blockposition.getZ()); nbttagcompound.set("Target", nbttagcompound1); } if (this.c != null) { nbttagcompound.setInt("Dir", this.c.a()); } nbttagcompound.setInt("Steps", this.d); nbttagcompound.setDouble("TXD", this.e); nbttagcompound.setDouble("TYD", this.f); nbttagcompound.setDouble("TZD", this.g); } protected void a(NBTTagCompound nbttagcompound) { this.d = nbttagcompound.getInt("Steps"); this.e = nbttagcompound.getDouble("TXD"); this.f = nbttagcompound.getDouble("TYD"); this.g = nbttagcompound.getDouble("TZD"); if (nbttagcompound.hasKeyOfType("Dir", 99)) { this.c = EnumDirection.fromType1(nbttagcompound.getInt("Dir")); } NBTTagCompound nbttagcompound1; if (nbttagcompound.hasKeyOfType("Owner", 10)) { nbttagcompound1 = nbttagcompound.getCompound("Owner"); this.h = GameProfileSerializer.b(nbttagcompound1); this.at = new BlockPosition(nbttagcompound1.getInt("X"), nbttagcompound1.getInt("Y"), nbttagcompound1.getInt("Z")); } if (nbttagcompound.hasKeyOfType("Target", 10)) { nbttagcompound1 = nbttagcompound.getCompound("Target"); this.au = GameProfileSerializer.b(nbttagcompound1); this.av = new BlockPosition(nbttagcompound1.getInt("X"), nbttagcompound1.getInt("Y"), nbttagcompound1.getInt("Z")); } } protected void i() {} private void a(@Nullable EnumDirection enumdirection) { this.c = enumdirection; } private void a(@Nullable EnumDirection.EnumAxis enumdirection_enumaxis) { double d0 = 0.5D; BlockPosition blockposition; if (this.target == null) { blockposition = (new BlockPosition(this)).down(); } else { d0 = (double) this.target.length * 0.5D; blockposition = new BlockPosition(this.target.locX, this.target.locY + d0, this.target.locZ); } double d1 = (double) blockposition.getX() + 0.5D; double d2 = (double) blockposition.getY() + d0; double d3 = (double) blockposition.getZ() + 0.5D; EnumDirection enumdirection = null; if (blockposition.g(this.locX, this.locY, this.locZ) >= 4.0D) { BlockPosition blockposition1 = new BlockPosition(this); ArrayList arraylist = Lists.newArrayList(); if (enumdirection_enumaxis != EnumDirection.EnumAxis.X) { if (blockposition1.getX() < blockposition.getX() && this.world.isEmpty(blockposition1.east())) { arraylist.add(EnumDirection.EAST); } else if (blockposition1.getX() > blockposition.getX() && this.world.isEmpty(blockposition1.west())) { arraylist.add(EnumDirection.WEST); } } if (enumdirection_enumaxis != EnumDirection.EnumAxis.Y) { if (blockposition1.getY() < blockposition.getY() && this.world.isEmpty(blockposition1.up())) { arraylist.add(EnumDirection.UP); } else if (blockposition1.getY() > blockposition.getY() && this.world.isEmpty(blockposition1.down())) { arraylist.add(EnumDirection.DOWN); } } if (enumdirection_enumaxis != EnumDirection.EnumAxis.Z) { if (blockposition1.getZ() < blockposition.getZ() && this.world.isEmpty(blockposition1.south())) { arraylist.add(EnumDirection.SOUTH); } else if (blockposition1.getZ() > blockposition.getZ() && this.world.isEmpty(blockposition1.north())) { arraylist.add(EnumDirection.NORTH); } } enumdirection = EnumDirection.a(this.random); if (arraylist.isEmpty()) { for (int i = 5; !this.world.isEmpty(blockposition1.shift(enumdirection)) && i > 0; --i) { enumdirection = EnumDirection.a(this.random); } } else { enumdirection = (EnumDirection) arraylist.get(this.random.nextInt(arraylist.size())); } d1 = this.locX + (double) enumdirection.getAdjacentX(); d2 = this.locY + (double) enumdirection.getAdjacentY(); d3 = this.locZ + (double) enumdirection.getAdjacentZ(); } this.a(enumdirection); double d4 = d1 - this.locX; double d5 = d2 - this.locY; double d6 = d3 - this.locZ; double d7 = (double) MathHelper.sqrt(d4 * d4 + d5 * d5 + d6 * d6); if (d7 == 0.0D) { this.e = 0.0D; this.f = 0.0D; this.g = 0.0D; } else { this.e = d4 / d7 * 0.15D; this.f = d5 / d7 * 0.15D; this.g = d6 / d7 * 0.15D; } this.impulse = true; this.d = 10 + this.random.nextInt(5) * 10; } public void A_() { if (!this.world.isClientSide && this.world.getDifficulty() == EnumDifficulty.PEACEFUL) { this.die(); } else { super.A_(); if (!this.world.isClientSide) { List list; Iterator iterator; EntityLiving entityliving; if (this.target == null && this.au != null) { list = this.world.a(EntityLiving.class, new AxisAlignedBB(this.av.a(-2, -2, -2), this.av.a(2, 2, 2))); iterator = list.iterator(); while (iterator.hasNext()) { entityliving = (EntityLiving) iterator.next(); if (entityliving.getUniqueID().equals(this.au)) { this.target = entityliving; break; } } this.au = null; } if (this.shooter == null && this.h != null) { list = this.world.a(EntityLiving.class, new AxisAlignedBB(this.at.a(-2, -2, -2), this.at.a(2, 2, 2))); iterator = list.iterator(); while (iterator.hasNext()) { entityliving = (EntityLiving) iterator.next(); if (entityliving.getUniqueID().equals(this.h)) { this.shooter = entityliving; break; } } this.h = null; } if (this.target != null && this.target.isAlive() && (!(this.target instanceof EntityHuman) || !((EntityHuman) this.target).isSpectator())) { this.e = MathHelper.a(this.e * 1.025D, -1.0D, 1.0D); this.f = MathHelper.a(this.f * 1.025D, -1.0D, 1.0D); this.g = MathHelper.a(this.g * 1.025D, -1.0D, 1.0D); this.motX += (this.e - this.motX) * 0.2D; this.motY += (this.f - this.motY) * 0.2D; this.motZ += (this.g - this.motZ) * 0.2D; } else if (!this.isNoGravity()) { this.motY -= 0.04D; } MovingObjectPosition movingobjectposition = ProjectileHelper.a(this, true, false, this.shooter); if (movingobjectposition != null) { this.a(movingobjectposition); } } this.setPosition(this.locX + this.motX, this.locY + this.motY, this.locZ + this.motZ); ProjectileHelper.a(this, 0.5F); if (this.world.isClientSide) { this.world.addParticle(EnumParticle.END_ROD, this.locX - this.motX, this.locY - this.motY + 0.15D, this.locZ - this.motZ, 0.0D, 0.0D, 0.0D, new int[0]); } else if (this.target != null && !this.target.dead) { if (this.d > 0) { --this.d; if (this.d == 0) { this.a(this.c == null ? null : this.c.k()); } } if (this.c != null) { BlockPosition blockposition = new BlockPosition(this); EnumDirection.EnumAxis enumdirection_enumaxis = this.c.k(); if (this.world.d(blockposition.shift(this.c), false)) { this.a(enumdirection_enumaxis); } else { BlockPosition blockposition1 = new BlockPosition(this.target); if (enumdirection_enumaxis == EnumDirection.EnumAxis.X && blockposition.getX() == blockposition1.getX() || enumdirection_enumaxis == EnumDirection.EnumAxis.Z && blockposition.getZ() == blockposition1.getZ() || enumdirection_enumaxis == EnumDirection.EnumAxis.Y && blockposition.getY() == blockposition1.getY()) { this.a(enumdirection_enumaxis); } } } } } } public boolean isBurning() { return false; } public float e(float f) { return 1.0F; } protected void a(MovingObjectPosition movingobjectposition) { if (movingobjectposition.entity == null) { ((WorldServer) this.world).a(EnumParticle.EXPLOSION_LARGE, this.locX, this.locY, this.locZ, 2, 0.2D, 0.2D, 0.2D, 0.0D, new int[0]); this.a(SoundEffects.fC, 1.0F, 1.0F); } else { boolean flag = movingobjectposition.entity.damageEntity(DamageSource.a(this, this.shooter).b(), 4.0F); if (flag) { this.a(this.shooter, movingobjectposition.entity); if (movingobjectposition.entity instanceof EntityLiving) { ((EntityLiving) movingobjectposition.entity).addEffect(new MobEffect(MobEffects.LEVITATION, 200)); } } } this.die(); } public boolean isInteractable() { return true; } public boolean damageEntity(DamageSource damagesource, float f) { if (!this.world.isClientSide) { this.a(SoundEffects.fD, 1.0F, 1.0F); ((WorldServer) this.world).a(EnumParticle.CRIT, this.locX, this.locY, this.locZ, 15, 0.2D, 0.2D, 0.2D, 0.0D, new int[0]); this.die(); } return true; } }