diff --git a/build.gradle b/build.gradle index 8aba2d8..a1f79e7 100644 --- a/build.gradle +++ b/build.gradle @@ -136,7 +136,6 @@ sourceSets.main.java { exclude 'com/extendedae_plus/client/**' // 包含配置包 include 'com/extendedae_plus/config/**' - exclude 'com/extendedae_plus/content/**' exclude 'com/extendedae_plus/hooks/**' exclude 'com/extendedae_plus/init/**' exclude 'com/extendedae_plus/integration/**' @@ -150,6 +149,8 @@ sourceSets.main.java { include 'com/extendedae_plus/mixin/ae2/helpers/**' // 启用 AEProcessingPattern 的 mixin(提供可缩放标记) include 'com/extendedae_plus/mixin/ae2/AEProcessingPatternMixin.java' + // 自动样板缩放注入(CraftingTreeProcess + 其 accessor) + include 'com/extendedae_plus/mixin/ae2/autopattern/**' // GUI 方案A:解禁最小 GUI 混入 include 'com/extendedae_plus/mixin/ae2/client/gui/PatternProviderScreenMixin.java' include 'com/extendedae_plus/mixin/ae2/menu/PatternProviderMenuAdvancedMixin.java' @@ -162,14 +163,22 @@ sourceSets.main.java { // 仅解禁样板倍增核心所需的两个 util 文件 include 'com/extendedae_plus/util/PatternProviderDataUtil.java' include 'com/extendedae_plus/util/PatternProviderUIHelper.java' + // 自动样板缩放所需工具类 + include 'com/extendedae_plus/util/PatternScaler.java' + include 'com/extendedae_plus/util/RequestedAmountHolder.java' // GUI 与网络最小依赖 // 全量包含 api 包,防止个别接口遗漏 include 'com/extendedae_plus/api/**' include 'com/extendedae_plus/util/ExtendedAELogger.java' + // 客户端高亮存储(单文件启用,保持 content 其余文件不参与编译) + include 'com/extendedae_plus/content/ClientPatternHighlightStore.java' + // 自动样板缩放所需内容类 + include 'com/extendedae_plus/content/ScaledProcessingPattern.java' include 'com/extendedae_plus/network/ModNetwork.java' include 'com/extendedae_plus/network/ToggleAdvancedBlockingC2SPacket.java' include 'com/extendedae_plus/network/ToggleSmartDoublingC2SPacket.java' include 'com/extendedae_plus/network/ScalePatternsC2SPacket.java' + include 'com/extendedae_plus/network/SetPatternHighlightS2CPacket.java' // 仅 include 需要的 util 文件(不再对 util/** 做全局排除,以免误伤) include 'com/extendedae_plus/util/PatternProviderDataUtil.java' include 'com/extendedae_plus/util/PatternProviderUIHelper.java' diff --git a/src/main/java/com/extendedae_plus/content/ScaledProcessingPattern.java b/src/main/java/com/extendedae_plus/content/ScaledProcessingPattern.java index 27a7c5a..353199a 100644 --- a/src/main/java/com/extendedae_plus/content/ScaledProcessingPattern.java +++ b/src/main/java/com/extendedae_plus/content/ScaledProcessingPattern.java @@ -9,6 +9,9 @@ import appeng.crafting.pattern.AEProcessingPattern; import net.minecraft.world.level.Level; import org.jetbrains.annotations.Nullable; +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; import java.util.Objects; /** @@ -19,25 +22,25 @@ public final class ScaledProcessingPattern implements IPatternDetails { private final AEProcessingPattern original; // 原始样板引用 private final AEItemKey definition; // 样板物品 - private final GenericStack[] sparseInputs; // 缩放后的稀疏输入 - private final GenericStack[] sparseOutputs; // 缩放后的稀疏输出 + private final List sparseInputs; // 缩放后的稀疏输入(List 以适配 1.21 API) + private final List sparseOutputs; // 缩放后的稀疏输出(List 以适配 1.21 API) private final IInput[] inputs; // 缩放后的压缩输入 - private final GenericStack[] condensedOutputs; // 缩放后的压缩输出 + private final List condensedOutputs; // 缩放后的压缩输出(List 以适配 1.21 API) public ScaledProcessingPattern( AEProcessingPattern original, AEItemKey definition, - GenericStack[] sparseInputs, - GenericStack[] sparseOutputs, + List sparseInputs, + List sparseOutputs, IInput[] inputs, - GenericStack[] condensedOutputs + List condensedOutputs ) { this.original = Objects.requireNonNull(original); this.definition = Objects.requireNonNull(definition); - this.sparseInputs = Objects.requireNonNull(sparseInputs); - this.sparseOutputs = Objects.requireNonNull(sparseOutputs); + this.sparseInputs = Collections.unmodifiableList(new ArrayList<>(Objects.requireNonNull(sparseInputs))); + this.sparseOutputs = Collections.unmodifiableList(new ArrayList<>(Objects.requireNonNull(sparseOutputs))); this.inputs = Objects.requireNonNull(inputs); - this.condensedOutputs = Objects.requireNonNull(condensedOutputs); + this.condensedOutputs = Collections.unmodifiableList(new ArrayList<>(Objects.requireNonNull(condensedOutputs))); } /* -------------------- API 实现 -------------------- */ @@ -57,21 +60,21 @@ public final class ScaledProcessingPattern implements IPatternDetails { } @Override - public GenericStack[] getOutputs() { + public List getOutputs() { return condensedOutputs; } - public GenericStack[] getSparseInputs() { + public List getSparseInputs() { return sparseInputs; } - public GenericStack[] getSparseOutputs() { + public List getSparseOutputs() { return sparseOutputs; } @Override public GenericStack getPrimaryOutput() { - if (condensedOutputs.length > 0) return condensedOutputs[0]; + if (!condensedOutputs.isEmpty()) return condensedOutputs.get(0); return original.getPrimaryOutput(); } @@ -83,7 +86,7 @@ public final class ScaledProcessingPattern implements IPatternDetails { @Override public void pushInputsToExternalInventory(KeyCounter[] inputHolder, PatternInputSink inputSink) { // 保持和 AEProcessingPattern 一致,用 sparseInputs 驱动 - if (sparseInputs.length == inputs.length) { + if (sparseInputs.size() == inputs.length) { IPatternDetails.super.pushInputsToExternalInventory(inputHolder, inputSink); } else { KeyCounter allInputs = new KeyCounter(); diff --git a/src/main/java/com/extendedae_plus/network/ModNetwork.java b/src/main/java/com/extendedae_plus/network/ModNetwork.java index ecd2d21..0b95f6f 100644 --- a/src/main/java/com/extendedae_plus/network/ModNetwork.java +++ b/src/main/java/com/extendedae_plus/network/ModNetwork.java @@ -10,5 +10,6 @@ public class ModNetwork { registrar.playToServer(ToggleAdvancedBlockingC2SPacket.TYPE, ToggleAdvancedBlockingC2SPacket.STREAM_CODEC, ToggleAdvancedBlockingC2SPacket::handle); registrar.playToServer(ToggleSmartDoublingC2SPacket.TYPE, ToggleSmartDoublingC2SPacket.STREAM_CODEC, ToggleSmartDoublingC2SPacket::handle); registrar.playToServer(ScalePatternsC2SPacket.TYPE, ScalePatternsC2SPacket.STREAM_CODEC, ScalePatternsC2SPacket::handle); + registrar.playToClient(SetPatternHighlightS2CPacket.TYPE, SetPatternHighlightS2CPacket.STREAM_CODEC, SetPatternHighlightS2CPacket::handle); } } diff --git a/src/main/java/com/extendedae_plus/network/SetPatternHighlightS2CPacket.java b/src/main/java/com/extendedae_plus/network/SetPatternHighlightS2CPacket.java index 6da5fda..affd830 100644 --- a/src/main/java/com/extendedae_plus/network/SetPatternHighlightS2CPacket.java +++ b/src/main/java/com/extendedae_plus/network/SetPatternHighlightS2CPacket.java @@ -2,15 +2,21 @@ package com.extendedae_plus.network; import appeng.api.stacks.AEKey; import com.extendedae_plus.content.ClientPatternHighlightStore; -import net.minecraft.network.FriendlyByteBuf; -import net.minecraftforge.network.NetworkEvent; - -import java.util.function.Supplier; +import com.extendedae_plus.ExtendedAEPlus; +import net.minecraft.network.RegistryFriendlyByteBuf; +import net.minecraft.network.codec.StreamCodec; +import net.minecraft.network.protocol.common.custom.CustomPacketPayload; +import net.minecraft.resources.ResourceLocation; +import net.neoforged.neoforge.network.handling.IPayloadContext; /** - * S2C: 指示客户端对某个 AEKey 的样板进行高亮/取消高亮(仅作用于接收该包的客户端) + * S2C: 指示客户端对某个 AEKey 的样板进行高亮/取消高亮(仅作用于接收该包的客户端)。 + * 使用 NeoForge 1.21 Payload API。 */ -public class SetPatternHighlightS2CPacket { +public class SetPatternHighlightS2CPacket implements CustomPacketPayload { + public static final Type TYPE = new Type<>( + ResourceLocation.fromNamespaceAndPath(ExtendedAEPlus.MODID, "set_pattern_highlight")); + private final AEKey key; private final boolean highlight; @@ -19,26 +25,29 @@ public class SetPatternHighlightS2CPacket { this.highlight = highlight; } - public static void encode(SetPatternHighlightS2CPacket msg, FriendlyByteBuf buf) { - AEKey.writeKey(buf, msg.key); - buf.writeBoolean(msg.highlight); + public AEKey key() { return key; } + public boolean highlight() { return highlight; } + + public static final StreamCodec STREAM_CODEC = StreamCodec.of( + (buf, pkt) -> { + AEKey.writeKey(buf, pkt.key); + buf.writeBoolean(pkt.highlight); + }, + buf -> new SetPatternHighlightS2CPacket(AEKey.readKey(buf), buf.readBoolean()) + ); + + @Override + public Type type() { + return TYPE; } - public static SetPatternHighlightS2CPacket decode(FriendlyByteBuf buf) { - AEKey key = AEKey.readKey(buf); - boolean h = buf.readBoolean(); - return new SetPatternHighlightS2CPacket(key, h); - } - - public static void handle(SetPatternHighlightS2CPacket msg, Supplier ctxSupplier) { - var ctx = ctxSupplier.get(); + public static void handle(final SetPatternHighlightS2CPacket msg, final IPayloadContext ctx) { ctx.enqueueWork(() -> { try { ClientPatternHighlightStore.setHighlight(msg.key, msg.highlight); } catch (Throwable ignored) { } }); - ctx.setPacketHandled(true); } } diff --git a/src/main/java/com/extendedae_plus/util/PatternScaler.java b/src/main/java/com/extendedae_plus/util/PatternScaler.java index 65aa98f..537d52c 100644 --- a/src/main/java/com/extendedae_plus/util/PatternScaler.java +++ b/src/main/java/com/extendedae_plus/util/PatternScaler.java @@ -8,6 +8,8 @@ import com.extendedae_plus.content.ScaledProcessingPattern; import com.extendedae_plus.api.SmartDoublingAwarePattern; import com.extendedae_plus.config.ModConfigs; +import java.util.ArrayList; +import java.util.List; import static com.extendedae_plus.util.ExtendedAELogger.LOGGER; @@ -24,34 +26,34 @@ public final class PatternScaler { return null; } - GenericStack[] baseSparseInputs = base.getSparseInputs(); - GenericStack[] baseSparseOutputs = base.getSparseOutputs(); + List baseSparseInputs = base.getSparseInputs(); + List baseSparseOutputs = base.getSparseOutputs(); IInput[] baseInputs = base.getInputs(); - GenericStack[] baseOutputs = base.getOutputs(); + List baseOutputs = base.getOutputs(); // 新逻辑:不再对样板进行单位化处理 // 找到目标输出在 outputs 中的索引(尝试匹配 target,否则取第一个非空输出) int targetOutIndex = -1; - for (int i = 0; i < baseOutputs.length; i++) { - var out = baseOutputs[i]; + for (int i = 0; i < baseOutputs.size(); i++) { + var out = baseOutputs.get(i); if (out != null && target != null && out.what() != null && out.what().equals(target)) { targetOutIndex = i; break; } } if (targetOutIndex == -1) { - for (int i = 0; i < baseOutputs.length; i++) { - if (baseOutputs[i] != null) { + for (int i = 0; i < baseOutputs.size(); i++) { + if (baseOutputs.get(i) != null) { targetOutIndex = i; break; } } } - if (targetOutIndex == -1 && baseOutputs.length > 0) targetOutIndex = 0; + if (targetOutIndex == -1 && !baseOutputs.isEmpty()) targetOutIndex = 0; long perOperationTarget = 1L; - if (targetOutIndex >= 0 && baseOutputs[targetOutIndex] != null) { - long amt = baseOutputs[targetOutIndex].amount(); + if (targetOutIndex >= 0 && baseOutputs.get(targetOutIndex) != null) { + long amt = baseOutputs.get(targetOutIndex).amount(); if (amt > 0) perOperationTarget = amt; } @@ -83,28 +85,34 @@ public final class PatternScaler { scaledInputs[i] = new ScaledProcessingPattern.Input(scaledTemplates, in.getMultiplier() * multiplier); } - /* 4. 构建压缩输出 */ - GenericStack[] scaledCondensedOutputs = new GenericStack[baseOutputs.length]; - for (int i = 0; i < baseOutputs.length; i++) { - GenericStack out = baseOutputs[i]; + // 构建压缩输出(List) + List scaledCondensedOutputs = new ArrayList<>(baseOutputs.size()); + for (int i = 0; i < baseOutputs.size(); i++) { + GenericStack out = baseOutputs.get(i); if (out != null) { - scaledCondensedOutputs[i] = new GenericStack(out.what(), out.amount() * multiplier); + scaledCondensedOutputs.add(new GenericStack(out.what(), out.amount() * multiplier)); + } else { + scaledCondensedOutputs.add(null); } } - // 构建并打印稀疏表示(直接按 multiplier 放大) - GenericStack[] scaledSparseInputs = new GenericStack[baseSparseInputs.length]; - for (int i = 0; i < baseSparseInputs.length; i++) { - var in = baseSparseInputs[i]; + // 构建稀疏表示(List,直接按 multiplier 放大) + List scaledSparseInputs = new ArrayList<>(baseSparseInputs.size()); + for (int i = 0; i < baseSparseInputs.size(); i++) { + var in = baseSparseInputs.get(i); if (in != null) { - scaledSparseInputs[i] = new GenericStack(in.what(), in.amount() * multiplier); + scaledSparseInputs.add(new GenericStack(in.what(), in.amount() * multiplier)); + } else { + scaledSparseInputs.add(null); } } - GenericStack[] scaledSparseOutputs = new GenericStack[baseSparseOutputs.length]; - for (int i = 0; i < baseSparseOutputs.length; i++) { - var out = baseSparseOutputs[i]; + List scaledSparseOutputs = new ArrayList<>(baseSparseOutputs.size()); + for (int i = 0; i < baseSparseOutputs.size(); i++) { + var out = baseSparseOutputs.get(i); if (out != null) { - scaledSparseOutputs[i] = new GenericStack(out.what(), out.amount() * multiplier); + scaledSparseOutputs.add(new GenericStack(out.what(), out.amount() * multiplier)); + } else { + scaledSparseOutputs.add(null); } } diff --git a/src/main/resources/extendedaeplus.mixins.json b/src/main/resources/extendedaeplus.mixins.json index f50ff9f..cb17956 100644 --- a/src/main/resources/extendedaeplus.mixins.json +++ b/src/main/resources/extendedaeplus.mixins.json @@ -12,7 +12,9 @@ "ae2.helpers.PatternProviderLogicAdvancedMixin", "ae2.helpers.PatternProviderLogicDoublingMixin", "ae2.AEProcessingPatternMixin", - "extendedae.client.gui.GuiExPatternProviderMixin" + "extendedae.client.gui.GuiExPatternProviderMixin", + "ae2.autopattern.CraftingTreeNodeAccessor", + "ae2.autopattern.CraftingTreeProcessMixin" ], "injectors": { "defaultRequire": 1