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
parent
95c9317572
commit
7976cfabff
|
@ -1,8 +1,12 @@
|
|||
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() {
|
||||
|
|
|
@ -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<Boolean> 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<Boolean> 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<Boolean> 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<Boolean> 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<Boolean> 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<Boolean> FIX_SADDLES_NOT_DROPPING = make("Fix saddles not dropping", true,
|
||||
"Fixes saddles not dropping when killing saddled pigs");
|
||||
public static final Option<Boolean> FIX_FURNACE_LAVA_BUCKET = make("Fix furnace lava bucket", true,
|
||||
|
|
|
@ -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.
|
||||
|
@ -94,28 +89,10 @@ public class WyHelper {
|
|||
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);
|
||||
|
|
|
@ -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 = "<init>", 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();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -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<Boolean> 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);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -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);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -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);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -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;
|
||||
// }
|
||||
}
|
|
@ -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<Boolean> cir) {
|
||||
Snowball fireball = ((Snowball)(Object)this);
|
||||
if (ModConfig.ENABLE_GHASTS_INSTA_DEATH.get() && attacker instanceof LivingEntity) {
|
||||
fireball.field_2193 = (LivingEntity) attacker;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -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;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -39,7 +39,8 @@
|
|||
"DoorTileMixin",
|
||||
"CraftingContainerMixin",
|
||||
"CraftingInventoryMixin",
|
||||
"RecipeRegistryMixin"
|
||||
"RecipeRegistryMixin",
|
||||
"SnowballMixin"
|
||||
],
|
||||
"injectors": {
|
||||
"defaultRequire": -1
|
||||
|
|
Loading…
Reference in New Issue