diff options
author | MiniDigger | Martin <[email protected]> | 2024-01-14 11:04:49 +0100 |
---|---|---|
committer | MiniDigger | Martin <[email protected]> | 2024-01-14 11:04:49 +0100 |
commit | bee74680e607c2e29b038329f62181238911cd83 (patch) | |
tree | 708fd1a4a0227d9071243adf2a42d5e9e96cde4a /patch-remap/mache-vineflower-stripped/net/minecraft/world/item | |
parent | 0a44692ef6ff6e255d48eb3ba1bb114166eafda9 (diff) | |
download | Paper-softspoon.tar.gz Paper-softspoon.zip |
add remapped patches as a testsoftspoon
Diffstat (limited to 'patch-remap/mache-vineflower-stripped/net/minecraft/world/item')
49 files changed, 2574 insertions, 0 deletions
diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ArmorItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ArmorItem.java.patch new file mode 100644 index 0000000000..0074fd1f09 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ArmorItem.java.patch @@ -0,0 +1,64 @@ +--- a/net/minecraft/world/item/ArmorItem.java ++++ b/net/minecraft/world/item/ArmorItem.java +@@ -25,6 +26,11 @@ + import net.minecraft.world.level.Level; + import net.minecraft.world.level.block.DispenserBlock; + import net.minecraft.world.phys.AABB; ++// CraftBukkit start ++import org.bukkit.craftbukkit.block.CraftBlock; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.event.block.BlockDispenseArmorEvent; ++// CraftBukkit end + + public class ArmorItem extends Item implements Equipable { + private static final EnumMap<ArmorItem.Type, UUID> ARMOR_MODIFIER_UUID_PER_TYPE = Util.make(new EnumMap<>(ArmorItem.Type.class), map -> { +@@ -55,15 +60,42 @@ + if (entitiesOfClass.isEmpty()) { + return false; + } else { +- LivingEntity livingEntity = entitiesOfClass.get(0); +- EquipmentSlot equipmentSlotForItem = Mob.getEquipmentSlotForItem(itemStack); +- ItemStack itemStack1 = itemStack.split(1); +- livingEntity.setItemSlot(equipmentSlotForItem, itemStack1); +- if (livingEntity instanceof Mob) { +- ((Mob)livingEntity).setDropChance(equipmentSlotForItem, 2.0F); +- ((Mob)livingEntity).setPersistenceRequired(); ++ LivingEntity entityliving = (LivingEntity) list.get(0); ++ EquipmentSlot enumitemslot = Mob.getEquipmentSlotForItem(itemstack); ++ ItemStack itemstack1 = itemstack.split(1); ++ // CraftBukkit start ++ Level world = sourceblock.level(); ++ org.bukkit.block.Block block = CraftBlock.at(world, sourceblock.pos()); ++ CraftItemStack craftItem = CraftItemStack.asCraftMirror(itemstack1); ++ ++ BlockDispenseArmorEvent event = new BlockDispenseArmorEvent(block, craftItem.clone(), (org.bukkit.craftbukkit.entity.CraftLivingEntity) entityliving.getBukkitEntity()); ++ if (!DispenserBlock.eventFired) { ++ world.getCraftServer().getPluginManager().callEvent(event); + } + ++ if (event.isCancelled()) { ++ itemstack.grow(1); ++ return false; ++ } ++ ++ if (!event.getItem().equals(craftItem)) { ++ itemstack.grow(1); ++ // Chain to handler for new item ++ ItemStack eventStack = CraftItemStack.asNMSCopy(event.getItem()); ++ DispenseItemBehavior idispensebehavior = (DispenseItemBehavior) DispenserBlock.DISPENSER_REGISTRY.get(eventStack.getItem()); ++ if (idispensebehavior != DispenseItemBehavior.NOOP && idispensebehavior != ArmorItem.DISPENSE_ITEM_BEHAVIOR) { ++ idispensebehavior.dispense(sourceblock, eventStack); ++ return true; ++ } ++ } ++ ++ entityliving.setItemSlot(enumitemslot, CraftItemStack.asNMSCopy(event.getItem())); ++ // CraftBukkit end ++ if (entityliving instanceof Mob) { ++ ((Mob) entityliving).setDropChance(enumitemslot, 2.0F); ++ ((Mob) entityliving).setPersistenceRequired(); ++ } ++ + return true; + } + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ArmorStandItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ArmorStandItem.java.patch new file mode 100644 index 0000000000..4c3a37c97b --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ArmorStandItem.java.patch @@ -0,0 +1,27 @@ +--- a/net/minecraft/world/item/ArmorStandItem.java ++++ b/net/minecraft/world/item/ArmorStandItem.java +@@ -44,13 +50,17 @@ + return InteractionResult.FAIL; + } + +- float f = (float)Mth.floor((Mth.wrapDegrees(context.getRotation() - 180.0F) + 22.5F) / 45.0F) * 45.0F; +- armorStand.moveTo(armorStand.getX(), armorStand.getY(), armorStand.getZ(), f, 0.0F); +- serverLevel.addFreshEntityWithPassengers(armorStand); +- level.playSound( +- null, armorStand.getX(), armorStand.getY(), armorStand.getZ(), SoundEvents.ARMOR_STAND_PLACE, SoundSource.BLOCKS, 0.75F, 0.8F +- ); +- armorStand.gameEvent(GameEvent.ENTITY_PLACE, context.getPlayer()); ++ float f = (float) Mth.floor((Mth.wrapDegrees(context.getRotation() - 180.0F) + 22.5F) / 45.0F) * 45.0F; ++ ++ entityarmorstand.moveTo(entityarmorstand.getX(), entityarmorstand.getY(), entityarmorstand.getZ(), f, 0.0F); ++ // CraftBukkit start ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(context, entityarmorstand).isCancelled()) { ++ return InteractionResult.FAIL; ++ } ++ // CraftBukkit end ++ worldserver.addFreshEntityWithPassengers(entityarmorstand); ++ world.playSound((Player) null, entityarmorstand.getX(), entityarmorstand.getY(), entityarmorstand.getZ(), SoundEvents.ARMOR_STAND_PLACE, SoundSource.BLOCKS, 0.75F, 0.8F); ++ entityarmorstand.gameEvent(GameEvent.ENTITY_PLACE, context.getPlayer()); + } + + itemInHand.shrink(1); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BlockItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BlockItem.java.patch new file mode 100644 index 0000000000..d8963fdd26 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BlockItem.java.patch @@ -0,0 +1,159 @@ +--- a/net/minecraft/world/item/BlockItem.java ++++ b/net/minecraft/world/item/BlockItem.java +@@ -29,6 +32,10 @@ + import net.minecraft.world.level.block.state.properties.Property; + import net.minecraft.world.level.gameevent.GameEvent; + import net.minecraft.world.phys.shapes.CollisionContext; ++import org.bukkit.craftbukkit.block.CraftBlock; ++import org.bukkit.craftbukkit.block.data.CraftBlockData; ++import org.bukkit.event.block.BlockCanBuildEvent; ++// CraftBukkit end + + public class BlockItem extends Item { + public static final String BLOCK_ENTITY_TAG = "BlockEntityTag"; +@@ -62,38 +74,53 @@ + if (blockPlaceContext == null) { + return InteractionResult.FAIL; + } else { +- BlockState placementState = this.getPlacementState(blockPlaceContext); +- if (placementState == null) { ++ IBlockData iblockdata = this.getPlacementState(blockactioncontext1); ++ // CraftBukkit start - special case for handling block placement with water lilies and snow buckets ++ org.bukkit.block.BlockState blockstate = null; ++ if (this instanceof PlaceOnWaterBlockItem || this instanceof SolidBucketItem) { ++ blockstate = org.bukkit.craftbukkit.block.CraftBlockStates.getBlockState(blockactioncontext1.getLevel(), blockactioncontext1.getClickedPos()); ++ } ++ // CraftBukkit end ++ ++ if (iblockdata == null) { + return InteractionResult.FAIL; + } else if (!this.placeBlock(blockPlaceContext, placementState)) { + return InteractionResult.FAIL; + } else { +- BlockPos clickedPos = blockPlaceContext.getClickedPos(); +- Level level = blockPlaceContext.getLevel(); +- Player player = blockPlaceContext.getPlayer(); +- ItemStack itemInHand = blockPlaceContext.getItemInHand(); +- BlockState blockState = level.getBlockState(clickedPos); +- if (blockState.is(placementState.getBlock())) { +- blockState = this.updateBlockStateFromTag(clickedPos, level, itemInHand, blockState); +- this.updateCustomBlockEntityTag(clickedPos, level, player, itemInHand, blockState); +- blockState.getBlock().setPlacedBy(level, clickedPos, blockState, player, itemInHand); +- if (player instanceof ServerPlayer) { +- CriteriaTriggers.PLACED_BLOCK.trigger((ServerPlayer)player, clickedPos, itemInHand); ++ BlockPos blockposition = blockactioncontext1.getClickedPos(); ++ Level world = blockactioncontext1.getLevel(); ++ Player entityhuman = blockactioncontext1.getPlayer(); ++ ItemStack itemstack = blockactioncontext1.getItemInHand(); ++ IBlockData iblockdata1 = world.getBlockState(blockposition); ++ ++ if (iblockdata1.is(iblockdata.getBlock())) { ++ iblockdata1 = this.updateBlockStateFromTag(blockposition, world, itemstack, iblockdata1); ++ this.updateCustomBlockEntityTag(blockposition, world, entityhuman, itemstack, iblockdata1); ++ iblockdata1.getBlock().setPlacedBy(world, blockposition, iblockdata1, entityhuman, itemstack); ++ // CraftBukkit start ++ if (blockstate != null) { ++ org.bukkit.event.block.BlockPlaceEvent placeEvent = org.bukkit.craftbukkit.event.CraftEventFactory.callBlockPlaceEvent((ServerLevel) world, entityhuman, blockactioncontext1.getHand(), blockstate, blockposition.getX(), blockposition.getY(), blockposition.getZ()); ++ if (placeEvent != null && (placeEvent.isCancelled() || !placeEvent.canBuild())) { ++ blockstate.update(true, false); ++ ++ if (this instanceof SolidBucketItem) { ++ ((ServerPlayer) entityhuman).getBukkitEntity().updateInventory(); // SPIGOT-4541 ++ } ++ return InteractionResult.FAIL; ++ } + } ++ // CraftBukkit end ++ if (entityhuman instanceof ServerPlayer) { ++ CriteriaTriggers.PLACED_BLOCK.trigger((ServerPlayer) entityhuman, blockposition, itemstack); ++ } + } + +- SoundType soundType = blockState.getSoundType(); +- level.playSound( +- player, +- clickedPos, +- this.getPlaceSound(blockState), +- SoundSource.BLOCKS, +- (soundType.getVolume() + 1.0F) / 2.0F, +- soundType.getPitch() * 0.8F +- ); +- level.gameEvent(GameEvent.BLOCK_PLACE, clickedPos, GameEvent.Context.of(player, blockState)); +- if (player == null || !player.getAbilities().instabuild) { +- itemInHand.shrink(1); ++ SoundType soundeffecttype = iblockdata1.getSoundType(); ++ ++ // world.playSound(entityhuman, blockposition, this.getPlaceSound(iblockdata1), SoundCategory.BLOCKS, (soundeffecttype.getVolume() + 1.0F) / 2.0F, soundeffecttype.getPitch() * 0.8F); ++ world.gameEvent(GameEvent.BLOCK_PLACE, blockposition, GameEvent.Context.of(entityhuman, iblockdata1)); ++ if ((entityhuman == null || !entityhuman.getAbilities().instabuild) && itemstack != ItemStack.EMPTY) { // CraftBukkit ++ itemstack.shrink(1); + } + + return InteractionResult.sidedSuccess(level.isClientSide); +@@ -128,13 +153,10 @@ + CompoundTag compound = tag.getCompound("BlockStateTag"); + StateDefinition<Block, BlockState> stateDefinition = state.getBlock().getStateDefinition(); + +- for (String string : compound.getAllKeys()) { +- Property<?> property = stateDefinition.getProperty(string); +- if (property != null) { +- String asString = compound.get(string).getAsString(); +- blockState = updateState(blockState, property, asString); +- } +- } ++ if (nbttagcompound != null) { ++ CompoundTag nbttagcompound1 = nbttagcompound.getCompound("BlockStateTag"); ++ // CraftBukkit start ++ iblockdata1 = getBlockState(iblockdata1, nbttagcompound1); + } + + if (blockState != state) { +@@ -144,8 +166,25 @@ + return blockState; + } + +- private static <T extends Comparable<T>> BlockState updateState(BlockState state, Property<T> property, String valueIdentifier) { +- return property.getValue(valueIdentifier).map(comparable -> state.setValue(property, comparable)).orElse(state); ++ public static IBlockData getBlockState(IBlockData iblockdata, CompoundTag nbttagcompound1) { ++ IBlockData iblockdata1 = iblockdata; ++ { ++ // CraftBukkit end ++ StateDefinition<Block, IBlockData> blockstatelist = iblockdata.getBlock().getStateDefinition(); ++ Iterator iterator = nbttagcompound1.getAllKeys().iterator(); ++ ++ while (iterator.hasNext()) { ++ String s = (String) iterator.next(); ++ Property<?> iblockstate = blockstatelist.getProperty(s); ++ ++ if (iblockstate != null) { ++ String s1 = nbttagcompound1.get(s).getAsString(); ++ ++ iblockdata1 = updateState(iblockdata1, iblockstate, s1); ++ } ++ } ++ } ++ return iblockdata1; + } + + protected boolean canPlace(BlockPlaceContext context, BlockState state) { +@@ -155,6 +193,20 @@ + && context.getLevel().isUnobstructed(state, context.getClickedPos(), collisionContext); + } + ++ protected boolean canPlace(BlockPlaceContext context, IBlockData state) { ++ Player entityhuman = context.getPlayer(); ++ CollisionContext voxelshapecollision = entityhuman == null ? CollisionContext.empty() : CollisionContext.of(entityhuman); ++ // CraftBukkit start - store default return ++ boolean defaultReturn = (!this.mustSurvive() || state.canSurvive(context.getLevel(), context.getClickedPos())) && context.getLevel().isUnobstructed(state, context.getClickedPos(), voxelshapecollision); ++ org.bukkit.entity.Player player = (context.getPlayer() instanceof ServerPlayer) ? (org.bukkit.entity.Player) context.getPlayer().getBukkitEntity() : null; ++ ++ BlockCanBuildEvent event = new BlockCanBuildEvent(CraftBlock.at(context.getLevel(), context.getClickedPos()), player, CraftBlockData.fromData(state), defaultReturn); ++ context.getLevel().getCraftServer().getPluginManager().callEvent(event); ++ ++ return event.isBuildable(); ++ // CraftBukkit end ++ } ++ + protected boolean mustSurvive() { + return true; + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BoatItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BoatItem.java.patch new file mode 100644 index 0000000000..28d2866305 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BoatItem.java.patch @@ -0,0 +1,43 @@ +--- a/net/minecraft/world/item/BoatItem.java ++++ b/net/minecraft/world/item/BoatItem.java +@@ -51,16 +59,32 @@ + } + } + +- if (playerPOVHitResult.getType() == HitResult.Type.BLOCK) { +- Boat boat = this.getBoat(level, playerPOVHitResult, itemInHand, player); +- boat.setVariant(this.type); +- boat.setYRot(player.getYRot()); +- if (!level.noCollision(boat, boat.getBoundingBox())) { +- return InteractionResultHolder.fail(itemInHand); ++ if (movingobjectpositionblock.getType() == HitResult.EnumMovingObjectType.BLOCK) { ++ // CraftBukkit start - Boat placement ++ org.bukkit.event.player.PlayerInteractEvent event = org.bukkit.craftbukkit.event.CraftEventFactory.callPlayerInteractEvent(player, org.bukkit.event.block.Action.RIGHT_CLICK_BLOCK, movingobjectpositionblock.getBlockPos(), movingobjectpositionblock.getDirection(), itemstack, false, hand, movingobjectpositionblock.getLocation()); ++ ++ if (event.isCancelled()) { ++ return InteractionResultHolder.pass(itemstack); ++ } ++ // CraftBukkit end ++ Boat entityboat = this.getBoat(level, movingobjectpositionblock, itemstack, player); ++ ++ entityboat.setVariant(this.type); ++ entityboat.setYRot(player.getYRot()); ++ if (!level.noCollision(entityboat, entityboat.getBoundingBox())) { ++ return InteractionResultHolder.fail(itemstack); + } else { + if (!level.isClientSide) { +- level.addFreshEntity(boat); +- level.gameEvent(player, GameEvent.ENTITY_PLACE, playerPOVHitResult.getLocation()); ++ // CraftBukkit start ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(level, movingobjectpositionblock.getBlockPos(), movingobjectpositionblock.getDirection(), player, entityboat, hand).isCancelled()) { ++ return InteractionResultHolder.fail(itemstack); ++ } ++ ++ if (!level.addFreshEntity(entityboat)) { ++ return InteractionResultHolder.pass(itemstack); ++ } ++ // CraftBukkit end ++ level.gameEvent((Entity) player, GameEvent.ENTITY_PLACE, movingobjectpositionblock.getLocation()); + if (!player.getAbilities().instabuild) { + itemInHand.shrink(1); + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BoneMealItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BoneMealItem.java.patch new file mode 100644 index 0000000000..8dec6340c2 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BoneMealItem.java.patch @@ -0,0 +1,47 @@ +--- a/net/minecraft/world/item/BoneMealItem.java ++++ b/net/minecraft/world/item/BoneMealItem.java +@@ -34,23 +34,31 @@ + + @Override + public InteractionResult useOn(UseOnContext context) { +- Level level = context.getLevel(); +- BlockPos clickedPos = context.getClickedPos(); +- BlockPos blockPos = clickedPos.relative(context.getClickedFace()); +- if (growCrop(context.getItemInHand(), level, clickedPos)) { +- if (!level.isClientSide) { +- context.getPlayer().gameEvent(GameEvent.ITEM_INTERACT_FINISH); +- level.levelEvent(1505, clickedPos, 0); ++ // CraftBukkit start - extract bonemeal application logic to separate, static method ++ return applyBonemeal(context); ++ } ++ ++ public static InteractionResult applyBonemeal(UseOnContext itemactioncontext) { ++ // CraftBukkit end ++ Level world = itemactioncontext.getLevel(); ++ BlockPos blockposition = itemactioncontext.getClickedPos(); ++ BlockPos blockposition1 = blockposition.relative(itemactioncontext.getClickedFace()); ++ ++ if (growCrop(itemactioncontext.getItemInHand(), world, blockposition)) { ++ if (!world.isClientSide) { ++ if (itemactioncontext.getPlayer() != null) itemactioncontext.getPlayer().gameEvent(GameEvent.ITEM_INTERACT_FINISH); // CraftBukkit - SPIGOT-7518 ++ world.levelEvent(1505, blockposition, 0); + } + + return InteractionResult.sidedSuccess(level.isClientSide); + } else { +- BlockState blockState = level.getBlockState(clickedPos); +- boolean isFaceSturdy = blockState.isFaceSturdy(level, clickedPos, context.getClickedFace()); +- if (isFaceSturdy && growWaterPlant(context.getItemInHand(), level, blockPos, context.getClickedFace())) { +- if (!level.isClientSide) { +- context.getPlayer().gameEvent(GameEvent.ITEM_INTERACT_FINISH); +- level.levelEvent(1505, blockPos, 0); ++ IBlockData iblockdata = world.getBlockState(blockposition); ++ boolean flag = iblockdata.isFaceSturdy(world, blockposition, itemactioncontext.getClickedFace()); ++ ++ if (flag && growWaterPlant(itemactioncontext.getItemInHand(), world, blockposition1, itemactioncontext.getClickedFace())) { ++ if (!world.isClientSide) { ++ if (itemactioncontext.getPlayer() != null) itemactioncontext.getPlayer().gameEvent(GameEvent.ITEM_INTERACT_FINISH); // CraftBukkit - SPIGOT-7518 ++ world.levelEvent(1505, blockposition1, 0); + } + + return InteractionResult.sidedSuccess(level.isClientSide); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BowItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BowItem.java.patch new file mode 100644 index 0000000000..9c7d43a137 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BowItem.java.patch @@ -0,0 +1,34 @@ +--- a/net/minecraft/world/item/BowItem.java ++++ b/net/minecraft/world/item/BowItem.java +@@ -56,13 +64,30 @@ + if (EnchantmentHelper.getItemEnchantmentLevel(Enchantments.FLAMING_ARROWS, stack) > 0) { + abstractArrow.setSecondsOnFire(100); + } ++ // CraftBukkit start ++ org.bukkit.event.entity.EntityShootBowEvent event = org.bukkit.craftbukkit.event.CraftEventFactory.callEntityShootBowEvent(entityhuman, stack, itemstack1, entityarrow, entityhuman.getUsedItemHand(), f, !flag1); ++ if (event.isCancelled()) { ++ event.getProjectile().remove(); ++ return; ++ } ++ flag1 = !event.shouldConsumeItem(); ++ // CraftBukkit end + + stack.hurtAndBreak(1, player, player1 -> player1.broadcastBreakEvent(player.getUsedItemHand())); + if (flag1 || player.getAbilities().instabuild && (projectile.is(Items.SPECTRAL_ARROW) || projectile.is(Items.TIPPED_ARROW))) { + abstractArrow.pickup = AbstractArrow.Pickup.CREATIVE_ONLY; + } + +- level.addFreshEntity(abstractArrow); ++ // CraftBukkit start ++ if (event.getProjectile() == entityarrow.getBukkitEntity()) { ++ if (!level.addFreshEntity(entityarrow)) { ++ if (entityhuman instanceof net.minecraft.server.level.ServerPlayer) { ++ ((net.minecraft.server.level.ServerPlayer) entityhuman).getBukkitEntity().updateInventory(); ++ } ++ return; ++ } ++ } ++ // CraftBukkit end + } + + level.playSound( diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BucketItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BucketItem.java.patch new file mode 100644 index 0000000000..744bc0754d --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/BucketItem.java.patch @@ -0,0 +1,138 @@ +--- a/net/minecraft/world/item/BucketItem.java ++++ b/net/minecraft/world/item/BucketItem.java +@@ -27,6 +30,12 @@ + import net.minecraft.world.level.material.Fluids; + import net.minecraft.world.phys.BlockHitResult; + import net.minecraft.world.phys.HitResult; ++import org.bukkit.craftbukkit.event.CraftEventFactory; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.util.DummyGeneratorAccess; ++import org.bukkit.event.player.PlayerBucketEmptyEvent; ++import org.bukkit.event.player.PlayerBucketFillEvent; ++// CraftBukkit end + + public class BucketItem extends Item implements DispensibleContainerItem { + private final Fluid content; +@@ -47,27 +56,39 @@ + } else if (playerPOVHitResult.getType() != HitResult.Type.BLOCK) { + return InteractionResultHolder.pass(itemInHand); + } else { +- BlockPos blockPos = playerPOVHitResult.getBlockPos(); +- Direction direction = playerPOVHitResult.getDirection(); +- BlockPos blockPos1 = blockPos.relative(direction); +- if (!level.mayInteract(player, blockPos) || !player.mayUseItemAt(blockPos1, direction, itemInHand)) { +- return InteractionResultHolder.fail(itemInHand); +- } else if (this.content == Fluids.EMPTY) { +- BlockState blockState = level.getBlockState(blockPos); +- if (blockState.getBlock() instanceof BucketPickup bucketPickup) { +- ItemStack itemStack = bucketPickup.pickupBlock(player, level, blockPos, blockState); +- if (!itemStack.isEmpty()) { +- player.awardStat(Stats.ITEM_USED.get(this)); +- bucketPickup.getPickupSound().ifPresent(soundEvent -> player.playSound(soundEvent, 1.0F, 1.0F)); +- level.gameEvent(player, GameEvent.FLUID_PICKUP, blockPos); +- ItemStack itemStack1 = ItemUtils.createFilledResult(itemInHand, player, itemStack); +- if (!level.isClientSide) { +- CriteriaTriggers.FILLED_BUCKET.trigger((ServerPlayer)player, itemStack); ++ BlockPos blockposition = movingobjectpositionblock.getBlockPos(); ++ Direction enumdirection = movingobjectpositionblock.getDirection(); ++ BlockPos blockposition1 = blockposition.relative(enumdirection); ++ ++ if (level.mayInteract(player, blockposition) && player.mayUseItemAt(blockposition1, enumdirection, itemstack)) { ++ IBlockData iblockdata; ++ ++ if (this.content == Fluids.EMPTY) { ++ iblockdata = level.getBlockState(blockposition); ++ Block block = iblockdata.getBlock(); ++ ++ if (block instanceof BucketPickup) { ++ BucketPickup ifluidsource = (BucketPickup) block; ++ // CraftBukkit start ++ ItemStack dummyFluid = ifluidsource.pickupBlock(player, DummyGeneratorAccess.INSTANCE, blockposition, iblockdata); ++ if (dummyFluid.isEmpty()) return InteractionResultHolder.fail(itemstack); // Don't fire event if the bucket won't be filled. ++ PlayerBucketFillEvent event = CraftEventFactory.callPlayerBucketFillEvent((ServerLevel) level, player, blockposition, blockposition, movingobjectpositionblock.getDirection(), itemstack, dummyFluid.getItem(), hand); ++ ++ if (event.isCancelled()) { ++ ((ServerPlayer) player).connection.send(new ClientboundBlockUpdatePacket(level, blockposition)); // SPIGOT-5163 (see PlayerInteractManager) ++ ((ServerPlayer) player).getBukkitEntity().updateInventory(); // SPIGOT-4541 ++ return InteractionResultHolder.fail(itemstack); + } ++ // CraftBukkit end ++ ItemStack itemstack1 = ifluidsource.pickupBlock(player, level, blockposition, iblockdata); + +- return InteractionResultHolder.sidedSuccess(itemStack1, level.isClientSide()); +- } +- } ++ if (!itemstack1.isEmpty()) { ++ player.awardStat(Stats.ITEM_USED.get(this)); ++ ifluidsource.getPickupSound().ifPresent((soundeffect) -> { ++ player.playSound(soundeffect, 1.0F, 1.0F); ++ }); ++ level.gameEvent((Entity) player, GameEvent.FLUID_PICKUP, blockposition); ++ ItemStack itemstack2 = ItemUtils.createFilledResult(itemstack, player, CraftItemStack.asNMSCopy(event.getItemStack())); // CraftBukkit + + return InteractionResultHolder.fail(itemInHand); + } else { +@@ -82,7 +100,20 @@ + player.awardStat(Stats.ITEM_USED.get(this)); + return InteractionResultHolder.sidedSuccess(getEmptySuccessItem(itemInHand, player), level.isClientSide()); + } else { +- return InteractionResultHolder.fail(itemInHand); ++ iblockdata = level.getBlockState(blockposition); ++ BlockPos blockposition2 = iblockdata.getBlock() instanceof LiquidBlockContainer && this.content == Fluids.WATER ? blockposition : blockposition1; ++ ++ if (this.emptyContents(player, level, blockposition2, movingobjectpositionblock, movingobjectpositionblock.getDirection(), blockposition, itemstack, hand)) { // CraftBukkit ++ this.checkExtraContent(player, level, itemstack, blockposition2); ++ if (player instanceof ServerPlayer) { ++ CriteriaTriggers.PLACED_BLOCK.trigger((ServerPlayer) player, blockposition2, itemstack); ++ } ++ ++ player.awardStat(Stats.ITEM_USED.get(this)); ++ return InteractionResultHolder.sidedSuccess(getEmptySuccessItem(itemstack, player), level.isClientSide()); ++ } else { ++ return InteractionResultHolder.fail(itemstack); ++ } + } + } + } +@@ -98,7 +130,15 @@ + + @Override + public boolean emptyContents(@Nullable Player player, Level level, BlockPos pos, @Nullable BlockHitResult result) { +- if (!(this.content instanceof FlowingFluid flowingFluid)) { ++ // CraftBukkit start ++ return emptyContents(player, level, pos, result, null, null, null, EnumHand.MAIN_HAND); ++ } ++ ++ public boolean emptyContents(Player entityhuman, Level world, BlockPos blockposition, @Nullable BlockHitResult movingobjectpositionblock, Direction enumdirection, BlockPos clicked, ItemStack itemstack, EnumHand enumhand) { ++ // CraftBukkit end ++ Fluid fluidtype = this.content; ++ ++ if (!(fluidtype instanceof FlowingFluid)) { + return false; + } else { + Block block; +@@ -134,9 +173,22 @@ + player, pos, SoundEvents.FIRE_EXTINGUISH, SoundSource.BLOCKS, 0.5F, 2.6F + (level.random.nextFloat() - level.random.nextFloat()) * 0.8F + ); + +- for (int i = 0; i < 8; i++) { +- level.addParticle(ParticleTypes.LARGE_SMOKE, (double)x + Math.random(), (double)y + Math.random(), (double)z + Math.random(), 0.0, 0.0, 0.0); ++ // CraftBukkit start ++ if (flag2 && entityhuman != null) { ++ PlayerBucketEmptyEvent event = CraftEventFactory.callPlayerBucketEmptyEvent((ServerLevel) world, entityhuman, blockposition, clicked, enumdirection, itemstack, enumhand); ++ if (event.isCancelled()) { ++ ((ServerPlayer) entityhuman).connection.send(new ClientboundBlockUpdatePacket(world, blockposition)); // SPIGOT-4238: needed when looking through entity ++ ((ServerPlayer) entityhuman).getBukkitEntity().updateInventory(); // SPIGOT-4541 ++ return false; + } ++ } ++ // CraftBukkit end ++ if (!flag2) { ++ return movingobjectpositionblock != null && this.emptyContents(entityhuman, world, movingobjectpositionblock.getBlockPos().relative(movingobjectpositionblock.getDirection()), (BlockHitResult) null, enumdirection, clicked, itemstack, enumhand); // CraftBukkit ++ } else if (world.dimensionType().ultraWarm() && this.content.is(FluidTags.WATER)) { ++ int i = blockposition.getX(); ++ int j = blockposition.getY(); ++ int k = blockposition.getZ(); + + return true; + } else { diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ChorusFruitItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ChorusFruitItem.java.patch new file mode 100644 index 0000000000..b5bec9cc49 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ChorusFruitItem.java.patch @@ -0,0 +1,30 @@ +--- a/net/minecraft/world/item/ChorusFruitItem.java ++++ b/net/minecraft/world/item/ChorusFruitItem.java +@@ -33,11 +33,22 @@ + entityLiving.stopRiding(); + } + +- Vec3 vec3 = entityLiving.position(); +- if (entityLiving.randomTeleport(d, d1, d2, true)) { +- level.gameEvent(GameEvent.TELEPORT, vec3, GameEvent.Context.of(entityLiving)); +- SoundSource soundSource; +- SoundEvent soundEvent; ++ Vec3 vec3d = entityLiving.position(); ++ ++ // CraftBukkit start - handle canceled status of teleport event ++ java.util.Optional<Boolean> status = entityLiving.randomTeleport(d0, d1, d2, true, org.bukkit.event.player.PlayerTeleportEvent.TeleportCause.CHORUS_FRUIT); ++ ++ if (!status.isPresent()) { ++ // teleport event was canceled, no more tries ++ break; ++ } ++ ++ if (status.get()) { ++ // CraftBukkit end ++ level.gameEvent(GameEvent.TELEPORT, vec3d, GameEvent.Context.of((Entity) entityLiving)); ++ SoundEvent soundeffect; ++ SoundSource soundcategory; ++ + if (entityLiving instanceof Fox) { + soundEvent = SoundEvents.FOX_TELEPORT; + soundSource = SoundSource.NEUTRAL; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/CrossbowItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/CrossbowItem.java.patch new file mode 100644 index 0000000000..49ad59c5bf --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/CrossbowItem.java.patch @@ -0,0 +1,34 @@ +--- a/net/minecraft/world/item/CrossbowItem.java ++++ b/net/minecraft/world/item/CrossbowItem.java +@@ -234,10 +236,28 @@ + Vector3f vector3f = viewVector.toVector3f().rotate(quaternionf); + projectile.shoot((double)vector3f.x(), (double)vector3f.y(), (double)vector3f.z(), velocity, inaccuracy); + } ++ // CraftBukkit start ++ org.bukkit.event.entity.EntityShootBowEvent event = org.bukkit.craftbukkit.event.CraftEventFactory.callEntityShootBowEvent(shooter, crossbowStack, ammoStack, (Entity) object, shooter.getUsedItemHand(), soundPitch, true); ++ if (event.isCancelled()) { ++ event.getProjectile().remove(); ++ return; ++ } ++ // CraftBukkit end + +- crossbowStack.hurtAndBreak(isFireworkRocket ? 3 : 1, shooter, contextEntity -> contextEntity.broadcastBreakEvent(hand)); +- level.addFreshEntity(projectile); +- level.playSound(null, shooter.getX(), shooter.getY(), shooter.getZ(), SoundEvents.CROSSBOW_SHOOT, SoundSource.PLAYERS, 1.0F, soundPitch); ++ crossbowStack.hurtAndBreak(flag1 ? 3 : 1, shooter, (entityliving1) -> { ++ entityliving1.broadcastBreakEvent(hand); ++ }); ++ // CraftBukkit start ++ if (event.getProjectile() == ((Entity) object).getBukkitEntity()) { ++ if (!level.addFreshEntity((Entity) object)) { ++ if (shooter instanceof ServerPlayer) { ++ ((ServerPlayer) shooter).getBukkitEntity().updateInventory(); ++ } ++ return; ++ } ++ } ++ // CraftBukkit end ++ level.playSound((Player) null, shooter.getX(), shooter.getY(), shooter.getZ(), SoundEvents.CROSSBOW_SHOOT, SoundSource.PLAYERS, 1.0F, soundPitch); + } + } + diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/DebugStickItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/DebugStickItem.java.patch new file mode 100644 index 0000000000..8b13789179 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/DebugStickItem.java.patch @@ -0,0 +1 @@ + diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/DyeItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/DyeItem.java.patch new file mode 100644 index 0000000000..0d41c2aec7 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/DyeItem.java.patch @@ -0,0 +1,38 @@ +--- a/net/minecraft/world/item/DyeItem.java ++++ b/net/minecraft/world/item/DyeItem.java +@@ -11,7 +12,7 @@ + import net.minecraft.world.entity.player.Player; + import net.minecraft.world.level.Level; + import net.minecraft.world.level.block.entity.SignBlockEntity; +-import net.minecraft.world.level.block.entity.SignText; ++import org.bukkit.event.entity.SheepDyeWoolEvent; // CraftBukkit + + public class DyeItem extends Item implements SignApplicator { + private static final Map<DyeColor, DyeItem> ITEM_BY_COLOR = Maps.newEnumMap(DyeColor.class); +@@ -32,7 +30,25 @@ + stack.shrink(1); + } + +- return InteractionResult.sidedSuccess(player.level().isClientSide); ++ if (entitysheep.isAlive() && !entitysheep.isSheared() && entitysheep.getColor() != this.dyeColor) { ++ entitysheep.level().playSound(player, (Entity) entitysheep, SoundEvents.DYE_USE, SoundSource.PLAYERS, 1.0F, 1.0F); ++ if (!player.level().isClientSide) { ++ // CraftBukkit start ++ byte bColor = (byte) this.dyeColor.getId(); ++ SheepDyeWoolEvent event = new SheepDyeWoolEvent((org.bukkit.entity.Sheep) entitysheep.getBukkitEntity(), org.bukkit.DyeColor.getByWoolData(bColor), (org.bukkit.entity.Player) player.getBukkitEntity()); ++ entitysheep.level().getCraftServer().getPluginManager().callEvent(event); ++ ++ if (event.isCancelled()) { ++ return InteractionResult.PASS; ++ } ++ ++ entitysheep.setColor(DyeColor.byId((byte) event.getColor().getWoolData())); ++ // CraftBukkit end ++ stack.shrink(1); ++ } ++ ++ return InteractionResult.sidedSuccess(player.level().isClientSide); ++ } + } + + return InteractionResult.PASS; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EggItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EggItem.java.patch new file mode 100644 index 0000000000..07e2bf1538 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EggItem.java.patch @@ -0,0 +1,42 @@ +--- a/net/minecraft/world/item/EggItem.java ++++ b/net/minecraft/world/item/EggItem.java +@@ -15,23 +16,23 @@ + } + + @Override +- public InteractionResultHolder<ItemStack> use(Level level, Player player, InteractionHand hand) { +- ItemStack itemInHand = player.getItemInHand(hand); +- level.playSound( +- null, +- player.getX(), +- player.getY(), +- player.getZ(), +- SoundEvents.EGG_THROW, +- SoundSource.PLAYERS, +- 0.5F, +- 0.4F / (level.getRandom().nextFloat() * 0.4F + 0.8F) +- ); ++ public InteractionResultHolder<ItemStack> use(Level level, Player player, EnumHand hand) { ++ ItemStack itemstack = player.getItemInHand(hand); ++ ++ // world.playSound((EntityHuman) null, entityhuman.getX(), entityhuman.getY(), entityhuman.getZ(), SoundEffects.EGG_THROW, SoundCategory.PLAYERS, 0.5F, 0.4F / (world.getRandom().nextFloat() * 0.4F + 0.8F)); // CraftBukkit - moved down + if (!level.isClientSide) { +- ThrownEgg thrownEgg = new ThrownEgg(level, player); +- thrownEgg.setItem(itemInHand); +- thrownEgg.shootFromRotation(player, player.getXRot(), player.getYRot(), 0.0F, 1.5F, 1.0F); +- level.addFreshEntity(thrownEgg); ++ ThrownEgg entityegg = new ThrownEgg(level, player); ++ ++ entityegg.setItem(itemstack); ++ entityegg.shootFromRotation(player, player.getXRot(), player.getYRot(), 0.0F, 1.5F, 1.0F); ++ // CraftBukkit start ++ if (!level.addFreshEntity(entityegg)) { ++ if (player instanceof net.minecraft.server.level.ServerPlayer) { ++ ((net.minecraft.server.level.ServerPlayer) player).getBukkitEntity().updateInventory(); ++ } ++ return InteractionResultHolder.fail(itemstack); ++ } ++ // CraftBukkit end + } + + player.awardStat(Stats.ITEM_USED.get(this)); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EndCrystalItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EndCrystalItem.java.patch new file mode 100644 index 0000000000..d755b53015 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EndCrystalItem.java.patch @@ -0,0 +1,33 @@ +--- a/net/minecraft/world/item/EndCrystalItem.java ++++ b/net/minecraft/world/item/EndCrystalItem.java +@@ -38,15 +42,22 @@ + if (!entities.isEmpty()) { + return InteractionResult.FAIL; + } else { +- if (level instanceof ServerLevel) { +- EndCrystal endCrystal = new EndCrystal(level, d + 0.5, d1, d2 + 0.5); +- endCrystal.setShowBottom(false); +- level.addFreshEntity(endCrystal); +- level.gameEvent(context.getPlayer(), GameEvent.ENTITY_PLACE, blockPos); +- EndDragonFight dragonFight = ((ServerLevel)level).getDragonFight(); +- if (dragonFight != null) { +- dragonFight.tryRespawn(); ++ if (world instanceof ServerLevel) { ++ EndCrystal entityendercrystal = new EndCrystal(world, d0 + 0.5D, d1, d2 + 0.5D); ++ ++ entityendercrystal.setShowBottom(false); ++ // CraftBukkit start ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(context, entityendercrystal).isCancelled()) { ++ return InteractionResult.FAIL; + } ++ // CraftBukkit end ++ world.addFreshEntity(entityendercrystal); ++ world.gameEvent((Entity) context.getPlayer(), GameEvent.ENTITY_PLACE, blockposition1); ++ EndDragonFight enderdragonbattle = ((ServerLevel) world).getDragonFight(); ++ ++ if (enderdragonbattle != null) { ++ enderdragonbattle.tryRespawn(); ++ } + } + + context.getItemInHand().shrink(1); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EnderEyeItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EnderEyeItem.java.patch new file mode 100644 index 0000000000..3d409494f3 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EnderEyeItem.java.patch @@ -0,0 +1,32 @@ +--- a/net/minecraft/world/item/EnderEyeItem.java ++++ b/net/minecraft/world/item/EnderEyeItem.java +@@ -71,14 +79,21 @@ + return InteractionResultHolder.pass(itemInHand); + } else { + player.startUsingItem(hand); +- if (level instanceof ServerLevel serverLevel) { +- BlockPos blockPos = serverLevel.findNearestMapStructure(StructureTags.EYE_OF_ENDER_LOCATED, player.blockPosition(), 100, false); +- if (blockPos != null) { +- EyeOfEnder eyeOfEnder = new EyeOfEnder(level, player.getX(), player.getY(0.5), player.getZ()); +- eyeOfEnder.setItem(itemInHand); +- eyeOfEnder.signalTo(blockPos); +- level.gameEvent(GameEvent.PROJECTILE_SHOOT, eyeOfEnder.position(), GameEvent.Context.of(player)); +- level.addFreshEntity(eyeOfEnder); ++ if (level instanceof ServerLevel) { ++ ServerLevel worldserver = (ServerLevel) level; ++ BlockPos blockposition = worldserver.findNearestMapStructure(StructureTags.EYE_OF_ENDER_LOCATED, player.blockPosition(), 100, false); ++ ++ if (blockposition != null) { ++ EyeOfEnder entityendersignal = new EyeOfEnder(level, player.getX(), player.getY(0.5D), player.getZ()); ++ ++ entityendersignal.setItem(itemstack); ++ entityendersignal.signalTo(blockposition); ++ level.gameEvent(GameEvent.PROJECTILE_SHOOT, entityendersignal.position(), GameEvent.Context.of((Entity) player)); ++ // CraftBukkit start ++ if (!level.addFreshEntity(entityendersignal)) { ++ return new InteractionResultHolder(InteractionResult.FAIL, itemstack); ++ } ++ // CraftBukkit end + if (player instanceof ServerPlayer) { + CriteriaTriggers.USED_ENDER_EYE.trigger((ServerPlayer)player, blockPos); + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EnderpearlItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EnderpearlItem.java.patch new file mode 100644 index 0000000000..4851eaadc8 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/EnderpearlItem.java.patch @@ -0,0 +1,37 @@ +--- a/net/minecraft/world/item/EnderpearlItem.java ++++ b/net/minecraft/world/item/EnderpearlItem.java +@@ -15,19 +16,10 @@ + } + + @Override +- public InteractionResultHolder<ItemStack> use(Level level, Player player, InteractionHand hand) { +- ItemStack itemInHand = player.getItemInHand(hand); +- level.playSound( +- null, +- player.getX(), +- player.getY(), +- player.getZ(), +- SoundEvents.ENDER_PEARL_THROW, +- SoundSource.NEUTRAL, +- 0.5F, +- 0.4F / (level.getRandom().nextFloat() * 0.4F + 0.8F) +- ); +- player.getCooldowns().addCooldown(this, 20); ++ public InteractionResultHolder<ItemStack> use(Level level, Player player, EnumHand hand) { ++ ItemStack itemstack = player.getItemInHand(hand); ++ ++ // CraftBukkit start - change order + if (!level.isClientSide) { + ThrownEnderpearl thrownEnderpearl = new ThrownEnderpearl(level, player); + thrownEnderpearl.setItem(itemInHand); +@@ -35,6 +33,10 @@ + level.addFreshEntity(thrownEnderpearl); + } + ++ level.playSound((Player) null, player.getX(), player.getY(), player.getZ(), SoundEvents.ENDER_PEARL_THROW, SoundSource.NEUTRAL, 0.5F, 0.4F / (level.getRandom().nextFloat() * 0.4F + 0.8F)); ++ player.getCooldowns().addCooldown(this, 20); ++ // CraftBukkit end ++ + player.awardStat(Stats.ITEM_USED.get(this)); + if (!player.getAbilities().instabuild) { + itemInHand.shrink(1); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FireChargeItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FireChargeItem.java.patch new file mode 100644 index 0000000000..3db64e44df --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FireChargeItem.java.patch @@ -0,0 +1,47 @@ +--- a/net/minecraft/world/item/FireChargeItem.java ++++ b/net/minecraft/world/item/FireChargeItem.java +@@ -26,18 +29,35 @@ + BlockPos clickedPos = context.getClickedPos(); + BlockState blockState = level.getBlockState(clickedPos); + boolean flag = false; +- if (!CampfireBlock.canLight(blockState) && !CandleBlock.canLight(blockState) && !CandleCakeBlock.canLight(blockState)) { +- BlockPos var6 = clickedPos.relative(context.getClickedFace()); +- if (BaseFireBlock.canBePlacedAt(level, var6, context.getHorizontalDirection())) { +- this.playSound(level, var6); +- level.setBlockAndUpdate(var6, BaseFireBlock.getState(level, var6)); +- level.gameEvent(context.getPlayer(), GameEvent.BLOCK_PLACE, var6); ++ ++ if (!CampfireBlock.canLight(iblockdata) && !CandleBlock.canLight(iblockdata) && !CandleCakeBlock.canLight(iblockdata)) { ++ blockposition = blockposition.relative(context.getClickedFace()); ++ if (BaseFireBlock.canBePlacedAt(world, blockposition, context.getHorizontalDirection())) { ++ // CraftBukkit start - fire BlockIgniteEvent ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callBlockIgniteEvent(world, blockposition, org.bukkit.event.block.BlockIgniteEvent.IgniteCause.FIREBALL, context.getPlayer()).isCancelled()) { ++ if (!context.getPlayer().getAbilities().instabuild) { ++ context.getItemInHand().shrink(1); ++ } ++ return InteractionResult.PASS; ++ } ++ // CraftBukkit end ++ this.playSound(world, blockposition); ++ world.setBlockAndUpdate(blockposition, BaseFireBlock.getState(world, blockposition)); ++ world.gameEvent((Entity) context.getPlayer(), GameEvent.BLOCK_PLACE, blockposition); + flag = true; + } + } else { +- this.playSound(level, clickedPos); +- level.setBlockAndUpdate(clickedPos, blockState.setValue(BlockStateProperties.LIT, Boolean.valueOf(true))); +- level.gameEvent(context.getPlayer(), GameEvent.BLOCK_CHANGE, clickedPos); ++ // CraftBukkit start - fire BlockIgniteEvent ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callBlockIgniteEvent(world, blockposition, org.bukkit.event.block.BlockIgniteEvent.IgniteCause.FIREBALL, context.getPlayer()).isCancelled()) { ++ if (!context.getPlayer().getAbilities().instabuild) { ++ context.getItemInHand().shrink(1); ++ } ++ return InteractionResult.PASS; ++ } ++ // CraftBukkit end ++ this.playSound(world, blockposition); ++ world.setBlockAndUpdate(blockposition, (IBlockData) iblockdata.setValue(BlockStateProperties.LIT, true)); ++ world.gameEvent((Entity) context.getPlayer(), GameEvent.BLOCK_CHANGE, blockposition); + flag = true; + } + diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FishingRodItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FishingRodItem.java.patch new file mode 100644 index 0000000000..cc2d211ac0 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FishingRodItem.java.patch @@ -0,0 +1,42 @@ +--- a/net/minecraft/world/item/FishingRodItem.java ++++ b/net/minecraft/world/item/FishingRodItem.java +@@ -11,7 +11,13 @@ + import net.minecraft.world.level.Level; + import net.minecraft.world.level.gameevent.GameEvent; + +-public class FishingRodItem extends Item implements Vanishable { ++// CraftBukkit start ++import org.bukkit.event.player.PlayerFishEvent; ++import org.bukkit.craftbukkit.CraftEquipmentSlot; ++// CraftBukkit end ++ ++public class FishingRodItem extends Item implements ItemVanishable { ++ + public FishingRodItem(Item.Properties properties) { + super(properties); + } +@@ -48,9 +40,21 @@ + 0.4F / (level.getRandom().nextFloat() * 0.4F + 0.8F) + ); + if (!level.isClientSide) { +- int i = EnchantmentHelper.getFishingSpeedBonus(itemInHand); +- int fishingLuckBonus = EnchantmentHelper.getFishingLuckBonus(itemInHand); +- level.addFreshEntity(new FishingHook(player, level, fishingLuckBonus, i)); ++ i = EnchantmentHelper.getFishingSpeedBonus(itemstack); ++ int j = EnchantmentHelper.getFishingLuckBonus(itemstack); ++ ++ // CraftBukkit start ++ FishingHook entityfishinghook = new FishingHook(player, level, j, i); ++ PlayerFishEvent playerFishEvent = new PlayerFishEvent((org.bukkit.entity.Player) player.getBukkitEntity(), null, (org.bukkit.entity.FishHook) entityfishinghook.getBukkitEntity(), CraftEquipmentSlot.getHand(hand), PlayerFishEvent.State.FISHING); ++ level.getCraftServer().getPluginManager().callEvent(playerFishEvent); ++ ++ if (playerFishEvent.isCancelled()) { ++ player.fishing = null; ++ return InteractionResultHolder.pass(itemstack); ++ } ++ level.playSound((Player) null, player.getX(), player.getY(), player.getZ(), SoundEvents.FISHING_BOBBER_THROW, SoundSource.NEUTRAL, 0.5F, 0.4F / (level.getRandom().nextFloat() * 0.4F + 0.8F)); ++ level.addFreshEntity(entityfishinghook); ++ // CraftBukkit end + } + + player.awardStat(Stats.ITEM_USED.get(this)); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FlintAndSteelItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FlintAndSteelItem.java.patch new file mode 100644 index 0000000000..33db34830e --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/FlintAndSteelItem.java.patch @@ -0,0 +1,70 @@ +--- a/net/minecraft/world/item/FlintAndSteelItem.java ++++ b/net/minecraft/world/item/FlintAndSteelItem.java +@@ -24,34 +26,47 @@ + + @Override + public InteractionResult useOn(UseOnContext context) { +- Player player = context.getPlayer(); +- Level level = context.getLevel(); +- BlockPos clickedPos = context.getClickedPos(); +- BlockState blockState = level.getBlockState(clickedPos); +- if (!CampfireBlock.canLight(blockState) && !CandleBlock.canLight(blockState) && !CandleCakeBlock.canLight(blockState)) { +- BlockPos blockPos = clickedPos.relative(context.getClickedFace()); +- if (BaseFireBlock.canBePlacedAt(level, blockPos, context.getHorizontalDirection())) { +- level.playSound(player, blockPos, SoundEvents.FLINTANDSTEEL_USE, SoundSource.BLOCKS, 1.0F, level.getRandom().nextFloat() * 0.4F + 0.8F); +- BlockState state = BaseFireBlock.getState(level, blockPos); +- level.setBlock(blockPos, state, 11); +- level.gameEvent(player, GameEvent.BLOCK_PLACE, clickedPos); +- ItemStack itemInHand = context.getItemInHand(); +- if (player instanceof ServerPlayer) { +- CriteriaTriggers.PLACED_BLOCK.trigger((ServerPlayer)player, blockPos, itemInHand); +- itemInHand.hurtAndBreak(1, player, contextPlayer -> contextPlayer.broadcastBreakEvent(context.getHand())); ++ Player entityhuman = context.getPlayer(); ++ Level world = context.getLevel(); ++ BlockPos blockposition = context.getClickedPos(); ++ IBlockData iblockdata = world.getBlockState(blockposition); ++ ++ if (!CampfireBlock.canLight(iblockdata) && !CandleBlock.canLight(iblockdata) && !CandleCakeBlock.canLight(iblockdata)) { ++ BlockPos blockposition1 = blockposition.relative(context.getClickedFace()); ++ ++ if (BaseFireBlock.canBePlacedAt(world, blockposition1, context.getHorizontalDirection())) { ++ // CraftBukkit start - Store the clicked block ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callBlockIgniteEvent(world, blockposition1, org.bukkit.event.block.BlockIgniteEvent.IgniteCause.FLINT_AND_STEEL, entityhuman).isCancelled()) { ++ context.getItemInHand().hurtAndBreak(1, entityhuman, (entityhuman1) -> { ++ entityhuman1.broadcastBreakEvent(context.getHand()); ++ }); ++ return InteractionResult.PASS; + } ++ // CraftBukkit end ++ world.playSound(entityhuman, blockposition1, SoundEvents.FLINTANDSTEEL_USE, SoundSource.BLOCKS, 1.0F, world.getRandom().nextFloat() * 0.4F + 0.8F); ++ IBlockData iblockdata1 = BaseFireBlock.getState(world, blockposition1); + + return InteractionResult.sidedSuccess(level.isClientSide()); + } else { + return InteractionResult.FAIL; + } + } else { +- level.playSound(player, clickedPos, SoundEvents.FLINTANDSTEEL_USE, SoundSource.BLOCKS, 1.0F, level.getRandom().nextFloat() * 0.4F + 0.8F); +- level.setBlock(clickedPos, blockState.setValue(BlockStateProperties.LIT, Boolean.valueOf(true)), 11); +- level.gameEvent(player, GameEvent.BLOCK_CHANGE, clickedPos); +- if (player != null) { +- context.getItemInHand().hurtAndBreak(1, player, contextPlayer -> contextPlayer.broadcastBreakEvent(context.getHand())); ++ // CraftBukkit start - Store the clicked block ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callBlockIgniteEvent(world, blockposition, org.bukkit.event.block.BlockIgniteEvent.IgniteCause.FLINT_AND_STEEL, entityhuman).isCancelled()) { ++ context.getItemInHand().hurtAndBreak(1, entityhuman, (entityhuman1) -> { ++ entityhuman1.broadcastBreakEvent(context.getHand()); ++ }); ++ return InteractionResult.PASS; + } ++ // CraftBukkit end ++ world.playSound(entityhuman, blockposition, SoundEvents.FLINTANDSTEEL_USE, SoundSource.BLOCKS, 1.0F, world.getRandom().nextFloat() * 0.4F + 0.8F); ++ world.setBlock(blockposition, (IBlockData) iblockdata.setValue(BlockStateProperties.LIT, true), 11); ++ world.gameEvent((Entity) entityhuman, GameEvent.BLOCK_CHANGE, blockposition); ++ if (entityhuman != null) { ++ context.getItemInHand().hurtAndBreak(1, entityhuman, (entityhuman1) -> { ++ entityhuman1.broadcastBreakEvent(context.getHand()); ++ }); ++ } + + return InteractionResult.sidedSuccess(level.isClientSide()); + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/HangingEntityItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/HangingEntityItem.java.patch new file mode 100644 index 0000000000..af58c26e59 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/HangingEntityItem.java.patch @@ -0,0 +1,44 @@ +--- a/net/minecraft/world/item/HangingEntityItem.java ++++ b/net/minecraft/world/item/HangingEntityItem.java +@@ -22,6 +21,11 @@ + import net.minecraft.world.level.Level; + import net.minecraft.world.level.gameevent.GameEvent; + ++// CraftBukkit start ++import org.bukkit.entity.Player; ++import org.bukkit.event.hanging.HangingPlaceEvent; ++// CraftBukkit end ++ + public class HangingEntityItem extends Item { + private static final Component TOOLTIP_RANDOM_VARIANT = Component.translatable("painting.random").withStyle(ChatFormatting.GRAY); + private final EntityType<? extends HangingEntity> type; +@@ -65,11 +74,24 @@ + EntityType.updateCustomEntityTag(level, player, hangingEntity, tag); + } + +- if (hangingEntity.survives()) { +- if (!level.isClientSide) { +- hangingEntity.playPlacementSound(); +- level.gameEvent(player, GameEvent.ENTITY_PLACE, hangingEntity.position()); +- level.addFreshEntity(hangingEntity); ++ if (((HangingEntity) object).survives()) { ++ if (!world.isClientSide) { ++ // CraftBukkit start - fire HangingPlaceEvent ++ Player who = (context.getPlayer() == null) ? null : (Player) context.getPlayer().getBukkitEntity(); ++ org.bukkit.block.Block blockClicked = world.getWorld().getBlockAt(blockposition.getX(), blockposition.getY(), blockposition.getZ()); ++ org.bukkit.block.BlockFace blockFace = org.bukkit.craftbukkit.block.CraftBlock.notchToBlockFace(enumdirection); ++ org.bukkit.inventory.EquipmentSlot hand = org.bukkit.craftbukkit.CraftEquipmentSlot.getHand(context.getHand()); ++ ++ HangingPlaceEvent event = new HangingPlaceEvent((org.bukkit.entity.Hanging) ((HangingEntity) object).getBukkitEntity(), who, blockClicked, blockFace, hand, org.bukkit.craftbukkit.inventory.CraftItemStack.asBukkitCopy(itemstack)); ++ world.getCraftServer().getPluginManager().callEvent(event); ++ ++ if (event.isCancelled()) { ++ return InteractionResult.FAIL; ++ } ++ // CraftBukkit end ++ ((HangingEntity) object).playPlacementSound(); ++ world.gameEvent((Entity) entityhuman, GameEvent.ENTITY_PLACE, ((HangingEntity) object).position()); ++ world.addFreshEntity((Entity) object); + } + + itemInHand.shrink(1); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ItemStack.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ItemStack.java.patch new file mode 100644 index 0000000000..e318ac0812 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/ItemStack.java.patch @@ -0,0 +1,327 @@ +--- a/net/minecraft/world/item/ItemStack.java ++++ b/net/minecraft/world/item/ItemStack.java +@@ -81,6 +82,41 @@ + import net.minecraft.world.level.block.state.pattern.BlockInWorld; + import org.slf4j.Logger; + ++// CraftBukkit start ++import com.mojang.serialization.Dynamic; ++import java.util.Map; ++import java.util.Objects; ++import net.minecraft.server.MinecraftServer; ++import net.minecraft.server.level.ServerLevel; ++import net.minecraft.server.level.ServerPlayer; ++import net.minecraft.sounds.SoundEvent; ++import net.minecraft.sounds.SoundSource; ++import net.minecraft.stats.Stats; ++import net.minecraft.util.datafix.fixes.DataConverterTypes; ++import net.minecraft.world.level.block.Blocks; ++import net.minecraft.world.level.block.SaplingBlock; ++import net.minecraft.world.level.block.SignBlock; ++import net.minecraft.world.level.block.SoundType; ++import net.minecraft.world.level.block.WitherSkullBlock; ++import net.minecraft.world.level.block.entity.BlockEntity; ++import net.minecraft.world.level.block.entity.JukeboxBlockEntity; ++import net.minecraft.world.level.block.entity.SignBlockEntity; ++import net.minecraft.world.level.block.entity.SkullBlockEntity; ++import net.minecraft.world.level.gameevent.GameEvent; ++import org.bukkit.Location; ++import org.bukkit.TreeType; ++import org.bukkit.block.BlockState; ++import org.bukkit.craftbukkit.block.CraftBlock; ++import org.bukkit.craftbukkit.block.CraftBlockState; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.util.CraftLocation; ++import org.bukkit.craftbukkit.util.CraftMagicNumbers; ++import org.bukkit.entity.Player; ++import org.bukkit.event.block.BlockFertilizeEvent; ++import org.bukkit.event.player.PlayerItemDamageEvent; ++import org.bukkit.event.world.StructureGrowEvent; ++// CraftBukkit end ++ + public final class ItemStack { + public static final Codec<ItemStack> CODEC = RecordCodecBuilder.create( + instance -> instance.group( +@@ -181,11 +211,22 @@ + this.item = null; + } + +- private ItemStack(CompoundTag compoundTag) { +- this.item = BuiltInRegistries.ITEM.get(new ResourceLocation(compoundTag.getString("id"))); +- this.count = compoundTag.getByte("Count"); +- if (compoundTag.contains("tag", 10)) { +- this.tag = compoundTag.getCompound("tag").copy(); ++ // Called to run this stack through the data converter to handle older storage methods and serialized items ++ public void convertStack(int version) { ++ if (0 < version && version < CraftMagicNumbers.INSTANCE.getDataVersion()) { ++ CompoundTag savedStack = new CompoundTag(); ++ this.save(savedStack); ++ savedStack = (CompoundTag) MinecraftServer.getServer().fixerUpper.update(DataConverterTypes.ITEM_STACK, new Dynamic(NbtOps.INSTANCE, savedStack), version, CraftMagicNumbers.INSTANCE.getDataVersion()).getValue(); ++ this.load(savedStack); ++ } ++ } ++ ++ // CraftBukkit - break into own method ++ private void load(CompoundTag nbttagcompound) { ++ this.item = (Item) BuiltInRegistries.ITEM.get(new ResourceLocation(nbttagcompound.getString("id"))); ++ this.count = nbttagcompound.getByte("Count"); ++ if (nbttagcompound.contains("tag", 10)) { ++ this.tag = nbttagcompound.getCompound("tag").copy(); + this.getItem().verifyTagAfterLoad(this.tag); + } + +@@ -194,6 +236,11 @@ + } + } + ++ private ItemStack(CompoundTag compoundTag) { ++ this.load(compoundTag); ++ // CraftBukkit end ++ } ++ + public static ItemStack of(CompoundTag compoundTag) { + try { + return new ItemStack(compoundTag); +@@ -270,12 +318,169 @@ + return InteractionResult.PASS; + } else { + Item item = this.getItem(); +- InteractionResult interactionResult = item.useOn(context); +- if (player != null && interactionResult.shouldAwardStats()) { +- player.awardStat(Stats.ITEM_USED.get(item)); ++ // CraftBukkit start - handle all block place event logic here ++ CompoundTag oldData = this.getTagClone(); ++ int oldCount = this.getCount(); ++ ServerLevel world = (ServerLevel) context.getLevel(); ++ ++ if (!(item instanceof BucketItem || item instanceof SolidBucketItem)) { // if not bucket ++ world.captureBlockStates = true; ++ // special case bonemeal ++ if (item == Items.BONE_MEAL) { ++ world.captureTreeGeneration = true; ++ } + } + +- return interactionResult; ++ BlockFertilizeEvent fertilizeEvent = new BlockFertilizeEvent(CraftBlock.at(world, blockposition), (Player) entityhuman.getBukkitEntity(), (List< BlockState>) (List<? extends BlockState>) blocks); ++ fertilizeEvent.setCancelled(structureEvent != null && structureEvent.isCancelled()); ++ org.bukkit.Bukkit.getPluginManager().callEvent(fertilizeEvent); ++ ++ if (!fertilizeEvent.isCancelled()) { ++ // Change the stack to its new contents if it hasn't been tampered with. ++ if (this.getCount() == oldCount && Objects.equals(this.tag, oldData)) { ++ this.setTag(newData); ++ this.setCount(newCount); ++ } ++ for (CraftBlockState blockstate : blocks) { ++ world.setBlock(blockstate.getPosition(),blockstate.getHandle(), blockstate.getFlag()); // SPIGOT-7248 - manual update to avoid physics where appropriate ++ } ++ entityhuman.awardStat(Stats.ITEM_USED.get(item)); // SPIGOT-7236 - award stat ++ } ++ ++ SignItem.openSign = null; // SPIGOT-6758 - Reset on early return ++ return enuminteractionresult; ++ } ++ world.captureTreeGeneration = false; ++ ++ if (entityhuman != null && enuminteractionresult.shouldAwardStats()) { ++ EnumHand enumhand = context.getHand(); ++ org.bukkit.event.block.BlockPlaceEvent placeEvent = null; ++ List<BlockState> blocks = new java.util.ArrayList<>(world.capturedBlockStates.values()); ++ world.capturedBlockStates.clear(); ++ if (blocks.size() > 1) { ++ placeEvent = org.bukkit.craftbukkit.event.CraftEventFactory.callBlockMultiPlaceEvent(world, entityhuman, enumhand, blocks, blockposition.getX(), blockposition.getY(), blockposition.getZ()); ++ } else if (blocks.size() == 1) { ++ placeEvent = org.bukkit.craftbukkit.event.CraftEventFactory.callBlockPlaceEvent(world, entityhuman, enumhand, blocks.get(0), blockposition.getX(), blockposition.getY(), blockposition.getZ()); ++ } ++ ++ if (placeEvent != null && (placeEvent.isCancelled() || !placeEvent.canBuild())) { ++ enuminteractionresult = InteractionResult.FAIL; // cancel placement ++ // PAIL: Remove this when MC-99075 fixed ++ placeEvent.getPlayer().updateInventory(); ++ // revert back all captured blocks ++ world.preventPoiUpdated = true; // CraftBukkit - SPIGOT-5710 ++ for (BlockState blockstate : blocks) { ++ blockstate.update(true, false); ++ } ++ world.preventPoiUpdated = false; ++ ++ // Brute force all possible updates ++ BlockPos placedPos = ((CraftBlock) placeEvent.getBlock()).getPosition(); ++ for (Direction dir : Direction.values()) { ++ ((ServerPlayer) entityhuman).connection.send(new ClientboundBlockUpdatePacket(world, placedPos.relative(dir))); ++ } ++ SignItem.openSign = null; // SPIGOT-6758 - Reset on early return ++ } else { ++ // Change the stack to its new contents if it hasn't been tampered with. ++ if (this.getCount() == oldCount && Objects.equals(this.tag, oldData)) { ++ this.setTag(newData); ++ this.setCount(newCount); ++ } ++ ++ for (Map.Entry<BlockPos, BlockEntity> e : world.capturedTileEntities.entrySet()) { ++ world.setBlockEntity(e.getValue()); ++ } ++ ++ for (BlockState blockstate : blocks) { ++ int updateFlag = ((CraftBlockState) blockstate).getFlag(); ++ IBlockData oldBlock = ((CraftBlockState) blockstate).getHandle(); ++ BlockPos newblockposition = ((CraftBlockState) blockstate).getPosition(); ++ IBlockData block = world.getBlockState(newblockposition); ++ ++ if (!(block.getBlock() instanceof BaseEntityBlock)) { // Containers get placed automatically ++ block.getBlock().onPlace(block, world, newblockposition, oldBlock, true); ++ } ++ ++ world.notifyAndUpdatePhysics(newblockposition, null, oldBlock, block, world.getBlockState(newblockposition), updateFlag, 512); // send null chunk as chunk.k() returns false by this point ++ } ++ ++ // Special case juke boxes as they update their tile entity. Copied from ItemRecord. ++ // PAIL: checkme on updates. ++ if (this.item instanceof RecordItem) { ++ BlockEntity tileentity = world.getBlockEntity(blockposition); ++ ++ if (tileentity instanceof JukeboxBlockEntity) { ++ JukeboxBlockEntity tileentityjukebox = (JukeboxBlockEntity) tileentity; ++ ++ // There can only be one ++ ItemStack record = this.copy(); ++ if (!record.isEmpty()) { ++ record.setCount(1); ++ } ++ ++ tileentityjukebox.setTheItem(record); ++ world.gameEvent(GameEvent.BLOCK_CHANGE, blockposition, GameEvent.Context.of(entityhuman, world.getBlockState(blockposition))); ++ } ++ ++ this.shrink(1); ++ entityhuman.awardStat(Stats.PLAY_RECORD); ++ } ++ ++ if (this.item == Items.WITHER_SKELETON_SKULL) { // Special case skulls to allow wither spawns to be cancelled ++ BlockPos bp = blockposition; ++ if (!world.getBlockState(blockposition).canBeReplaced()) { ++ if (!world.getBlockState(blockposition).isSolid()) { ++ bp = null; ++ } else { ++ bp = bp.relative(context.getClickedFace()); ++ } ++ } ++ if (bp != null) { ++ BlockEntity te = world.getBlockEntity(bp); ++ if (te instanceof SkullBlockEntity) { ++ WitherSkullBlock.checkSpawn(world, bp, (SkullBlockEntity) te); ++ } ++ } ++ } ++ ++ // SPIGOT-4678 ++ if (this.item instanceof SignItem && SignItem.openSign != null) { ++ try { ++ if (world.getBlockEntity(SignItem.openSign) instanceof SignBlockEntity tileentitysign) { ++ if (world.getBlockState(SignItem.openSign).getBlock() instanceof SignBlock blocksign) { ++ blocksign.openTextEdit(entityhuman, tileentitysign, true, org.bukkit.event.player.PlayerSignOpenEvent.Cause.PLACE); // Craftbukkit ++ } ++ } ++ } finally { ++ SignItem.openSign = null; ++ } ++ } ++ ++ // SPIGOT-7315: Moved from BlockBed#setPlacedBy ++ if (placeEvent != null && this.item instanceof BedItem) { ++ BlockPos position = ((CraftBlock) placeEvent.getBlock()).getPosition(); ++ IBlockData blockData = world.getBlockState(position); ++ ++ if (blockData.getBlock() instanceof BedBlock) { ++ world.blockUpdated(position, Blocks.AIR); ++ blockData.updateNeighbourShapes(world, position, 3); ++ } ++ } ++ ++ // SPIGOT-1288 - play sound stripped from ItemBlock ++ if (this.item instanceof BlockItem) { ++ SoundType soundeffecttype = ((BlockItem) this.item).getBlock().defaultBlockState().getSoundType(); // TODO: not strictly correct, however currently only affects decorated pots ++ world.playSound(entityhuman, blockposition, soundeffecttype.getPlaceSound(), SoundSource.BLOCKS, (soundeffecttype.getVolume() + 1.0F) / 2.0F, soundeffecttype.getPitch() * 0.8F); ++ } ++ ++ entityhuman.awardStat(Stats.ITEM_USED.get(item)); ++ } ++ } ++ world.capturedTileEntities.clear(); ++ world.capturedBlockStates.clear(); ++ // CraftBukkit end ++ ++ return enuminteractionresult; + } + } + +@@ -349,7 +581,22 @@ + } + } + +- amount -= i; ++ amount -= k; ++ // CraftBukkit start ++ if (user != null) { ++ PlayerItemDamageEvent event = new PlayerItemDamageEvent(user.getBukkitEntity(), CraftItemStack.asCraftMirror(this), amount); ++ event.getPlayer().getServer().getPluginManager().callEvent(event); ++ ++ if (amount != event.getDamage() || event.isCancelled()) { ++ event.getPlayer().updateInventory(); ++ } ++ if (event.isCancelled()) { ++ return false; ++ } ++ ++ amount = event.getDamage(); ++ } ++ // CraftBukkit end + if (amount <= 0) { + return false; + } +@@ -371,6 +618,12 @@ + if (this.hurt(amount, entity.getRandom(), entity instanceof ServerPlayer ? (ServerPlayer)entity : null)) { + onBroken.accept(entity); + Item item = this.getItem(); ++ // CraftBukkit start - Check for item breaking ++ if (this.count == 1 && entity instanceof net.minecraft.world.entity.player.Player) { ++ org.bukkit.craftbukkit.event.CraftEventFactory.callPlayerItemBreakEvent((net.minecraft.world.entity.player.Player) entity, this); ++ } ++ // CraftBukkit end ++ + this.shrink(1); + if (entity instanceof Player) { + ((Player)entity).awardStat(Stats.ITEM_BROKEN.get(item)); +@@ -513,6 +775,17 @@ + return this.tag; + } + ++ // CraftBukkit start ++ @Nullable ++ private CompoundTag getTagClone() { ++ return this.tag == null ? null : this.tag.copy(); ++ } ++ ++ private void setTagClone(@Nullable CompoundTag nbtttagcompound) { ++ this.setTag(nbtttagcompound == null ? null : nbtttagcompound.copy()); ++ } ++ // CraftBukkit end ++ + public CompoundTag getOrCreateTag() { + if (this.tag == null) { + this.setTag(new CompoundTag()); +@@ -925,6 +1210,13 @@ + list.add(compoundTag); + } + ++ // CraftBukkit start ++ @Deprecated ++ public void setItem(Item item) { ++ this.item = item; ++ } ++ // CraftBukkit end ++ + public Component getDisplayName() { + MutableComponent mutableComponent = Component.empty().append(this.getHoverName()); + if (this.hasCustomHoverName()) { diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/LeadItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/LeadItem.java.patch new file mode 100644 index 0000000000..db1ad8e4ff --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/LeadItem.java.patch @@ -0,0 +1,99 @@ +--- a/net/minecraft/world/item/LeadItem.java ++++ b/net/minecraft/world/item/LeadItem.java +@@ -11,6 +14,10 @@ + import net.minecraft.world.level.block.state.BlockState; + import net.minecraft.world.level.gameevent.GameEvent; + import net.minecraft.world.phys.AABB; ++// CraftBukkit start ++import org.bukkit.craftbukkit.CraftEquipmentSlot; ++import org.bukkit.event.hanging.HangingPlaceEvent; ++// CraftBukkit end + + public class LeadItem extends Item { + public LeadItem(Item.Properties properties) { +@@ -19,13 +27,15 @@ + + @Override + public InteractionResult useOn(UseOnContext context) { +- Level level = context.getLevel(); +- BlockPos clickedPos = context.getClickedPos(); +- BlockState blockState = level.getBlockState(clickedPos); +- if (blockState.is(BlockTags.FENCES)) { +- Player player = context.getPlayer(); +- if (!level.isClientSide && player != null) { +- bindPlayerMobs(player, level, clickedPos); ++ Level world = context.getLevel(); ++ BlockPos blockposition = context.getClickedPos(); ++ IBlockData iblockdata = world.getBlockState(blockposition); ++ ++ if (iblockdata.is(BlockTags.FENCES)) { ++ Player entityhuman = context.getPlayer(); ++ ++ if (!world.isClientSide && entityhuman != null) { ++ bindPlayerMobs(entityhuman, world, blockposition, context.getHand()); // CraftBukkit - Pass hand + } + + return InteractionResult.sidedSuccess(level.isClientSide); +@@ -34,24 +44,41 @@ + } + } + +- public static InteractionResult bindPlayerMobs(Player player, Level level, BlockPos pos) { +- LeashFenceKnotEntity leashFenceKnotEntity = null; ++ public static InteractionResult bindPlayerMobs(Player entityhuman, Level world, BlockPos blockposition, net.minecraft.world.EnumHand enumhand) { // CraftBukkit - Add EnumHand ++ LeashFenceKnotEntity entityleash = null; + boolean flag = false; + double d = 7.0; + int x = pos.getX(); + int y = pos.getY(); + int z = pos.getZ(); + +- for (Mob mob : level.getEntitiesOfClass( +- Mob.class, new AABB((double)x - 7.0, (double)y - 7.0, (double)z - 7.0, (double)x + 7.0, (double)y + 7.0, (double)z + 7.0) +- )) { +- if (mob.getLeashHolder() == player) { +- if (leashFenceKnotEntity == null) { +- leashFenceKnotEntity = LeashFenceKnotEntity.getOrCreateKnot(level, pos); +- leashFenceKnotEntity.playPlacementSound(); ++ while (iterator.hasNext()) { ++ Mob entityinsentient = (Mob) iterator.next(); ++ ++ if (entityinsentient.getLeashHolder() == entityhuman) { ++ if (entityleash == null) { ++ entityleash = LeashFenceKnotEntity.getOrCreateKnot(world, blockposition); ++ ++ // CraftBukkit start - fire HangingPlaceEvent ++ org.bukkit.inventory.EquipmentSlot hand = CraftEquipmentSlot.getHand(enumhand); ++ HangingPlaceEvent event = new HangingPlaceEvent((org.bukkit.entity.Hanging) entityleash.getBukkitEntity(), entityhuman != null ? (org.bukkit.entity.Player) entityhuman.getBukkitEntity() : null, world.getWorld().getBlockAt(i, j, k), org.bukkit.block.BlockFace.SELF, hand); ++ world.getCraftServer().getPluginManager().callEvent(event); ++ ++ if (event.isCancelled()) { ++ entityleash.discard(); ++ return InteractionResult.PASS; ++ } ++ // CraftBukkit end ++ entityleash.playPlacementSound(); + } + +- mob.setLeashedTo(leashFenceKnotEntity, true); ++ // CraftBukkit start ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callPlayerLeashEntityEvent(entityinsentient, entityleash, entityhuman, enumhand).isCancelled()) { ++ continue; ++ } ++ // CraftBukkit end ++ ++ entityinsentient.setLeashedTo(entityleash, true); + flag = true; + } + } +@@ -62,4 +91,10 @@ + + return flag ? InteractionResult.SUCCESS : InteractionResult.PASS; + } ++ ++ // CraftBukkit start ++ public static InteractionResult bindPlayerMobs(Player player, Level level, BlockPos pos) { ++ return bindPlayerMobs(player, level, pos, net.minecraft.world.EnumHand.MAIN_HAND); ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MapItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MapItem.java.patch new file mode 100644 index 0000000000..06b6d7d15a --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MapItem.java.patch @@ -0,0 +1,14 @@ +--- a/net/minecraft/world/item/MapItem.java ++++ b/net/minecraft/world/item/MapItem.java +@@ -64,8 +67,9 @@ + + @Nullable + public static Integer getMapId(ItemStack stack) { +- CompoundTag tag = stack.getTag(); +- return tag != null && tag.contains("map", 99) ? tag.getInt("map") : null; ++ CompoundTag nbttagcompound = stack.getTag(); ++ ++ return nbttagcompound != null && nbttagcompound.contains("map", 99) ? nbttagcompound.getInt("map") : -1; // CraftBukkit - make new maps for no tag + } + + private static int createNewSavedData( diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MilkBucketItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MilkBucketItem.java.patch new file mode 100644 index 0000000000..45e78e72b9 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MilkBucketItem.java.patch @@ -0,0 +1,11 @@ +--- a/net/minecraft/world/item/MilkBucketItem.java ++++ b/net/minecraft/world/item/MilkBucketItem.java +@@ -28,7 +31,7 @@ + } + + if (!level.isClientSide) { +- entityLiving.removeAllEffects(); ++ entityLiving.removeAllEffects(org.bukkit.event.entity.EntityPotionEffectEvent.Cause.MILK); // CraftBukkit + } + + return stack.isEmpty() ? new ItemStack(Items.BUCKET) : stack; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MinecartItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MinecartItem.java.patch new file mode 100644 index 0000000000..5c82298462 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/MinecartItem.java.patch @@ -0,0 +1,90 @@ +--- a/net/minecraft/world/item/MinecartItem.java ++++ b/net/minecraft/world/item/MinecartItem.java +@@ -17,6 +18,11 @@ + import net.minecraft.world.level.block.state.properties.RailShape; + import net.minecraft.world.level.gameevent.GameEvent; + import net.minecraft.world.phys.Vec3; ++// CraftBukkit start ++import org.bukkit.craftbukkit.block.CraftBlock; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.event.block.BlockDispenseEvent; ++// CraftBukkit end + + public class MinecartItem extends Item { + private static final DispenseItemBehavior DISPENSE_ITEM_BEHAVIOR = new DefaultDispenseItemBehavior() { +@@ -58,12 +63,40 @@ + } + } + +- AbstractMinecart abstractMinecart = AbstractMinecart.createMinecart( +- serverLevel, d, d1 + d3, d2, ((MinecartItem)itemStack.getItem()).type, itemStack, null +- ); +- serverLevel.addFreshEntity(abstractMinecart); +- itemStack.shrink(1); +- return itemStack; ++ // CraftBukkit start ++ // EntityMinecartAbstract entityminecartabstract = EntityMinecartAbstract.createMinecart(worldserver, d0, d1 + d3, d2, ((ItemMinecart) itemstack.getItem()).type); ++ ItemStack itemstack1 = itemstack.split(1); ++ org.bukkit.block.Block block2 = CraftBlock.at(worldserver, sourceblock.pos()); ++ CraftItemStack craftItem = CraftItemStack.asCraftMirror(itemstack1); ++ ++ BlockDispenseEvent event = new BlockDispenseEvent(block2, craftItem.clone(), new org.bukkit.util.Vector(d0, d1 + d3, d2)); ++ if (!DispenserBlock.eventFired) { ++ worldserver.getCraftServer().getPluginManager().callEvent(event); ++ } ++ ++ if (event.isCancelled()) { ++ itemstack.grow(1); ++ return itemstack; ++ } ++ ++ if (!event.getItem().equals(craftItem)) { ++ itemstack.grow(1); ++ // Chain to handler for new item ++ ItemStack eventStack = CraftItemStack.asNMSCopy(event.getItem()); ++ DispenseItemBehavior idispensebehavior = (DispenseItemBehavior) DispenserBlock.DISPENSER_REGISTRY.get(eventStack.getItem()); ++ if (idispensebehavior != DispenseItemBehavior.NOOP && idispensebehavior != this) { ++ idispensebehavior.dispense(sourceblock, eventStack); ++ return itemstack; ++ } ++ } ++ ++ itemstack1 = CraftItemStack.asNMSCopy(event.getItem()); ++ AbstractMinecart entityminecartabstract = AbstractMinecart.createMinecart(worldserver, event.getVelocity().getX(), event.getVelocity().getY(), event.getVelocity().getZ(), ((MinecartItem) itemstack1.getItem()).type, itemstack1, (Player) null); ++ ++ if (!worldserver.addFreshEntity(entityminecartabstract)) itemstack.grow(1); ++ // itemstack.shrink(1); // CraftBukkit - handled during event processing ++ // CraftBukkit end ++ return itemstack; + } + + @Override +@@ -97,19 +132,15 @@ + d = 0.5; + } + +- AbstractMinecart abstractMinecart = AbstractMinecart.createMinecart( +- serverLevel, +- (double)clickedPos.getX() + 0.5, +- (double)clickedPos.getY() + 0.0625 + d, +- (double)clickedPos.getZ() + 0.5, +- this.type, +- itemInHand, +- context.getPlayer() +- ); +- serverLevel.addFreshEntity(abstractMinecart); +- serverLevel.gameEvent( +- GameEvent.ENTITY_PLACE, clickedPos, GameEvent.Context.of(context.getPlayer(), serverLevel.getBlockState(clickedPos.below())) +- ); ++ AbstractMinecart entityminecartabstract = AbstractMinecart.createMinecart(worldserver, (double) blockposition.getX() + 0.5D, (double) blockposition.getY() + 0.0625D + d0, (double) blockposition.getZ() + 0.5D, this.type, itemstack, context.getPlayer()); ++ ++ // CraftBukkit start ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.callEntityPlaceEvent(context, entityminecartabstract).isCancelled()) { ++ return InteractionResult.FAIL; ++ } ++ // CraftBukkit end ++ if (!worldserver.addFreshEntity(entityminecartabstract)) return InteractionResult.PASS; // CraftBukkit ++ worldserver.gameEvent(GameEvent.ENTITY_PLACE, blockposition, GameEvent.Context.of(context.getPlayer(), worldserver.getBlockState(blockposition.below()))); + } + + itemInHand.shrink(1); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/PotionItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/PotionItem.java.patch new file mode 100644 index 0000000000..fce2791a33 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/PotionItem.java.patch @@ -0,0 +1,11 @@ +--- a/net/minecraft/world/item/PotionItem.java ++++ b/net/minecraft/world/item/PotionItem.java +@@ -51,7 +60,7 @@ + if (mobEffectInstance.getEffect().isInstantenous()) { + mobEffectInstance.getEffect().applyInstantenousEffect(player, player, entityLiving, mobEffectInstance.getAmplifier(), 1.0); + } else { +- entityLiving.addEffect(new MobEffectInstance(mobEffectInstance)); ++ entityLiving.addEffect(new MobEffectInstance(mobeffect), org.bukkit.event.entity.EntityPotionEffectEvent.Cause.POTION_DRINK); // CraftBukkit + } + } + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/RecordItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/RecordItem.java.patch new file mode 100644 index 0000000000..d1ff6cdcae --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/RecordItem.java.patch @@ -0,0 +1,36 @@ +--- a/net/minecraft/world/item/RecordItem.java ++++ b/net/minecraft/world/item/RecordItem.java +@@ -36,16 +38,23 @@ + + @Override + public InteractionResult useOn(UseOnContext context) { +- Level level = context.getLevel(); +- BlockPos clickedPos = context.getClickedPos(); +- BlockState blockState = level.getBlockState(clickedPos); +- if (blockState.is(Blocks.JUKEBOX) && !blockState.getValue(JukeboxBlock.HAS_RECORD)) { +- ItemStack itemInHand = context.getItemInHand(); +- if (!level.isClientSide) { +- Player player = context.getPlayer(); +- if (level.getBlockEntity(clickedPos) instanceof JukeboxBlockEntity jukeboxBlockEntity) { +- jukeboxBlockEntity.setTheItem(itemInHand.copy()); +- level.gameEvent(GameEvent.BLOCK_CHANGE, clickedPos, GameEvent.Context.of(player, blockState)); ++ Level world = context.getLevel(); ++ BlockPos blockposition = context.getClickedPos(); ++ IBlockData iblockdata = world.getBlockState(blockposition); ++ ++ if (iblockdata.is(Blocks.JUKEBOX) && !(Boolean) iblockdata.getValue(JukeboxBlock.HAS_RECORD)) { ++ ItemStack itemstack = context.getItemInHand(); ++ ++ if (!world.isClientSide) { ++ if (true) return InteractionResult.SUCCESS; // CraftBukkit - handled in ItemStack ++ Player entityhuman = context.getPlayer(); ++ BlockEntity tileentity = world.getBlockEntity(blockposition); ++ ++ if (tileentity instanceof JukeboxBlockEntity) { ++ JukeboxBlockEntity tileentityjukebox = (JukeboxBlockEntity) tileentity; ++ ++ tileentityjukebox.setTheItem(itemstack.copy()); ++ world.gameEvent(GameEvent.BLOCK_CHANGE, blockposition, GameEvent.Context.of(entityhuman, iblockdata)); + } + + itemInHand.shrink(1); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SignItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SignItem.java.patch new file mode 100644 index 0000000000..686ee12c1c --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SignItem.java.patch @@ -0,0 +1,42 @@ +--- a/net/minecraft/world/item/SignItem.java ++++ b/net/minecraft/world/item/SignItem.java +@@ -11,6 +12,9 @@ + import net.minecraft.world.level.block.state.BlockState; + + public class SignItem extends StandingAndWallBlockItem { ++ ++ public static BlockPos openSign; // CraftBukkit ++ + public SignItem(Item.Properties properties, Block standingBlock, Block wallBlock) { + super(standingBlock, wallBlock, properties, Direction.DOWN); + } +@@ -22,12 +26,23 @@ + @Override + protected boolean updateCustomBlockEntityTag(BlockPos pos, Level level, @Nullable Player player, ItemStack stack, BlockState state) { + boolean flag = super.updateCustomBlockEntityTag(pos, level, player, stack, state); +- if (!level.isClientSide +- && !flag +- && player != null +- && level.getBlockEntity(pos) instanceof SignBlockEntity signBlockEntity +- && level.getBlockState(pos).getBlock() instanceof SignBlock signBlock) { +- signBlock.openTextEdit(player, signBlockEntity, true); ++ ++ if (!level.isClientSide && !flag && player != null) { ++ BlockEntity tileentity = level.getBlockEntity(pos); ++ ++ if (tileentity instanceof SignBlockEntity) { ++ SignBlockEntity tileentitysign = (SignBlockEntity) tileentity; ++ Block block = level.getBlockState(pos).getBlock(); ++ ++ if (block instanceof SignBlock) { ++ SignBlock blocksign = (SignBlock) block; ++ ++ // CraftBukkit start - SPIGOT-4678 ++ // blocksign.openTextEdit(entityhuman, tileentitysign, true); ++ SignItem.openSign = pos; ++ // CraftBukkit end ++ } ++ } + } + + return flag; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SnowballItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SnowballItem.java.patch new file mode 100644 index 0000000000..84d40286bb --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SnowballItem.java.patch @@ -0,0 +1,41 @@ +--- a/net/minecraft/world/item/SnowballItem.java ++++ b/net/minecraft/world/item/SnowballItem.java +@@ -15,28 +16,24 @@ + } + + @Override +- public InteractionResultHolder<ItemStack> use(Level level, Player player, InteractionHand hand) { +- ItemStack itemInHand = player.getItemInHand(hand); +- level.playSound( +- null, +- player.getX(), +- player.getY(), +- player.getZ(), +- SoundEvents.SNOWBALL_THROW, +- SoundSource.NEUTRAL, +- 0.5F, +- 0.4F / (level.getRandom().nextFloat() * 0.4F + 0.8F) +- ); ++ public InteractionResultHolder<ItemStack> use(Level level, Player player, EnumHand hand) { ++ ItemStack itemstack = player.getItemInHand(hand); ++ ++ // CraftBukkit - moved down ++ // world.playSound((EntityHuman) null, entityhuman.getX(), entityhuman.getY(), entityhuman.getZ(), SoundEffects.SNOWBALL_THROW, SoundCategory.NEUTRAL, 0.5F, 0.4F / (world.getRandom().nextFloat() * 0.4F + 0.8F)); + if (!level.isClientSide) { + Snowball snowball = new Snowball(level, player); + snowball.setItem(itemInHand); + snowball.shootFromRotation(player, player.getXRot(), player.getYRot(), 0.0F, 1.5F, 1.0F); + level.addFreshEntity(snowball); + } ++ // CraftBukkit end + + player.awardStat(Stats.ITEM_USED.get(this)); +- if (!player.getAbilities().instabuild) { +- itemInHand.shrink(1); ++ // CraftBukkit start - moved up ++ /* ++ if (!entityhuman.getAbilities().instabuild) { ++ itemstack.shrink(1); + } + + return InteractionResultHolder.sidedSuccess(itemInHand, level.isClientSide()); diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SpawnEggItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SpawnEggItem.java.patch new file mode 100644 index 0000000000..dad4efbbc6 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/SpawnEggItem.java.patch @@ -0,0 +1,13 @@ +--- a/net/minecraft/world/item/SpawnEggItem.java ++++ b/net/minecraft/world/item/SpawnEggItem.java +@@ -176,8 +179,8 @@ + if (!breedOffspring.isBaby()) { + return Optional.empty(); + } else { +- breedOffspring.moveTo(pos.x(), pos.y(), pos.z(), 0.0F, 0.0F); +- serverLevel.addFreshEntityWithPassengers(breedOffspring); ++ ((Mob) object).moveTo(pos.x(), pos.y(), pos.z(), 0.0F, 0.0F); ++ serverLevel.addFreshEntityWithPassengers((Entity) object, org.bukkit.event.entity.CreatureSpawnEvent.SpawnReason.SPAWNER_EGG); // CraftBukkit + if (stack.hasCustomHoverName()) { + breedOffspring.setCustomName(stack.getHoverName()); + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/StandingAndWallBlockItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/StandingAndWallBlockItem.java.patch new file mode 100644 index 0000000000..5c47dd78db --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/StandingAndWallBlockItem.java.patch @@ -0,0 +1,34 @@ +--- a/net/minecraft/world/item/StandingAndWallBlockItem.java ++++ b/net/minecraft/world/item/StandingAndWallBlockItem.java +@@ -9,6 +11,10 @@ + import net.minecraft.world.level.block.Block; + import net.minecraft.world.level.block.state.BlockState; + import net.minecraft.world.phys.shapes.CollisionContext; ++import org.bukkit.craftbukkit.block.CraftBlock; ++import org.bukkit.craftbukkit.block.data.CraftBlockData; ++import org.bukkit.event.block.BlockCanBuildEvent; ++// CraftBukkit end + + public class StandingAndWallBlockItem extends BlockItem { + protected final Block wallBlock; +@@ -42,7 +54,19 @@ + } + } + +- return blockState != null && level.isUnobstructed(blockState, clickedPos, CollisionContext.empty()) ? blockState : null; ++ // CraftBukkit start ++ if (iblockdata1 != null) { ++ boolean defaultReturn = world.isUnobstructed(iblockdata1, blockposition, CollisionContext.empty()); ++ org.bukkit.entity.Player player = (context.getPlayer() instanceof ServerPlayer) ? (org.bukkit.entity.Player) context.getPlayer().getBukkitEntity() : null; ++ ++ BlockCanBuildEvent event = new BlockCanBuildEvent(CraftBlock.at(world, blockposition), player, CraftBlockData.fromData(iblockdata1), defaultReturn); ++ context.getLevel().getCraftServer().getPluginManager().callEvent(event); ++ ++ return (event.isBuildable()) ? iblockdata1 : null; ++ } else { ++ return null; ++ } ++ // CraftBukkit end + } + + @Override diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/TridentItem.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/TridentItem.java.patch new file mode 100644 index 0000000000..e2792900ad --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/TridentItem.java.patch @@ -0,0 +1,100 @@ +--- a/net/minecraft/world/item/TridentItem.java ++++ b/net/minecraft/world/item/TridentItem.java +@@ -62,39 +68,70 @@ + int riptide = EnchantmentHelper.getRiptide(stack); + if (riptide <= 0 || player.isInWaterOrRain()) { + if (!level.isClientSide) { +- stack.hurtAndBreak(1, player, contextEntity -> contextEntity.broadcastBreakEvent(entityLiving.getUsedItemHand())); +- if (riptide == 0) { +- ThrownTrident thrownTrident = new ThrownTrident(level, player, stack); +- thrownTrident.shootFromRotation(player, player.getXRot(), player.getYRot(), 0.0F, 2.5F + (float)riptide * 0.5F, 1.0F); +- if (player.getAbilities().instabuild) { +- thrownTrident.pickup = AbstractArrow.Pickup.CREATIVE_ONLY; ++ // CraftBukkit - moved down ++ /* ++ itemstack.hurtAndBreak(1, entityhuman, (entityhuman1) -> { ++ entityhuman1.broadcastBreakEvent(entityliving.getUsedItemHand()); ++ }); ++ */ ++ if (k == 0) { ++ ThrownTrident entitythrowntrident = new ThrownTrident(level, entityhuman, stack); ++ ++ entitythrowntrident.shootFromRotation(entityhuman, entityhuman.getXRot(), entityhuman.getYRot(), 0.0F, 2.5F + (float) k * 0.5F, 1.0F); ++ if (entityhuman.getAbilities().instabuild) { ++ entitythrowntrident.pickup = AbstractArrow.Pickup.CREATIVE_ONLY; + } + +- level.addFreshEntity(thrownTrident); +- level.playSound(null, thrownTrident, SoundEvents.TRIDENT_THROW, SoundSource.PLAYERS, 1.0F, 1.0F); +- if (!player.getAbilities().instabuild) { +- player.getInventory().removeItem(stack); ++ // CraftBukkit start ++ if (!level.addFreshEntity(entitythrowntrident)) { ++ if (entityhuman instanceof net.minecraft.server.level.ServerPlayer) { ++ ((net.minecraft.server.level.ServerPlayer) entityhuman).getBukkitEntity().updateInventory(); ++ } ++ return; + } ++ ++ stack.hurtAndBreak(1, entityhuman, (entityhuman1) -> { ++ entityhuman1.broadcastBreakEvent(entityLiving.getUsedItemHand()); ++ }); ++ entitythrowntrident.pickupItemStack = stack.copy(); // SPIGOT-4511 update since damage call moved ++ // CraftBukkit end ++ ++ level.playSound((Player) null, (Entity) entitythrowntrident, SoundEvents.TRIDENT_THROW, SoundSource.PLAYERS, 1.0F, 1.0F); ++ if (!entityhuman.getAbilities().instabuild) { ++ entityhuman.getInventory().removeItem(stack); ++ } ++ // CraftBukkit start - SPIGOT-5458 also need in this branch :( ++ } else { ++ stack.hurtAndBreak(1, entityhuman, (entityhuman1) -> { ++ entityhuman1.broadcastBreakEvent(entityLiving.getUsedItemHand()); ++ }); ++ // CraftBukkkit end + } + } + +- player.awardStat(Stats.ITEM_USED.get(this)); +- if (riptide > 0) { +- float yRot = player.getYRot(); +- float xRot = player.getXRot(); +- float f = -Mth.sin(yRot * (float) (Math.PI / 180.0)) * Mth.cos(xRot * (float) (Math.PI / 180.0)); +- float f1 = -Mth.sin(xRot * (float) (Math.PI / 180.0)); +- float f2 = Mth.cos(yRot * (float) (Math.PI / 180.0)) * Mth.cos(xRot * (float) (Math.PI / 180.0)); +- float squareRoot = Mth.sqrt(f * f + f1 * f1 + f2 * f2); +- float f3 = 3.0F * ((1.0F + (float)riptide) / 4.0F); +- f *= f3 / squareRoot; +- f1 *= f3 / squareRoot; +- f2 *= f3 / squareRoot; +- player.push((double)f, (double)f1, (double)f2); +- player.startAutoSpinAttack(20); +- if (player.onGround()) { +- float f4 = 1.1999999F; +- player.move(MoverType.SELF, new Vec3(0.0, 1.1999999F, 0.0)); ++ entityhuman.awardStat(Stats.ITEM_USED.get(this)); ++ if (k > 0) { ++ // CraftBukkit start ++ org.bukkit.event.player.PlayerRiptideEvent event = new org.bukkit.event.player.PlayerRiptideEvent((org.bukkit.entity.Player) entityhuman.getBukkitEntity(), org.bukkit.craftbukkit.inventory.CraftItemStack.asCraftMirror(stack)); ++ event.getPlayer().getServer().getPluginManager().callEvent(event); ++ // CraftBukkit end ++ float f = entityhuman.getYRot(); ++ float f1 = entityhuman.getXRot(); ++ float f2 = -Mth.sin(f * 0.017453292F) * Mth.cos(f1 * 0.017453292F); ++ float f3 = -Mth.sin(f1 * 0.017453292F); ++ float f4 = Mth.cos(f * 0.017453292F) * Mth.cos(f1 * 0.017453292F); ++ float f5 = Mth.sqrt(f2 * f2 + f3 * f3 + f4 * f4); ++ float f6 = 3.0F * ((1.0F + (float) k) / 4.0F); ++ ++ f2 *= f6 / f5; ++ f3 *= f6 / f5; ++ f4 *= f6 / f5; ++ entityhuman.push((double) f2, (double) f3, (double) f4); ++ entityhuman.startAutoSpinAttack(20); ++ if (entityhuman.onGround()) { ++ float f7 = 1.1999999F; ++ ++ entityhuman.move(EnumMoveType.SELF, new Vec3(0.0D, 1.1999999284744263D, 0.0D)); + } + + SoundEvent soundEvent; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/BlastingRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/BlastingRecipe.java.patch new file mode 100644 index 0000000000..f73982496b --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/BlastingRecipe.java.patch @@ -0,0 +1,35 @@ +--- a/net/minecraft/world/item/crafting/BlastingRecipe.java ++++ b/net/minecraft/world/item/crafting/BlastingRecipe.java +@@ -3,6 +3,14 @@ + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.block.Blocks; + ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftBlastingRecipe; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end ++ + public class BlastingRecipe extends AbstractCookingRecipe { + public BlastingRecipe(String string, CookingBookCategory cookingBookCategory, Ingredient ingredient, ItemStack itemStack, float f, int i) { + super(RecipeType.BLASTING, string, cookingBookCategory, ingredient, itemStack, f, i); +@@ -17,4 +26,17 @@ + public RecipeSerializer<?> getSerializer() { + return RecipeSerializer.BLASTING_RECIPE; + } ++ ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ ++ CraftBlastingRecipe recipe = new CraftBlastingRecipe(id, result, CraftRecipe.toBukkit(this.ingredient), this.experience, this.cookingTime); ++ recipe.setGroup(this.group); ++ recipe.setCategory(CraftRecipe.getCategory(this.category())); ++ ++ return recipe; ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/CampfireCookingRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/CampfireCookingRecipe.java.patch new file mode 100644 index 0000000000..c33d2d4a9b --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/CampfireCookingRecipe.java.patch @@ -0,0 +1,35 @@ +--- a/net/minecraft/world/item/crafting/CampfireCookingRecipe.java ++++ b/net/minecraft/world/item/crafting/CampfireCookingRecipe.java +@@ -3,6 +3,14 @@ + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.block.Blocks; + ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftCampfireRecipe; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end ++ + public class CampfireCookingRecipe extends AbstractCookingRecipe { + public CampfireCookingRecipe(String string, CookingBookCategory cookingBookCategory, Ingredient ingredient, ItemStack itemStack, float f, int i) { + super(RecipeType.CAMPFIRE_COOKING, string, cookingBookCategory, ingredient, itemStack, f, i); +@@ -17,4 +26,17 @@ + public RecipeSerializer<?> getSerializer() { + return RecipeSerializer.CAMPFIRE_COOKING_RECIPE; + } ++ ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ ++ CraftCampfireRecipe recipe = new CraftCampfireRecipe(id, result, CraftRecipe.toBukkit(this.ingredient), this.experience, this.cookingTime); ++ recipe.setGroup(this.group); ++ recipe.setCategory(CraftRecipe.getCategory(this.category())); ++ ++ return recipe; ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/CustomRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/CustomRecipe.java.patch new file mode 100644 index 0000000000..0a032bd01d --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/CustomRecipe.java.patch @@ -0,0 +1,29 @@ +--- a/net/minecraft/world/item/crafting/CustomRecipe.java ++++ b/net/minecraft/world/item/crafting/CustomRecipe.java +@@ -3,7 +3,13 @@ + import net.minecraft.core.RegistryAccess; + import net.minecraft.world.item.ItemStack; + +-public abstract class CustomRecipe implements CraftingRecipe { ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end ++ ++public abstract class CustomRecipe implements RecipeCrafting { ++ + private final CraftingBookCategory category; + + public CustomRecipe(CraftingBookCategory craftingBookCategory) { +@@ -24,4 +30,11 @@ + public CraftingBookCategory category() { + return this.category; + } ++ ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ return new org.bukkit.craftbukkit.inventory.CraftComplexRecipe(id, this); ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/Ingredient.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/Ingredient.java.patch new file mode 100644 index 0000000000..17af072826 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/Ingredient.java.patch @@ -0,0 +1,35 @@ +--- a/net/minecraft/world/item/crafting/Ingredient.java ++++ b/net/minecraft/world/item/crafting/Ingredient.java +@@ -34,6 +35,7 @@ + private ItemStack[] itemStacks; + @Nullable + private IntList stackingIds; ++ public boolean exact; // CraftBukkit + public static final Codec<Ingredient> CODEC = codec(true); + public static final Codec<Ingredient> CODEC_NONEMPTY = codec(false); + +@@ -60,8 +67,22 @@ + } else if (this.isEmpty()) { + return stack.isEmpty(); + } else { +- for (ItemStack itemStack : this.getItems()) { +- if (itemStack.is(stack.getItem())) { ++ ItemStack[] aitemstack = this.getItems(); ++ int i = aitemstack.length; ++ ++ for (int j = 0; j < i; ++j) { ++ ItemStack itemstack1 = aitemstack[j]; ++ ++ // CraftBukkit start ++ if (exact) { ++ if (itemstack1.getItem() == stack.getItem() && ItemStack.isSameItemSameTags(stack, itemstack1)) { ++ return true; ++ } ++ ++ continue; ++ } ++ // CraftBukkit end ++ if (itemstack1.is(stack.getItem())) { + return true; + } + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/Recipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/Recipe.java.patch new file mode 100644 index 0000000000..00d4c5ced3 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/Recipe.java.patch @@ -0,0 +1,9 @@ +--- a/net/minecraft/world/item/crafting/Recipe.java ++++ b/net/minecraft/world/item/crafting/Recipe.java +@@ -62,4 +67,6 @@ + NonNullList<Ingredient> ingredients = this.getIngredients(); + return ingredients.isEmpty() || ingredients.stream().anyMatch(ingredient -> ingredient.getItems().length == 0); + } ++ ++ org.bukkit.inventory.Recipe toBukkitRecipe(org.bukkit.NamespacedKey id); // CraftBukkit + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/RecipeHolder.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/RecipeHolder.java.patch new file mode 100644 index 0000000000..d7bfcda029 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/RecipeHolder.java.patch @@ -0,0 +1,22 @@ +--- a/net/minecraft/world/item/crafting/RecipeHolder.java ++++ b/net/minecraft/world/item/crafting/RecipeHolder.java +@@ -1,9 +1,17 @@ + package net.minecraft.world.item.crafting; + + import net.minecraft.resources.ResourceLocation; ++// CraftBukkit start ++import org.bukkit.craftbukkit.util.CraftNamespacedKey; ++import org.bukkit.inventory.Recipe; + +-public record RecipeHolder<T extends Recipe<?>>(ResourceLocation id, T value) { +- @Override ++public record RecipeHolder<T extends net.minecraft.world.item.crafting.Recipe<?>>(ResourceLocation id, T value) { ++ ++ public final Recipe toBukkitRecipe() { ++ return this.value.toBukkitRecipe(CraftNamespacedKey.fromMinecraft(this.id)); ++ } ++ // CraftBukkit end ++ + public boolean equals(Object object) { + if (this == object) { + return true; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/RecipeManager.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/RecipeManager.java.patch new file mode 100644 index 0000000000..ea766ea2ff --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/RecipeManager.java.patch @@ -0,0 +1,165 @@ +--- a/net/minecraft/world/item/crafting/RecipeManager.java ++++ b/net/minecraft/world/item/crafting/RecipeManager.java +@@ -23,6 +24,15 @@ + import javax.annotation.Nullable; + import net.minecraft.Util; + import net.minecraft.core.NonNullList; ++import net.minecraft.world.Container; ++import net.minecraft.world.item.ItemStack; ++import net.minecraft.world.level.Level; ++import org.slf4j.Logger; ++ ++// CraftBukkit start ++import it.unimi.dsi.fastutil.objects.Object2ObjectLinkedOpenHashMap; ++import net.minecraft.core.registries.BuiltInRegistries; ++// CraftBukkit end + import net.minecraft.resources.ResourceLocation; + import net.minecraft.server.packs.resources.ResourceManager; + import net.minecraft.server.packs.resources.SimpleJsonResourceReloadListener; +@@ -36,7 +43,7 @@ + public class RecipeManager extends SimpleJsonResourceReloadListener { + private static final Gson GSON = new GsonBuilder().setPrettyPrinting().disableHtmlEscaping().create(); + private static final Logger LOGGER = LogUtils.getLogger(); +- private Map<RecipeType<?>, Map<ResourceLocation, RecipeHolder<?>>> recipes = ImmutableMap.of(); ++ public Map<RecipeType<?>, Object2ObjectLinkedOpenHashMap<ResourceLocation, RecipeHolder<?>>> recipes = ImmutableMap.of(); // CraftBukkit + private Map<ResourceLocation, RecipeHolder<?>> byName = ImmutableMap.of(); + private boolean hasErrors; + +@@ -47,32 +53,63 @@ + @Override + protected void apply(Map<ResourceLocation, JsonElement> object, ResourceManager resourceManager, ProfilerFiller profiler) { + this.hasErrors = false; +- Map<RecipeType<?>, Builder<ResourceLocation, RecipeHolder<?>>> map = Maps.newHashMap(); ++ // CraftBukkit start - SPIGOT-5667 make sure all types are populated and mutable ++ Map<RecipeType<?>, Object2ObjectLinkedOpenHashMap<ResourceLocation, RecipeHolder<?>>> map1 = Maps.newHashMap(); ++ for (RecipeType<?> recipeType : BuiltInRegistries.RECIPE_TYPE) { ++ map1.put(recipeType, new Object2ObjectLinkedOpenHashMap<>()); ++ } ++ // CraftBukkit end + Builder<ResourceLocation, RecipeHolder<?>> builder = ImmutableMap.builder(); + + for (Entry<ResourceLocation, JsonElement> entry : object.entrySet()) { + ResourceLocation resourceLocation = entry.getKey(); + + try { +- RecipeHolder<?> recipeHolder = fromJson(resourceLocation, GsonHelper.convertToJsonObject(entry.getValue(), "top element")); +- map.computeIfAbsent(recipeHolder.value().getType(), type -> ImmutableMap.builder()).put(resourceLocation, recipeHolder); +- builder.put(resourceLocation, recipeHolder); +- } catch (IllegalArgumentException | JsonParseException var10) { +- LOGGER.error("Parsing error loading recipe {}", resourceLocation, var10); ++ RecipeHolder<?> recipeholder = fromJson(minecraftkey, GsonHelper.convertToJsonObject((JsonElement) entry.getValue(), "top element")); ++ ++ // CraftBukkit start ++ (map1.computeIfAbsent(recipeholder.value().getType(), (recipes) -> { ++ return new Object2ObjectLinkedOpenHashMap<>(); ++ // CraftBukkit end ++ })).put(minecraftkey, recipeholder); ++ builder.put(minecraftkey, recipeholder); ++ } catch (IllegalArgumentException | JsonParseException jsonparseexception) { ++ RecipeManager.LOGGER.error("Parsing error loading recipe {}", minecraftkey, jsonparseexception); + } + } + +- this.recipes = map.entrySet().stream().collect(ImmutableMap.toImmutableMap(Entry::getKey, entry1 -> entry1.getValue().build())); +- this.byName = builder.build(); +- LOGGER.info("Loaded {} recipes", map.size()); ++ this.recipes = (Map) map1.entrySet().stream().collect(ImmutableMap.toImmutableMap(Entry::getKey, (entry1) -> { ++ return (entry1.getValue()); // CraftBukkit ++ })); ++ this.byName = Maps.newHashMap(builder.build()); // CraftBukkit ++ RecipeManager.LOGGER.info("Loaded {} recipes", map1.size()); + } + ++ // CraftBukkit start ++ public void addRecipe(RecipeHolder<?> irecipe) { ++ Object2ObjectLinkedOpenHashMap<ResourceLocation, RecipeHolder<?>> map = this.recipes.get(irecipe.value().getType()); // CraftBukkit ++ ++ if (byName.containsKey(irecipe.id()) || map.containsKey(irecipe.id())) { ++ throw new IllegalStateException("Duplicate recipe ignored with ID " + irecipe.id()); ++ } else { ++ map.putAndMoveToFirst(irecipe.id(), irecipe); // CraftBukkit - SPIGOT-4638: last recipe gets priority ++ byName.put(irecipe.id(), irecipe); ++ } ++ } ++ // CraftBukkit end ++ + public boolean hadErrorsLoading() { + return this.hasErrors; + } + + public <C extends Container, T extends Recipe<C>> Optional<RecipeHolder<T>> getRecipeFor(RecipeType<T> recipeType, C inventory, Level level) { +- return this.byType(recipeType).values().stream().filter(recipeHolder -> recipeHolder.value().matches(inventory, level)).findFirst(); ++ // CraftBukkit start ++ Optional<RecipeHolder<T>> recipe = this.byType(recipeType).values().stream().filter((recipeholder) -> { ++ return recipeholder.value().matches(inventory, level); ++ }).findFirst(); ++ inventory.setCurrentRecipe(recipe.orElse(null)); // CraftBukkit - Clear recipe when no recipe is found ++ return recipe; ++ // CraftBukkit end + } + + public <C extends Container, T extends Recipe<C>> Optional<Pair<ResourceLocation, RecipeHolder<T>>> getRecipeFor( +@@ -107,7 +145,7 @@ + } + + private <C extends Container, T extends Recipe<C>> Map<ResourceLocation, RecipeHolder<T>> byType(RecipeType<T> recipeType) { +- return (Map<ResourceLocation, RecipeHolder<T>>) ((Map<ResourceLocation, ?>) this.recipes.getOrDefault(recipeType, Collections.emptyMap())); ++ return (Map) this.recipes.getOrDefault(recipeType, new Object2ObjectLinkedOpenHashMap<>()); // CraftBukkit + } + + public <C extends Container, T extends Recipe<C>> NonNullList<ItemStack> getRemainingItemsFor(RecipeType<T> recipeType, C inventory, Level level) { +@@ -144,21 +188,45 @@ + + public void replaceRecipes(Iterable<RecipeHolder<?>> recipes) { + this.hasErrors = false; +- Map<RecipeType<?>, Map<ResourceLocation, RecipeHolder<?>>> map = Maps.newHashMap(); ++ Map<RecipeType<?>, Object2ObjectLinkedOpenHashMap<ResourceLocation, RecipeHolder<?>>> map = Maps.newHashMap(); // CraftBukkit + Builder<ResourceLocation, RecipeHolder<?>> builder = ImmutableMap.builder(); +- recipes.forEach(recipeHolder -> { +- Map<ResourceLocation, RecipeHolder<?>> map1 = map.computeIfAbsent(recipeHolder.value().getType(), recipeType -> Maps.newHashMap()); +- ResourceLocation resourceLocation = recipeHolder.id(); +- RecipeHolder<?> recipeHolder1 = map1.put(resourceLocation, (RecipeHolder<?>)recipeHolder); +- builder.put(resourceLocation, (RecipeHolder<?>)recipeHolder); +- if (recipeHolder1 != null) { +- throw new IllegalStateException("Duplicate recipe ignored with ID " + resourceLocation); ++ ++ recipes.forEach((recipeholder) -> { ++ Map<ResourceLocation, RecipeHolder<?>> map1 = (Map) map.computeIfAbsent(recipeholder.value().getType(), (recipes) -> { ++ return new Object2ObjectLinkedOpenHashMap<>(); // CraftBukkit ++ }); ++ ResourceLocation minecraftkey = recipeholder.id(); ++ RecipeHolder<?> recipeholder1 = (RecipeHolder) map1.put(minecraftkey, recipeholder); ++ ++ builder.put(minecraftkey, recipeholder); ++ if (recipeholder1 != null) { ++ throw new IllegalStateException("Duplicate recipe ignored with ID " + minecraftkey); + } + }); + this.recipes = ImmutableMap.copyOf(map); +- this.byName = builder.build(); ++ this.byName = Maps.newHashMap(builder.build()); // CraftBukkit + } + ++ // CraftBukkit start ++ public boolean removeRecipe(ResourceLocation mcKey) { ++ for (Object2ObjectLinkedOpenHashMap<ResourceLocation, RecipeHolder<?>> recipes : recipes.values()) { ++ recipes.remove(mcKey); ++ } ++ ++ return byName.remove(mcKey) != null; ++ } ++ ++ public void clearRecipes() { ++ this.recipes = Maps.newHashMap(); ++ ++ for (RecipeType<?> recipeType : BuiltInRegistries.RECIPE_TYPE) { ++ this.recipes.put(recipeType, new Object2ObjectLinkedOpenHashMap<>()); ++ } ++ ++ this.byName = Maps.newHashMap(); ++ } ++ // CraftBukkit end ++ + public static <C extends Container, T extends Recipe<C>> RecipeManager.CachedCheck<C, T> createCheck(final RecipeType<T> recipeType) { + return new RecipeManager.CachedCheck<C, T>() { + @Nullable diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/ShapedRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/ShapedRecipe.java.patch new file mode 100644 index 0000000000..f5537291f4 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/ShapedRecipe.java.patch @@ -0,0 +1,86 @@ +--- a/net/minecraft/world/item/crafting/ShapedRecipe.java ++++ b/net/minecraft/world/item/crafting/ShapedRecipe.java +@@ -10,6 +9,13 @@ + import net.minecraft.world.inventory.CraftingContainer; + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.Level; ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.craftbukkit.inventory.CraftShapedRecipe; ++import org.bukkit.inventory.RecipeChoice; ++// CraftBukkit end + + public class ShapedRecipe implements CraftingRecipe { + final ShapedRecipePattern pattern; +@@ -30,7 +37,69 @@ + this(string, craftingBookCategory, shapedRecipePattern, itemStack, true); + } + ++ // CraftBukkit start + @Override ++ public org.bukkit.inventory.ShapedRecipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ CraftShapedRecipe recipe = new CraftShapedRecipe(id, result, this); ++ recipe.setGroup(this.group); ++ recipe.setCategory(CraftRecipe.getCategory(this.category())); ++ ++ switch (this.pattern.height()) { ++ case 1: ++ switch (this.pattern.width()) { ++ case 1: ++ recipe.shape("a"); ++ break; ++ case 2: ++ recipe.shape("ab"); ++ break; ++ case 3: ++ recipe.shape("abc"); ++ break; ++ } ++ break; ++ case 2: ++ switch (this.pattern.width()) { ++ case 1: ++ recipe.shape("a","b"); ++ break; ++ case 2: ++ recipe.shape("ab","cd"); ++ break; ++ case 3: ++ recipe.shape("abc","def"); ++ break; ++ } ++ break; ++ case 3: ++ switch (this.pattern.width()) { ++ case 1: ++ recipe.shape("a","b","c"); ++ break; ++ case 2: ++ recipe.shape("ab","cd","ef"); ++ break; ++ case 3: ++ recipe.shape("abc","def","ghi"); ++ break; ++ } ++ break; ++ } ++ char c = 'a'; ++ for (Ingredient list : this.pattern.ingredients()) { ++ RecipeChoice choice = CraftRecipe.toBukkit(list); ++ if (choice != null) { ++ recipe.setIngredient(c, choice); ++ } ++ ++ c++; ++ } ++ return recipe; ++ } ++ // CraftBukkit end ++ ++ @Override + public RecipeSerializer<?> getSerializer() { + return RecipeSerializer.SHAPED_RECIPE; + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/ShapelessRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/ShapelessRecipe.java.patch new file mode 100644 index 0000000000..97a06c348e --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/ShapelessRecipe.java.patch @@ -0,0 +1,39 @@ +--- a/net/minecraft/world/item/crafting/ShapelessRecipe.java ++++ b/net/minecraft/world/item/crafting/ShapelessRecipe.java +@@ -13,6 +13,12 @@ + import net.minecraft.world.inventory.CraftingContainer; + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.Level; ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.craftbukkit.inventory.CraftShapelessRecipe; ++// CraftBukkit end + + public class ShapelessRecipe implements CraftingRecipe { + final String group; +@@ -27,7 +34,23 @@ + this.ingredients = list; + } + ++ // CraftBukkit start ++ @SuppressWarnings("unchecked") + @Override ++ public org.bukkit.inventory.ShapelessRecipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ CraftShapelessRecipe recipe = new CraftShapelessRecipe(id, result, this); ++ recipe.setGroup(this.group); ++ recipe.setCategory(CraftRecipe.getCategory(this.category())); ++ ++ for (Ingredient list : this.ingredients) { ++ recipe.addIngredient(CraftRecipe.toBukkit(list)); ++ } ++ return recipe; ++ } ++ // CraftBukkit end ++ ++ @Override + public RecipeSerializer<?> getSerializer() { + return RecipeSerializer.SHAPELESS_RECIPE; + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmeltingRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmeltingRecipe.java.patch new file mode 100644 index 0000000000..352ab54802 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmeltingRecipe.java.patch @@ -0,0 +1,35 @@ +--- a/net/minecraft/world/item/crafting/SmeltingRecipe.java ++++ b/net/minecraft/world/item/crafting/SmeltingRecipe.java +@@ -3,6 +3,14 @@ + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.block.Blocks; + ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftFurnaceRecipe; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end ++ + public class SmeltingRecipe extends AbstractCookingRecipe { + public SmeltingRecipe(String string, CookingBookCategory cookingBookCategory, Ingredient ingredient, ItemStack itemStack, float f, int i) { + super(RecipeType.SMELTING, string, cookingBookCategory, ingredient, itemStack, f, i); +@@ -17,4 +26,17 @@ + public RecipeSerializer<?> getSerializer() { + return RecipeSerializer.SMELTING_RECIPE; + } ++ ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ ++ CraftFurnaceRecipe recipe = new CraftFurnaceRecipe(id, result, CraftRecipe.toBukkit(this.ingredient), this.experience, this.cookingTime); ++ recipe.setGroup(this.group); ++ recipe.setCategory(CraftRecipe.getCategory(this.category())); ++ ++ return recipe; ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmithingTransformRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmithingTransformRecipe.java.patch new file mode 100644 index 0000000000..1928a3054d --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmithingTransformRecipe.java.patch @@ -0,0 +1,60 @@ +--- a/net/minecraft/world/item/crafting/SmithingTransformRecipe.java ++++ b/net/minecraft/world/item/crafting/SmithingTransformRecipe.java +@@ -10,6 +9,13 @@ + import net.minecraft.world.Container; + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.Level; ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.craftbukkit.inventory.CraftSmithingTransformRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end + + public class SmithingTransformRecipe implements SmithingRecipe { + final Ingredient template; +@@ -70,17 +78,33 @@ + return Stream.of(this.template, this.base, this.addition).anyMatch(Ingredient::isEmpty); + } + +- public static class Serializer implements RecipeSerializer<SmithingTransformRecipe> { +- private static final Codec<SmithingTransformRecipe> CODEC = RecordCodecBuilder.create( +- instance -> instance.group( +- Ingredient.CODEC.fieldOf("template").forGetter(smithingTransformRecipe -> smithingTransformRecipe.template), +- Ingredient.CODEC.fieldOf("base").forGetter(smithingTransformRecipe -> smithingTransformRecipe.base), +- Ingredient.CODEC.fieldOf("addition").forGetter(smithingTransformRecipe -> smithingTransformRecipe.addition), +- ItemStack.ITEM_WITH_COUNT_CODEC.fieldOf("result").forGetter(smithingTransformRecipe -> smithingTransformRecipe.result) +- ) +- .apply(instance, SmithingTransformRecipe::new) +- ); ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); + ++ CraftSmithingTransformRecipe recipe = new CraftSmithingTransformRecipe(id, result, CraftRecipe.toBukkit(this.template), CraftRecipe.toBukkit(this.base), CraftRecipe.toBukkit(this.addition)); ++ ++ return recipe; ++ } ++ // CraftBukkit end ++ ++ public static class a implements RecipeSerializer<SmithingTransformRecipe> { ++ ++ private static final Codec<SmithingTransformRecipe> CODEC = RecordCodecBuilder.create((instance) -> { ++ return instance.group(Ingredient.CODEC.fieldOf("template").forGetter((smithingtransformrecipe) -> { ++ return smithingtransformrecipe.template; ++ }), Ingredient.CODEC.fieldOf("base").forGetter((smithingtransformrecipe) -> { ++ return smithingtransformrecipe.base; ++ }), Ingredient.CODEC.fieldOf("addition").forGetter((smithingtransformrecipe) -> { ++ return smithingtransformrecipe.addition; ++ }), ItemStack.ITEM_WITH_COUNT_CODEC.fieldOf("result").forGetter((smithingtransformrecipe) -> { ++ return smithingtransformrecipe.result; ++ })).apply(instance, SmithingTransformRecipe::new); ++ }); ++ ++ public a() {} ++ + @Override + public Codec<SmithingTransformRecipe> codec() { + return CODEC; diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmithingTrimRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmithingTrimRecipe.java.patch new file mode 100644 index 0000000000..400058b878 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmithingTrimRecipe.java.patch @@ -0,0 +1,37 @@ +--- a/net/minecraft/world/item/crafting/SmithingTrimRecipe.java ++++ b/net/minecraft/world/item/crafting/SmithingTrimRecipe.java +@@ -18,6 +17,12 @@ + import net.minecraft.world.item.armortrim.TrimPattern; + import net.minecraft.world.item.armortrim.TrimPatterns; + import net.minecraft.world.level.Level; ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.craftbukkit.inventory.CraftSmithingTrimRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end + + public class SmithingTrimRecipe implements SmithingRecipe { + final Ingredient template; +@@ -99,15 +113,12 @@ + return Stream.of(this.template, this.base, this.addition).anyMatch(Ingredient::isEmpty); + } + +- public static class Serializer implements RecipeSerializer<SmithingTrimRecipe> { +- private static final Codec<SmithingTrimRecipe> CODEC = RecordCodecBuilder.create( +- instance -> instance.group( +- Ingredient.CODEC.fieldOf("template").forGetter(smithingTrimRecipe -> smithingTrimRecipe.template), +- Ingredient.CODEC.fieldOf("base").forGetter(smithingTrimRecipe -> smithingTrimRecipe.base), +- Ingredient.CODEC.fieldOf("addition").forGetter(smithingTrimRecipe -> smithingTrimRecipe.addition) +- ) +- .apply(instance, SmithingTrimRecipe::new) +- ); ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ return new CraftSmithingTrimRecipe(id, CraftRecipe.toBukkit(this.template), CraftRecipe.toBukkit(this.base), CraftRecipe.toBukkit(this.addition)); ++ } ++ // CraftBukkit end + + @Override + public Codec<SmithingTrimRecipe> codec() { diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmokingRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmokingRecipe.java.patch new file mode 100644 index 0000000000..8ca8e06845 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/SmokingRecipe.java.patch @@ -0,0 +1,35 @@ +--- a/net/minecraft/world/item/crafting/SmokingRecipe.java ++++ b/net/minecraft/world/item/crafting/SmokingRecipe.java +@@ -3,6 +3,14 @@ + import net.minecraft.world.item.ItemStack; + import net.minecraft.world.level.block.Blocks; + ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.craftbukkit.inventory.CraftSmokingRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end ++ + public class SmokingRecipe extends AbstractCookingRecipe { + public SmokingRecipe(String string, CookingBookCategory cookingBookCategory, Ingredient ingredient, ItemStack itemStack, float f, int i) { + super(RecipeType.SMOKING, string, cookingBookCategory, ingredient, itemStack, f, i); +@@ -17,4 +26,17 @@ + public RecipeSerializer<?> getSerializer() { + return RecipeSerializer.SMOKING_RECIPE; + } ++ ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ ++ CraftSmokingRecipe recipe = new CraftSmokingRecipe(id, result, CraftRecipe.toBukkit(this.ingredient), this.experience, this.cookingTime); ++ recipe.setGroup(this.group); ++ recipe.setCategory(CraftRecipe.getCategory(this.category())); ++ ++ return recipe; ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/StonecutterRecipe.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/StonecutterRecipe.java.patch new file mode 100644 index 0000000000..3d3dd4157c --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/crafting/StonecutterRecipe.java.patch @@ -0,0 +1,34 @@ +--- a/net/minecraft/world/item/crafting/StonecutterRecipe.java ++++ b/net/minecraft/world/item/crafting/StonecutterRecipe.java +@@ -5,6 +5,14 @@ + import net.minecraft.world.level.Level; + import net.minecraft.world.level.block.Blocks; + ++// CraftBukkit start ++import org.bukkit.NamespacedKey; ++import org.bukkit.craftbukkit.inventory.CraftItemStack; ++import org.bukkit.craftbukkit.inventory.CraftRecipe; ++import org.bukkit.craftbukkit.inventory.CraftStonecuttingRecipe; ++import org.bukkit.inventory.Recipe; ++// CraftBukkit end ++ + public class StonecutterRecipe extends SingleItemRecipe { + public StonecutterRecipe(String string, Ingredient ingredient, ItemStack itemStack) { + super(RecipeType.STONECUTTING, RecipeSerializer.STONECUTTER, string, ingredient, itemStack); +@@ -19,4 +28,16 @@ + public ItemStack getToastSymbol() { + return new ItemStack(Blocks.STONECUTTER); + } ++ ++ // CraftBukkit start ++ @Override ++ public Recipe toBukkitRecipe(NamespacedKey id) { ++ CraftItemStack result = CraftItemStack.asCraftMirror(this.result); ++ ++ CraftStonecuttingRecipe recipe = new CraftStonecuttingRecipe(id, result, CraftRecipe.toBukkit(this.ingredient)); ++ recipe.setGroup(this.group); ++ ++ return recipe; ++ } ++ // CraftBukkit end + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/enchantment/DamageEnchantment.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/enchantment/DamageEnchantment.java.patch new file mode 100644 index 0000000000..e89dde3451 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/enchantment/DamageEnchantment.java.patch @@ -0,0 +1,20 @@ +--- a/net/minecraft/world/item/enchantment/DamageEnchantment.java ++++ b/net/minecraft/world/item/enchantment/DamageEnchantment.java +@@ -62,9 +57,14 @@ + + @Override + public void doPostAttack(LivingEntity user, Entity target, int level) { +- if (target instanceof LivingEntity livingEntity && this.type == 2 && level > 0 && livingEntity.getMobType() == MobType.ARTHROPOD) { +- int i = 20 + user.getRandom().nextInt(10 * level); +- livingEntity.addEffect(new MobEffectInstance(MobEffects.MOVEMENT_SLOWDOWN, i, 3)); ++ if (target instanceof LivingEntity) { ++ LivingEntity entityliving1 = (LivingEntity) target; ++ ++ if (this.type == 2 && level > 0 && entityliving1.getMobType() == EnumMonsterType.ARTHROPOD) { ++ int j = 20 + user.getRandom().nextInt(10 * level); ++ ++ entityliving1.addEffect(new MobEffectInstance(MobEffects.MOVEMENT_SLOWDOWN, j, 3), org.bukkit.event.entity.EntityPotionEffectEvent.Cause.ATTACK); // CraftBukkit ++ } + } + } + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/enchantment/FrostWalkerEnchantment.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/enchantment/FrostWalkerEnchantment.java.patch new file mode 100644 index 0000000000..89a7a488e8 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/enchantment/FrostWalkerEnchantment.java.patch @@ -0,0 +1,36 @@ +--- a/net/minecraft/world/item/enchantment/FrostWalkerEnchantment.java ++++ b/net/minecraft/world/item/enchantment/FrostWalkerEnchantment.java +@@ -41,17 +44,22 @@ + int min = Math.min(16, 2 + levelConflicting); + BlockPos.MutableBlockPos mutableBlockPos = new BlockPos.MutableBlockPos(); + +- for (BlockPos blockPos : BlockPos.betweenClosed(pos.offset(-min, -1, -min), pos.offset(min, -1, min))) { +- if (blockPos.closerToCenterThan(living.position(), (double)min)) { +- mutableBlockPos.set(blockPos.getX(), blockPos.getY() + 1, blockPos.getZ()); +- BlockState blockState1 = level.getBlockState(mutableBlockPos); +- if (blockState1.isAir()) { +- BlockState blockState2 = level.getBlockState(blockPos); +- if (blockState2 == FrostedIceBlock.meltsInto() +- && blockState.canSurvive(level, blockPos) +- && level.isUnobstructed(blockState, blockPos, CollisionContext.empty())) { +- level.setBlockAndUpdate(blockPos, blockState); +- level.scheduleTick(blockPos, Blocks.FROSTED_ICE, Mth.nextInt(living.getRandom(), 60, 120)); ++ while (iterator.hasNext()) { ++ BlockPos blockposition1 = (BlockPos) iterator.next(); ++ ++ if (blockposition1.closerToCenterThan(living.position(), (double) j)) { ++ blockposition_mutableblockposition.set(blockposition1.getX(), blockposition1.getY() + 1, blockposition1.getZ()); ++ IBlockData iblockdata1 = level.getBlockState(blockposition_mutableblockposition); ++ ++ if (iblockdata1.isAir()) { ++ IBlockData iblockdata2 = level.getBlockState(blockposition1); ++ ++ if (iblockdata2 == FrostedIceBlock.meltsInto() && iblockdata.canSurvive(level, blockposition1) && level.isUnobstructed(iblockdata, blockposition1, CollisionContext.empty())) { ++ // CraftBukkit Start - Call EntityBlockFormEvent for Frost Walker ++ if (org.bukkit.craftbukkit.event.CraftEventFactory.handleBlockFormEvent(level, blockposition1, iblockdata, living)) { ++ level.scheduleTick(blockposition1, Blocks.FROSTED_ICE, Mth.nextInt(living.getRandom(), 60, 120)); ++ } ++ // CraftBukkit End + } + } + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/trading/Merchant.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/trading/Merchant.java.patch new file mode 100644 index 0000000000..75f2487c54 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/trading/Merchant.java.patch @@ -0,0 +1,9 @@ +--- a/net/minecraft/world/item/trading/Merchant.java ++++ b/net/minecraft/world/item/trading/Merchant.java +@@ -49,4 +52,6 @@ + } + + boolean isClientSide(); ++ ++ org.bukkit.craftbukkit.inventory.CraftMerchant getCraftMerchant(); // CraftBukkit + } diff --git a/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/trading/MerchantOffer.java.patch b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/trading/MerchantOffer.java.patch new file mode 100644 index 0000000000..260f3829e8 --- /dev/null +++ b/patch-remap/mache-vineflower-stripped/net/minecraft/world/item/trading/MerchantOffer.java.patch @@ -0,0 +1,73 @@ +--- a/net/minecraft/world/item/trading/MerchantOffer.java ++++ b/net/minecraft/world/item/trading/MerchantOffer.java +@@ -5,6 +5,8 @@ + import net.minecraft.util.Mth; + import net.minecraft.world.item.ItemStack; + ++import org.bukkit.craftbukkit.inventory.CraftMerchantRecipe; // CraftBukkit ++ + public class MerchantOffer { + private final ItemStack baseCostA; + private final ItemStack costB; +@@ -17,6 +9,33 @@ + private float priceMultiplier; + private int xp = 1; + ++ public ItemStack baseCostA; ++ public ItemStack costB; ++ public final ItemStack result; ++ public int uses; ++ public int maxUses; ++ public boolean rewardExp; ++ public int specialPriceDiff; ++ public int demand; ++ public float priceMultiplier; ++ public int xp; ++ // CraftBukkit start ++ private CraftMerchantRecipe bukkitHandle; ++ ++ public CraftMerchantRecipe asBukkit() { ++ return (bukkitHandle == null) ? bukkitHandle = new CraftMerchantRecipe(this) : bukkitHandle; ++ } ++ ++ public MerchantOffer(ItemStack itemstack, ItemStack itemstack1, ItemStack itemstack2, int uses, int maxUses, int experience, float priceMultiplier, CraftMerchantRecipe bukkit) { ++ this(itemstack, itemstack1, itemstack2, uses, maxUses, experience, priceMultiplier, 0, bukkit); ++ } ++ ++ public MerchantOffer(ItemStack itemstack, ItemStack itemstack1, ItemStack itemstack2, int uses, int maxUses, int experience, float priceMultiplier, int demand, CraftMerchantRecipe bukkit) { ++ this(itemstack, itemstack1, itemstack2, uses, maxUses, experience, priceMultiplier, demand); ++ this.bukkitHandle = bukkit; ++ } ++ // CraftBukkit end ++ + public MerchantOffer(CompoundTag compoundTag) { + this.baseCostA = ItemStack.of(compoundTag.getCompound("buy")); + this.costB = ItemStack.of(compoundTag.getCompound("buyB")); +@@ -88,9 +113,11 @@ + if (this.baseCostA.isEmpty()) { + return ItemStack.EMPTY; + } else { +- int count = this.baseCostA.getCount(); +- int max = Math.max(0, Mth.floor((float)(count * this.demand) * this.priceMultiplier)); +- return this.baseCostA.copyWithCount(Mth.clamp(count + max + this.specialPriceDiff, 1, this.baseCostA.getItem().getMaxStackSize())); ++ int i = this.baseCostA.getCount(); ++ if (i <= 0) return ItemStack.EMPTY; // CraftBukkit - SPIGOT-5476 ++ int j = Math.max(0, Mth.floor((float) (i * this.demand) * this.priceMultiplier)); ++ ++ return this.baseCostA.copyWithCount(Mth.clamp(i + j + this.specialPriceDiff, 1, this.baseCostA.getItem().getMaxStackSize())); + } + } + +@@ -210,7 +235,11 @@ + if (!this.satisfiedBy(playerOfferA, playerOfferB)) { + return false; + } else { +- playerOfferA.shrink(this.getCostA().getCount()); ++ // CraftBukkit start ++ if (!this.getCostA().isEmpty()) { ++ playerOfferA.shrink(this.getCostA().getCount()); ++ } ++ // CraftBukkit end + if (!this.getCostB().isEmpty()) { + playerOfferB.shrink(this.getCostB().getCount()); + } |