Skip to content

Commit

Permalink
Add the ability for sorters to ignore enchants, meta, and/or durability
Browse files Browse the repository at this point in the history
  • Loading branch information
BillyGalbreath authored and me4502 committed Jan 22, 2018
1 parent 6355e7c commit caad5d5
Show file tree
Hide file tree
Showing 3 changed files with 106 additions and 48 deletions.
Expand Up @@ -24,6 +24,7 @@
import com.sk89q.craftbook.mechanics.pipe.PipeRequestEvent;
import com.sk89q.craftbook.util.InventoryUtil;
import com.sk89q.craftbook.util.ItemUtil;
import com.sk89q.craftbook.util.RegexUtil;
import com.sk89q.craftbook.util.SignUtil;

public class Sorter extends AbstractSelfTriggeredIC implements PipeInputIC {
Expand All @@ -35,12 +36,24 @@ public Sorter(Server server, ChangedSign sign, ICFactory factory) {

Block chestBlock;
boolean inverted;
boolean ignoreDurability;
boolean ignoreEnchants;
boolean ignoreMeta;

@Override
public void load() {

chestBlock = getBackBlock().getRelative(0, 1, 0);
inverted = getSign().getLine(2).equalsIgnoreCase("invert");

for (String line4 : RegexUtil.PIPE_PATTERN.split(getSign().getLine(3))) {
if (line4.equalsIgnoreCase("!D"))
ignoreDurability = true;
if (line4.equalsIgnoreCase("!E"))
ignoreEnchants = true;
if (line4.equalsIgnoreCase("!M"))
ignoreMeta = true;
}
}

@Override
Expand Down Expand Up @@ -102,7 +115,7 @@ public boolean sortItemStack(final ItemStack item) {
public boolean isInAboveContainer(ItemStack item) {
ItemStack itemClone = item.clone();
itemClone.setAmount(1);
return InventoryUtil.doesBlockHaveInventory(chestBlock) && InventoryUtil.doesInventoryContain(((InventoryHolder) chestBlock.getState()).getInventory(), false, itemClone);
return InventoryUtil.doesBlockHaveInventory(chestBlock) && InventoryUtil.doesInventoryContain(((InventoryHolder) chestBlock.getState()).getInventory(), true, ignoreDurability, ignoreMeta, ignoreEnchants, itemClone);
}

public static class Factory extends AbstractICFactory {
Expand Down
38 changes: 35 additions & 3 deletions src/main/java/com/sk89q/craftbook/util/InventoryUtil.java
Expand Up @@ -134,6 +134,21 @@ public static ArrayList<ItemStack> addItemsToBrewingStand(BrewingStand brewingSt
* @return whether the inventory contains all the items. If there are no items to check, it returns true.
*/
public static boolean doesInventoryContain(Inventory inv, boolean exact, ItemStack ... stacks) {
return doesInventoryContain(inv, !exact, false, false, false, stacks);
}

/**
* Checks whether the inventory contains all the given itemstacks.
*
* @param inv The inventory to check.
* @param ignoreStackSize Whether to ignore stack size count.
* @param ignoreDurability Whether to ignore durability if damageable.
* @param ignoreMeta Whether to ignore meta/nbt data.
* @param ignoreEnchants Whether to ignore enchantment data.
* @param stacks The stacks to check.
* @return whether the inventory contains all the items. If there are no items to check, it returns true.
*/
public static boolean doesInventoryContain(Inventory inv, boolean ignoreStackSize, boolean ignoreDurability, boolean ignoreMeta, boolean ignoreEnchants, ItemStack ... stacks) {

ArrayList<ItemStack> itemsToFind = new ArrayList<>(Arrays.asList(stacks));

Expand All @@ -146,7 +161,7 @@ public static boolean doesInventoryContain(Inventory inv, boolean exact, ItemSta
items.add(((PlayerInventory) inv).getItemInOffHand());
}

for (ItemStack item : inv.getContents()) {
for (ItemStack item : items) {
if(!ItemUtil.isStackValid(item))
continue;

Expand All @@ -159,10 +174,27 @@ public static boolean doesInventoryContain(Inventory inv, boolean exact, ItemSta
continue;
}

if(ItemUtil.areItemsIdentical(base, item)) {
if(exact && base.getAmount() != item.getAmount())
if(ItemUtil.areItemsSimilar(base, item)) {
if(!ignoreStackSize && base.getAmount() != item.getAmount())
continue;

if(!ignoreDurability && (base.getType().getMaxDurability() > 0 || item.getType().getMaxDurability() > 0) && base.getDurability() != item.getDurability())
continue;

if(!ignoreMeta) {
if(base.hasItemMeta() != item.hasItemMeta()) {
if(!ignoreEnchants)
continue;
if(base.hasItemMeta() && ItemUtil.hasDisplayNameOrLore(base))
continue;
else if(item.hasItemMeta() && ItemUtil.hasDisplayNameOrLore(item))
continue;
} else if(base.hasItemMeta()) {
if(base.hasItemMeta() && !ItemUtil.areItemMetaIdentical(base.getItemMeta(), item.getItemMeta(), !ignoreEnchants))
continue;
}
}

itemsToFind.remove(base);
break;
}
Expand Down
101 changes: 57 additions & 44 deletions src/main/java/com/sk89q/craftbook/util/ItemUtil.java
Expand Up @@ -237,7 +237,10 @@ public static boolean isValidItemMeta(ItemMeta meta) {
}

public static boolean areItemMetaIdentical(ItemMeta meta, ItemMeta meta2) {
return areItemMetaIdentical(meta, meta2, true);
}

public static boolean areItemMetaIdentical(ItemMeta meta, ItemMeta meta2, boolean checkEnchants) {
//Display Names
String displayName1;
if(meta.hasDisplayName())
Expand Down Expand Up @@ -280,57 +283,59 @@ public static boolean areItemMetaIdentical(ItemMeta meta, ItemMeta meta2) {

CraftBookPlugin.logDebugMessage("Lore is the same", "item-checks.meta.lores");

//Enchants
List<Enchantment> ench1 = new ArrayList<>();
if(meta.hasEnchants())
ench1.addAll(meta.getEnchants().keySet());

List<Enchantment> ench2 = new ArrayList<>();
if(meta2.hasEnchants())
ench2.addAll(meta2.getEnchants().keySet());
if(checkEnchants) {
//Enchants
List<Enchantment> ench1 = new ArrayList<>();
if(meta.hasEnchants())
ench1.addAll(meta.getEnchants().keySet());

if(ench1.size() != ench2.size())
return false;
CraftBookPlugin.logDebugMessage("Has same enchantment lengths", "item-checks.meta.enchants");
List<Enchantment> ench2 = new ArrayList<>();
if(meta2.hasEnchants())
ench2.addAll(meta2.getEnchants().keySet());

for(Enchantment ench : ench1) {
if(!ench2.contains(ench))
if(ench1.size() != ench2.size())
return false;
if(meta.getEnchantLevel(ench) != meta2.getEnchantLevel(ench))
return false;
}
CraftBookPlugin.logDebugMessage("Has same enchantment lengths", "item-checks.meta.enchants");

CraftBookPlugin.logDebugMessage("Enchants are the same", "item-checks.meta.enchants");
for(Enchantment ench : ench1) {
if(!ench2.contains(ench))
return false;
if(meta.getEnchantLevel(ench) != meta2.getEnchantLevel(ench))
return false;
}

//StoredEnchants
if (meta instanceof EnchantmentStorageMeta) {
if (!(meta2 instanceof EnchantmentStorageMeta))
return false; // meta type mismatch
CraftBookPlugin.logDebugMessage("Enchants are the same", "item-checks.meta.enchants");

EnchantmentStorageMeta storageMeta = (EnchantmentStorageMeta) meta;
List<Enchantment> storedEnchantments = new ArrayList<>();
if (storageMeta.hasStoredEnchants())
storedEnchantments.addAll(storageMeta.getStoredEnchants().keySet());

EnchantmentStorageMeta storageMeta2 = (EnchantmentStorageMeta) meta2;
List<Enchantment> storedEnchantments2 = new ArrayList<>();
if (storageMeta2.hasStoredEnchants())
storedEnchantments2.addAll(storageMeta2.getStoredEnchants().keySet());

if (storedEnchantments.size() != storedEnchantments2.size())
return false; // mismatch enchantment counts
CraftBookPlugin.logDebugMessage("Has same stored enchantment lengths", "item-checks.meta.enchants");

for (Enchantment ench : storedEnchantments) {
if (!storedEnchantments2.contains(ench))
return false; // mismatch stored enchantments
if (storageMeta.getStoredEnchantLevel(ench) != storageMeta2.getStoredEnchantLevel(ench))
return false; // mismatch stored enchantment levels
}
//StoredEnchants
if (meta instanceof EnchantmentStorageMeta) {
if (!(meta2 instanceof EnchantmentStorageMeta))
return false; // meta type mismatch

EnchantmentStorageMeta storageMeta = (EnchantmentStorageMeta) meta;
List<Enchantment> storedEnchantments = new ArrayList<>();
if (storageMeta.hasStoredEnchants())
storedEnchantments.addAll(storageMeta.getStoredEnchants().keySet());

CraftBookPlugin.logDebugMessage("Stored enchants are the same", "item-checks.meta.enchants");
} else if (meta2 instanceof EnchantmentStorageMeta)
return false; // meta type mismatch
EnchantmentStorageMeta storageMeta2 = (EnchantmentStorageMeta) meta2;
List<Enchantment> storedEnchantments2 = new ArrayList<>();
if (storageMeta2.hasStoredEnchants())
storedEnchantments2.addAll(storageMeta2.getStoredEnchants().keySet());

if (storedEnchantments.size() != storedEnchantments2.size())
return false; // mismatch enchantment counts
CraftBookPlugin.logDebugMessage("Has same stored enchantment lengths", "item-checks.meta.enchants");

for (Enchantment ench : storedEnchantments) {
if (!storedEnchantments2.contains(ench))
return false; // mismatch stored enchantments
if (storageMeta.getStoredEnchantLevel(ench) != storageMeta2.getStoredEnchantLevel(ench))
return false; // mismatch stored enchantment levels
}

CraftBookPlugin.logDebugMessage("Stored enchants are the same", "item-checks.meta.enchants");
} else if (meta2 instanceof EnchantmentStorageMeta)
return false; // meta type mismatch
}

if (meta instanceof BookMeta) {
if (!(meta2 instanceof BookMeta))
Expand Down Expand Up @@ -416,6 +421,14 @@ public static boolean isStackValid(ItemStack item) {
return true;
}

public static boolean hasDisplayNameOrLore(ItemStack item) {
if(item.hasItemMeta()) {
ItemMeta meta = item.getItemMeta();
return meta.hasDisplayName() || meta.hasLore();
}
return false;
}

/**
* Removes a specified amount from an item entity.
*
Expand Down

0 comments on commit caad5d5

Please sign in to comment.