Last active
August 29, 2015 14:02
-
-
Save Unh0lyTigg/c1a98c86bb6a51077a50 to your computer and use it in GitHub Desktop.
CraftingRecipeBuilder
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package net.minecraftforge.common; | |
import java.util.List; | |
import java.util.Map; | |
import net.minecraft.block.Block; | |
import net.minecraft.item.Item; | |
import net.minecraft.item.ItemStack; | |
import net.minecraft.item.crafting.IRecipe; | |
import net.minecraft.item.crafting.ShapedRecipes; | |
import net.minecraft.item.crafting.ShapelessRecipes; | |
import org.apache.commons.lang3.ArrayUtils; | |
import com.google.common.collect.Lists; | |
import com.google.common.collect.Maps; | |
import cpw.mods.fml.common.FMLLog; | |
import cpw.mods.fml.common.registry.GameRegistry; | |
public abstract class CraftingRecipeBuilder { | |
public static ShapedCraftingRecipeBuilder shaped() { | |
return new ShapedCraftingRecipeBuilder(); | |
} | |
public static ShapelessCraftingRecipeBuilder shapeless() { | |
return new ShapelessCraftingRecipeBuilder(); | |
} | |
protected ItemStack output = null; | |
protected IRecipe cached = null; | |
public abstract IRecipe build(); | |
public final void add() { | |
IRecipe r = build(); | |
if (r != null) | |
GameRegistry.addRecipe(r); | |
} | |
public static final class ShapedCraftingRecipeBuilder extends CraftingRecipeBuilder { | |
private int width; | |
private int height; | |
private String[] grid; | |
private Map<Character, ItemStack> replacements = Maps.newHashMap(); | |
private ShapedCraftingRecipeBuilder() { } | |
public ShapedCraftingRecipeBuilder output(ItemStack item) { | |
this.output = item; | |
// invalidate cached recipe if it exists | |
if (cached != null) | |
cached = null; | |
return this; | |
} | |
public ShapedCraftingRecipeBuilder output(Item item) { | |
return output(new ItemStack(item)); | |
} | |
public ShapedCraftingRecipeBuilder output(Block item) { | |
return output(new ItemStack(item)); | |
} | |
public ShapedCraftingRecipeBuilder where(char ingredient, ItemStack input) { | |
if (replacements.containsKey(Character.valueOf(ingredient))) { | |
FMLLog.warning("ShapedCraftingRecipeBuilder: It is bad practice to have more than one where(char,[ItemStack|Item|Block]) calls where the ingredient (char) is not unique. Replacing now."); | |
replacements.remove(Character.valueOf(ingredient)); | |
} | |
replacements.put(Character.valueOf(ingredient), input); | |
// invalidate cached recipe if it exists | |
if (cached != null) | |
cached = null; | |
return this; | |
} | |
public ShapedCraftingRecipeBuilder where(char ingredient, Item input) { | |
return where(ingredient, new ItemStack(input)); | |
} | |
public ShapedCraftingRecipeBuilder where(char ingredient, Block input) { | |
return where(ingredient, new ItemStack(input)); | |
} | |
public ShapedCraftingRecipeBuilder input(String... recipe) { | |
if (recipe.length > 3) { | |
FMLLog.warning("ShapedCraftingRecipeBuilder: Recipe input array has more than 3 elements, truncating to maximum."); | |
recipe = ArrayUtils.subarray(recipe, 0, 3); | |
} | |
grid = ArrayUtils.subarray(recipe, 0, recipe.length); | |
this.height = grid.length; | |
for (int i = 0; i < grid.length; i++) { | |
this.width = Math.max(this.width, grid[i].length() > 3 ? 3 : grid[i].length()); | |
} | |
// invalidate cached recipe if it exists | |
if (cached != null) | |
cached = null; | |
return this; | |
} | |
public IRecipe build() { | |
if (cached != null) | |
return cached; | |
return (cached = new ShapedRecipes(width, height, generateRecipe(), output)); | |
} | |
private ItemStack[] generateRecipe() { | |
ItemStack[] recipe = new ItemStack[width * height]; | |
String pattern = ""; | |
for (int i = 0; i < height; i++) { | |
pattern += grid[i].substring(0, Math.min(grid[i].length(), 3)); | |
} | |
for (int i = 0; i < width * height; i++) { | |
char c = pattern.charAt(i); | |
if (replacements.containsKey(Character.valueOf(c))) { | |
recipe[i] = replacements.get(Character.valueOf(c)).copy(); | |
} else { | |
recipe[i] = null; | |
} | |
} | |
return recipe; | |
} | |
} | |
public static final class ShapelessCraftingRecipeBuilder extends CraftingRecipeBuilder { | |
private List<ItemStack> inputs; | |
private ShapelessCraftingRecipeBuilder() { | |
inputs = Lists.newArrayList(); | |
} | |
public ShapelessCraftingRecipeBuilder output(ItemStack item) { | |
this.output = item; | |
// invalidate cached recipe if it exists | |
if (cached != null) | |
cached = null; | |
return this; | |
} | |
public ShapelessCraftingRecipeBuilder output(Item item) { | |
return output(new ItemStack(item)); | |
} | |
public ShapelessCraftingRecipeBuilder output(Block block) { | |
return output(new ItemStack(block)); | |
} | |
public ShapelessCraftingRecipeBuilder addInput(ItemStack item) { | |
this.inputs.add(item); | |
// invalidate cached recipe if it exists | |
if (cached != null) | |
cached = null; | |
return this; | |
} | |
public ShapelessCraftingRecipeBuilder addInput(ItemStack item, int times) { | |
for (int i = 0; i < times; i++) { | |
this.inputs.add(item); | |
} | |
// invalidate cached recipe if it exists | |
if (cached != null) | |
cached = null; | |
return this; | |
} | |
public ShapelessCraftingRecipeBuilder addInput(Item item) { | |
return addInput(new ItemStack(item)); | |
} | |
public ShapelessCraftingRecipeBuilder addInput(Item item, int times) { | |
return addInput(new ItemStack(item), times); | |
} | |
public ShapelessCraftingRecipeBuilder addInput(Block block) { | |
return addInput(new ItemStack(block)); | |
} | |
public ShapelessCraftingRecipeBuilder addInput(Block block, int times) { | |
return addInput(new ItemStack(block), times); | |
} | |
@Override | |
public IRecipe build() { | |
if (cached != null) | |
return cached; | |
return (cached = new ShapelessRecipes(output, inputs)); | |
} | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import cpw.mods.fml.common.registry.GameRegistry; | |
import net.minecraft.init.Blocks; | |
import net.minecraft.init.Items; | |
import net.minecraft.item.crafting.IRecipe; | |
import net.minecraftforge.common.CraftingRecipeBuilder; | |
public class CraftingRecipeBuilderUsage { | |
public static void addRecipes() { | |
// Replicates the recipe for an anvil, but it's much more verbose... | |
IRecipe recipe = CraftingRecipeBuilder.shaped() | |
.input("III", | |
" i ", | |
"iii") | |
.output(Blocks.anvil) | |
.where('I', Blocks.iron_block) | |
.where('i', Items.iron_ingot) | |
.build(); | |
GameRegistry.addRecipe(recipe); | |
// Replicates the recipe for a book, is more verbose, and shows you don't have to store the IRecipe (or even feed it directly to GameRegistry) to add it... | |
CraftingRecipeBuilder.shapeless() | |
.output(Items.book) | |
.addInput(Items.paper, 3) | |
.addInput(Items.leather) | |
.add(); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment