diff --git a/src/main/java/de/ellpeck/prettypipes/Registry.java b/src/main/java/de/ellpeck/prettypipes/Registry.java index efdd864..555cbd3 100644 --- a/src/main/java/de/ellpeck/prettypipes/Registry.java +++ b/src/main/java/de/ellpeck/prettypipes/Registry.java @@ -3,6 +3,7 @@ package de.ellpeck.prettypipes; import de.ellpeck.prettypipes.entities.PipeFrameEntity; import de.ellpeck.prettypipes.entities.PipeFrameRenderer; import de.ellpeck.prettypipes.items.*; +import de.ellpeck.prettypipes.pipe.modules.FilterModifierModule; import de.ellpeck.prettypipes.pipe.modules.LowPriorityModuleItem; import de.ellpeck.prettypipes.pipe.modules.SpeedModuleItem; import de.ellpeck.prettypipes.pipe.modules.extraction.ExtractionModuleContainer; @@ -52,6 +53,7 @@ import net.minecraftforge.registries.IForgeRegistry; import javax.annotation.Nullable; import java.util.ArrayList; +import java.util.Arrays; import java.util.List; import java.util.Locale; import java.util.function.BiFunction; @@ -104,6 +106,7 @@ public final class Registry { registry.registerAll(createTieredModule("low_priority_module", LowPriorityModuleItem::new)); registry.registerAll(createTieredModule("retrieval_module", RetrievalModuleItem::new)); registry.register(new StackSizeModuleItem("stack_size_module")); + registry.registerAll(Arrays.stream(FilterModifierModule.Type.values()).map(t -> new FilterModifierModule(t.name().toLowerCase(Locale.ROOT) + "_filter_modifier", t)).toArray(Item[]::new)); ForgeRegistries.BLOCKS.getValues().stream() .filter(b -> b.getRegistryName().getNamespace().equals(PrettyPipes.ID)) diff --git a/src/main/java/de/ellpeck/prettypipes/misc/ItemFilter.java b/src/main/java/de/ellpeck/prettypipes/misc/ItemFilter.java index 6ceb300..3ed9181 100644 --- a/src/main/java/de/ellpeck/prettypipes/misc/ItemFilter.java +++ b/src/main/java/de/ellpeck/prettypipes/misc/ItemFilter.java @@ -1,9 +1,10 @@ package de.ellpeck.prettypipes.misc; import de.ellpeck.prettypipes.PrettyPipes; +import de.ellpeck.prettypipes.items.IModule; import de.ellpeck.prettypipes.packets.PacketButton; -import de.ellpeck.prettypipes.packets.PacketHandler; import de.ellpeck.prettypipes.pipe.PipeTileEntity; +import de.ellpeck.prettypipes.pipe.modules.FilterModifierModule; import net.minecraft.client.gui.screen.Screen; import net.minecraft.client.gui.widget.Widget; import net.minecraft.client.gui.widget.button.Button; @@ -18,10 +19,13 @@ import net.minecraftforge.api.distmarker.OnlyIn; import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.ItemHandlerHelper; import net.minecraftforge.items.ItemStackHandler; +import org.apache.commons.lang3.tuple.Pair; import java.util.ArrayList; import java.util.List; import java.util.function.Supplier; +import java.util.stream.Collectors; +import java.util.stream.Stream; public class ItemFilter extends ItemStackHandler { @@ -95,10 +99,23 @@ public class ItemFilter extends ItemStackHandler { } private boolean isFiltered(ItemStack stack) { + List modifiers = this.pipe.streamModules() + .map(Pair::getRight) + .filter(m -> m instanceof FilterModifierModule) + .map(m -> ((FilterModifierModule) m).type) + .collect(Collectors.toList()); for (int i = 0; i < this.getSlots(); i++) { - ItemStack other = this.getStackInSlot(i); - if (ItemStack.areItemsEqual(stack, other)) - return true; + ItemStack filter = this.getStackInSlot(i); + if(filter.isEmpty()) + continue; + boolean equal = ItemStack.areItemsEqual(stack, filter); + if (modifiers.isEmpty()) { + if (equal) + return true; + } else { + if (modifiers.stream().allMatch(m -> (m.ignoreItemEquality || equal) && m.filter.apply(stack, filter))) + return true; + } } return false; } diff --git a/src/main/java/de/ellpeck/prettypipes/pipe/PipeTileEntity.java b/src/main/java/de/ellpeck/prettypipes/pipe/PipeTileEntity.java index 125b3aa..a451e7b 100644 --- a/src/main/java/de/ellpeck/prettypipes/pipe/PipeTileEntity.java +++ b/src/main/java/de/ellpeck/prettypipes/pipe/PipeTileEntity.java @@ -201,7 +201,7 @@ public class PipeTileEntity extends TileEntity implements INamedContainerProvide return this.streamModules().allMatch(m -> m.getRight().canNetworkSee(m.getLeft(), this)); } - private Stream> streamModules() { + public Stream> streamModules() { Stream.Builder> builder = Stream.builder(); for (int i = 0; i < this.modules.getSlots(); i++) { ItemStack stack = this.modules.getStackInSlot(i); diff --git a/src/main/java/de/ellpeck/prettypipes/pipe/modules/FilterModifierModule.java b/src/main/java/de/ellpeck/prettypipes/pipe/modules/FilterModifierModule.java new file mode 100644 index 0000000..8c5ba73 --- /dev/null +++ b/src/main/java/de/ellpeck/prettypipes/pipe/modules/FilterModifierModule.java @@ -0,0 +1,61 @@ +package de.ellpeck.prettypipes.pipe.modules; + +import de.ellpeck.prettypipes.items.IModule; +import de.ellpeck.prettypipes.items.ModuleItem; +import de.ellpeck.prettypipes.pipe.PipeTileEntity; +import net.minecraft.client.util.ITooltipFlag; +import net.minecraft.item.ItemStack; +import net.minecraft.util.ResourceLocation; +import net.minecraft.util.text.ITextComponent; +import net.minecraft.world.World; + +import javax.annotation.Nullable; +import java.util.List; +import java.util.Set; +import java.util.function.BiFunction; + +public class FilterModifierModule extends ModuleItem { + + public final Type type; + + public FilterModifierModule(String name, Type type) { + super(name); + this.type = type; + this.setRegistryName(name); + } + + @Override + public boolean isCompatible(ItemStack module, PipeTileEntity tile, IModule other) { + return other != this; + } + + @Override + public boolean hasContainer(ItemStack module, PipeTileEntity tile) { + return false; + } + + @Override + public void addInformation(ItemStack stack, @Nullable World worldIn, List tooltip, ITooltipFlag flagIn) { + super.addInformation(stack, worldIn, tooltip, flagIn); + } + + public enum Type { + DAMAGE(false, (stack, filter) -> stack.getDamage() == filter.getDamage()), + NBT(false, ItemStack::areItemStackTagsEqual), + TAG(true, (stack, filter) -> { + Set stackTags = stack.getItem().getTags(); + Set filterTags = filter.getItem().getTags(); + if (filterTags.isEmpty()) + return false; + return stackTags.containsAll(filterTags); + }); + + public final boolean ignoreItemEquality; + public final BiFunction filter; + + Type(boolean ignoreItemEquality, BiFunction filter) { + this.ignoreItemEquality = ignoreItemEquality; + this.filter = filter; + } + } +} diff --git a/src/main/resources/assets/prettypipes/lang/en_us.json b/src/main/resources/assets/prettypipes/lang/en_us.json index 4c6945a..15a5885 100644 --- a/src/main/resources/assets/prettypipes/lang/en_us.json +++ b/src/main/resources/assets/prettypipes/lang/en_us.json @@ -19,12 +19,18 @@ "item.prettypipes.medium_retrieval_module": "Medium Retrieval Module", "item.prettypipes.high_retrieval_module": "High Retrieval Module", "item.prettypipes.stack_size_module": "Stack Limiter Module", + "item.prettypipes.damage_filter_modifier": "Damage Filter Modifier", + "item.prettypipes.nbt_filter_modifier": "Data Filter Modifier", + "item.prettypipes.tag_filter_modifier": "Tag Filter Modifier", "info.prettypipes.extraction_module": "Pulls items from adjacent inventories\nFilters and pull rates vary by tier\nHigh tiers prevent over-sending", "info.prettypipes.filter_module": "Restricts flow from pipes into adjacent inventories\nFilter amount varies by tier", "info.prettypipes.speed_module": "Increases speed of items exiting adjacent inventories\nSpeed varies by tier", "info.prettypipes.low_priority_module": "Decreases the reception priority of adjacent inventories\nLower priority means items will prefer other inventories", "info.prettypipes.retrieval_module": "Pulls items from other inventories in the network\nFilters and pull rates vary by tier\nHigh tiers prevent over-sending", "info.prettypipes.stack_size_module": "Limits the amount of items that can enter adjacent inventories\nAutomatically prevents over-sending", + "info.prettypipes.damage_filter_modifier": "Causes any filter slots to filter by item damage", + "info.prettypipes.nbt_filter_modifier": "Causes any filter slots to filter by item data (NBT)", + "info.prettypipes.tag_filter_modifier": "Causes any filter slots to filter by tags\n(Modern equivalent of the Ore Dictionary)", "block.prettypipes.pipe": "Pipe", "itemGroup.prettypipes": "Pretty Pipes", "container.prettypipes.pipe": "Pipe", diff --git a/src/main/resources/assets/prettypipes/models/item/damage_filter_modifier.json b/src/main/resources/assets/prettypipes/models/item/damage_filter_modifier.json new file mode 100644 index 0000000..0c1a90c --- /dev/null +++ b/src/main/resources/assets/prettypipes/models/item/damage_filter_modifier.json @@ -0,0 +1,6 @@ +{ + "parent": "item/generated", + "textures": { + "layer0": "prettypipes:item/damage_filter_modifier" + } +} diff --git a/src/main/resources/assets/prettypipes/models/item/nbt_filter_modifier.json b/src/main/resources/assets/prettypipes/models/item/nbt_filter_modifier.json new file mode 100644 index 0000000..099a1e1 --- /dev/null +++ b/src/main/resources/assets/prettypipes/models/item/nbt_filter_modifier.json @@ -0,0 +1,6 @@ +{ + "parent": "item/generated", + "textures": { + "layer0": "prettypipes:item/nbt_filter_modifier" + } +} diff --git a/src/main/resources/assets/prettypipes/models/item/tag_filter_modifier.json b/src/main/resources/assets/prettypipes/models/item/tag_filter_modifier.json new file mode 100644 index 0000000..252a74a --- /dev/null +++ b/src/main/resources/assets/prettypipes/models/item/tag_filter_modifier.json @@ -0,0 +1,6 @@ +{ + "parent": "item/generated", + "textures": { + "layer0": "prettypipes:item/tag_filter_modifier" + } +} diff --git a/src/main/resources/assets/prettypipes/textures/item/damage_filter_modifier.png b/src/main/resources/assets/prettypipes/textures/item/damage_filter_modifier.png new file mode 100644 index 0000000..20b27ed Binary files /dev/null and b/src/main/resources/assets/prettypipes/textures/item/damage_filter_modifier.png differ diff --git a/src/main/resources/assets/prettypipes/textures/item/nbt_filter_modifier.png b/src/main/resources/assets/prettypipes/textures/item/nbt_filter_modifier.png new file mode 100644 index 0000000..4efd26e Binary files /dev/null and b/src/main/resources/assets/prettypipes/textures/item/nbt_filter_modifier.png differ diff --git a/src/main/resources/assets/prettypipes/textures/item/tag_filter_modifier.png b/src/main/resources/assets/prettypipes/textures/item/tag_filter_modifier.png new file mode 100644 index 0000000..e05eedd Binary files /dev/null and b/src/main/resources/assets/prettypipes/textures/item/tag_filter_modifier.png differ diff --git a/src/main/resources/data/prettypipes/recipes/damage_filter_modifier.json b/src/main/resources/data/prettypipes/recipes/damage_filter_modifier.json new file mode 100644 index 0000000..21a375c --- /dev/null +++ b/src/main/resources/data/prettypipes/recipes/damage_filter_modifier.json @@ -0,0 +1,22 @@ +{ + "type": "minecraft:crafting_shaped", + "pattern": [ + " H ", + "RMR", + " R " + ], + "key": { + "R": { + "item": "minecraft:redstone" + }, + "H": { + "item": "minecraft:iron_pickaxe" + }, + "M": { + "item": "prettypipes:blank_module" + } + }, + "result": { + "item": "prettypipes:damage_filter_modifier" + } +} \ No newline at end of file diff --git a/src/main/resources/data/prettypipes/recipes/nbt_filter_modifier.json b/src/main/resources/data/prettypipes/recipes/nbt_filter_modifier.json new file mode 100644 index 0000000..7e69408 --- /dev/null +++ b/src/main/resources/data/prettypipes/recipes/nbt_filter_modifier.json @@ -0,0 +1,22 @@ +{ + "type": "minecraft:crafting_shaped", + "pattern": [ + " H ", + "RMR", + " R " + ], + "key": { + "R": { + "item": "minecraft:redstone" + }, + "H": { + "item": "minecraft:book" + }, + "M": { + "item": "prettypipes:blank_module" + } + }, + "result": { + "item": "prettypipes:nbt_filter_modifier" + } +} \ No newline at end of file diff --git a/src/main/resources/data/prettypipes/recipes/tag_filter_modifier.json b/src/main/resources/data/prettypipes/recipes/tag_filter_modifier.json new file mode 100644 index 0000000..5b6694b --- /dev/null +++ b/src/main/resources/data/prettypipes/recipes/tag_filter_modifier.json @@ -0,0 +1,22 @@ +{ + "type": "minecraft:crafting_shaped", + "pattern": [ + " H ", + "RMR", + " R " + ], + "key": { + "R": { + "item": "minecraft:redstone" + }, + "H": { + "item": "minecraft:iron_ore" + }, + "M": { + "item": "prettypipes:blank_module" + } + }, + "result": { + "item": "prettypipes:tag_filter_modifier" + } +} \ No newline at end of file