package mekanism.common.recipe; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import mekanism.common.Mekanism; import mekanism.common.util.RecipeUtils; import net.minecraft.block.Block; import net.minecraft.inventory.InventoryCrafting; import net.minecraft.item.Item; import net.minecraft.item.ItemStack; import net.minecraft.item.crafting.IRecipe; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagList; import net.minecraft.world.World; import net.minecraftforge.common.ForgeHooks; import net.minecraftforge.common.util.Constants.NBT; import net.minecraftforge.oredict.OreDictionary; public class ShapelessMekanismRecipe implements IRecipe { private ItemStack output = null; private ArrayList<Object> input = new ArrayList<Object>(); public ShapelessMekanismRecipe(Block result, Object... recipe){ this(new ItemStack(result), recipe); } public ShapelessMekanismRecipe(Item result, Object... recipe){ this(new ItemStack(result), recipe); } public ShapelessMekanismRecipe(ItemStack result, Object... recipe) { output = result.copy(); for(Object obj : recipe) { if(obj instanceof ItemStack) { input.add(((ItemStack)obj).copy()); } else if(obj instanceof Item) { input.add(new ItemStack((Item)obj)); } else if(obj instanceof Block) { input.add(new ItemStack((Block)obj)); } else if(obj instanceof String) { input.add(OreDictionary.getOres((String)obj)); } else { String ret = "Invalid shapeless Mekanism recipe: "; for(Object tmp : recipe) { ret += tmp + ", "; } ret += output; throw new RuntimeException(ret); } } } @Override public int getRecipeSize() { return input.size(); } @Override public ItemStack getRecipeOutput() { return output; } @Override public ItemStack[] getRemainingItems(InventoryCrafting inv) { return ForgeHooks.defaultRecipeGetRemainingItems(inv); } @Override public ItemStack getCraftingResult(InventoryCrafting inv) { return RecipeUtils.getCraftingResult(inv, output.copy()); } @SuppressWarnings("unchecked") @Override public boolean matches(InventoryCrafting inv, World world) { ArrayList<Object> required = new ArrayList<Object>(input); for(int x = 0; x < inv.getSizeInventory(); x++) { ItemStack slot = inv.getStackInSlot(x); if(slot != null) { boolean inRecipe = false; Iterator<Object> req = required.iterator(); while(req.hasNext()) { boolean match = false; Object next = req.next(); if(next instanceof ItemStack) { match = RecipeUtils.areItemsEqualForCrafting((ItemStack)next, slot); } else if(next instanceof List) { Iterator<ItemStack> itr = ((List<ItemStack>)next).iterator(); while(itr.hasNext() && !match) { match = RecipeUtils.areItemsEqualForCrafting(itr.next(), slot); } } if(match) { inRecipe = true; required.remove(next); break; } } if(!inRecipe) { return false; } } } return required.isEmpty(); } public ArrayList<Object> getInput() { return input; } public static ShapelessMekanismRecipe create(NBTTagCompound nbtTags) { if(!nbtTags.hasKey("result") || !nbtTags.hasKey("input")) { Mekanism.logger.error("[Mekanism] Shapeless recipe parse error: missing input or result compound tag."); return null; } ItemStack result = ItemStack.loadItemStackFromNBT(nbtTags.getCompoundTag("result")); NBTTagList list = nbtTags.getTagList("input", NBT.TAG_COMPOUND); if(result == null || list.tagCount() == 0) { Mekanism.logger.error("[Mekanism] Shapeless recipe parse error: invalid result stack or input data list."); return null; } Object[] ret = new Object[list.tagCount()]; for(int i = 0; i < list.tagCount(); i++) { NBTTagCompound compound = list.getCompoundTagAt(i); if(compound.hasKey("oredict")) { ret[i] = compound.getString("oredict"); } else if(compound.hasKey("itemstack")) { ret[i] = ItemStack.loadItemStackFromNBT(compound.getCompoundTag("itemstack")); } else { Mekanism.logger.error("[Mekanism] Shapeless recipe parse error: invalid input tag data key."); return null; } } return new ShapelessMekanismRecipe(result, ret); } }