mirror of
https://gitlab.com/phoenix-dvpmt/mmoitems.git
synced 2025-02-23 14:51:21 +01:00
Added Super Shaped recipes. **Requires MythicLib Update** to access super workbench with /swb
This commit is contained in:
parent
246235e655
commit
510417c9aa
@ -5,10 +5,7 @@ import io.lumine.mythic.utils.items.ItemFactory;
|
||||
import net.Indyuce.mmoitems.api.item.template.MMOItemTemplate;
|
||||
import net.Indyuce.mmoitems.api.util.message.FFPMMOItems;
|
||||
import net.Indyuce.mmoitems.gui.edition.EditionInventory;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.RMGRR_Shaped;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.RMGRR_Shapeless;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.RMGRR_Smithing;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.RecipeRegistry;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.*;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.burninglegacy.RMGRR_LBBlast;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.burninglegacy.RMGRR_LBCampfire;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.burninglegacy.RMGRR_LBFurnace;
|
||||
@ -233,6 +230,7 @@ public class RecipeBrowserGUI extends EditionInventory {
|
||||
registerRecipe(new RMGRR_Smithing());
|
||||
registerRecipe(new RMGRR_Shapeless());
|
||||
registerRecipe(new RMGRR_Shaped());
|
||||
registerRecipe(new RMGRR_SuperShaped());
|
||||
|
||||
/*
|
||||
* These don't go through mythiclib, I, gunging, merely
|
||||
@ -241,7 +239,7 @@ public class RecipeBrowserGUI extends EditionInventory {
|
||||
*
|
||||
* After the RMGRR_LegacyBurning.sendToMythicLib method (that
|
||||
* sends the recipes back to RecipeManager.registerBurningRecipe)
|
||||
* I have no clue what happens; didn't even read that far.
|
||||
* I have no clue what happens; barely even read that far.
|
||||
*/
|
||||
registerRecipe(new RMGRR_LBFurnace());
|
||||
registerRecipe(new RMGRR_LBBlast());
|
||||
|
@ -55,7 +55,7 @@ public class RMGRI_BurningLegacy implements RMG_RecipeInterpreter{
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editInput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editInput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
if (slot != 0) { return; }
|
||||
|
||||
@ -66,11 +66,11 @@ public class RMGRI_BurningLegacy implements RMG_RecipeInterpreter{
|
||||
section.set(ITEM, input.toString());
|
||||
}
|
||||
|
||||
@Override public void editOutput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) { }
|
||||
@Override public void editOutput(@NotNull ProvidedUIFilter input, int slot) { }
|
||||
|
||||
@Override public void deleteInput(@NotNull ConfigurationSection section, int slot) { editInput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteInput(int slot) { editInput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
@Override public void deleteOutput(@NotNull ConfigurationSection section, int slot) { }
|
||||
@Override public void deleteOutput(int slot) { }
|
||||
|
||||
@Nullable @Override public ProvidedUIFilter getInput(int slot) { if (slot == 0) { return input; } return null; }
|
||||
|
||||
|
@ -181,7 +181,7 @@ public class RMGRI_Shaped implements RMG_RecipeInterpreter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editInput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editInput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setInput(slot, input);
|
||||
@ -191,7 +191,7 @@ public class RMGRI_Shaped implements RMG_RecipeInterpreter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editOutput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editOutput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setOutput(slot, input);
|
||||
@ -200,9 +200,9 @@ public class RMGRI_Shaped implements RMG_RecipeInterpreter {
|
||||
section.set(RecipeMakerGUI.OUTPUT_INGREDIENTS, toYML(outputRecipe));
|
||||
}
|
||||
|
||||
@Override public void deleteInput(@NotNull ConfigurationSection section, int slot) { editInput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteInput(int slot) { editInput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
@Override public void deleteOutput(@NotNull ConfigurationSection section, int slot) { editOutput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteOutput(int slot) { editOutput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
//region Updater, to update old recipes
|
||||
/**
|
||||
|
@ -165,7 +165,7 @@ public class RMGRI_Shapeless implements RMG_RecipeInterpreter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editInput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editInput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setInput(slot, input);
|
||||
@ -175,7 +175,7 @@ public class RMGRI_Shapeless implements RMG_RecipeInterpreter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editOutput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editOutput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setOutput(slot, input);
|
||||
@ -184,7 +184,7 @@ public class RMGRI_Shapeless implements RMG_RecipeInterpreter {
|
||||
section.set(RecipeMakerGUI.OUTPUT_INGREDIENTS, toYML(outputRecipe));
|
||||
}
|
||||
|
||||
@Override public void deleteInput(@NotNull ConfigurationSection section, int slot) { editInput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteInput(int slot) { editInput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
@Override public void deleteOutput(@NotNull ConfigurationSection section, int slot) { editOutput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteOutput(int slot) { editOutput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
}
|
||||
|
@ -128,7 +128,7 @@ public class RMGRI_Smithing implements RMG_RecipeInterpreter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editInput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editInput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setInput(slot, input);
|
||||
@ -138,7 +138,7 @@ public class RMGRI_Smithing implements RMG_RecipeInterpreter {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editOutput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot) {
|
||||
public void editOutput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setOutput(slot, input);
|
||||
@ -147,9 +147,9 @@ public class RMGRI_Smithing implements RMG_RecipeInterpreter {
|
||||
section.set(RecipeMakerGUI.OUTPUT_INGREDIENTS, toYML(getOutputItem(), getOutputIngot()));
|
||||
}
|
||||
|
||||
@Override public void deleteInput(@NotNull ConfigurationSection section, int slot) { editInput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteInput(int slot) { editInput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
@Override public void deleteOutput(@NotNull ConfigurationSection section, int slot) { editOutput(section, RecipeMakerGUI.AIR.clone(), slot); }
|
||||
@Override public void deleteOutput(int slot) { editOutput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
//region Updater, to update old recipes
|
||||
/**
|
||||
|
@ -0,0 +1,287 @@
|
||||
package net.Indyuce.mmoitems.gui.edition.recipe.interpreters;
|
||||
|
||||
import io.lumine.mythic.lib.api.crafting.uimanager.ProvidedUIFilter;
|
||||
import io.lumine.mythic.lib.api.util.ui.SilentNumbers;
|
||||
import net.Indyuce.mmoitems.api.crafting.recipe.Recipe;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.recipes.RecipeMakerGUI;
|
||||
import org.bukkit.configuration.ConfigurationSection;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* This class is in charge of converting Shaped Recipes to and fro YML format,
|
||||
* as well as editing it in a YML configuration and such. <br> <br>
|
||||
*
|
||||
* YML Save Format: <br> <code>
|
||||
*
|
||||
* - A|B|C|D|E <br>
|
||||
* - F|G|H|I|J <br>
|
||||
* - K|L|M|N|O <br>
|
||||
* - P|Q|R|S|T <br>
|
||||
* - U|V|W|X|Y
|
||||
* </code>
|
||||
*
|
||||
* @author Gunging
|
||||
*/
|
||||
public class RMGRI_SuperShaped implements RMG_RecipeInterpreter {
|
||||
|
||||
|
||||
/**
|
||||
* Builds a valid 5x5 matrix of input/output recipe.
|
||||
*
|
||||
* @param config List as it is saved in the config.
|
||||
*
|
||||
* @return Transcribed into array of arrays.
|
||||
*/
|
||||
@NotNull ProvidedUIFilter[][] buildIngredientsFromList(@NotNull List<String> config) {
|
||||
|
||||
// Start with a base
|
||||
ProvidedUIFilter[][] ret = new ProvidedUIFilter[5][5];
|
||||
|
||||
// Each row ig
|
||||
for (int r = 0; r < 5; r++) {
|
||||
|
||||
// Get current row
|
||||
String row = config.size() > r ? config.get(r) : null;
|
||||
//READ//MMOItems.log("\u00a7b*\u00a77 Reading\u00a7b " + row);
|
||||
|
||||
// Update it ig
|
||||
String s = updateRow(row);
|
||||
//READ//MMOItems.log("\u00a7b*\u00a77 Updated to\u00a7b " + row);
|
||||
|
||||
// Split
|
||||
String[] poofs = s.split("\\|");
|
||||
|
||||
// Parse
|
||||
for (int p = 0; p < 5; p++) {
|
||||
|
||||
String poof = poofs.length > p ? poofs[p] : null;
|
||||
//READ//MMOItems.log("\u00a7b*\u00a77 Coord\u00a7b " + r + " " + p + "\u00a77 as\u00a73 " + poof);
|
||||
|
||||
// Parse
|
||||
ProvidedUIFilter parsed = ProvidedUIFilter.getFromString(poof, null);
|
||||
if (parsed == null) { parsed = RecipeMakerGUI.AIR.clone(); }
|
||||
|
||||
// Add
|
||||
ret[r][p] = parsed; } }
|
||||
|
||||
// And that's your result
|
||||
return ret;
|
||||
}
|
||||
/**
|
||||
* Turns something like <br> <code>
|
||||
*
|
||||
* [ A, B, C, D, E ], <br>
|
||||
* [ F, G, H, I, J ], <br>
|
||||
* [ K, L, M, N, O ], <br>
|
||||
* [ P, Q, R, S, T ], <br>
|
||||
* [ U, V, W, X, Y ] <br>
|
||||
*
|
||||
* </code> <br>
|
||||
* into <br> <code>
|
||||
*
|
||||
* - A|B|C|D|E <br>
|
||||
* - F|G|H|I|J <br>
|
||||
* - K|L|M|N|O <br>
|
||||
* - P|Q|R|S|T <br>
|
||||
* - U|V|W|X|Y
|
||||
* </code>
|
||||
*
|
||||
* @param ingredients Array of arrays of UIFilters
|
||||
*
|
||||
* @return A list of strings to save in a YML Config
|
||||
*/
|
||||
@NotNull
|
||||
ArrayList<String> toYML(@NotNull ProvidedUIFilter[][] ingredients) {
|
||||
|
||||
// Well, build it would ye?
|
||||
ArrayList<String> ret = new ArrayList<>();
|
||||
|
||||
for (int r = 0; r < 5; r++) {
|
||||
|
||||
// Get row
|
||||
ProvidedUIFilter[] poofs = ingredients.length > r ? ingredients[r] : new ProvidedUIFilter[5];
|
||||
|
||||
// Concatenate
|
||||
StringBuilder sb = new StringBuilder();
|
||||
|
||||
// Build
|
||||
for (ProvidedUIFilter poof : poofs) {
|
||||
ProvidedUIFilter providedUIFilter = poof;
|
||||
if (providedUIFilter == null) { providedUIFilter = RecipeMakerGUI.AIR.clone(); }
|
||||
|
||||
// Add bar
|
||||
if (sb.length() != 0) { sb.append("|"); }
|
||||
|
||||
// Add poof
|
||||
sb.append(providedUIFilter);
|
||||
}
|
||||
|
||||
ret.add(sb.toString());
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@NotNull final ProvidedUIFilter[][] inputRecipe;
|
||||
/**
|
||||
* Sets the ingredient in the rows matrix.
|
||||
*
|
||||
* @param slot The slot, which must be between 0 and 24 (or this method will do nothing)
|
||||
* @param poof Ingredient to register
|
||||
*/
|
||||
public void setInput(int slot, @NotNull ProvidedUIFilter poof) {
|
||||
if (slot < 0 || slot > 24) { return; }
|
||||
inputRecipe[SilentNumbers.floor(slot / 5.0)][slot - (5 * SilentNumbers.floor(slot / 5.0))] = poof;
|
||||
}
|
||||
@Nullable
|
||||
@Override public ProvidedUIFilter getInput(int slot) {
|
||||
if (slot < 0 || slot > 24) { return null; }
|
||||
return inputRecipe[SilentNumbers.floor(slot / 5.0)][slot - (5 * SilentNumbers.floor(slot / 5.0))];
|
||||
}
|
||||
|
||||
@NotNull final ProvidedUIFilter[][] outputRecipe;
|
||||
/**
|
||||
* Sets the ingredient in the rows matrix.
|
||||
*
|
||||
* @param slot The slot, which must be between 0 and 24 (or this method will do nothing)
|
||||
* @param poof Ingredient to register
|
||||
*/
|
||||
public void setOutput(int slot, @NotNull ProvidedUIFilter poof) {
|
||||
if (slot < 0 || slot > 24) { return; }
|
||||
outputRecipe[SilentNumbers.floor(slot / 5.0)][slot - (5 * SilentNumbers.floor(slot / 5.0))] = poof;
|
||||
}
|
||||
@Nullable
|
||||
@Override public ProvidedUIFilter getOutput(int slot) {
|
||||
if (slot < 0 || slot > 24) { return null; }
|
||||
return outputRecipe[SilentNumbers.floor(slot / 5.0)][slot - (5 * SilentNumbers.floor(slot / 5.0))];
|
||||
}
|
||||
|
||||
@NotNull final ConfigurationSection section;
|
||||
/**
|
||||
* @return The recipe name section of this recipe. <br>
|
||||
* <br>
|
||||
* Basically <b><code>[ID].base.crafting.shaped.[name]</code></b> section
|
||||
*/
|
||||
@NotNull public ConfigurationSection getSection() { return section; }
|
||||
|
||||
/**
|
||||
* Generate an interpreter from this <i>updated</i> configuration section.
|
||||
* <br><br>
|
||||
* By 'updated' I mean that, for now, we <b>should call {@link RecipeMakerGUI#moveInput()}
|
||||
* on this configuration before passing it here</b>, to move the input list from being the recipe name
|
||||
* section itself to the 'input' section within.
|
||||
*
|
||||
* @param recipeNameSection <b><code>[ID].base.crafting.shaped.[name]</code></b> section
|
||||
*/
|
||||
public RMGRI_SuperShaped(@NotNull ConfigurationSection recipeNameSection) {
|
||||
|
||||
// Save
|
||||
section = recipeNameSection;
|
||||
|
||||
// Build Input list
|
||||
inputRecipe = buildIngredientsFromList(section.getStringList(RecipeMakerGUI.INPUT_INGREDIENTS));
|
||||
outputRecipe = buildIngredientsFromList(section.getStringList(RecipeMakerGUI.OUTPUT_INGREDIENTS));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editInput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setInput(slot, input);
|
||||
|
||||
// Save
|
||||
section.set(RecipeMakerGUI.INPUT_INGREDIENTS, toYML(inputRecipe));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void editOutput(@NotNull ProvidedUIFilter input, int slot) {
|
||||
|
||||
// Just edit bro
|
||||
setOutput(slot, input);
|
||||
|
||||
// Save
|
||||
section.set(RecipeMakerGUI.OUTPUT_INGREDIENTS, toYML(outputRecipe));
|
||||
}
|
||||
|
||||
@Override public void deleteInput(int slot) { editInput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
@Override public void deleteOutput(int slot) { editOutput(RecipeMakerGUI.AIR.clone(), slot); }
|
||||
|
||||
//region Updater, to update old recipes
|
||||
/**
|
||||
* No matter what input, the output will always be three Provided UIFilters
|
||||
* separated by bars, as expected in the current system, filling with AIR
|
||||
* where necessary.
|
||||
*
|
||||
* @param curr Current string
|
||||
*
|
||||
* @return A row in correct format
|
||||
*/
|
||||
@NotNull public static String updateRow(@Nullable String curr) {
|
||||
if (curr == null || curr.isEmpty()) { return emptyRow;}
|
||||
|
||||
// Bars used? I guess we can check that its written correctly
|
||||
if (curr.contains("|")) {
|
||||
|
||||
// Split by bars
|
||||
String[] curSplit = curr.split("\\|");
|
||||
|
||||
// Correct length?
|
||||
if (curSplit.length == 5) {
|
||||
|
||||
// Assumed to be updated.
|
||||
return curr;
|
||||
|
||||
} else {
|
||||
|
||||
// Make sure it is of size three
|
||||
StringBuilder ret = new StringBuilder();
|
||||
|
||||
// Must append three
|
||||
for (int r = 0; r < 5; r++) {
|
||||
|
||||
// Append a bar after the first
|
||||
if (r != 0) { ret.append("|"); }
|
||||
|
||||
// Array has it?
|
||||
if (r < curSplit.length) { ret.append(RecipeMakerGUI.poofFromLegacy(curSplit[r])); } else { ret.append("v AIR 0"); }
|
||||
}
|
||||
|
||||
// Build and return
|
||||
return ret.toString();
|
||||
}
|
||||
|
||||
// Not bars, but spaces, might be old format
|
||||
} else if (curr.contains(" ")) {
|
||||
|
||||
// Make string builder
|
||||
StringBuilder ret = new StringBuilder();
|
||||
String[] curSplit = curr.split(" ");
|
||||
|
||||
// Must append three
|
||||
for (int r = 0; r < 5; r++) {
|
||||
|
||||
// Append a bar after the first
|
||||
if (r != 0) { ret.append("|"); }
|
||||
|
||||
// Array has it?
|
||||
if (r < curSplit.length) { ret.append(RecipeMakerGUI.poofFromLegacy(curSplit[r])); } else { ret.append("v AIR 0"); }
|
||||
}
|
||||
|
||||
// Build and return
|
||||
return ret.toString();
|
||||
|
||||
// No spaces nor bars, this will just be the first ingredient of the row I guess
|
||||
} else {
|
||||
|
||||
// Just that i guess
|
||||
return RecipeMakerGUI.poofFromLegacy(curr) + "|v AIR 0|v AIR 0|v AIR 0|v AIR 0";
|
||||
}
|
||||
}
|
||||
public static final String emptyRow = "v AIR 0|v AIR 0|v AIR 0|v AIR 0|v AIR 0";
|
||||
//endregion
|
||||
}
|
@ -17,66 +17,34 @@ public interface RMG_RecipeInterpreter {
|
||||
/**
|
||||
* Edits the configuration section's INPUT list.
|
||||
*
|
||||
* @param section <b>The 'crafting' section - [ID].base.crafting</b>
|
||||
* <br><br>
|
||||
* Note that this is not editing the recipe type nor name itself.
|
||||
* It is up to the interpreter to create the sections if missing
|
||||
* or edit them if they are already there.
|
||||
* <br><br>
|
||||
* Ex: [ID].base.crafting.shaped.1.input
|
||||
*
|
||||
* @param input The user's input, item that will be required
|
||||
*
|
||||
* @param slot Slot that the item is going into
|
||||
*/
|
||||
void editInput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot);
|
||||
void editInput(@NotNull ProvidedUIFilter input, int slot);
|
||||
|
||||
/**
|
||||
* Edits the configuration section's OUTPUT list.
|
||||
*
|
||||
* @param section <b>The 'crafting' section - [ID].base.crafting</b>
|
||||
* <br><br>
|
||||
* Note that this is not editing the recipe type nor name itself.
|
||||
* It is up to the interpreter to create the sections if missing
|
||||
* or edit them if they are already there.
|
||||
* <br><br>
|
||||
* Ex: [ID].base.crafting.shaped.1.output
|
||||
*
|
||||
* @param input The user's input, item that will be required
|
||||
*
|
||||
* @param slot Slot that the item is going into
|
||||
*/
|
||||
void editOutput(@NotNull ConfigurationSection section, @NotNull ProvidedUIFilter input, int slot);
|
||||
void editOutput(@NotNull ProvidedUIFilter input, int slot);
|
||||
|
||||
/**
|
||||
* Edits the configuration section's INPUT list.
|
||||
*
|
||||
* @param section <b>The 'crafting' section - [ID].base.crafting</b>
|
||||
* <br><br>
|
||||
* Note that this is not editing the recipe type nor name itself.
|
||||
* It is up to the interpreter to create the sections if missing
|
||||
* or edit them if they are already there.
|
||||
* <br><br>
|
||||
* Ex: [ID].base.crafting.shaped.1.input
|
||||
*
|
||||
* @param slot Slot that is getting reset
|
||||
*/
|
||||
void deleteInput(@NotNull ConfigurationSection section, int slot);
|
||||
void deleteInput(int slot);
|
||||
|
||||
/**
|
||||
* Edits the configuration section's OUTPUT list.
|
||||
*
|
||||
* @param section <b>The 'crafting' section - [ID].base.crafting</b>
|
||||
* <br><br>
|
||||
* Note that this is not editing the recipe type nor name itself.
|
||||
* It is up to the interpreter to create the sections if missing
|
||||
* or edit them if they are already there.
|
||||
* <br><br>
|
||||
* Ex: [ID].base.crafting.shaped.1.output
|
||||
*
|
||||
* @param slot Slot that is getting reset
|
||||
*/
|
||||
void deleteOutput(@NotNull ConfigurationSection section, int slot);
|
||||
void deleteOutput(int slot);
|
||||
|
||||
/**
|
||||
* Fetch the Provided UI Filter in the YML configuration
|
||||
|
@ -6,6 +6,7 @@ import io.lumine.mythic.lib.api.util.ui.SilentNumbers;
|
||||
import io.lumine.mythic.utils.items.ItemFactory;
|
||||
import io.lumine.mythic.utils.version.ServerVersion;
|
||||
import net.Indyuce.mmoitems.ItemStats;
|
||||
import net.Indyuce.mmoitems.MMOItems;
|
||||
import net.Indyuce.mmoitems.api.edition.StatEdition;
|
||||
import net.Indyuce.mmoitems.api.util.message.FFPMMOItems;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.recipes.RecipeMakerGUI;
|
||||
@ -46,7 +47,7 @@ public class RBA_AmountOutput extends RecipeButtonAction {
|
||||
@NotNull ItemMeta buttonMeta = Objects.requireNonNull(button.getItemMeta());
|
||||
@NotNull ItemMeta resultMeta = Objects.requireNonNull(resultItem.getItemMeta());
|
||||
|
||||
if (ServerVersion.get().getMinor() >= 14 && buttonMeta.hasCustomModelData()) { buttonMeta.setCustomModelData(resultMeta.getCustomModelData()); }
|
||||
if (ServerVersion.get().getMinor() >= 14 && resultMeta.hasCustomModelData()) { buttonMeta.setCustomModelData(resultMeta.getCustomModelData()); }
|
||||
if (resultMeta instanceof LeatherArmorMeta) { ((LeatherArmorMeta) buttonMeta).setColor(((LeatherArmorMeta) resultMeta).getColor()); }
|
||||
if (resultMeta instanceof BannerMeta) { ((BannerMeta) buttonMeta).setPatterns(((BannerMeta) resultMeta).getPatterns()); }
|
||||
buttonMeta.addItemFlags(ItemFlag.HIDE_ATTRIBUTES, ItemFlag.HIDE_DYE, ItemFlag.HIDE_POTION_EFFECTS);
|
||||
|
@ -2,7 +2,6 @@ package net.Indyuce.mmoitems.gui.edition.recipe.recipes;
|
||||
|
||||
import net.Indyuce.mmoitems.api.item.template.MMOItemTemplate;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMGRI_BurningLegacy;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMGRI_Shaped;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMG_RecipeInterpreter;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.rba.RBA_CookingTime;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.rba.RBA_Experience;
|
||||
|
@ -1,6 +1,5 @@
|
||||
package net.Indyuce.mmoitems.gui.edition.recipe.recipes;
|
||||
|
||||
import net.Indyuce.mmoitems.MMOItems;
|
||||
import net.Indyuce.mmoitems.api.item.template.MMOItemTemplate;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMGRI_Shaped;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMG_RecipeInterpreter;
|
||||
@ -15,11 +14,6 @@ import java.util.HashMap;
|
||||
|
||||
/**
|
||||
* Edits shaped recipes, very nice.
|
||||
* <br> <br> <code>
|
||||
* - - - - - - - - - <br>
|
||||
* 0 1 2 = 0 1 2 - - <br>
|
||||
* 3 4 5 = 3 4 5 - R <br>
|
||||
* 6 7 8 = 6 7 8 - - </code>
|
||||
*
|
||||
* @author Gunging
|
||||
*/
|
||||
|
@ -0,0 +1,96 @@
|
||||
package net.Indyuce.mmoitems.gui.edition.recipe.recipes;
|
||||
|
||||
import net.Indyuce.mmoitems.api.item.template.MMOItemTemplate;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMGRI_SuperShaped;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMG_RecipeInterpreter;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.rba.RBA_HideFromBook;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.rba.RBA_InputOutput;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.registry.RecipeRegistry;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
/**
|
||||
* Edits super shaped recipes, very nice.
|
||||
*
|
||||
* @author Gunging
|
||||
*/
|
||||
public class RMG_SuperShaped extends RecipeMakerGUI {
|
||||
|
||||
@NotNull HashMap<Integer, Integer> inputLinks = new HashMap<>();
|
||||
|
||||
/**
|
||||
* An editor for a Super Shaped Recipe. Because the recipe is loaded from the YML when this is created,
|
||||
* concurrent modifications of the same recipe are unsupported.
|
||||
*
|
||||
* @param player Player editing the recipe ig
|
||||
* @param template Template of which a recipe is being edited
|
||||
* @param recipeName Name of this recipe
|
||||
*/
|
||||
public RMG_SuperShaped(@NotNull Player player, @NotNull MMOItemTemplate template, @NotNull String recipeName, @NotNull RecipeRegistry recipeRegistry) {
|
||||
super(player, template, recipeName, recipeRegistry);
|
||||
addButton(new RBA_InputOutput(this));
|
||||
addButton(new RBA_HideFromBook(this));
|
||||
|
||||
// Get section and build interpreter
|
||||
interpreter = new RMGRI_SuperShaped(getNameSection());
|
||||
|
||||
// Bind inputs
|
||||
inputLinks.put(11, 0);
|
||||
inputLinks.put(12, 1);
|
||||
inputLinks.put(13, 2);
|
||||
inputLinks.put(14, 3);
|
||||
inputLinks.put(15, 4);
|
||||
|
||||
inputLinks.put(20, 5);
|
||||
inputLinks.put(21, 6);
|
||||
inputLinks.put(22, 7);
|
||||
inputLinks.put(23, 8);
|
||||
inputLinks.put(24, 9);
|
||||
|
||||
inputLinks.put(29, 10);
|
||||
inputLinks.put(30, 11);
|
||||
inputLinks.put(31, 12);
|
||||
inputLinks.put(32, 13);
|
||||
inputLinks.put(33, 14);
|
||||
|
||||
inputLinks.put(38, 15);
|
||||
inputLinks.put(39, 16);
|
||||
inputLinks.put(40, 17);
|
||||
inputLinks.put(41, 18);
|
||||
inputLinks.put(42, 19);
|
||||
|
||||
inputLinks.put(47, 20);
|
||||
inputLinks.put(48, 21);
|
||||
inputLinks.put(49, 22);
|
||||
inputLinks.put(50, 23);
|
||||
inputLinks.put(51, 24);
|
||||
}
|
||||
|
||||
@Override public int getButtonsRow() { return 0; }
|
||||
|
||||
@Override
|
||||
public void putRecipe(@NotNull Inventory target) {
|
||||
|
||||
// Fill inputs
|
||||
for (Integer s : inputLinks.keySet()) { target.setItem(s, getDisplay(isShowingInput(), inputLinks.get(s))); }
|
||||
}
|
||||
|
||||
@Override
|
||||
int getInputSlot(int absolute) {
|
||||
|
||||
// Not an input? Not our business
|
||||
@Nullable Integer found = inputLinks.get(absolute);
|
||||
|
||||
// Found or negative
|
||||
return found != null ? found : -1;
|
||||
}
|
||||
|
||||
@NotNull final RMGRI_SuperShaped interpreter;
|
||||
@NotNull
|
||||
@Override
|
||||
public RMG_RecipeInterpreter getInterpreter() { return interpreter; }
|
||||
}
|
@ -415,12 +415,15 @@ public abstract class RecipeMakerGUI extends EditionInventory {
|
||||
if (isShowingInput()) {
|
||||
|
||||
// Delete Input
|
||||
getInterpreter().deleteInput(getSection(getEditedSection(), "crafting"), ingredient);
|
||||
getInterpreter().deleteInput(ingredient);
|
||||
|
||||
} else {
|
||||
|
||||
// Delete Output
|
||||
getInterpreter().deleteOutput(getSection(getEditedSection(), "crafting"), getInputSlot(event.getRawSlot())); }
|
||||
getInterpreter().deleteOutput(getInputSlot(event.getRawSlot())); }
|
||||
|
||||
// Register
|
||||
registerTemplateEdition();
|
||||
|
||||
// Refresh yes
|
||||
refreshInventory();
|
||||
|
@ -9,7 +9,6 @@ import io.lumine.mythic.lib.api.crafting.recipes.ShapedRecipe;
|
||||
import io.lumine.mythic.lib.api.crafting.uimanager.ProvidedUIFilter;
|
||||
import io.lumine.mythic.lib.api.util.Ref;
|
||||
import io.lumine.mythic.lib.api.util.ui.FriendlyFeedbackProvider;
|
||||
import net.Indyuce.mmoitems.MMOItems;
|
||||
import net.Indyuce.mmoitems.api.crafting.MMOItemUIFilter;
|
||||
import net.Indyuce.mmoitems.api.item.template.MMOItemTemplate;
|
||||
import net.Indyuce.mmoitems.api.util.message.FFPMMOItems;
|
||||
|
@ -0,0 +1,191 @@
|
||||
package net.Indyuce.mmoitems.gui.edition.recipe.registry;
|
||||
|
||||
import io.lumine.mythic.lib.api.crafting.ingredients.ShapedIngredient;
|
||||
import io.lumine.mythic.lib.api.crafting.outputs.MRORecipe;
|
||||
import io.lumine.mythic.lib.api.crafting.outputs.MythicRecipeOutput;
|
||||
import io.lumine.mythic.lib.api.crafting.recipes.MythicRecipeBlueprint;
|
||||
import io.lumine.mythic.lib.api.crafting.recipes.MythicRecipeStation;
|
||||
import io.lumine.mythic.lib.api.crafting.recipes.ShapedRecipe;
|
||||
import io.lumine.mythic.lib.api.crafting.uimanager.ProvidedUIFilter;
|
||||
import io.lumine.mythic.lib.api.util.Ref;
|
||||
import io.lumine.mythic.lib.api.util.ui.FriendlyFeedbackProvider;
|
||||
import net.Indyuce.mmoitems.api.crafting.MMOItemUIFilter;
|
||||
import net.Indyuce.mmoitems.api.item.template.MMOItemTemplate;
|
||||
import net.Indyuce.mmoitems.api.util.message.FFPMMOItems;
|
||||
import net.Indyuce.mmoitems.gui.edition.EditionInventory;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.interpreters.RMGRI_SuperShaped;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.rba.RBA_AmountOutput;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.rba.RBA_HideFromBook;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.recipes.RMG_SuperShaped;
|
||||
import net.Indyuce.mmoitems.gui.edition.recipe.recipes.RecipeMakerGUI;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.NamespacedKey;
|
||||
import org.bukkit.configuration.ConfigurationSection;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
public class RMGRR_SuperShaped implements RecipeRegistry {
|
||||
|
||||
@NotNull
|
||||
@Override public String getRecipeConfigPath() { return "supershaped"; }
|
||||
@NotNull @Override public String getRecipeTypeName() { return "Super Shaped"; }
|
||||
|
||||
@NotNull final ItemStack displayListItem = RecipeMakerGUI.rename(new ItemStack(Material.NOTE_BLOCK), FFPMMOItems.get().getExampleFormat() + "Super Shaped Recipe");
|
||||
@NotNull @Override public ItemStack getDisplayListItem() { return displayListItem; }
|
||||
|
||||
@Override public void openForPlayer(@NotNull EditionInventory inv, @NotNull String recipeName, Object... otherParams) {
|
||||
new RMG_SuperShaped(inv.getPlayer(), inv.getEdited(), recipeName, this).open(inv.getPreviousPage());
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public MythicRecipeBlueprint sendToMythicLib(@NotNull MMOItemTemplate template, @NotNull ConfigurationSection recipeTypeSection, @NotNull String recipeName, @NotNull Ref<NamespacedKey> namespace, @NotNull FriendlyFeedbackProvider ffp) throws IllegalArgumentException {
|
||||
|
||||
// Read some values
|
||||
ConfigurationSection recipeSection = RecipeMakerGUI.moveInput(recipeTypeSection, recipeName);
|
||||
|
||||
NamespacedKey nk = namespace.getValue();
|
||||
if (nk == null) { throw new IllegalArgumentException(FriendlyFeedbackProvider.quickForConsole(FFPMMOItems.get(), "Illegal (Null) Namespace")); }
|
||||
|
||||
// Identify the input
|
||||
ShapedRecipe input = superShapedRecipeFromList(nk.getKey(), new ArrayList<>(recipeSection.getStringList(RecipeMakerGUI.INPUT_INGREDIENTS)), ffp);
|
||||
if (input == null) { throw new IllegalArgumentException(FriendlyFeedbackProvider.quickForConsole(FFPMMOItems.get(), "Shaped recipe containing only AIR, $fignored$b.")); }
|
||||
|
||||
// Read the options and output
|
||||
ShapedRecipe output = superShapedRecipeFromList(nk.getKey(), new ArrayList<>(recipeSection.getStringList(RecipeMakerGUI.OUTPUT_INGREDIENTS)), ffp);
|
||||
int outputAmount = recipeSection.getInt(RBA_AmountOutput.AMOUNT_INGREDIENTS, 1);
|
||||
boolean hideBook = recipeSection.getBoolean(RBA_HideFromBook.BOOK_HIDDEN, false);
|
||||
|
||||
// Build Output
|
||||
ShapedRecipe outputItem = ShapedRecipe.single(nk.getKey(), new ProvidedUIFilter(MMOItemUIFilter.get(), template.getType().getId(), template.getId(), Math.max(outputAmount, 1)));
|
||||
MythicRecipeOutput outputRecipe = new MRORecipe(outputItem, output);
|
||||
|
||||
// That's our blueprint :)
|
||||
MythicRecipeBlueprint ret = new MythicRecipeBlueprint(input, outputRecipe, nk);
|
||||
|
||||
// Enable it
|
||||
ret.deploy(MythicRecipeStation.WORKBENCH, namespace);
|
||||
|
||||
// Hide book if specified
|
||||
if (hideBook) { namespace.setValue(null); }
|
||||
|
||||
// That's it
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
* Shorthand for reading list of strings that are intended to be shaped recipes: <br><br>
|
||||
* <code>
|
||||
* v AIR 0|v STICK 0|v AIR 0|v STICK 0|v AIR 0 <br>
|
||||
* v AIR 0|v STICK 0|v AIR 0|v STICK 0|v AIR 0 <br>
|
||||
* v AIR 0|v STICK 0|v AIR 0|v STICK 0|v AIR 0 <br>
|
||||
* v AIR 0|v STICK 0|v AIR 0|v STICK 0|v AIR 0 <br>
|
||||
* v AIR 0|v STICK 0|v AIR 0|v STICK 0|v AIR 0
|
||||
* </code>
|
||||
*
|
||||
* @param namespace Some name to give to this thing, it can be anything really.
|
||||
*
|
||||
* @param recipe The list of strings, probably directly from your YML Config
|
||||
*
|
||||
* @param ffp Provider of failure text
|
||||
*
|
||||
* @return The most optimized version of this recipe, ready to be put into a Blueprint.
|
||||
* <br> <br>
|
||||
* Will be <code>null</code> if it would have been only AIR.
|
||||
*
|
||||
* @throws IllegalArgumentException If any ingredient is illegal (wrong syntax or something).
|
||||
*/
|
||||
@Nullable
|
||||
public static ShapedRecipe superShapedRecipeFromList(@NotNull String namespace, @NotNull ArrayList<String> recipe, @NotNull FriendlyFeedbackProvider ffp) throws IllegalArgumentException {
|
||||
|
||||
// All right lets read them
|
||||
ArrayList<ShapedIngredient> poofs = new ArrayList<>();
|
||||
boolean nonAirFound = false;
|
||||
int rowNumber = 0;
|
||||
//UPT//MMOItems.log("\u00a7e" + namespace + "\u00a77 loading:");
|
||||
|
||||
// Read through the recipe
|
||||
for (String row : recipe) {
|
||||
//UPT//MMOItems.log("\u00a7e-\u00a77 " + row);
|
||||
|
||||
// Update
|
||||
String updatedRow = RMGRI_SuperShaped.updateRow(row);
|
||||
//UPT//MMOItems.log("\u00a7eU-\u00a77 " + updatedRow);
|
||||
|
||||
/*
|
||||
* This row could be in either legacy or new format, and we will assume no combination of them.
|
||||
*
|
||||
* Either:
|
||||
* ANYTHING ANY.THING ANYTHING
|
||||
*
|
||||
* or
|
||||
* A NYT THIN G|A NYT THING|A NYT THIN G
|
||||
*/
|
||||
|
||||
// What are the three ingredients encoded in this row?
|
||||
String[] positions;
|
||||
|
||||
if (updatedRow.contains("|")) {
|
||||
|
||||
// Split by |s
|
||||
positions = updatedRow.split("\\|");
|
||||
|
||||
// Is legacy
|
||||
} else {
|
||||
|
||||
// Split by spaces
|
||||
positions = updatedRow.split(" ");
|
||||
}
|
||||
|
||||
// Size not 3? BRUH
|
||||
if (positions.length != 5) { throw new IllegalArgumentException("Invalid super crafting table row $u" + updatedRow + "$b ($fNot exactly 5 ingredients wide$b)."); }
|
||||
|
||||
// Identify
|
||||
ProvidedUIFilter left = RecipeMakerGUI.readIngredientFrom(positions[0], ffp);
|
||||
ProvidedUIFilter midLeft = RecipeMakerGUI.readIngredientFrom(positions[1], ffp);
|
||||
ProvidedUIFilter center = RecipeMakerGUI.readIngredientFrom(positions[2], ffp);
|
||||
ProvidedUIFilter midRight = RecipeMakerGUI.readIngredientFrom(positions[3], ffp);
|
||||
ProvidedUIFilter right = RecipeMakerGUI.readIngredientFrom(positions[4], ffp);
|
||||
if (!left.isAir()) { nonAirFound = true; }
|
||||
if (!midLeft.isAir()) { nonAirFound = true; }
|
||||
if (!center.isAir()) { nonAirFound = true; }
|
||||
if (!midRight.isAir()) { nonAirFound = true; }
|
||||
if (!right.isAir()) { nonAirFound = true; }
|
||||
|
||||
/*
|
||||
* To detect if a recipe can be crafted in the survival inventory (and remove extra AIR),
|
||||
* we must see that a whole row AND a whole column be air. Not any column or row though,
|
||||
* but any of those that do not cross the center.
|
||||
*
|
||||
* If a single left item is not air, LEFT is no longer an unsharped column.
|
||||
* If a single right item is not air, RIGHT is no longer an unsharped column.
|
||||
*
|
||||
* All items must be air in TOP or BOTTOM for they to be unsharped.
|
||||
*/
|
||||
|
||||
// Bake
|
||||
ShapedIngredient leftIngredient = new ShapedIngredient(left, 0, -rowNumber);
|
||||
ShapedIngredient midLeftIngredient = new ShapedIngredient(midLeft, 1, -rowNumber);
|
||||
ShapedIngredient centerIngredient = new ShapedIngredient(center, 2, -rowNumber);
|
||||
ShapedIngredient midRightIngredient = new ShapedIngredient(midRight, 3, -rowNumber);
|
||||
ShapedIngredient rightIngredient = new ShapedIngredient(right, 4, -rowNumber);
|
||||
|
||||
// Parse and add
|
||||
poofs.add(leftIngredient);
|
||||
poofs.add(midLeftIngredient);
|
||||
poofs.add(centerIngredient);
|
||||
poofs.add(midRightIngredient);
|
||||
poofs.add(rightIngredient);
|
||||
|
||||
// Prepare for next row
|
||||
rowNumber++;
|
||||
}
|
||||
if (!nonAirFound) { return null; }
|
||||
|
||||
// Make ingredients
|
||||
return ShapedRecipe.unsharpen((new ShapedRecipe(namespace, poofs)));
|
||||
}
|
||||
}
|
@ -169,11 +169,11 @@ public class Crafting extends ItemStat {
|
||||
|
||||
// Redirect
|
||||
if (type == RecipeMakerGUI.INPUT) {
|
||||
interpreter.editInput(section, read, slot);
|
||||
interpreter.editInput(read, slot);
|
||||
|
||||
// It must be output
|
||||
} else {
|
||||
interpreter.editOutput(section, read, slot); }
|
||||
interpreter.editOutput(read, slot); }
|
||||
|
||||
// Save changes
|
||||
inv.registerTemplateEdition();
|
||||
|
Loading…
Reference in New Issue
Block a user