Skip to content

Commit

Permalink
Only allow the configured fluid/item in configured interface slots (#…
Browse files Browse the repository at this point in the history
…7752)

Fixes #7695
  • Loading branch information
shartte authored Mar 12, 2024
1 parent 8435f3d commit 3228dca
Show file tree
Hide file tree
Showing 28 changed files with 423 additions and 215 deletions.
23 changes: 22 additions & 1 deletion src/main/java/appeng/api/behaviors/GenericInternalInventory.java
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,28 @@ public interface GenericInternalInventory {
/**
* Return true if the key would generally be allowed, ignoring the current state of the inventory.
*/
boolean isAllowed(AEKey what);
boolean isSupportedType(AEKeyType type);

/**
* Return true if the key would generally be allowed, ignoring the current state of the inventory.
*/
default boolean isSupportedType(AEKey what) {
return isSupportedType(what.getType());
}

/**
* Return true if the key would generally be allowed, ignoring the current state of the inventory.
*/
@Deprecated(since = "1.20.4")
default boolean isAllowed(AEKey what) {
return isSupportedType(what);
}

/**
* Return true if the key is {@link #isSupportedType(AEKey) of a supported type} and would pass a potential filter
* configured for the given slot.
*/
boolean isAllowedIn(int slot, AEKey what);

/**
* Try to insert something into a given slot.
Expand Down
6 changes: 3 additions & 3 deletions src/main/java/appeng/api/stacks/AEKeyTypes.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
package appeng.api.stacks;

import java.util.Objects;
import java.util.Set;

import net.minecraft.resources.ResourceLocation;

Expand Down Expand Up @@ -78,8 +79,7 @@ public static AEKeyType get(ResourceLocation id) {
* <p>
* This is mainly used as helper to let storage grids construct their internal storage for each type.
*/

public static Iterable<AEKeyType> getAll() {
return AEKeyTypesInternal.getRegistry();
public static Set<AEKeyType> getAll() {
return AEKeyTypesInternal.getAllTypes();
}
}
19 changes: 19 additions & 0 deletions src/main/java/appeng/api/stacks/AEKeyTypesInternal.java
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
package appeng.api.stacks;

import java.util.HashSet;
import java.util.Set;

import com.google.common.base.Preconditions;

import org.jetbrains.annotations.ApiStatus;
import org.jetbrains.annotations.Nullable;

import net.minecraft.core.Registry;
import net.neoforged.neoforge.registries.callback.BakeCallback;

/**
* Manages the registry used to synchronize key spaces to the client.
Expand All @@ -15,6 +19,9 @@ public final class AEKeyTypesInternal {
@Nullable
private static Registry<AEKeyType> registry;

@Nullable
private static Set<AEKeyType> allTypes;

private AEKeyTypesInternal() {
}

Expand All @@ -26,6 +33,18 @@ public static Registry<AEKeyType> getRegistry() {
public static void setRegistry(Registry<AEKeyType> registry) {
Preconditions.checkState(AEKeyTypesInternal.registry == null);
AEKeyTypesInternal.registry = registry;
registry.addCallback((BakeCallback<AEKeyType>) (ignored -> {
var types = new HashSet<AEKeyType>();
for (var aeKeyType : registry) {
types.add(aeKeyType);
}
allTypes = Set.copyOf(types);
}));
}

public static Set<AEKeyType> getAllTypes() {
Preconditions.checkState(allTypes != null, "AE2 isn't initialized yet.");
return allTypes;
}

public static void register(AEKeyType keyType) {
Expand Down
8 changes: 8 additions & 0 deletions src/main/java/appeng/api/storage/AEKeySlotFilter.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package appeng.api.storage;

import appeng.api.stacks.AEKey;

@FunctionalInterface
public interface AEKeySlotFilter {
boolean isAllowed(int slot, AEKey what);
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,6 @@
import java.util.Map;
import java.util.function.Consumer;

import com.google.common.collect.Iterables;

import net.minecraft.client.Minecraft;
import net.minecraft.client.gui.components.AbstractWidget;
import net.minecraft.client.renderer.Rect2i;
Expand Down Expand Up @@ -117,7 +115,7 @@ public void populateScreen(Consumer<AbstractWidget> addWidget, Rect2i bounds, AE
yPos += KEY_TYPE_SPACING;
}

int height = this.bounds.getY() + Iterables.size(AEKeyTypes.getAll()) * KEY_TYPE_SPACING + PADDING;
int height = this.bounds.getY() + AEKeyTypes.getAll().size() * KEY_TYPE_SPACING + PADDING;
KeyTypeSelectionScreen.this.setHeight(height);
}
}
Expand Down
14 changes: 12 additions & 2 deletions src/main/java/appeng/helpers/InterfaceLogic.java
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@
import appeng.api.networking.ticking.TickRateModulation;
import appeng.api.networking.ticking.TickingRequest;
import appeng.api.stacks.AEKey;
import appeng.api.stacks.AEKeyTypes;
import appeng.api.stacks.GenericStack;
import appeng.api.storage.MEStorage;
import appeng.api.storage.StorageHelper;
Expand Down Expand Up @@ -102,8 +103,9 @@ public InterfaceLogic(IManagedGridNode gridNode, InterfaceLogicHost host, Item i

public InterfaceLogic(IManagedGridNode gridNode, InterfaceLogicHost host, Item is, int slots) {
this.host = host;
this.config = ConfigInventory.configStacks(null, slots, this::onConfigRowChanged, false);
this.storage = ConfigInventory.storage(slots, this::onStorageChanged);
this.config = ConfigInventory.configStacks(AEKeyTypes.getAll(), slots, this::onConfigRowChanged, false);
this.storage = ConfigInventory.storage(AEKeyTypes.getAll(), this::isAllowedInStorageSlot, slots,
this::onStorageChanged);
this.mainNode = gridNode
.setFlags(GridFlags.REQUIRE_CHANNEL)
.addService(IGridTickable.class, new Ticker());
Expand All @@ -121,6 +123,14 @@ public InterfaceLogic(IManagedGridNode gridNode, InterfaceLogicHost host, Item i
getStorage().useRegisteredCapacities();
}

private boolean isAllowedInStorageSlot(int slot, AEKey what) {
if (slot < config.size()) {
var configured = config.getKey(slot);
return configured == null || configured.equals(what);
}
return true;
}

public int getPriority() {
return priority;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,8 +44,11 @@ public int getTankCapacity(int tank) {

@Override
public boolean isFluidValid(int tank, @NotNull FluidStack stack) {
if (stack.isEmpty()) {
return true;
}
var what = AEFluidKey.of(stack);
return what == null || inv.isAllowed(what);
return what != null && inv.isAllowedIn(tank, what);
}

@Override
Expand Down
32 changes: 20 additions & 12 deletions src/main/java/appeng/helpers/externalstorage/GenericStackInv.java
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
package appeng.helpers.externalstorage;

import java.util.Objects;
import java.util.Set;

import com.google.common.base.Preconditions;

Expand All @@ -39,9 +40,10 @@
import appeng.api.stacks.AEItemKey;
import appeng.api.stacks.AEKey;
import appeng.api.stacks.AEKeyType;
import appeng.api.stacks.AEKeyTypes;
import appeng.api.stacks.GenericStack;
import appeng.api.stacks.KeyCounter;
import appeng.api.storage.AEKeyFilter;
import appeng.api.storage.AEKeySlotFilter;
import appeng.api.storage.MEStorage;
import appeng.core.AELog;
import appeng.util.ConfigMenuInventory;
Expand All @@ -52,8 +54,9 @@ public class GenericStackInv implements MEStorage, GenericInternalInventory {
private boolean suppressOnChange;
private boolean onChangeSuppressed;
private final Reference2LongMap<AEKeyType> capacities = new Reference2LongArrayMap<>();
private final Set<AEKeyType> supportedKeyTypes;
@Nullable
private AEKeyFilter filter;
private AEKeySlotFilter filter;
protected final Mode mode;
private Component description = Component.empty();

Expand All @@ -68,27 +71,28 @@ public GenericStackInv(@Nullable Runnable listener, int size) {
}

public GenericStackInv(@Nullable Runnable listener, Mode mode, int size) {
this(AEKeyTypes.getAll(), listener, mode, size);
}

public GenericStackInv(Set<AEKeyType> supportedKeyTypes, @Nullable Runnable listener, Mode mode, int size) {
this.supportedKeyTypes = Set.copyOf(Objects.requireNonNull(supportedKeyTypes, "supportedKeyTypes"));
this.stacks = new GenericStack[size];
this.listener = listener;
this.mode = mode;
}

protected void setFilter(@Nullable AEKeyFilter filter) {
protected void setFilter(@Nullable AEKeySlotFilter filter) {
this.filter = filter;
}

@Nullable
public AEKeyFilter getFilter() {
public AEKeySlotFilter getFilter() {
return filter;
}

@Override
public boolean isAllowed(AEKey what) {
return filter == null || filter.matches(what);
}

public boolean isAllowed(@Nullable GenericStack stack) {
return stack == null || isAllowed(stack.what());
public boolean isSupportedType(AEKeyType type) {
return supportedKeyTypes.contains(type);
}

@Override
Expand Down Expand Up @@ -139,7 +143,7 @@ public long insert(int slot, AEKey what, long amount, Actionable mode) {
Objects.requireNonNull(what, "what");
Preconditions.checkArgument(amount >= 0, "amount >= 0");

if (!canInsert() || !isAllowed(what)) {
if (!canInsert() || !isAllowedIn(slot, what)) {
return 0;
}

Expand All @@ -159,6 +163,10 @@ public long insert(int slot, AEKey what, long amount, Actionable mode) {
return 0;
}

public boolean isAllowedIn(int slot, AEKey what) {
return isSupportedType(what) && (filter == null || filter.isAllowed(slot, what));
}

@Override
public long extract(int slot, AEKey what, long amount, Actionable mode) {
Objects.requireNonNull(what, "what");
Expand Down Expand Up @@ -371,7 +379,7 @@ public ConfigMenuInventory createMenuWrapper() {
public long insert(AEKey what, long amount, Actionable mode, IActionSource source) {
Objects.requireNonNull(what, "what");
Preconditions.checkArgument(amount >= 0, "amount >= 0");
if (!isAllowed(what)) {
if (!isSupportedType(what)) {
return 0;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,10 @@ public int getSlotLimit(int slot) {

@Override
public boolean isItemValid(int slot, @NotNull ItemStack stack) {
if (stack.isEmpty()) {
return true;
}
var what = AEItemKey.of(stack);
return what == null || inv.isAllowed(what);
return what != null && inv.isAllowedIn(slot, what);
}
}
17 changes: 9 additions & 8 deletions src/main/java/appeng/items/contents/CellConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -18,38 +18,39 @@

package appeng.items.contents;

import com.google.common.base.Preconditions;
import java.util.Set;

import org.jetbrains.annotations.Nullable;
import com.google.common.base.Preconditions;

import net.minecraft.world.item.ItemStack;

import appeng.api.storage.AEKeyFilter;
import appeng.api.stacks.AEKeyType;
import appeng.api.stacks.AEKeyTypes;
import appeng.util.ConfigInventory;

public final class CellConfig {
private CellConfig() {
}

public static ConfigInventory create(@Nullable AEKeyFilter filter, ItemStack is, int size) {
public static ConfigInventory create(Set<AEKeyType> supportedTypes, ItemStack is, int size) {
Preconditions.checkArgument(size >= 1 && size <= 63,
"Config inventory must have between 1 and 63 slots inclusive.");
var holder = new Holder(is);
holder.inv = ConfigInventory.configTypes(filter, size, holder::save);
holder.inv = ConfigInventory.configTypes(supportedTypes, size, holder::save);
holder.load();
return holder.inv;
}

public static ConfigInventory create(@Nullable AEKeyFilter filter, ItemStack is) {
public static ConfigInventory create(Set<AEKeyType> supportedTypes, ItemStack is) {
var holder = new Holder(is);
holder.inv = ConfigInventory.configTypes(filter, 63, holder::save);
holder.inv = ConfigInventory.configTypes(supportedTypes, 63, holder::save);
holder.load();
return holder.inv;
}

public static ConfigInventory create(ItemStack is) {
var holder = new Holder(is);
holder.inv = ConfigInventory.configTypes(null, 63, holder::save);
holder.inv = ConfigInventory.configTypes(AEKeyTypes.getAll(), 63, holder::save);
holder.load();
return holder.inv;
}
Expand Down
3 changes: 2 additions & 1 deletion src/main/java/appeng/items/storage/BasicStorageCell.java
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@

import java.util.List;
import java.util.Optional;
import java.util.Set;

import net.minecraft.network.chat.Component;
import net.minecraft.world.InteractionHand;
Expand Down Expand Up @@ -126,7 +127,7 @@ public IUpgradeInventory getUpgrades(ItemStack is) {

@Override
public ConfigInventory getConfigInventory(ItemStack is) {
return CellConfig.create(keyType.filter(), is);
return CellConfig.create(Set.of(keyType), is);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
import java.util.function.Function;
import java.util.stream.Collectors;

Expand Down Expand Up @@ -534,7 +535,7 @@ private void onUpgradesChanged(ItemStack stack, IUpgradeInventory upgrades) {

@Override
public ConfigInventory getConfigInventory(ItemStack is) {
return CellConfig.create(AEItemKey.filter(), is);
return CellConfig.create(Set.of(AEKeyType.items()), is);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@

import java.util.List;
import java.util.Optional;
import java.util.Set;

import org.jetbrains.annotations.Nullable;

Expand Down Expand Up @@ -390,7 +391,7 @@ private void onUpgradesChanged(ItemStack stack, IUpgradeInventory upgrades) {

@Override
public ConfigInventory getConfigInventory(ItemStack is) {
return CellConfig.create(AEItemKey.filter(), is);
return CellConfig.create(Set.of(AEKeyType.items()), is);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
import java.util.List;
import java.util.Objects;
import java.util.Optional;
import java.util.Set;

import net.minecraft.network.chat.Component;
import net.minecraft.resources.ResourceLocation;
Expand Down Expand Up @@ -108,7 +109,7 @@ public IUpgradeInventory getUpgrades(ItemStack is) {

@Override
public ConfigInventory getConfigInventory(ItemStack is) {
return CellConfig.create(keyType.filter(), is);
return CellConfig.create(Set.of(keyType), is);
}

@Override
Expand Down
Loading

0 comments on commit 3228dca

Please sign in to comment.