feat: 添加样板总成中处理样板数量显示。添加合成监控界面跳转支持,并高亮对应样板。调整依赖便于在gtlcore中测试
This commit is contained in:
parent
b0815924cc
commit
dec1edbca3
BIN
libs/ExtendedAE-1.20-1.1.12-forge.jar
Normal file
BIN
libs/ExtendedAE-1.20-1.1.12-forge.jar
Normal file
Binary file not shown.
|
|
@ -40,6 +40,38 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||||
@Mixin(AEBaseScreen.class)
|
@Mixin(AEBaseScreen.class)
|
||||||
public abstract class AEBaseScreenMixin {
|
public abstract class AEBaseScreenMixin {
|
||||||
|
|
||||||
|
@Unique
|
||||||
|
private static int eap$getIntField(Object self, String name, int def) {
|
||||||
|
Class<?> c = self.getClass();
|
||||||
|
while (c != null && c != Object.class) {
|
||||||
|
try {
|
||||||
|
var f = c.getDeclaredField(name);
|
||||||
|
f.setAccessible(true);
|
||||||
|
Object v = f.get(self);
|
||||||
|
if (v instanceof Integer i) return i;
|
||||||
|
} catch (Throwable ignored) {
|
||||||
|
}
|
||||||
|
c = c.getSuperclass();
|
||||||
|
}
|
||||||
|
return def;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Unique
|
||||||
|
private static Font eap$getFont(Object self) {
|
||||||
|
Class<?> c = self.getClass();
|
||||||
|
while (c != null && c != Object.class) {
|
||||||
|
try {
|
||||||
|
var f = c.getDeclaredField("font");
|
||||||
|
f.setAccessible(true);
|
||||||
|
Object v = f.get(self);
|
||||||
|
if (v instanceof Font font) return font;
|
||||||
|
} catch (Throwable ignored) {
|
||||||
|
}
|
||||||
|
c = c.getSuperclass();
|
||||||
|
}
|
||||||
|
return net.minecraft.client.Minecraft.getInstance().font;
|
||||||
|
}
|
||||||
|
|
||||||
@Unique
|
@Unique
|
||||||
private ScreenStyle eap$getStyle(Object self) {
|
private ScreenStyle eap$getStyle(Object self) {
|
||||||
try {
|
try {
|
||||||
|
|
@ -47,7 +79,8 @@ public abstract class AEBaseScreenMixin {
|
||||||
f.setAccessible(true);
|
f.setAccessible(true);
|
||||||
Object v = f.get(self);
|
Object v = f.get(self);
|
||||||
if (v instanceof ScreenStyle s) return s;
|
if (v instanceof ScreenStyle s) return s;
|
||||||
} catch (Throwable ignored) {}
|
} catch (Throwable ignored) {
|
||||||
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -78,7 +111,8 @@ public abstract class AEBaseScreenMixin {
|
||||||
// Debug: 标记一次发送
|
// Debug: 标记一次发送
|
||||||
try {
|
try {
|
||||||
LogUtils.getLogger().info("EAP: Send CraftingMonitorJumpC2SPacket: {}", key);
|
LogUtils.getLogger().info("EAP: Send CraftingMonitorJumpC2SPacket: {}", key);
|
||||||
} catch (Throwable ignored2) {}
|
} catch (Throwable ignored2) {
|
||||||
|
}
|
||||||
ModNetwork.CHANNEL.sendToServer(new CraftingMonitorJumpC2SPacket(key));
|
ModNetwork.CHANNEL.sendToServer(new CraftingMonitorJumpC2SPacket(key));
|
||||||
cir.setReturnValue(true);
|
cir.setReturnValue(true);
|
||||||
} catch (Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
|
@ -112,43 +146,14 @@ public abstract class AEBaseScreenMixin {
|
||||||
// Debug: 标记一次发送(打开供应器UI)
|
// Debug: 标记一次发送(打开供应器UI)
|
||||||
try {
|
try {
|
||||||
LogUtils.getLogger().info("EAP: Send CraftingMonitorOpenProviderC2SPacket: {}", key);
|
LogUtils.getLogger().info("EAP: Send CraftingMonitorOpenProviderC2SPacket: {}", key);
|
||||||
} catch (Throwable ignored2) {}
|
} catch (Throwable ignored2) {
|
||||||
|
}
|
||||||
ModNetwork.CHANNEL.sendToServer(new CraftingMonitorOpenProviderC2SPacket(key));
|
ModNetwork.CHANNEL.sendToServer(new CraftingMonitorOpenProviderC2SPacket(key));
|
||||||
cir.setReturnValue(true);
|
cir.setReturnValue(true);
|
||||||
} catch (Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Unique
|
|
||||||
private static int eap$getIntField(Object self, String name, int def) {
|
|
||||||
Class<?> c = self.getClass();
|
|
||||||
while (c != null && c != Object.class) {
|
|
||||||
try {
|
|
||||||
var f = c.getDeclaredField(name);
|
|
||||||
f.setAccessible(true);
|
|
||||||
Object v = f.get(self);
|
|
||||||
if (v instanceof Integer i) return i;
|
|
||||||
} catch (Throwable ignored) {}
|
|
||||||
c = c.getSuperclass();
|
|
||||||
}
|
|
||||||
return def;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Unique
|
|
||||||
private static Font eap$getFont(Object self) {
|
|
||||||
Class<?> c = self.getClass();
|
|
||||||
while (c != null && c != Object.class) {
|
|
||||||
try {
|
|
||||||
var f = c.getDeclaredField("font");
|
|
||||||
f.setAccessible(true);
|
|
||||||
Object v = f.get(self);
|
|
||||||
if (v instanceof Font font) return font;
|
|
||||||
} catch (Throwable ignored) {}
|
|
||||||
c = c.getSuperclass();
|
|
||||||
}
|
|
||||||
return net.minecraft.client.Minecraft.getInstance().font;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 重写renderSlot方法,为所有可见的样板槽位添加数量显示
|
* 重写renderSlot方法,为所有可见的样板槽位添加数量显示
|
||||||
*/
|
*/
|
||||||
|
|
@ -184,17 +189,14 @@ public abstract class AEBaseScreenMixin {
|
||||||
|
|
||||||
try {
|
try {
|
||||||
var details = PatternDetailsHelper.decodePattern(itemStack, Minecraft.getInstance().level, false);
|
var details = PatternDetailsHelper.decodePattern(itemStack, Minecraft.getInstance().level, false);
|
||||||
try {
|
if (details != null && details.getOutputs() != null && details.getOutputs().length > 0) {
|
||||||
if (details != null && details.getOutputs() != null && details.getOutputs().length > 0) {
|
AEKey key = details.getOutputs()[0].what();
|
||||||
AEKey key = details.getOutputs()[0].what();
|
if (key != null && ClientPatternHighlightStore.hasHighlight(key)) {
|
||||||
if (key != null && ClientPatternHighlightStore.hasHighlight(key)) {
|
GuiUtil.drawSlotRainbowHighlight(guiGraphics, s.x, s.y);
|
||||||
try {
|
|
||||||
GuiUtil.drawSlotRainbowHighlight(guiGraphics, s.x, s.y);
|
|
||||||
} catch (Throwable ignored) {}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} catch (Throwable ignore) {}
|
}
|
||||||
} catch (Throwable ignore) {}
|
} catch (Throwable ignore) {
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// 在 AEBaseScreen.drawText 完成某个文本绘制后,若该文本为“样板”标签,则紧接着绘制页码。
|
// 在 AEBaseScreen.drawText 完成某个文本绘制后,若该文本为“样板”标签,则紧接着绘制页码。
|
||||||
|
|
@ -313,18 +315,22 @@ public abstract class AEBaseScreenMixin {
|
||||||
|
|
||||||
|
|
||||||
@Shadow
|
@Shadow
|
||||||
protected void setTextContent(String id, Component content) {};
|
protected void setTextContent(String id, Component content) {
|
||||||
|
}
|
||||||
|
|
||||||
|
;
|
||||||
|
|
||||||
@Inject(method = "updateBeforeRender", at = @At("RETURN"), remap = false)
|
@Inject(method = "updateBeforeRender", at = @At("RETURN"), remap = false)
|
||||||
private void onUpdateBeforeRender(CallbackInfo ci) {
|
private void onUpdateBeforeRender(CallbackInfo ci) {
|
||||||
try {
|
try {
|
||||||
AEBaseScreen<?> self = (AEBaseScreen<?>) (Object) this;
|
AEBaseScreen<?> self = (AEBaseScreen<?>) (Object) this;
|
||||||
if (self instanceof PatternProviderScreen screen){
|
if (self instanceof PatternProviderScreen screen) {
|
||||||
Component t = screen.getTitle();
|
Component t = screen.getTitle();
|
||||||
if (t != null && !t.getString().isEmpty()) {
|
if (t != null && !t.getString().isEmpty()) {
|
||||||
this.setTextContent(AEBaseScreen.TEXT_ID_DIALOG_TITLE, t);
|
this.setTextContent(AEBaseScreen.TEXT_ID_DIALOG_TITLE, t);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Throwable ignored) {}
|
} catch (Throwable ignored) {
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,54 @@
|
||||||
|
package com.extendedae_plus.mixin.gtceu;
|
||||||
|
|
||||||
|
import appeng.api.crafting.PatternDetailsHelper;
|
||||||
|
import appeng.api.stacks.AEKey;
|
||||||
|
import com.extendedae_plus.content.ClientPatternHighlightStore;
|
||||||
|
import com.extendedae_plus.util.GuiUtil;
|
||||||
|
import com.gregtechceu.gtceu.integration.ae2.gui.widget.slot.AEPatternViewSlotWidget;
|
||||||
|
import com.lowdragmc.lowdraglib.gui.widget.SlotWidget;
|
||||||
|
import com.lowdragmc.lowdraglib.utils.Position;
|
||||||
|
import net.minecraft.client.Minecraft;
|
||||||
|
import net.minecraft.client.gui.GuiGraphics;
|
||||||
|
import net.minecraft.world.inventory.Slot;
|
||||||
|
import net.minecraft.world.item.ItemStack;
|
||||||
|
import net.minecraftforge.api.distmarker.Dist;
|
||||||
|
import net.minecraftforge.api.distmarker.OnlyIn;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
|
@OnlyIn(Dist.CLIENT)
|
||||||
|
@Mixin(value = AEPatternViewSlotWidget.class, remap = false)
|
||||||
|
public abstract class AEPatternViewSlotWidgetMixin {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 在 AEPatternViewSlotWidget.drawBackgroundTexture(...) 尾部注入绘制数字逻辑
|
||||||
|
*/
|
||||||
|
@Inject(method = "drawBackgroundTexture", at = @At("TAIL"))
|
||||||
|
private void onDrawInBackgroundTail(GuiGraphics graphics, int mouseX, int mouseY, CallbackInfo ci) {
|
||||||
|
if (!AEPatternViewSlotWidget.class.isInstance(this)) return;
|
||||||
|
// 把 this 强转为 SlotWidget(目标类继承自 SlotWidget)
|
||||||
|
SlotWidget self = (SlotWidget) (Object) this;
|
||||||
|
|
||||||
|
Slot handler = self.getHandler();
|
||||||
|
if (handler == null) return;
|
||||||
|
|
||||||
|
// 使用 getRealStack 来尊重 setItemHook 的渲染替换
|
||||||
|
ItemStack displayStack = self.getRealStack(handler.getItem());
|
||||||
|
if (displayStack == null || displayStack.isEmpty()) return;
|
||||||
|
|
||||||
|
ItemStack stack = handler.getItem();
|
||||||
|
Position pos = self.getPosition(); // 来自 Widget 的方法,继承可用
|
||||||
|
try {
|
||||||
|
var details = PatternDetailsHelper.decodePattern(stack, Minecraft.getInstance().level, false);
|
||||||
|
if (details != null && details.getOutputs() != null && details.getOutputs().length > 0) {
|
||||||
|
AEKey key = details.getOutputs()[0].what();
|
||||||
|
if (key != null && ClientPatternHighlightStore.hasHighlight(key)) {
|
||||||
|
GuiUtil.drawSlotRainbowHighlight(graphics, pos.x + 1, pos.y + 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (Throwable ignore) {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,19 @@
|
||||||
|
package com.extendedae_plus.mixin.gtceu;
|
||||||
|
|
||||||
|
import com.extendedae_plus.content.ClientPatternHighlightStore;
|
||||||
|
import com.lowdragmc.lowdraglib.gui.modular.ModularUIContainer;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
|
@Mixin(value = ModularUIContainer.class, remap = false)
|
||||||
|
public class ModularUIContainerCloseMixin {
|
||||||
|
|
||||||
|
@Inject(method = "removed", at = @At("HEAD"))
|
||||||
|
private void onRemoved(CallbackInfo ci) {
|
||||||
|
try {
|
||||||
|
ClientPatternHighlightStore.clearAll();
|
||||||
|
} catch (Throwable ignored) {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,61 @@
|
||||||
|
package com.extendedae_plus.mixin.gtceu;
|
||||||
|
|
||||||
|
import com.extendedae_plus.util.GuiUtil;
|
||||||
|
import com.gregtechceu.gtceu.integration.ae2.gui.widget.slot.AEPatternViewSlotWidget;
|
||||||
|
import com.lowdragmc.lowdraglib.gui.util.DrawerHelper;
|
||||||
|
import com.lowdragmc.lowdraglib.gui.widget.SlotWidget;
|
||||||
|
import com.lowdragmc.lowdraglib.utils.Position;
|
||||||
|
import com.lowdragmc.lowdraglib.utils.Size;
|
||||||
|
import com.mojang.blaze3d.systems.RenderSystem;
|
||||||
|
import net.minecraft.client.gui.GuiGraphics;
|
||||||
|
import net.minecraft.world.inventory.Slot;
|
||||||
|
import net.minecraft.world.item.ItemStack;
|
||||||
|
import net.minecraftforge.api.distmarker.Dist;
|
||||||
|
import net.minecraftforge.api.distmarker.OnlyIn;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
|
|
||||||
|
@OnlyIn(Dist.CLIENT)
|
||||||
|
@Mixin(value = SlotWidget.class, remap = false)
|
||||||
|
public abstract class SlotWidgetMixin {
|
||||||
|
/**
|
||||||
|
* 在 SlotWidget.drawInBackground(...) 尾部注入绘制数字逻辑
|
||||||
|
*/
|
||||||
|
@Inject(method = "drawInBackground(Lnet/minecraft/client/gui/GuiGraphics;IIF)V", at = @At("TAIL"))
|
||||||
|
private void onDrawInBackgroundTail(GuiGraphics graphics, int mouseX, int mouseY, float partialTicks, CallbackInfo ci) {
|
||||||
|
if (!AEPatternViewSlotWidget.class.isInstance(this)) return;
|
||||||
|
// 把 this 强转为 SlotWidget(目标类继承自 SlotWidget)
|
||||||
|
SlotWidget self = (SlotWidget) (Object) this;
|
||||||
|
|
||||||
|
Slot handler = self.getHandler();
|
||||||
|
if (handler == null) return;
|
||||||
|
|
||||||
|
// 使用 getRealStack 来尊重 setItemHook 的渲染替换
|
||||||
|
ItemStack displayStack = self.getRealStack(handler.getItem());
|
||||||
|
if (displayStack == null || displayStack.isEmpty()) return;
|
||||||
|
|
||||||
|
ItemStack stack = handler.getItem();
|
||||||
|
|
||||||
|
String patternOutputText = GuiUtil.getPatternOutputText(stack);
|
||||||
|
|
||||||
|
Position pos = self.getPosition(); // 来自 Widget 的方法,继承可用
|
||||||
|
Size size = self.getSize(); // 同上
|
||||||
|
|
||||||
|
graphics.pose().pushPose();
|
||||||
|
graphics.pose().translate(0.0F, 0.0F, 300.0F);
|
||||||
|
RenderSystem.disableDepthTest();
|
||||||
|
DrawerHelper.drawStringFixedCorner(
|
||||||
|
graphics,
|
||||||
|
patternOutputText,
|
||||||
|
pos.x + size.width,
|
||||||
|
pos.y + size.height,
|
||||||
|
0xFFFFFFFF,
|
||||||
|
true,
|
||||||
|
0.75f);
|
||||||
|
RenderSystem.enableDepthTest();
|
||||||
|
graphics.pose().popPose();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -15,6 +15,8 @@ import com.extendedae_plus.mixin.ae2.accessor.PatternProviderLogicAccessor;
|
||||||
import com.extendedae_plus.util.PatternProviderDataUtil;
|
import com.extendedae_plus.util.PatternProviderDataUtil;
|
||||||
import com.glodblock.github.extendedae.util.FCClientUtil;
|
import com.glodblock.github.extendedae.util.FCClientUtil;
|
||||||
import com.glodblock.github.glodium.util.GlodUtil;
|
import com.glodblock.github.glodium.util.GlodUtil;
|
||||||
|
import com.gregtechceu.gtceu.api.gui.factory.MachineUIFactory;
|
||||||
|
import com.gregtechceu.gtceu.api.machine.MetaMachine;
|
||||||
import net.minecraft.core.BlockPos;
|
import net.minecraft.core.BlockPos;
|
||||||
import net.minecraft.core.Direction;
|
import net.minecraft.core.Direction;
|
||||||
import net.minecraft.network.FriendlyByteBuf;
|
import net.minecraft.network.FriendlyByteBuf;
|
||||||
|
|
@ -133,6 +135,41 @@ public class CraftingMonitorOpenProviderC2SPacket {
|
||||||
return;
|
return;
|
||||||
} catch (Exception ignored) {
|
} catch (Exception ignored) {
|
||||||
}
|
}
|
||||||
|
} else if (provider instanceof com.gregtechceu.gtceu.integration.ae2.machine.MEPatternBufferPartMachine machine) {
|
||||||
|
// 处理 MEPatternBufferPartMachine:打开其界面并高亮位置,尽量反射获取槽位页码
|
||||||
|
try {
|
||||||
|
BlockPos pos = machine.getPos();
|
||||||
|
Level level = machine.getLevel();
|
||||||
|
if (pos == null || level == null) continue;
|
||||||
|
if (!level.isClientSide) { // 确保在服务器端执行
|
||||||
|
MachineUIFactory.INSTANCE.openUI(MetaMachine.getMachine(level, pos), player);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 最后发送高亮包,保证界面已打开
|
||||||
|
if (pattern.getOutputs() != null && pattern.getOutputs().length > 0 && pattern.getOutputs()[0] != null) {
|
||||||
|
AEKey key = pattern.getOutputs()[0].what();
|
||||||
|
ModNetwork.CHANNEL.sendTo(new SetPatternHighlightS2CPacket(key, true), player.connection.connection, NetworkDirection.PLAY_TO_CLIENT);
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (Exception ignored) {
|
||||||
|
}
|
||||||
|
} else if (provider instanceof org.gtlcore.gtlcore.common.machine.multiblock.part.ae.MEPatternBufferPartMachine machine) {
|
||||||
|
// 处理 MEPatternBufferPartMachine:打开其界面并高亮位置,尽量反射获取槽位页码
|
||||||
|
try {
|
||||||
|
BlockPos pos = machine.getPos();
|
||||||
|
Level level = machine.getLevel();
|
||||||
|
if (pos == null || level == null) continue;
|
||||||
|
if (!level.isClientSide) { // 确保在服务器端执行
|
||||||
|
MachineUIFactory.INSTANCE.openUI(MetaMachine.getMachine(level, pos), player);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 最后发送高亮包,保证界面已打开
|
||||||
|
if (pattern.getOutputs() != null && pattern.getOutputs().length > 0 && pattern.getOutputs()[0] != null) {
|
||||||
|
AEKey key = pattern.getOutputs()[0].what();
|
||||||
|
ModNetwork.CHANNEL.sendTo(new SetPatternHighlightS2CPacket(key, true), player.connection.connection, NetworkDirection.PLAY_TO_CLIENT);
|
||||||
|
}
|
||||||
|
} catch (Exception ignored) {
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,7 @@ side = "BOTH"
|
||||||
[[dependencies.extendedae_plus]]
|
[[dependencies.extendedae_plus]]
|
||||||
modId = "expatternprovider"
|
modId = "expatternprovider"
|
||||||
mandatory = true
|
mandatory = true
|
||||||
versionRange = "[1.20-1.4.0-forge,)"
|
versionRange = "[1.20-1.1.12-forge,)"
|
||||||
ordering = "AFTER"
|
ordering = "AFTER"
|
||||||
side = "BOTH"
|
side = "BOTH"
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -23,6 +23,8 @@
|
||||||
"extendedae.client.HighlightButtonMixin",
|
"extendedae.client.HighlightButtonMixin",
|
||||||
"extendedae.client.gui.GuiExPatternProviderMixin",
|
"extendedae.client.gui.GuiExPatternProviderMixin",
|
||||||
"extendedae.client.gui.GuiExPatternTerminalMixin",
|
"extendedae.client.gui.GuiExPatternTerminalMixin",
|
||||||
|
"gtceu.AEPatternViewSlotWidgetMixin",
|
||||||
|
"gtceu.SlotWidgetMixin",
|
||||||
"hooks.ModelBakeryMixin",
|
"hooks.ModelBakeryMixin",
|
||||||
"jei.EncodePatternTransferHandlerMixin",
|
"jei.EncodePatternTransferHandlerMixin",
|
||||||
"jei.EncodingHelperMixin",
|
"jei.EncodingHelperMixin",
|
||||||
|
|
@ -56,7 +58,8 @@
|
||||||
"extendedae.common.TileExPatternProviderMixin",
|
"extendedae.common.TileExPatternProviderMixin",
|
||||||
"extendedae.container.ContainerExPatternProviderMixin",
|
"extendedae.container.ContainerExPatternProviderMixin",
|
||||||
"extendedae.container.ContainerExPatternTerminalMixin",
|
"extendedae.container.ContainerExPatternTerminalMixin",
|
||||||
"extendedae.container.ContainerWirelessExPatternTerminalMixin"
|
"extendedae.container.ContainerWirelessExPatternTerminalMixin",
|
||||||
|
"gtceu.ModularUIContainerCloseMixin"
|
||||||
],
|
],
|
||||||
"injectors": {
|
"injectors": {
|
||||||
"defaultRequire": 1
|
"defaultRequire": 1
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user