package net.shadowfacts.autoswap.mixin; import net.minecraft.entity.player.PlayerEntity; import net.minecraft.item.ItemStack; import net.minecraft.item.ItemUsageContext; import net.minecraft.server.network.ServerPlayerEntity; import net.minecraft.server.network.ServerPlayerInteractionManager; import net.minecraft.util.ActionResult; import net.minecraft.util.Hand; import net.minecraft.util.hit.BlockHitResult; import net.minecraft.util.math.BlockPos; import net.minecraft.world.World; import net.shadowfacts.autoswap.AutoSwap; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.Shadow; import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.Redirect; import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; import java.awt.dnd.Autoscroll; /** * @author shadowfacts */ @Mixin(ServerPlayerInteractionManager.class) public abstract class MixinServerPlayerInteractionManager { @Shadow private ServerPlayerEntity player; @Shadow abstract boolean isCreative(); private ItemStack heldStackAtBeginningOfBreak = ItemStack.EMPTY; private ItemStack heldStackAtBeginningOfUse = ItemStack.EMPTY; @Inject(method = "tryBreakBlock", at = @At("HEAD")) private void beginTryBreakBlock(BlockPos pos, CallbackInfoReturnable cb) { heldStackAtBeginningOfBreak = player.inventory.getMainHandStack().copy(); } @Inject(method = "tryBreakBlock", at = @At("RETURN")) private void endTryBreakBlock(BlockPos pos, CallbackInfoReturnable cb) { AutoSwap.INSTANCE.endBreakBlock(player.inventory, heldStackAtBeginningOfBreak); heldStackAtBeginningOfBreak = ItemStack.EMPTY; } @Inject( method = "interactBlock", at = @At(value = "INVOKE", target = "Lnet/minecraft/item/ItemStack;useOnBlock(Lnet/minecraft/item/ItemUsageContext;)Lnet/minecraft/util/ActionResult;") ) private void beforeUseOnBlock(PlayerEntity player, World world, ItemStack heldStack, Hand hand, BlockHitResult result, CallbackInfoReturnable cb) { heldStackAtBeginningOfUse = heldStack.copy(); } @Inject( method = "interactBlock", at = @At( value = "INVOKE", target = "Lnet/minecraft/item/ItemStack;useOnBlock(Lnet/minecraft/item/ItemUsageContext;)Lnet/minecraft/util/ActionResult;", shift = At.Shift.AFTER ) ) private void afterUseOnBlock(PlayerEntity player, World world, ItemStack heldStack, Hand hand, BlockHitResult result, CallbackInfoReturnable cb) { if (!isCreative() && cb.getReturnValue() == ActionResult.SUCCESS) { AutoSwap.INSTANCE.afterUseOnBlock(this.player, player.inventory, heldStackAtBeginningOfUse, hand); } heldStackAtBeginningOfUse = ItemStack.EMPTY; } }