From 7976cfabffc797fb44c804d15f172060a690c77e Mon Sep 17 00:00:00 2001 From: Wynd Date: Wed, 7 Aug 2024 21:25:44 +0300 Subject: [PATCH] Expanded on how new sounds are allowed to be registered, shovel effectiveness for soul sand, ghasts insta dying from their own fireballs and ladder climbing SFX --- .../xyz/pixelatedw/finalbeta/MainMod.java | 6 ++- .../xyz/pixelatedw/finalbeta/ModConfig.java | 4 ++ .../xyz/pixelatedw/finalbeta/WyHelper.java | 29 ++----------- .../mixin/CraftingInventoryMixin.java | 29 ++++++++++++- .../finalbeta/mixin/LivingEntityMixin.java | 27 ++++++++++++ .../finalbeta/mixin/MinecartMixin.java | 2 +- .../finalbeta/mixin/MinecraftMixin.java | 20 +++++++-- .../mixin/ResourceDownloadThreadMixin.java | 10 ++--- .../finalbeta/mixin/SnowballMixin.java | 41 +++++++++++++++++++ .../finalbeta/mixin/ToolItemMixin.java | 8 ++++ src/main/resources/finalbeta.mixins.json | 3 +- 11 files changed, 140 insertions(+), 39 deletions(-) create mode 100644 src/main/java/xyz/pixelatedw/finalbeta/mixin/SnowballMixin.java diff --git a/src/main/java/xyz/pixelatedw/finalbeta/MainMod.java b/src/main/java/xyz/pixelatedw/finalbeta/MainMod.java index 6b6d357..d460d06 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/MainMod.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/MainMod.java @@ -1,9 +1,13 @@ package xyz.pixelatedw.finalbeta; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + import net.fabricmc.api.ModInitializer; public class MainMod implements ModInitializer { - + public static final Logger LOGGER = LogManager.getLogger(); + @Override public void onInitialize() { ModConfig.instance(); diff --git a/src/main/java/xyz/pixelatedw/finalbeta/ModConfig.java b/src/main/java/xyz/pixelatedw/finalbeta/ModConfig.java index 7b6eea0..5873601 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/ModConfig.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/ModConfig.java @@ -36,6 +36,8 @@ public class ModConfig { "Allows 2 or more items of the same type to be repaired using a crafting table using the same formula as modern day vanilla uses"); public static final Option ENABLE_WHITE_WOOL_RECIPE = make("Enable White Wool Recipe", true, "Allows dyed wool to be dyed back white using bone meal"); + public static final Option ENABLE_GHASTS_INSTA_DEATH = make("Enable Ghast Insta Death", true, + "Allows ghasts to die in 1 shot when their fireballs get reflected at them"); public static final Option FIX_BOW_MODEL = make("Fix bow model", true, "Makes the box model held by players and skeletons bigger and facing forward"); @@ -51,6 +53,8 @@ public class ModConfig { "Fixes pickaxes not being effective agaist certain blocks that it should be effective on"); public static final Option FIX_AXE_EFFECTIVENESS = make("Fix axe effectiveness", true, "Fixes axes not being effective agaist certain blocks that it should be effective on"); + public static final Option FIX_SHOVEL_EFFECTIVENESS = make("Fix shovel effectiveness", true, + "Fixes shovels not being effective agaist certain blocks that it should be effective on"); public static final Option FIX_SADDLES_NOT_DROPPING = make("Fix saddles not dropping", true, "Fixes saddles not dropping when killing saddled pigs"); public static final Option FIX_FURNACE_LAVA_BUCKET = make("Fix furnace lava bucket", true, diff --git a/src/main/java/xyz/pixelatedw/finalbeta/WyHelper.java b/src/main/java/xyz/pixelatedw/finalbeta/WyHelper.java index dfbe2dc..e10788e 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/WyHelper.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/WyHelper.java @@ -2,7 +2,6 @@ package xyz.pixelatedw.finalbeta; import java.lang.management.ManagementFactory; import java.lang.reflect.Field; -import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.time.Duration; import java.util.HashMap; @@ -10,10 +9,7 @@ import java.util.HashMap; import net.minecraft.client.Minecraft; import net.minecraft.entity.player.Player; import net.minecraft.item.ItemInstance; -import net.minecraft.item.ItemType; -import net.minecraft.recipe.RecipeRegistry; import net.minecraft.tile.Tile; -import net.minecraft.tile.WoolTile; public class WyHelper { @@ -22,7 +18,6 @@ public class WyHelper { public static final String PLAY_TIME_TAG = "PlayTime"; public static long playTime; - // Look if they're allowed to hold all block and item data in fucking arrays // I am also allowed to abuse maps to extend the shitty metadata excuse // doors have ok ? I don't even care about the overhead at this point. @@ -93,29 +88,11 @@ public class WyHelper { public static float clamp(float val, float min, float max) { return val < min ? min : Math.min(val, max); } - - public static void registerWhiteWoolRecipe() { - Method method = getMethod(RecipeRegistry.class, new String[] { "addShapelessRecipe", "method_542" }, ItemInstance.class, Object[].class); - - if (method == null) { - return; - } - - try { - // Makes new recipes for all colored wools so they can be dyed back - // white using bone meal - for (int colorId = 0; colorId < 16; ++colorId) { - method.invoke(RecipeRegistry.getInstance(), new ItemInstance(Tile.WOOL, 1, 0), new Object[]{ - new ItemInstance(Tile.WOOL, 1, WoolTile.method_2(colorId)), new ItemInstance(ItemType.dyePowder, 1, 15)}); - } - } catch (SecurityException | IllegalAccessException | IllegalArgumentException | InvocationTargetException ex) { - ex.printStackTrace(); - } - } public static void cheatCommand(Player player) { - - player.dropItem(new ItemInstance(ItemType.redstone, 64)); + player.dropItem(new ItemInstance(Tile.LADDER, 64)); + player.dropItem(new ItemInstance(Tile.WOOD, 64)); +// player.dropItem(new ItemInstance(ItemType.snowball, 60)); player.level.setLevelTime(0); player.level.getProperties().setRaining(false); diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/CraftingInventoryMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/CraftingInventoryMixin.java index 43cd195..a377f3e 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/mixin/CraftingInventoryMixin.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/CraftingInventoryMixin.java @@ -1,5 +1,8 @@ package xyz.pixelatedw.finalbeta.mixin; +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; + import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.Inject; @@ -7,6 +10,11 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; import net.minecraft.container.Container; import net.minecraft.inventory.CraftingInventory; +import net.minecraft.item.ItemInstance; +import net.minecraft.item.ItemType; +import net.minecraft.recipe.RecipeRegistry; +import net.minecraft.tile.Tile; +import net.minecraft.tile.WoolTile; import xyz.pixelatedw.finalbeta.ModConfig; import xyz.pixelatedw.finalbeta.WyHelper; @@ -18,8 +26,27 @@ public class CraftingInventoryMixin { @Inject(method = "", at = @At("TAIL")) public void init(Container container, int x, int y, CallbackInfo ci) { if (ModConfig.ENABLE_WHITE_WOOL_RECIPE.get() && !hasCustomRecipesRegistered) { - WyHelper.registerWhiteWoolRecipe(); + registerWhiteWoolRecipe(); hasCustomRecipesRegistered = true; } } + + private static void registerWhiteWoolRecipe() { + Method method = WyHelper.getMethod(RecipeRegistry.class, new String[] { "addShapelessRecipe", "method_542" }, ItemInstance.class, Object[].class); + + if (method == null) { + return; + } + + try { + // Makes new recipes for all colored wools so they can be dyed back + // white using bone meal + for (int colorId = 0; colorId < 16; ++colorId) { + method.invoke(RecipeRegistry.getInstance(), new ItemInstance(Tile.WOOL, 1, 0), new Object[]{ + new ItemInstance(Tile.WOOL, 1, WoolTile.method_2(colorId)), new ItemInstance(ItemType.dyePowder, 1, 15)}); + } + } catch (SecurityException | IllegalAccessException | IllegalArgumentException | InvocationTargetException ex) { + ex.printStackTrace(); + } + } } diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/LivingEntityMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/LivingEntityMixin.java index 232f4ed..1568b24 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/mixin/LivingEntityMixin.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/LivingEntityMixin.java @@ -4,12 +4,18 @@ import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; +import net.minecraft.entity.Entity; import net.minecraft.entity.LivingEntity; import net.minecraft.entity.animal.Chicken; import net.minecraft.entity.animal.Pig; +import net.minecraft.entity.monster.Ghast; +import net.minecraft.entity.player.Player; +import net.minecraft.entity.projectile.Snowball; import net.minecraft.item.ItemType; import xyz.pixelatedw.finalbeta.ModConfig; +import xyz.pixelatedw.finalbeta.WyHelper; @Mixin(LivingEntity.class) public class LivingEntityMixin { @@ -33,4 +39,25 @@ public class LivingEntityMixin { } } } + + @Inject(method = "damage", at = @At("HEAD"), cancellable = true) + public void damage(Entity thrower, int damage, CallbackInfoReturnable cir) { + LivingEntity entity = (LivingEntity) (Object) this; + if (ModConfig.ENABLE_GHASTS_INSTA_DEATH.get() && thrower != null && entity instanceof Ghast && thrower instanceof Snowball) { + LivingEntity fireballThrower = ((Snowball) thrower).field_2193; + if (fireballThrower instanceof Player) { + entity.damage(fireballThrower, 1_000); + cir.setReturnValue(true); + } + } + } + + @Inject(method = "travel", at = @At("HEAD")) + public void travel(float f, float f1, CallbackInfo ci) { + LivingEntity entity = (LivingEntity) (Object) this; + if (ModConfig.ADD_MORE_SOUNDS.get() && entity.isOnLadder() && entity.velocityY != 0 && entity.field_1645 % 20 == 0 && !entity.onGround) { + float pitch = WyHelper.clamp(0.85f + entity.level.rand.nextFloat() / 2, 0.0f, 1.0f); + entity.level.playSound(entity.x, entity.y, entity.z, "step.ladder", 0.3f, pitch); + } + } } diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecartMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecartMixin.java index 15586a0..62cad9a 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecartMixin.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecartMixin.java @@ -57,7 +57,7 @@ public class MinecartMixin { } if (speed >= 0.01D && ModConfig.ADD_MORE_SOUNDS.get()) { - if (minecart.field_1645 % 33 == 1) { + if (minecart.field_1645 % 39 == 1) { minecart.level.playSound(x, y, z, "minecart.base", volume, pitch); } } diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecraftMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecraftMixin.java index 7700742..89031f1 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecraftMixin.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/MinecraftMixin.java @@ -12,11 +12,14 @@ import org.spongepowered.asm.mixin.injection.Redirect; import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; import net.minecraft.client.Minecraft; +import xyz.pixelatedw.finalbeta.MainMod; import xyz.pixelatedw.finalbeta.ModConfig; @Mixin(Minecraft.class) public class MinecraftMixin { + private static final String[] ALLOWED_NEW_SOUNDS = {"minecart/", "step/ladder"}; + @Redirect(method = "init()V", at = @At(value = "INVOKE", target = "Lorg/lwjgl/opengl/Display;create()V"), remap = false) public void createDisplay() throws LWJGLException { // Why the fuck is this even a thing ? What was its intended purpose ? I NEED TO KNOW @@ -26,15 +29,26 @@ public class MinecraftMixin { @Inject(method = "loadSoundFromDir", at = @At("HEAD")) public void loadSoundFromDir(String string, File file, CallbackInfo ci) { - if(ModConfig.ADD_MORE_SOUNDS.get()) { + if(!ModConfig.ADD_MORE_SOUNDS.get()) { Minecraft mc = (Minecraft) (Object) this; int split = string.indexOf("/"); String type = string.substring(0, split); String newSound = string.substring(split + 1); // For now only allow the minecart sounds, allowing all of them causes weird effects with same name sounds when the game decides which one to use // XXX Could always incorporate the sound3 part into the sound's name and have it accessible as sound3.random.bow for example, which would avoid the overlap with current sounds - if (type.equalsIgnoreCase("sound3") && newSound.startsWith("minecart/")) { - mc.soundHelper.method_2011(newSound, file); + if (type.equalsIgnoreCase("sound3")) { + boolean registerSound = false; + for (String test : ALLOWED_NEW_SOUNDS) { + if (newSound.startsWith(test)) { + registerSound = true; + break; + } + } + + if (registerSound) { + MainMod.LOGGER.info("Registered a new sound " + newSound + " from " + file); + mc.soundHelper.method_2011(newSound, file); + } } } } diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/ResourceDownloadThreadMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/ResourceDownloadThreadMixin.java index 71f9fc9..ff8942a 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/mixin/ResourceDownloadThreadMixin.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/ResourceDownloadThreadMixin.java @@ -1,8 +1,6 @@ package xyz.pixelatedw.finalbeta.mixin; import org.spongepowered.asm.mixin.Mixin; -import org.spongepowered.asm.mixin.injection.Constant; -import org.spongepowered.asm.mixin.injection.ModifyConstant; import net.minecraft.client.util.ResourceDownloadThread; @@ -11,8 +9,8 @@ public class ResourceDownloadThreadMixin { private static final String RESOURCES_URL = "http://mcresources.modification-station.net/MinecraftResources/"; - @ModifyConstant(method = "run", constant = @Constant(stringValue = "http://s3.amazonaws.com/MinecraftResources/"), remap = false) - private String getResourcesUrl(String def) { - return RESOURCES_URL; - } +// @ModifyConstant(method = "run", constant = @Constant(stringValue = "http://s3.amazonaws.com/MinecraftResources/"), remap = false) +// private String getResourcesUrl(String def) { +// return RESOURCES_URL; +// } } \ No newline at end of file diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/SnowballMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/SnowballMixin.java new file mode 100644 index 0000000..52f30f7 --- /dev/null +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/SnowballMixin.java @@ -0,0 +1,41 @@ +package xyz.pixelatedw.finalbeta.mixin; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; +import org.spongepowered.asm.mixin.injection.callback.LocalCapture; + +import net.minecraft.entity.Entity; +import net.minecraft.entity.LivingEntity; +import net.minecraft.entity.projectile.Snowball; +import net.minecraft.util.hit.HitResult; +import net.minecraft.util.maths.Vec3d; +import xyz.pixelatedw.finalbeta.ModConfig; + +@Mixin(Snowball.class) +public class SnowballMixin { + // Note, this is actually the "fireball" used by Ghasts. I guess they didn't have the fire charges done yet + + @Inject(method = "tick", at = @At(value = "INVOKE", target = "Lnet/minecraft/entity/Entity;damage(Lnet/minecraft/entity/Entity;I)Z", shift = At.Shift.BEFORE), locals = LocalCapture.CAPTURE_FAILHARD, cancellable = true) + private void newDamageRouter(CallbackInfo ci, Vec3d _v1, Vec3d _v2, HitResult result) { + Snowball fireball = ((Snowball)(Object)this); + if (ModConfig.ENABLE_GHASTS_INSTA_DEATH.get() && result != null && !fireball.level.isClient) { + if (result.entity != null && result.entity.damage(fireball, 0)) { + } + + fireball.level.createExplosion((Entity) null, fireball.x, fireball.y, fireball.z, 1.0F, true); + fireball.remove(); + ci.cancel(); + } + } + + @Inject(method = "damage", at = @At(value = "INVOKE", target = "Lnet/minecraft/entity/Entity;getRotation()Lnet/minecraft/util/maths/Vec3d;"), cancellable = true) + public void damage(Entity attacker, int damage, CallbackInfoReturnable cir) { + Snowball fireball = ((Snowball)(Object)this); + if (ModConfig.ENABLE_GHASTS_INSTA_DEATH.get() && attacker instanceof LivingEntity) { + fireball.field_2193 = (LivingEntity) attacker; + } + } +} diff --git a/src/main/java/xyz/pixelatedw/finalbeta/mixin/ToolItemMixin.java b/src/main/java/xyz/pixelatedw/finalbeta/mixin/ToolItemMixin.java index 27d1887..2d7f204 100644 --- a/src/main/java/xyz/pixelatedw/finalbeta/mixin/ToolItemMixin.java +++ b/src/main/java/xyz/pixelatedw/finalbeta/mixin/ToolItemMixin.java @@ -8,6 +8,7 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; import net.minecraft.item.tool.HatchetItem; import net.minecraft.item.tool.PickaxeItem; +import net.minecraft.item.tool.ShovelItem; import net.minecraft.item.tool.ToolItem; import net.minecraft.item.tool.ToolMaterial; import net.minecraft.tile.Tile; @@ -28,6 +29,11 @@ public class ToolItemMixin { Tile.STAIRS_WOOD, Tile.DOOR_WOOD, Tile.WOODEN_PRESSURE_PLATE, Tile.JUKEBOX, Tile.NOTEBLOCK, Tile.PUMPKIN, Tile.LIT_PUMPKIN, Tile.STANDING_SIGN, Tile.WALL_SIGN, Tile.TRAPDOOR, Tile.LADDER, Tile.WORKBENCH, Tile.FENCE}; + private static final Tile[] SHOVEL_BLOCKS = new Tile[]{Tile.GRASS, Tile.DIRT, Tile.SAND, Tile.GRAVEL, Tile.SNOW, Tile.SNOW_BLOCK, + Tile.CLAY, Tile.FARMLAND, + // Here starts the list of blocks that are not affected by default + Tile.SOUL_SAND}; + @Shadow public Tile[] field_2712; @@ -39,6 +45,8 @@ public class ToolItemMixin { this.field_2712 = PICKAXE_BLOCKS; } else if (tool instanceof HatchetItem && ModConfig.FIX_AXE_EFFECTIVENESS.get()) { this.field_2712 = HATCHET_BLOCKS; + } else if (tool instanceof ShovelItem && ModConfig.FIX_SHOVEL_EFFECTIVENESS.get()) { + this.field_2712 = SHOVEL_BLOCKS; } } } diff --git a/src/main/resources/finalbeta.mixins.json b/src/main/resources/finalbeta.mixins.json index 3f3c8ce..3790458 100644 --- a/src/main/resources/finalbeta.mixins.json +++ b/src/main/resources/finalbeta.mixins.json @@ -39,7 +39,8 @@ "DoorTileMixin", "CraftingContainerMixin", "CraftingInventoryMixin", - "RecipeRegistryMixin" + "RecipeRegistryMixin", + "SnowballMixin" ], "injectors": { "defaultRequire": -1