--- a/net/minecraft/world/entity/animal/Bucketable.java +++ b/net/minecraft/world/entity/animal/Bucketable.java @@ -15,6 +15,14 @@ import net.minecraft.world.item.Items; import net.minecraft.world.level.World; +// CraftBukkit start +import net.minecraft.network.protocol.game.PacketPlayOutEntityMetadata; +import net.minecraft.network.protocol.game.PacketPlayOutSpawnEntityLiving; +import org.bukkit.craftbukkit.event.CraftEventFactory; +import org.bukkit.craftbukkit.inventory.CraftItemStack; +import org.bukkit.event.player.PlayerBucketEntityEvent; +// CraftBukkit end + public interface Bucketable { boolean isFromBucket(); @@ -92,10 +100,22 @@ ItemStack itemstack = entityhuman.b(enumhand); if (itemstack.getItem() == Items.WATER_BUCKET && t0.isAlive()) { - t0.playSound(((Bucketable) t0).t(), 1.0F, 1.0F); + // CraftBukkit start + // t0.playSound(((Bucketable) t0).t(), 1.0F, 1.0F); // CraftBukkit - moved down ItemStack itemstack1 = ((Bucketable) t0).getBucketItem(); ((Bucketable) t0).setBucketName(itemstack1); + + PlayerBucketEntityEvent playerBucketFishEvent = CraftEventFactory.callPlayerFishBucketEvent(t0, entityhuman, itemstack, itemstack1); + itemstack1 = CraftItemStack.asNMSCopy(playerBucketFishEvent.getEntityBucket()); + if (playerBucketFishEvent.isCancelled()) { + ((EntityPlayer) entityhuman).containerMenu.updateInventory(); // We need to update inventory to resync client's bucket + ((EntityPlayer) entityhuman).connection.sendPacket(new PacketPlayOutSpawnEntityLiving(t0)); // We need to play out these packets as the client assumes the fish is gone + ((EntityPlayer) entityhuman).connection.sendPacket(new PacketPlayOutEntityMetadata(t0.getId(), t0.getDataWatcher(), true)); // Need to send data such as the display name to client + return Optional.of(EnumInteractionResult.FAIL); + } + t0.playSound(((Bucketable) t0).t(), 1.0F, 1.0F); + // CraftBukkit end ItemStack itemstack2 = ItemLiquidUtil.a(itemstack, entityhuman, itemstack1, false); entityhuman.a(enumhand, itemstack2);