From 3fb6ef7fbed5602ab27fe97cdb90e82fdc26fcb1 Mon Sep 17 00:00:00 2001 From: Sollace Date: Fri, 1 Feb 2019 18:29:58 +0200 Subject: [PATCH] All items involving apples (vanilla or modded) should now work with every apple variant --- .../com/minelittlepony/unicopia/UItems.java | 7 + .../com/minelittlepony/unicopia/Unicopia.java | 2 + .../unicopia/forgebullshit/OreReplacer.java | 146 ++++++++++++++++++ .../assets/unicopia/recipes/cider.json | 5 +- .../assets/unicopia/recipes/cider_two.json | 5 +- .../assets/unicopia/recipes/juice.json | 5 +- 6 files changed, 158 insertions(+), 12 deletions(-) create mode 100644 src/main/java/com/minelittlepony/unicopia/forgebullshit/OreReplacer.java diff --git a/src/main/java/com/minelittlepony/unicopia/UItems.java b/src/main/java/com/minelittlepony/unicopia/UItems.java index 5d3ed08b6..755daf636 100644 --- a/src/main/java/com/minelittlepony/unicopia/UItems.java +++ b/src/main/java/com/minelittlepony/unicopia/UItems.java @@ -48,6 +48,7 @@ import com.minelittlepony.unicopia.edibles.UItemFoodDelegate; import com.minelittlepony.unicopia.forgebullshit.BuildInTexturesBakery; import com.minelittlepony.unicopia.forgebullshit.ItemModels; +import com.minelittlepony.unicopia.forgebullshit.OreReplacer; import com.minelittlepony.unicopia.forgebullshit.RegistryLockSpinner; public class UItems { @@ -243,6 +244,12 @@ static void registerFuels() { FurnaceRecipes.instance().addSmeltingRecipe(new ItemStack(juice), new ItemStack(burned_juice), 0); } + static void fixRecipes() { + new OreReplacer() + .registerAll(stack -> stack.getItem().getRegistryName().equals(apple.getRegistryName())) + .done(); + } + @SideOnly(Side.CLIENT) static void registerColors(ItemColors registry) { registry.registerItemColorHandler((stack, tint) -> { diff --git a/src/main/java/com/minelittlepony/unicopia/Unicopia.java b/src/main/java/com/minelittlepony/unicopia/Unicopia.java index 2af741c8a..25141e7a2 100644 --- a/src/main/java/com/minelittlepony/unicopia/Unicopia.java +++ b/src/main/java/com/minelittlepony/unicopia/Unicopia.java @@ -113,6 +113,8 @@ protected void registerRecipeTypes(Map> ty Biome.REGISTRY.forEach(UEntities::registerSpawnEntries); UClient.instance().posInit(event); + + UItems.fixRecipes(); } public static CraftingManager getCraftingManager() { diff --git a/src/main/java/com/minelittlepony/unicopia/forgebullshit/OreReplacer.java b/src/main/java/com/minelittlepony/unicopia/forgebullshit/OreReplacer.java new file mode 100644 index 000000000..d2041c8dc --- /dev/null +++ b/src/main/java/com/minelittlepony/unicopia/forgebullshit/OreReplacer.java @@ -0,0 +1,146 @@ +package com.minelittlepony.unicopia.forgebullshit; + +import java.util.ArrayList; +import java.util.List; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +import com.google.common.collect.Lists; +import com.google.common.collect.Streams; + +import net.minecraft.creativetab.CreativeTabs; +import net.minecraft.item.ItemStack; +import net.minecraft.item.crafting.IRecipe; +import net.minecraft.item.crafting.Ingredient; +import net.minecraft.item.crafting.ShapedRecipes; +import net.minecraft.item.crafting.ShapelessRecipes; +import net.minecraft.util.NonNullList; +import net.minecraftforge.fml.common.registry.ForgeRegistries; + +/** + * An Ore Replacer. + * Similar to what the OreDictionary does + * except this is configurable and works for vanilla and modded recipes. + */ +public class OreReplacer { + + /** + * The vanilla remapper. Supports shaped recipes and shapeless recipes, and that's about it. + */ + public static final IIngredientRemapper VANILLA = new IIngredientRemapper() { + + @Override + public boolean canRemap(IRecipe recipe) { + return recipe.getClass() == ShapedRecipes.class + || recipe.getClass() == ShapelessRecipes.class; + } + + @Override + public int replaceIngredients(OreReplacer sender, IRecipe recipe) { + NonNullList ingredients = recipe.getIngredients(); + + int replacements = 0; + + for (int i = 0; i < ingredients.size(); i++) { + Ingredient ingredient = ingredients.get(i); + + NonNullList newStacks = NonNullList.create(); + + boolean altered = false; + + ItemStack[] stacks = ingredient.getMatchingStacks(); + + for (int k = 0; k < stacks.length; k++) { + ItemStack stack = stacks[k]; + + boolean found = !stack.isEmpty() && sender.replaceOre(stack, newStacks); + + if (!found) { + newStacks.add(stack); + } + + altered |= found; + } + + if (altered) { + replacements++; + ingredients.set(i, Ingredient.fromStacks(newStacks.stream().distinct().toArray(ItemStack[]::new))); + } + } + + return replacements; + } + + }; + + private static final Logger log = LogManager.getLogger(); + + private int replacements = 0; + + private List ores = new ArrayList<>(); + + private final List remappers = Lists.newArrayList(VANILLA); + + /** + * Adds additional recipe handlers. + * By default only the vanilla crafting recipes are supported. + */ + public OreReplacer registerRecipeTypeHandler(IIngredientRemapper... remappers) { + this.remappers.addAll(Lists.newArrayList(remappers)); + + return this; + } + + /** + * Adds all the specified ore conversions to be processed by this replacer. + */ + public OreReplacer registerAll(IOre... ores) { + this.ores.addAll(Lists.newArrayList(ores)); + + return this; + } + + public void done() { + log.info("Searching for ore replacements..."); + Streams.stream(ForgeRegistries.RECIPES).forEach(recipe -> { + remappers.stream() + .filter(remapper -> remapper.canRemap(recipe)) + .findFirst() + .ifPresent(remapper -> remapper.replaceIngredients(this, recipe)); + }); + log.info("Replaced {} ingredients.", replacements); + } + + public boolean replaceOre(ItemStack stack, NonNullList newStacks) { + return ores.stream().filter(ore -> ore.matches(stack)).map(ore -> { + ore.getSubItems(stack, newStacks); + + return ore; + }).findFirst().isPresent(); + } + + public interface IIngredientRemapper { + + boolean canRemap(IRecipe recipe); + + int replaceIngredients(OreReplacer sender, IRecipe recipe); + } + + @FunctionalInterface + public interface IOre { + boolean matches(ItemStack stack); + + default void getSubItems(ItemStack stack, NonNullList newStacks) { + NonNullList newList = NonNullList.create(); + + stack.getItem().getSubItems(CreativeTabs.SEARCH, newList); + + if (stack.hasTagCompound()) { + newList.forEach(i -> i.setTagCompound(stack.getTagCompound().copy())); + } + + newStacks.addAll(newList); + } + } +} \ No newline at end of file diff --git a/src/main/resources/assets/unicopia/recipes/cider.json b/src/main/resources/assets/unicopia/recipes/cider.json index 9c522592f..fbfcc927d 100644 --- a/src/main/resources/assets/unicopia/recipes/cider.json +++ b/src/main/resources/assets/unicopia/recipes/cider.json @@ -16,10 +16,7 @@ { "item": "minecraft:iron_nugget" } ], "A": [ - { "item": "minecraft:apple", "data": 0 }, - { "item": "minecraft:apple", "data": 1 }, - { "item": "minecraft:apple", "data": 2 }, - { "item": "minecraft:apple", "data": 3 } + { "item": "minecraft:apple", "data": 0 } ] }, "result": { "item": "unicopia:apple_cider", "data": 0, "count": 1 } diff --git a/src/main/resources/assets/unicopia/recipes/cider_two.json b/src/main/resources/assets/unicopia/recipes/cider_two.json index df04b4ce3..7ecbc7bf6 100644 --- a/src/main/resources/assets/unicopia/recipes/cider_two.json +++ b/src/main/resources/assets/unicopia/recipes/cider_two.json @@ -17,10 +17,7 @@ { "item": "unicopia:burned_juice", "data": 0 } ], "A": [ - { "item": "minecraft:apple", "data": 0 }, - { "item": "minecraft:apple", "data": 1 }, - { "item": "minecraft:apple", "data": 2 }, - { "item": "minecraft:apple", "data": 3 } + { "item": "minecraft:apple", "data": 0 } ] }, "result": { "item": "unicopia:apple_cider", "data": 0, "count": 1 } diff --git a/src/main/resources/assets/unicopia/recipes/juice.json b/src/main/resources/assets/unicopia/recipes/juice.json index 8c58f4ee3..5be036abc 100644 --- a/src/main/resources/assets/unicopia/recipes/juice.json +++ b/src/main/resources/assets/unicopia/recipes/juice.json @@ -11,10 +11,7 @@ { "item": "minecraft:glass_bottle" } ], "A": [ - { "item": "minecraft:apple", "data": 0 }, - { "item": "minecraft:apple", "data": 1 }, - { "item": "minecraft:apple", "data": 2 }, - { "item": "minecraft:apple", "data": 3 } + { "item": "minecraft:apple", "data": 0 } ] }, "result": { "item": "unicopia:juice", "data": 0, "count": 1 }