From 6628f11d437e2105a2d69eee8d1520091875e38b Mon Sep 17 00:00:00 2001 From: Arborsm Date: Fri, 6 Dec 2024 22:25:55 +0800 Subject: [PATCH 01/14] ender fluid cover. --- .../api/gui/widget/ColorBlockWidget.java | 51 ++++ .../gui/widget/ConfirmTextInputWidget.java | 65 +++++ .../api/misc/virtualregistry/EntryTypes.java | 62 +++++ .../virtualregistry/VirtualEnderRegistry.java | 135 ++++++++++ .../misc/virtualregistry/VirtualEntry.java | 76 ++++++ .../virtualregistry/VirtualRegistryMap.java | 84 +++++++ .../virtualregistry/entries/VirtualTank.java | 140 +++++++++++ .../virtualregistry/entries/VisualTank.java | 51 ++++ .../cover/ender/CoverAbstractEnderLink.java | 238 ++++++++++++++++++ .../cover/ender/EnderFluidLinkCover.java | 185 ++++++++++++++ .../gtceu/common/data/GTCovers.java | 9 +- .../gtceu/common/data/GTItems.java | 50 ++-- .../gtceu/forge/ForgeCommonEventListener.java | 13 +- 13 files changed, 1125 insertions(+), 34 deletions(-) create mode 100644 src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java create mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java create mode 100644 src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java create mode 100644 src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java new file mode 100644 index 0000000000..1d42cb6fcd --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java @@ -0,0 +1,51 @@ +package com.gregtechceu.gtceu.api.gui.widget; + +import com.lowdragmc.lowdraglib.gui.util.DrawerHelper; +import com.lowdragmc.lowdraglib.gui.widget.Widget; +import lombok.Getter; +import lombok.Setter; +import lombok.experimental.Accessors; +import net.minecraft.client.gui.GuiGraphics; +import net.minecraftforge.api.distmarker.Dist; +import net.minecraftforge.api.distmarker.OnlyIn; +import org.jetbrains.annotations.NotNull; + +import java.util.function.IntSupplier; + +@Setter +@Accessors(chain = true) +public class ColorBlockWidget extends Widget { + private IntSupplier colorSupplier; + @Getter + private int currentColor; + + public ColorBlockWidget(int x, int y, int width, int height) { + super(x, y, width, height); + this.currentColor = 0xFFFFFFFF; + } + + @Override + public void updateScreen() { + super.updateScreen(); + if (isClientSideWidget && colorSupplier != null) { + currentColor = colorSupplier.getAsInt(); + } + } + + @OnlyIn(Dist.CLIENT) + @Override + public void drawInBackground(@NotNull GuiGraphics graphics, int mouseX, int mouseY, float partialTicks) { + int x = getPosition().x + 1; + int y = getPosition().y + 1; + int width = getSize().width - 2; + int height = getSize().height - 2; + + if (colorSupplier != null) { + currentColor = colorSupplier.getAsInt(); + } + final int BORDER_COLOR = 0xFF000000; + + graphics.fill(x, y, x + width, y + height, currentColor); + DrawerHelper.drawBorder(graphics, x, y, width, height, BORDER_COLOR, 1); + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java new file mode 100644 index 0000000000..87d4e9e906 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java @@ -0,0 +1,65 @@ +package com.gregtechceu.gtceu.api.gui.widget; + +import com.gregtechceu.gtceu.api.gui.GuiTextures; +import com.lowdragmc.lowdraglib.gui.texture.GuiTextureGroup; +import com.lowdragmc.lowdraglib.gui.widget.ButtonWidget; +import com.lowdragmc.lowdraglib.gui.widget.TextFieldWidget; +import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; +import lombok.AccessLevel; +import lombok.Getter; +import lombok.Setter; +import lombok.experimental.Accessors; + +import java.util.function.Consumer; +import java.util.function.Function; + +@Accessors(chain = true) +public class ConfirmTextInputWidget extends WidgetGroup { + + private final Consumer textResponder; + private final Function validator; + @Getter + @Setter + private String text = ""; + @Getter(AccessLevel.PRIVATE) + @Setter(AccessLevel.PRIVATE) + private String inputText = ""; + private String hoverText = ""; + + public ConfirmTextInputWidget(int x, int y, int width, int height, String text, Consumer textResponder, Function validator) { + super(x, y, width, height); + this.textResponder = textResponder; + this.validator = validator; + if (text != null) { + this.inputText = text; + } + } + + public ConfirmTextInputWidget setInputBoxTooltips(String text) { + this.hoverText = text; + return this; + } + + @Override + public void initWidget() { + super.initWidget(); + this.addWidget(new ButtonWidget( + getSizeWidth() - getSizeHeight(), + 0, + getSizeHeight(), + getSizeHeight(), + pressed -> textResponder.accept(inputText)) + .setButtonTexture( + new GuiTextureGroup(GuiTextures.VANILLA_BUTTON, + GuiTextures.CLIPBOARD_BUTTON.getSubTexture(0, 0.25, 1, 0.25)))); + this.addWidget(new TextFieldWidget( + 1, + 1, + getSizeWidth() - getSizeHeight() - 4, + getSizeHeight() - 2, + this::getInputText, + this::setInputText) + .setValidator(validator) + .setHoverTooltips(hoverText)); + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java new file mode 100644 index 0000000000..77c4afd17d --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java @@ -0,0 +1,62 @@ +package com.gregtechceu.gtceu.api.misc.virtualregistry; + +import com.gregtechceu.gtceu.GTCEu; +import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; +import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.resources.ResourceLocation; +import org.jetbrains.annotations.Nullable; + +import java.util.Map; +import java.util.function.Supplier; + +public final class EntryTypes { + + private static final Map> TYPES_MAP = new Object2ObjectOpenHashMap<>(); + public static final EntryTypes ENDER_FLUID = addEntryType(GTCEu.id("ender_fluid"), VirtualTank::new); + // ENDER_ITEM("ender_item", null), + // ENDER_ENERGY("ender_energy", null), + // ENDER_REDSTONE("ender_redstone", null); + private final ResourceLocation location; + private final Supplier factory; + + private EntryTypes(ResourceLocation location, Supplier supplier) { + this.location = location; + this.factory = supplier; + } + + @Nullable + public static EntryTypes fromString(String name) { + return TYPES_MAP.getOrDefault(GTCEu.id(name), null); + } + + @Nullable + public static EntryTypes fromLocation(String location) { + return TYPES_MAP.getOrDefault(new ResourceLocation(location), null); + } + + public static EntryTypes addEntryType(ResourceLocation location, Supplier supplier) { + var type = new EntryTypes<>(location, supplier); + if (!TYPES_MAP.containsKey(location)) { + TYPES_MAP.put(location, type); + } else { + GTCEu.LOGGER.warn("Entry \"{}\" is already registered!", location); + } + return type; + } + + public T createInstance(CompoundTag nbt) { + var entry = createInstance(); + entry.deserializeNBT(nbt); + return entry; + } + + public T createInstance() { + return factory.get(); + } + + @Override + public String toString() { + return this.location.toString(); + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java new file mode 100644 index 0000000000..e5ef9bef42 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java @@ -0,0 +1,135 @@ +package com.gregtechceu.gtceu.api.misc.virtualregistry; + +import com.gregtechceu.gtceu.GTCEu; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.world.level.saveddata.SavedData; +import net.minecraftforge.server.ServerLifecycleHooks; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.util.HashMap; +import java.util.Map; +import java.util.Set; +import java.util.UUID; +import java.util.function.Predicate; + +public class VirtualEnderRegistry extends SavedData { + private static final String DATA_ID = GTCEu.MOD_ID + ".virtual_entry_data"; + private static final String PUBLIC_KEY = "Public"; + private static final String PRIVATE_KEY = "Private"; + private static volatile VirtualEnderRegistry data; + private final Map VIRTUAL_REGISTRIES = new HashMap<>(); + + public VirtualEnderRegistry() { + } + + public VirtualEnderRegistry(CompoundTag name) { + readFromNBT(name); + } + + public static VirtualEnderRegistry getInstance() { + if (data == null) { + var server = ServerLifecycleHooks.getCurrentServer(); + if (server != null) { + data = server.overworld().getDataStorage() + .computeIfAbsent(VirtualEnderRegistry::new, VirtualEnderRegistry::new, DATA_ID); + GTCEu.LOGGER.debug("VirtualEnderRegistry has been successfully loaded"); + } + } + + return data; + } + + /** + * To be called on server stopped event + */ + public static void release() { + if (data != null) { + data = null; + GTCEu.LOGGER.debug("VirtualEnderRegistry has been unloaded"); + } + } + + public T getEntry(@Nullable UUID owner, EntryTypes type, String name) { + return getRegistry(owner).getEntry(type, name); + } + + public void addEntry(@Nullable UUID owner, String name, VirtualEntry entry) { + getRegistry(owner).addEntry(name, entry); + } + + public boolean hasEntry(@Nullable UUID owner, EntryTypes type, String name) { + return getRegistry(owner).contains(type, name); + } + + public @NotNull T getOrCreateEntry(@Nullable UUID owner, EntryTypes type, String name) { + if (!hasEntry(owner, type, name)) addEntry(owner, name, type.createInstance()); + return getEntry(owner, type, name); + } + + /** + * Removes an entry from the registry. Use with caution! + * + * @param owner The uuid of the player the entry is private to, or null if the entry is public + * @param type Type of the registry to remove from + * @param name The name of the entry + */ + public void deleteEntry(@Nullable UUID owner, EntryTypes type, String name) { + var registry = getRegistry(owner); + if (registry.contains(type, name)) { + registry.deleteEntry(type, name); + return; + } + GTCEu.LOGGER.warn("Attempted to delete {} entry {} of type {}, which does not exist", + owner == null ? "public" : String.format("private [%s]", owner), name, type); + } + + public void deleteEntryIf(@Nullable UUID owner, EntryTypes type, String name, Predicate shouldDelete) { + T entry = getEntry(owner, type, name); + if (entry != null && shouldDelete.test(entry)) deleteEntry(owner, type, name); + } + + public Set getEntryNames(UUID owner, EntryTypes type) { + return getRegistry(owner).getEntryNames(type); + } + + private VirtualRegistryMap getRegistry(UUID owner) { + if (data == null) getInstance(); + return data.VIRTUAL_REGISTRIES.computeIfAbsent(owner, key -> new VirtualRegistryMap()); + } + + public final void readFromNBT(CompoundTag nbt) { + if (nbt.contains(PUBLIC_KEY)) { + VIRTUAL_REGISTRIES.put(null, new VirtualRegistryMap(nbt.getCompound(PUBLIC_KEY))); + } + if (nbt.contains(PRIVATE_KEY)) { + CompoundTag privateEntries = nbt.getCompound(PRIVATE_KEY); + for (String owner : privateEntries.getAllKeys()) { + var privateMap = privateEntries.getCompound(owner); + VIRTUAL_REGISTRIES.put(UUID.fromString(owner), new VirtualRegistryMap(privateMap)); + } + } + } + + @NotNull + @Override + public final CompoundTag save(@NotNull CompoundTag tag) { + var privateTag = new CompoundTag(); + for (var owner : VIRTUAL_REGISTRIES.keySet()) { + var mapTag = VIRTUAL_REGISTRIES.get(owner).serializeNBT(); + if (owner != null) { + privateTag.put(owner.toString(), mapTag); + } else { + tag.put(PUBLIC_KEY, mapTag); + } + } + tag.put(PRIVATE_KEY, privateTag); + return tag; + } + + @Override + public boolean isDirty() { + // can't think of a good way to mark dirty other than always return true; + return true; + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java new file mode 100644 index 0000000000..57097e44e8 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java @@ -0,0 +1,76 @@ +package com.gregtechceu.gtceu.api.misc.virtualregistry; + +import lombok.Getter; +import net.minecraft.nbt.CompoundTag; +import net.minecraftforge.common.util.INBTSerializable; +import org.jetbrains.annotations.NotNull; + +public abstract class VirtualEntry implements INBTSerializable { + + public static final String DEFAULT_COLOR = "FFFFFFFF"; + protected static final String COLOR_KEY = "color"; + protected static final String DESC_KEY = "description"; + + @Getter + private int color = 0xFFFFFFFF; + @Getter + private String colorStr = DEFAULT_COLOR; + @NotNull + private String description = ""; + + public abstract EntryTypes getType(); + + public void setColor(String color) { + this.color = parseColor(color); + this.colorStr = color.toUpperCase(); + } + + public void setColor(int color) { + setColor(Integer.toHexString(color)); + } + + private int parseColor(String s) { + // stupid java not having actual unsigned ints + long tmp = Long.parseLong(s, 16); + if (tmp > 0x7FFFFFFF) { + tmp -= 0x100000000L; + } + return (int) tmp; + } + + @NotNull + public String getDescription() { + return this.description; + } + + public void setDescription(@NotNull String desc) { + this.description = desc; + } + + @Override + public boolean equals(Object o) { + if (!(o instanceof VirtualEntry other)) return false; + return this.getType() == other.getType() && this.color == other.color; + } + + @Override + public CompoundTag serializeNBT() { + var tag = new CompoundTag(); + tag.putString(COLOR_KEY, this.colorStr); + + if (!description.isEmpty()) + this.description = tag.getString(DESC_KEY); + + return tag; + } + + @Override + public void deserializeNBT(CompoundTag nbt) { + setColor(nbt.getString(COLOR_KEY)); + + if (nbt.contains(DESC_KEY)) + setDescription(nbt.getString(DESC_KEY)); + } + + public abstract boolean canRemove(); +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java new file mode 100644 index 0000000000..9d336ff6d5 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java @@ -0,0 +1,84 @@ +package com.gregtechceu.gtceu.api.misc.virtualregistry; + +import net.minecraft.nbt.CompoundTag; +import net.minecraftforge.common.util.INBTSerializable; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.util.Collections; +import java.util.HashSet; +import java.util.Map; +import java.util.Set; +import java.util.concurrent.ConcurrentHashMap; + +public class VirtualRegistryMap implements INBTSerializable { + private final Map, Map> registryMap = new ConcurrentHashMap<>(); + + public VirtualRegistryMap() { + } + + public VirtualRegistryMap(CompoundTag tag) { + deserializeNBT(tag); + } + + @SuppressWarnings("unchecked") + public @Nullable T getEntry(EntryTypes type, String name) { + return (T) registryMap.getOrDefault(type, Collections.emptyMap()).get(name); + } + + public void addEntry(String name, VirtualEntry entry) { + registryMap.computeIfAbsent(entry.getType(), k -> new ConcurrentHashMap<>()).put(name, entry); + } + + public boolean contains(EntryTypes type, String name) { + return registryMap.containsKey(type) && registryMap.get(type).containsKey(name); + } + + public void deleteEntry(EntryTypes type, String name) { + Map entries = registryMap.get(type); + if (entries != null) { + entries.remove(name); + if (entries.isEmpty()) { + registryMap.remove(type); + } + } + } + + public void clear() { + registryMap.clear(); + } + + public Set getEntryNames(EntryTypes type) { + return new HashSet<>(registryMap.getOrDefault(type, Collections.emptyMap()).keySet()); + } + + @Override + public @NotNull CompoundTag serializeNBT() { + CompoundTag tag = new CompoundTag(); + for (Map.Entry, Map> entry : registryMap.entrySet()) { + CompoundTag entriesTag = new CompoundTag(); + for (Map.Entry subEntry : entry.getValue().entrySet()) { + entriesTag.put(subEntry.getKey(), subEntry.getValue().serializeNBT()); + } + tag.put(entry.getKey().toString(), entriesTag); + } + return tag; + } + + @Override + public void deserializeNBT(CompoundTag nbt) { + for (String entryTypeString : nbt.getAllKeys()) { + EntryTypes type = entryTypeString.contains(":") + ? EntryTypes.fromLocation(entryTypeString) + : EntryTypes.fromString(entryTypeString); + + if (type == null) continue; + + CompoundTag virtualEntries = nbt.getCompound(entryTypeString); + for (String name : virtualEntries.getAllKeys()) { + CompoundTag entryTag = virtualEntries.getCompound(name); + addEntry(name, type.createInstance(entryTag)); + } + } + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java new file mode 100644 index 0000000000..3a4c6c1636 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java @@ -0,0 +1,140 @@ +package com.gregtechceu.gtceu.api.misc.virtualregistry.entries; + +import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEntry; +import lombok.Setter; +import net.minecraft.nbt.CompoundTag; +import net.minecraftforge.fluids.FluidStack; +import net.minecraftforge.fluids.IFluidTank; +import net.minecraftforge.fluids.capability.IFluidHandler; +import net.minecraftforge.fluids.capability.templates.FluidTank; +import org.jetbrains.annotations.NotNull; + +public class VirtualTank extends VirtualEntry implements IFluidTank, IFluidHandler { + public static final int DEFAULT_CAPACITY = 64000; // 64B + protected static final String CAPACITY_KEY = "capacity"; + protected static final String FLUID_KEY = "fluid"; + @NotNull + private final FluidTank fluidTank; + private int capacity; + @Setter + private Runnable onChange; + + public VirtualTank(int capacity) { + this.capacity = capacity; + fluidTank = new FluidTank(this.capacity) { + @Override + protected void onContentsChanged() { + super.onContentsChanged(); + VirtualTank.this.onContentsChanged(); + } + }; + } + + public VirtualTank() { + this(DEFAULT_CAPACITY); + } + + @Override + public EntryTypes getType() { + return EntryTypes.ENDER_FLUID; + } + + @NotNull + @Override + public FluidStack getFluid() { + return this.fluidTank.getFluid(); + } + + public void setFluid(FluidStack fluid) { + this.fluidTank.setFluid(fluid); + } + + @Override + public int getFluidAmount() { + return this.fluidTank.getFluidAmount(); + } + + @Override + public int getCapacity() { + return this.capacity; + } + + @Override + public boolean isFluidValid(FluidStack fluidStack) { + return this.fluidTank.isFluidValid(fluidStack); + } + + @Override + public int getTanks() { + return this.fluidTank.getTanks(); + } + + @Override + public @NotNull FluidStack getFluidInTank(int i) { + return this.fluidTank.getFluidInTank(i); + } + + @Override + public int getTankCapacity(int i) { + if (i != 0) return 0; + return this.capacity; + } + + @Override + public boolean isFluidValid(int i, @NotNull FluidStack fluidStack) { + return this.fluidTank.isFluidValid(i, fluidStack); + } + + @Override + public boolean equals(Object o) { + if (!(o instanceof VirtualTank other)) return false; + return this.fluidTank == other.fluidTank; + } + + @Override + public CompoundTag serializeNBT() { + var tag = super.serializeNBT(); + tag.putInt(CAPACITY_KEY, this.capacity); + + if (this.fluidTank.getFluid() != FluidStack.EMPTY) + tag.put(FLUID_KEY, this.fluidTank.getFluid().writeToNBT(new CompoundTag())); + + return tag; + } + + @Override + public void deserializeNBT(CompoundTag nbt) { + super.deserializeNBT(nbt); + this.capacity = nbt.getInt(CAPACITY_KEY); + + if (nbt.contains(FLUID_KEY)) + setFluid(FluidStack.loadFluidStackFromNBT(nbt.getCompound(FLUID_KEY))); + } + + @Override + public boolean canRemove() { + return this.fluidTank.isEmpty(); + } + + @Override + public int fill(FluidStack fluidStack, FluidAction fluidAction) { + return this.fluidTank.fill(fluidStack, fluidAction); + } + + @NotNull + @Override + public FluidStack drain(FluidStack fluidStack, FluidAction doDrain) { + return this.fluidTank.drain(fluidStack, doDrain); + } + + @NotNull + @Override + public FluidStack drain(int amount, FluidAction fluidAction) { + return this.fluidTank.drain(amount, fluidAction); + } + + protected void onContentsChanged() { + if (onChange != null) onChange.run(); + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java new file mode 100644 index 0000000000..93dba6ad8f --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java @@ -0,0 +1,51 @@ +package com.gregtechceu.gtceu.api.misc.virtualregistry.entries; + +import com.lowdragmc.lowdraglib.syncdata.ITagSerializable; +import lombok.Getter; +import lombok.Setter; +import lombok.experimental.Accessors; +import net.minecraft.nbt.CompoundTag; +import net.minecraftforge.common.util.INBTSerializable; +import net.minecraftforge.fluids.capability.templates.FluidTank; + +@Accessors(chain = true) +public class VisualTank extends FluidTank implements INBTSerializable, ITagSerializable { + @Getter + private VirtualTank virtualTank; + @Setter + private Runnable onChange; + + public VisualTank(VirtualTank tank) { + super(VirtualTank.DEFAULT_CAPACITY); + setVirtualTank(tank); + } + + public VisualTank() { + super(VirtualTank.DEFAULT_CAPACITY); + setVirtualTank(new VirtualTank()); + } + + public void setVirtualTank(VirtualTank tank) { + virtualTank = tank; + setFluid(tank.getFluid()); + virtualTank.setOnChange(() -> setFluid(virtualTank.getFluid())); + } + + @Override + protected void onContentsChanged() { + super.onContentsChanged(); + virtualTank.setFluid(getFluid()); + if (onChange != null) onChange.run(); + } + + @Override + public CompoundTag serializeNBT() { + return virtualTank.serializeNBT(); + } + + @Override + public void deserializeNBT(CompoundTag nbt) { + virtualTank.deserializeNBT(nbt); + fluid = virtualTank.getFluid(); + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java new file mode 100644 index 0000000000..8ccee0ae1c --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java @@ -0,0 +1,238 @@ +package com.gregtechceu.gtceu.common.cover.ender; + +import com.gregtechceu.gtceu.api.capability.IControllable; +import com.gregtechceu.gtceu.api.capability.ICoverable; +import com.gregtechceu.gtceu.api.capability.recipe.IO; +import com.gregtechceu.gtceu.api.cover.CoverBehavior; +import com.gregtechceu.gtceu.api.cover.CoverDefinition; +import com.gregtechceu.gtceu.api.cover.IUICover; +import com.gregtechceu.gtceu.api.gui.GuiTextures; +import com.gregtechceu.gtceu.api.gui.widget.ColorBlockWidget; +import com.gregtechceu.gtceu.api.gui.widget.ConfirmTextInputWidget; +import com.gregtechceu.gtceu.api.gui.widget.EnumSelectorWidget; +import com.gregtechceu.gtceu.api.gui.widget.ToggleButtonWidget; +import com.gregtechceu.gtceu.api.machine.ConditionalSubscriptionHandler; +import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEntry; +import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; +import com.gregtechceu.gtceu.common.cover.data.ManualIOMode; +import com.lowdragmc.lowdraglib.gui.widget.LabelWidget; +import com.lowdragmc.lowdraglib.gui.widget.Widget; +import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; +import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; +import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; +import com.lowdragmc.lowdraglib.syncdata.annotation.RequireRerender; +import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; +import lombok.Getter; +import lombok.Setter; +import net.minecraft.core.Direction; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.item.ItemStack; +import org.jetbrains.annotations.NotNull; + +import java.util.List; +import java.util.UUID; +import java.util.regex.Pattern; + +public abstract class CoverAbstractEnderLink extends CoverBehavior implements IUICover, IControllable { + public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(CoverAbstractEnderLink.class, + CoverBehavior.MANAGED_FIELD_HOLDER); + public static final Pattern COLOR_INPUT_PATTERN = Pattern.compile("[0-9a-fA-F]*"); + protected final ConditionalSubscriptionHandler subscriptionHandler; + @Persisted + @DescSynced + protected String channelName = VirtualEntry.DEFAULT_COLOR; + @Persisted + @DescSynced + protected String description = VirtualEntry.DEFAULT_COLOR; + @Getter + @Persisted + @DescSynced + protected UUID playerUUID = null; + @Getter + @Setter + @Persisted + @DescSynced + protected boolean isPrivate = false; + @Persisted + @Getter + protected boolean isWorkingEnabled = true; + @Persisted + @DescSynced + @Getter + protected ManualIOMode manualIOMode = ManualIOMode.DISABLED; + @Persisted + @DescSynced + @Getter + @RequireRerender + protected IO io = IO.OUT; + + public CoverAbstractEnderLink(CoverDefinition definition, ICoverable coverHolder, Direction attachedSide) { + super(definition, coverHolder, attachedSide); + subscriptionHandler = new ConditionalSubscriptionHandler(coverHolder, this::update, this::isSubscriptionActive); + } + + protected boolean isSubscriptionActive() { + return isWorkingEnabled(); + } + + @Override + public void onLoad() { + super.onLoad(); + subscriptionHandler.initialize(coverHolder.getLevel()); + } + + @Override + public void onRemoved() { + super.onRemoved(); + subscriptionHandler.unsubscribe(); + } + + @Override + public abstract boolean canAttach(); + + @Override + public void onAttached(@NotNull ItemStack itemStack, @NotNull ServerPlayer player) { + super.onAttached(itemStack, player); + playerUUID = player.getUUID(); + } + + protected void setChannelName(String name) { + beforeChannelNameChanging(this.channelName); + this.channelName = name; + } + + protected void beforeChannelNameChanging(String oldChannelName) { + var reg = VirtualEnderRegistry.getInstance(); + if (reg == null) return; + reg.deleteEntryIf(getOwner(), getEntryType(), oldChannelName, VirtualEntry::canRemove); + } + + protected abstract EntryTypes getEntryType(); + + protected abstract void updateEntry(); + + public UUID getOwner() { + return isPrivate ? playerUUID : null; + } + + protected void update() { + long timer = coverHolder.getOffsetTimer(); + if (timer % 5 != 0) return; + + if (isWorkingEnabled()) { + transfer(); + } + updateEntry(); + + subscriptionHandler.updateSubscription(); + } + + protected abstract void transfer(); + + @Override + public void setWorkingEnabled(boolean isWorkingAllowed) { + if (this.isWorkingEnabled != isWorkingAllowed) { + this.isWorkingEnabled = isWorkingAllowed; + subscriptionHandler.updateSubscription(); + } + } + + public void setIo(IO io) { + if (io == IO.IN || io == IO.OUT) { + this.io = io; + } + } + + protected void setManualIOMode(ManualIOMode manualIOMode) { + this.manualIOMode = manualIOMode; + coverHolder.markDirty(); + } + + @Override + public Widget createUIWidget() { + updateEntry(); + final int GROUP_WIDTH = 176; + final int WIDGET_HEIGHT = 20; + final int SMALL_WIDGET_WIDTH = 20; + final int GROUP_X = 10; + final int GROUP_Y = 20; + int channelGroupWidth = GROUP_WIDTH - GROUP_X * 2; + int currentX = 0; + + final var group = new WidgetGroup(0, 0, 176, 137); + final var channelGroup = new WidgetGroup(GROUP_X, GROUP_Y, channelGroupWidth, WIDGET_HEIGHT); + group.addWidget(new LabelWidget(10, 5, getUITitle())); + + var toggleButtonWidget = new ToggleButtonWidget(currentX, 0, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + GuiTextures.BUTTON_PUBLIC_PRIVATE, this::isPrivate, null); + toggleButtonWidget.setOnPressCallback((clickData, isPrivate) -> { + setPrivate(isPrivate); + toggleButtonWidget.setHoverTooltips(isPrivate ? + "cover.ender_link.permission.public" : "cover.ender_link.permission.private"); + }); + channelGroup.addWidget(toggleButtonWidget); + currentX += SMALL_WIDGET_WIDTH + 2; + + channelGroup.addWidget(new ColorBlockWidget(currentX, 0, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT) + .setColorSupplier(this::getColor)); + currentX += SMALL_WIDGET_WIDTH + 2; + + int textInputWidth = channelGroupWidth - currentX - SMALL_WIDGET_WIDTH - 2; + var confirmTextInputWidget = new ConfirmTextInputWidget(currentX, 0, textInputWidth, WIDGET_HEIGHT, + channelName, + text -> { + if (text != null && !text.isEmpty()) { + setChannelName(text); + } + }, + text -> { + if (text == null || !COLOR_INPUT_PATTERN.matcher(text).matches() || text.length() > 8) { + return VirtualTank.DEFAULT_COLOR; + } + return text; + } + ).setInputBoxTooltips(description); + channelGroup.addWidget(confirmTextInputWidget); + group.addWidget(channelGroup); + + + group.addWidget(new ToggleButtonWidget(116, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + GuiTextures.BUTTON_POWER, this::isWorkingEnabled, this::setWorkingEnabled)); + group.addWidget(new EnumSelectorWidget<>(146, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + List.of(IO.IN, IO.OUT), io, this::setIo)); + group.addWidget(new EnumSelectorWidget<>(146, 107, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + ManualIOMode.VALUES, manualIOMode, this::setManualIOMode) + .setHoverTooltips("cover.universal.manual_import_export.mode.description")); + + buildAdditionalUI(group); + return group; + } + + protected void buildAdditionalUI(WidgetGroup group) { + } + + protected abstract String getUITitle(); + + protected int getColor() { + var colorString = this.channelName; + colorString = String.format("%8s", colorString).replace(' ', '0'); + + if (colorString.length() > 8) { + colorString = colorString.substring(colorString.length() - 8); + } + + int alpha = Integer.parseInt(colorString.substring(6, 8), 16); + int red = Integer.parseInt(colorString.substring(0, 2), 16); + int green = Integer.parseInt(colorString.substring(2, 4), 16); + int blue = Integer.parseInt(colorString.substring(4, 6), 16); + + return (alpha << 24) | (red << 16) | (green << 8) | blue; + } + + @Override + public @NotNull ManagedFieldHolder getFieldHolder() { + return MANAGED_FIELD_HOLDER; + } +} diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java new file mode 100644 index 0000000000..7f12bc3e43 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -0,0 +1,185 @@ +package com.gregtechceu.gtceu.common.cover.ender; + +import com.gregtechceu.gtceu.api.capability.ICoverable; +import com.gregtechceu.gtceu.api.cover.CoverDefinition; +import com.gregtechceu.gtceu.api.cover.filter.FilterHandler; +import com.gregtechceu.gtceu.api.cover.filter.FilterHandlers; +import com.gregtechceu.gtceu.api.cover.filter.FluidFilter; +import com.gregtechceu.gtceu.api.gui.GuiTextures; +import com.gregtechceu.gtceu.api.gui.widget.TankWidget; +import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; +import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; +import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VisualTank; +import com.gregtechceu.gtceu.api.transfer.fluid.IFluidHandlerModifiable; +import com.gregtechceu.gtceu.utils.GTTransferUtils; +import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; +import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; +import com.lowdragmc.lowdraglib.syncdata.annotation.LazyManaged; +import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; +import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; +import net.minecraft.core.Direction; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.item.ItemStack; +import net.minecraftforge.fluids.FluidStack; +import net.minecraftforge.fluids.FluidUtil; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import javax.annotation.ParametersAreNonnullByDefault; + +@ParametersAreNonnullByDefault +public class EnderFluidLinkCover extends CoverAbstractEnderLink { + public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(EnderFluidLinkCover.class, + CoverAbstractEnderLink.MANAGED_FIELD_HOLDER); + public static final int TRANSFER_RATE = 8000; // mB/t + + @Persisted + @DescSynced + @LazyManaged + protected final VisualTank visualTank = new VisualTank(); + @Persisted + @DescSynced + protected final FilterHandler filterHandler; + protected int mBLeftToTransferLastSecond; + + public EnderFluidLinkCover(CoverDefinition definition, ICoverable coverHolder, Direction attachedSide) { + super(definition, coverHolder, attachedSide); + this.mBLeftToTransferLastSecond = TRANSFER_RATE * 20; + filterHandler = FilterHandlers.fluid(this); + } + + @Override + public boolean canAttach() { + return FluidUtil.getFluidHandler(coverHolder.getLevel(), coverHolder.getPos(), attachedSide).isPresent(); + } + + @Override + protected EntryTypes getEntryType() { + return EntryTypes.ENDER_FLUID; + } + + @Override + protected void updateEntry() { + var reg = VirtualEnderRegistry.getInstance(); + if (reg == null) return; + var tank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, this.channelName); + this.visualTank.setVirtualTank(tank); + this.visualTank.getVirtualTank().setColor(this.channelName); + markAsDirty(); + markDirty("visualTank"); + this.visualTank.setFluid(this.visualTank.getVirtualTank().getFluid()); + } + + @Override + protected void transfer() { + long timer = coverHolder.getOffsetTimer(); + if (mBLeftToTransferLastSecond > 0) { + int platformTransferredFluid = doTransferFluids(mBLeftToTransferLastSecond); + this.mBLeftToTransferLastSecond -= platformTransferredFluid; + } + + if (timer % 20 == 0) { + this.mBLeftToTransferLastSecond = TRANSFER_RATE * 20; + } + } + + protected @Nullable IFluidHandlerModifiable getOwnFluidHandler() { + return coverHolder.getFluidHandlerCap(attachedSide, false); + } + + private int doTransferFluids(int platformTransferLimit) { + var ownFluidHandler = getOwnFluidHandler(); + + if (ownFluidHandler != null) { + return switch (io) { + case IN -> GTTransferUtils.transferFluidsFiltered(ownFluidHandler, visualTank.getVirtualTank(), + filterHandler.getFilter(), platformTransferLimit); + case OUT -> GTTransferUtils.transferFluidsFiltered(visualTank.getVirtualTank(), ownFluidHandler, + filterHandler.getFilter(), platformTransferLimit); + default -> 0; + }; + + } + return 0; + } + + @Override + public void onAttached(ItemStack itemStack, ServerPlayer player) { + super.onAttached(itemStack, player); + playerUUID = player.getUUID(); + } + + @Override + public @NotNull ManagedFieldHolder getFieldHolder() { + return MANAGED_FIELD_HOLDER; + } + + ////////////////////////////////////// + // *********** GUI ************ // + + /// /////////////////////////////////// + + @Override + protected void buildAdditionalUI(WidgetGroup group) { + group.addWidget(new TankWidget(visualTank, 0, 146, 20, 20, 20, + true, true).setBackground(GuiTextures.FLUID_SLOT)); + + group.addWidget(filterHandler.createFilterSlotUI(117, 108)); + group.addWidget(filterHandler.createFilterConfigUI(10, 72, 156, 60)); + } + + @NotNull + @Override + protected String getUITitle() { + return "cover.ender_fluid_link.title"; + } + +// damn I can't make the list panel work in the server side +// private SelectableWidgetGroup createVisualTankWidget(VisualTank tank, int y) { +// final int TOTAL_WIDTH = 116; +// final int BUTTON_SIZE = 20; +// final int MARGIN = 2; +// +// int currentX = 0; +// int availableWidth = TOTAL_WIDTH - BUTTON_SIZE + MARGIN; +// +// SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(0, y, TOTAL_WIDTH, BUTTON_SIZE){ +// @Override +// public void drawInForeground(@NotNull GuiGraphics graphics, int mouseX, int mouseY, float partialTicks) { +// super.drawInForeground(graphics, mouseX, mouseY, partialTicks); +// if (super.isSelected) +// DrawerHelper.drawBorder(graphics, getPositionX(), getPositionY(), TOTAL_WIDTH, BUTTON_SIZE, 0xFFFFFFFF, 1); +// } +// }; +// var name = tank.getVirtualTank().getColorStr(); +// +// // Color block +// channelGroup.addWidget(new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) +// .setCurrentColor(tank.getVirtualTank().getColor())); +// currentX += BUTTON_SIZE + MARGIN; +// +// // Text box +// int textBoxWidth = availableWidth; +// textBoxWidth -= BUTTON_SIZE + MARGIN; +// if (tank.getFluidAmount() == 0) { +// textBoxWidth -= BUTTON_SIZE + MARGIN; +// } +// channelGroup.addWidget( +// new TextBoxWidget(currentX, 6, textBoxWidth, List.of(name)).setCenter(true)); +// currentX += textBoxWidth + MARGIN; +// +// // Tank slot +// channelGroup.addWidget(new TankWidget(tank, currentX, 0, +// BUTTON_SIZE, BUTTON_SIZE, false, false) +// .setBackground(GuiTextures.FLUID_SLOT)); +// currentX += BUTTON_SIZE + MARGIN; +// +// // Remove button (if tank is empty) +// if (tank.getFluidAmount() == 0) { +// channelGroup.addWidget(new ButtonWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE, +// GuiTextures.BUTTON_INT_CIRCUIT_MINUS, cd -> removeChannel(tank))); +// } +// return channelGroup; +// } +} diff --git a/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java b/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java index 36fb5c432c..1a9bfb1da7 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java +++ b/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java @@ -10,14 +10,13 @@ import com.gregtechceu.gtceu.client.renderer.cover.*; import com.gregtechceu.gtceu.common.cover.*; import com.gregtechceu.gtceu.common.cover.detector.*; +import com.gregtechceu.gtceu.common.cover.ender.EnderFluidLinkCover; import com.gregtechceu.gtceu.common.cover.voiding.AdvancedFluidVoidingCover; import com.gregtechceu.gtceu.common.cover.voiding.AdvancedItemVoidingCover; import com.gregtechceu.gtceu.common.cover.voiding.FluidVoidingCover; import com.gregtechceu.gtceu.common.cover.voiding.ItemVoidingCover; - -import net.minecraftforge.fml.ModLoader; - import it.unimi.dsi.fastutil.ints.Int2ObjectFunction; +import net.minecraftforge.fml.ModLoader; import java.util.Arrays; import java.util.Locale; @@ -54,6 +53,10 @@ public class GTCovers { "infinite_water", InfiniteWaterCover::new, new SimpleCoverRenderer(GTCEu.id("block/cover/overlay_infinite_water"))); + public final static CoverDefinition ENDER_FLUID_LINK = register( + "ender_fluid_link", EnderFluidLinkCover::new, + new SimpleCoverRenderer(GTCEu.id("block/cover/overlay_ender_fluid_link"))); + public final static CoverDefinition SHUTTER = register( "shutter", ShutterCover::new, new SimpleCoverRenderer(GTCEu.id("block/cover/overlay_shutter"))); diff --git a/src/main/java/com/gregtechceu/gtceu/common/data/GTItems.java b/src/main/java/com/gregtechceu/gtceu/common/data/GTItems.java index b121857b4e..0404fbf480 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/data/GTItems.java +++ b/src/main/java/com/gregtechceu/gtceu/common/data/GTItems.java @@ -1,5 +1,8 @@ package com.gregtechceu.gtceu.common.data; +import com.google.common.collect.ArrayTable; +import com.google.common.collect.ImmutableTable; +import com.google.common.collect.Table; import com.gregtechceu.gtceu.GTCEu; import com.gregtechceu.gtceu.api.GTCEuAPI; import com.gregtechceu.gtceu.api.GTValues; @@ -39,10 +42,17 @@ import com.gregtechceu.gtceu.utils.FormattingUtil; import com.gregtechceu.gtceu.utils.GTUtil; import com.gregtechceu.gtceu.utils.SupplierMemoizer; - import com.lowdragmc.lowdraglib.LDLib; import com.lowdragmc.lowdraglib.gui.texture.ItemStackTexture; - +import com.tterrag.registrate.builders.ItemBuilder; +import com.tterrag.registrate.providers.DataGenContext; +import com.tterrag.registrate.providers.ProviderType; +import com.tterrag.registrate.providers.RegistrateLangProvider; +import com.tterrag.registrate.util.entry.ItemEntry; +import com.tterrag.registrate.util.entry.ItemProviderEntry; +import com.tterrag.registrate.util.nullness.NonNullBiConsumer; +import com.tterrag.registrate.util.nullness.NonNullConsumer; +import com.tterrag.registrate.util.nullness.NonNullFunction; import net.minecraft.client.color.item.ItemColor; import net.minecraft.client.renderer.item.ItemProperties; import net.minecraft.client.renderer.item.ItemPropertyFunction; @@ -66,19 +76,6 @@ import net.minecraftforge.fluids.FluidStack; import net.minecraftforge.fluids.FluidType; import net.minecraftforge.fluids.FluidUtil; - -import com.google.common.collect.ArrayTable; -import com.google.common.collect.ImmutableTable; -import com.google.common.collect.Table; -import com.tterrag.registrate.builders.ItemBuilder; -import com.tterrag.registrate.providers.DataGenContext; -import com.tterrag.registrate.providers.ProviderType; -import com.tterrag.registrate.providers.RegistrateLangProvider; -import com.tterrag.registrate.util.entry.ItemEntry; -import com.tterrag.registrate.util.entry.ItemProviderEntry; -import com.tterrag.registrate.util.nullness.NonNullBiConsumer; -import com.tterrag.registrate.util.nullness.NonNullConsumer; -import com.tterrag.registrate.util.nullness.NonNullFunction; import org.apache.commons.lang3.StringUtils; import org.jetbrains.annotations.NotNull; @@ -649,7 +646,7 @@ public Component getItemName(ItemStack stack) { new ItemFluidContainer())) .onRegister(modelPredicate(GTCEu.id("lighter_open"), (itemStack) -> itemStack.getOrCreateTag().getBoolean(LighterBehavior.LIGHTER_OPEN) ? 1.0f : 0.0f)) - .register();; + .register(); public static ItemEntry CARBON_FIBERS = REGISTRATE.item("carbon_fibers", Item::new) .onRegister(compassNodeExist(GTCompassSections.MISC, "raw_carbon_fibers")).lang("Raw Carbon Fibers") @@ -975,7 +972,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_HV = REGISTRATE.item("hv_electric_pump", ComponentItem::create) .lang("HV Electric Pump") .onRegister(attach(new CoverPlaceBehavior(GTCovers.PUMPS[2]))) @@ -986,7 +983,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_EV = REGISTRATE.item("ev_electric_pump", ComponentItem::create) .lang("EV Electric Pump") .onRegister(attach(new CoverPlaceBehavior(GTCovers.PUMPS[3]))) @@ -997,7 +994,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_IV = REGISTRATE.item("iv_electric_pump", ComponentItem::create) .lang("IV Electric Pump") .onRegister(attach(new CoverPlaceBehavior(GTCovers.PUMPS[4]))) @@ -1008,7 +1005,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_LuV = REGISTRATE .item("luv_electric_pump", ComponentItem::create) .lang("LuV Electric Pump") @@ -1020,7 +1017,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_ZPM = REGISTRATE .item("zpm_electric_pump", ComponentItem::create) .lang("ZPM Electric Pump") @@ -1032,7 +1029,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_UV = REGISTRATE.item("uv_electric_pump", ComponentItem::create) .lang("UV Electric Pump") .onRegister(attach(new CoverPlaceBehavior(GTCovers.PUMPS[7]))) @@ -1044,7 +1041,7 @@ public Component getItemName(ItemStack stack) { }))) .onRegister(compassNodeExist(GTCompassSections.COVERS, "pump", GTCompassNodes.COVER)) .tag(CustomTags.ELECTRIC_PUMPS) - .register();; + .register(); public static ItemEntry ELECTRIC_PUMP_UHV = GTCEuAPI.isHighTier() ? REGISTRATE.item("uhv_electric_pump", ComponentItem::create) @@ -2232,7 +2229,8 @@ public Component getItemName(ItemStack stack) { .item("ender_fluid_link_cover", ComponentItem::create) .lang("Ender Fluid Link") .onRegister(compassNode(GTCompassSections.COVERS, GTCompassNodes.COVER)) - .register(); + .onRegister(attach(new CoverPlaceBehavior(GTCovers.ENDER_FLUID_LINK))).register(); + public static ItemEntry COVER_FLUID_VOIDING = REGISTRATE .item("fluid_voiding_cover", ComponentItem::create) .lang("Fluid Voiding Cover") @@ -2969,8 +2967,8 @@ public static NonNullConsumer modelPredicate(ResourceLocatio public static void registerToolTier(MaterialToolTier tier, ResourceLocation id, Collection before, Collection after) { - TierSortingRegistry.registerTier(tier, id, Arrays.asList((Object[]) before.toArray(ResourceLocation[]::new)), - Arrays.asList((Object[]) after.toArray(ResourceLocation[]::new))); + TierSortingRegistry.registerTier(tier, id, Arrays.asList(before.toArray(ResourceLocation[]::new)), + Arrays.asList(after.toArray(ResourceLocation[]::new))); } public static ResourceLocation getTierName(Tier tier) { diff --git a/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java b/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java index af70b7c113..15ea030a3b 100644 --- a/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java +++ b/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java @@ -20,6 +20,7 @@ import com.gregtechceu.gtceu.api.item.armor.ArmorComponentItem; import com.gregtechceu.gtceu.api.machine.MetaMachine; import com.gregtechceu.gtceu.api.machine.feature.IInteractedMachine; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; import com.gregtechceu.gtceu.api.pattern.MultiblockWorldSavedData; import com.gregtechceu.gtceu.api.registry.GTRegistries; import com.gregtechceu.gtceu.common.capability.EnvironmentalHazardSavedData; @@ -36,7 +37,10 @@ import com.gregtechceu.gtceu.common.item.ToggleEnergyConsumerBehavior; import com.gregtechceu.gtceu.common.item.armor.IJetpack; import com.gregtechceu.gtceu.common.network.GTNetwork; -import com.gregtechceu.gtceu.common.network.packets.*; +import com.gregtechceu.gtceu.common.network.packets.SPacketSendWorldID; +import com.gregtechceu.gtceu.common.network.packets.SPacketSyncBedrockOreVeins; +import com.gregtechceu.gtceu.common.network.packets.SPacketSyncFluidVeins; +import com.gregtechceu.gtceu.common.network.packets.SPacketSyncOreVeins; import com.gregtechceu.gtceu.common.network.packets.hazard.SPacketAddHazardZone; import com.gregtechceu.gtceu.common.network.packets.hazard.SPacketRemoveHazardZone; import com.gregtechceu.gtceu.common.network.packets.hazard.SPacketSyncLevelHazards; @@ -49,7 +53,8 @@ import com.gregtechceu.gtceu.integration.map.WaypointManager; import com.gregtechceu.gtceu.integration.map.cache.server.ServerCache; import com.gregtechceu.gtceu.utils.TaskHandler; - +import com.tterrag.registrate.util.entry.BlockEntry; +import com.tterrag.registrate.util.entry.ItemEntry; import net.minecraft.core.Direction; import net.minecraft.core.registries.Registries; import net.minecraft.nbt.CompoundTag; @@ -89,9 +94,6 @@ import net.minecraftforge.fml.common.Mod; import net.minecraftforge.items.IItemHandler; import net.minecraftforge.registries.MissingMappingsEvent; - -import com.tterrag.registrate.util.entry.BlockEntry; -import com.tterrag.registrate.util.entry.ItemEntry; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -281,6 +283,7 @@ public static void serverStarting(ServerStartingEvent event) { @SubscribeEvent public static void serverStopped(ServerStoppedEvent event) { ServerCache.instance.clear(); + VirtualEnderRegistry.release(); } @SubscribeEvent From 3ad93a9d29d44d497fbb72daf1abe82279a0a81f Mon Sep 17 00:00:00 2001 From: Arborsm Date: Fri, 6 Dec 2024 22:42:03 +0800 Subject: [PATCH 02/14] spotless --- .../api/gui/widget/ColorBlockWidget.java | 9 +- .../gui/widget/ConfirmTextInputWidget.java | 5 +- .../api/misc/virtualregistry/EntryTypes.java | 4 +- .../virtualregistry/VirtualEnderRegistry.java | 9 +- .../misc/virtualregistry/VirtualEntry.java | 3 +- .../virtualregistry/VirtualRegistryMap.java | 10 +- .../virtualregistry/entries/VirtualTank.java | 6 +- .../virtualregistry/entries/VisualTank.java | 9 +- .../cover/ender/CoverAbstractEnderLink.java | 18 ++-- .../cover/ender/EnderFluidLinkCover.java | 100 +++++++++--------- .../gtceu/common/data/GTCovers.java | 4 +- .../gtceu/forge/ForgeCommonEventListener.java | 6 +- 12 files changed, 106 insertions(+), 77 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java index 1d42cb6fcd..9814698421 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ColorBlockWidget.java @@ -2,12 +2,14 @@ import com.lowdragmc.lowdraglib.gui.util.DrawerHelper; import com.lowdragmc.lowdraglib.gui.widget.Widget; -import lombok.Getter; -import lombok.Setter; -import lombok.experimental.Accessors; + import net.minecraft.client.gui.GuiGraphics; import net.minecraftforge.api.distmarker.Dist; import net.minecraftforge.api.distmarker.OnlyIn; + +import lombok.Getter; +import lombok.Setter; +import lombok.experimental.Accessors; import org.jetbrains.annotations.NotNull; import java.util.function.IntSupplier; @@ -15,6 +17,7 @@ @Setter @Accessors(chain = true) public class ColorBlockWidget extends Widget { + private IntSupplier colorSupplier; @Getter private int currentColor; diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java index 87d4e9e906..a9ddc6b2cf 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java @@ -1,10 +1,12 @@ package com.gregtechceu.gtceu.api.gui.widget; import com.gregtechceu.gtceu.api.gui.GuiTextures; + import com.lowdragmc.lowdraglib.gui.texture.GuiTextureGroup; import com.lowdragmc.lowdraglib.gui.widget.ButtonWidget; import com.lowdragmc.lowdraglib.gui.widget.TextFieldWidget; import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; + import lombok.AccessLevel; import lombok.Getter; import lombok.Setter; @@ -26,7 +28,8 @@ public class ConfirmTextInputWidget extends WidgetGroup { private String inputText = ""; private String hoverText = ""; - public ConfirmTextInputWidget(int x, int y, int width, int height, String text, Consumer textResponder, Function validator) { + public ConfirmTextInputWidget(int x, int y, int width, int height, String text, Consumer textResponder, + Function validator) { super(x, y, width, height); this.textResponder = textResponder; this.validator = validator; diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java index 77c4afd17d..c2e3e3b560 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java @@ -2,9 +2,11 @@ import com.gregtechceu.gtceu.GTCEu; import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; -import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap; + import net.minecraft.nbt.CompoundTag; import net.minecraft.resources.ResourceLocation; + +import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap; import org.jetbrains.annotations.Nullable; import java.util.Map; diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java index e5ef9bef42..e38e3ef206 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java @@ -1,9 +1,11 @@ package com.gregtechceu.gtceu.api.misc.virtualregistry; import com.gregtechceu.gtceu.GTCEu; + import net.minecraft.nbt.CompoundTag; import net.minecraft.world.level.saveddata.SavedData; import net.minecraftforge.server.ServerLifecycleHooks; + import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -14,14 +16,14 @@ import java.util.function.Predicate; public class VirtualEnderRegistry extends SavedData { + private static final String DATA_ID = GTCEu.MOD_ID + ".virtual_entry_data"; private static final String PUBLIC_KEY = "Public"; private static final String PRIVATE_KEY = "Private"; private static volatile VirtualEnderRegistry data; private final Map VIRTUAL_REGISTRIES = new HashMap<>(); - public VirtualEnderRegistry() { - } + public VirtualEnderRegistry() {} public VirtualEnderRegistry(CompoundTag name) { readFromNBT(name); @@ -84,7 +86,8 @@ public void deleteEntry(@Nullable UUID owner, EntryTypes type, String name) { owner == null ? "public" : String.format("private [%s]", owner), name, type); } - public void deleteEntryIf(@Nullable UUID owner, EntryTypes type, String name, Predicate shouldDelete) { + public void deleteEntryIf(@Nullable UUID owner, EntryTypes type, String name, + Predicate shouldDelete) { T entry = getEntry(owner, type, name); if (entry != null && shouldDelete.test(entry)) deleteEntry(owner, type, name); } diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java index 57097e44e8..0c4cf56a9c 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java @@ -1,8 +1,9 @@ package com.gregtechceu.gtceu.api.misc.virtualregistry; -import lombok.Getter; import net.minecraft.nbt.CompoundTag; import net.minecraftforge.common.util.INBTSerializable; + +import lombok.Getter; import org.jetbrains.annotations.NotNull; public abstract class VirtualEntry implements INBTSerializable { diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java index 9d336ff6d5..af026dca63 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java @@ -2,6 +2,7 @@ import net.minecraft.nbt.CompoundTag; import net.minecraftforge.common.util.INBTSerializable; + import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -12,10 +13,10 @@ import java.util.concurrent.ConcurrentHashMap; public class VirtualRegistryMap implements INBTSerializable { + private final Map, Map> registryMap = new ConcurrentHashMap<>(); - public VirtualRegistryMap() { - } + public VirtualRegistryMap() {} public VirtualRegistryMap(CompoundTag tag) { deserializeNBT(tag); @@ -68,9 +69,8 @@ public Set getEntryNames(EntryTypes type) { @Override public void deserializeNBT(CompoundTag nbt) { for (String entryTypeString : nbt.getAllKeys()) { - EntryTypes type = entryTypeString.contains(":") - ? EntryTypes.fromLocation(entryTypeString) - : EntryTypes.fromString(entryTypeString); + EntryTypes type = entryTypeString.contains(":") ? EntryTypes.fromLocation(entryTypeString) : + EntryTypes.fromString(entryTypeString); if (type == null) continue; diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java index 3a4c6c1636..d89ff125e1 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java @@ -2,15 +2,18 @@ import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEntry; -import lombok.Setter; + import net.minecraft.nbt.CompoundTag; import net.minecraftforge.fluids.FluidStack; import net.minecraftforge.fluids.IFluidTank; import net.minecraftforge.fluids.capability.IFluidHandler; import net.minecraftforge.fluids.capability.templates.FluidTank; + +import lombok.Setter; import org.jetbrains.annotations.NotNull; public class VirtualTank extends VirtualEntry implements IFluidTank, IFluidHandler { + public static final int DEFAULT_CAPACITY = 64000; // 64B protected static final String CAPACITY_KEY = "capacity"; protected static final String FLUID_KEY = "fluid"; @@ -23,6 +26,7 @@ public class VirtualTank extends VirtualEntry implements IFluidTank, IFluidHandl public VirtualTank(int capacity) { this.capacity = capacity; fluidTank = new FluidTank(this.capacity) { + @Override protected void onContentsChanged() { super.onContentsChanged(); diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java index 93dba6ad8f..84ae73fe7b 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java @@ -1,15 +1,18 @@ package com.gregtechceu.gtceu.api.misc.virtualregistry.entries; import com.lowdragmc.lowdraglib.syncdata.ITagSerializable; -import lombok.Getter; -import lombok.Setter; -import lombok.experimental.Accessors; + import net.minecraft.nbt.CompoundTag; import net.minecraftforge.common.util.INBTSerializable; import net.minecraftforge.fluids.capability.templates.FluidTank; +import lombok.Getter; +import lombok.Setter; +import lombok.experimental.Accessors; + @Accessors(chain = true) public class VisualTank extends FluidTank implements INBTSerializable, ITagSerializable { + @Getter private VirtualTank virtualTank; @Setter diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java index 8ccee0ae1c..de8fb4558d 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java @@ -17,6 +17,7 @@ import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEntry; import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; import com.gregtechceu.gtceu.common.cover.data.ManualIOMode; + import com.lowdragmc.lowdraglib.gui.widget.LabelWidget; import com.lowdragmc.lowdraglib.gui.widget.Widget; import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; @@ -24,18 +25,22 @@ import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; import com.lowdragmc.lowdraglib.syncdata.annotation.RequireRerender; import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; -import lombok.Getter; -import lombok.Setter; + import net.minecraft.core.Direction; import net.minecraft.server.level.ServerPlayer; import net.minecraft.world.item.ItemStack; + +import lombok.Getter; +import lombok.Setter; import org.jetbrains.annotations.NotNull; import java.util.List; import java.util.UUID; import java.util.regex.Pattern; -public abstract class CoverAbstractEnderLink extends CoverBehavior implements IUICover, IControllable { +public abstract class CoverAbstractEnderLink extends CoverBehavior + implements IUICover, IControllable { + public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(CoverAbstractEnderLink.class, CoverBehavior.MANAGED_FIELD_HOLDER); public static final Pattern COLOR_INPUT_PATTERN = Pattern.compile("[0-9a-fA-F]*"); @@ -192,12 +197,10 @@ public Widget createUIWidget() { return VirtualTank.DEFAULT_COLOR; } return text; - } - ).setInputBoxTooltips(description); + }).setInputBoxTooltips(description); channelGroup.addWidget(confirmTextInputWidget); group.addWidget(channelGroup); - group.addWidget(new ToggleButtonWidget(116, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, GuiTextures.BUTTON_POWER, this::isWorkingEnabled, this::setWorkingEnabled)); group.addWidget(new EnumSelectorWidget<>(146, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, @@ -210,8 +213,7 @@ public Widget createUIWidget() { return group; } - protected void buildAdditionalUI(WidgetGroup group) { - } + protected void buildAdditionalUI(WidgetGroup group) {} protected abstract String getUITitle(); diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index 7f12bc3e43..7af0abbd4e 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -13,16 +13,19 @@ import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VisualTank; import com.gregtechceu.gtceu.api.transfer.fluid.IFluidHandlerModifiable; import com.gregtechceu.gtceu.utils.GTTransferUtils; + import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; import com.lowdragmc.lowdraglib.syncdata.annotation.LazyManaged; import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; + import net.minecraft.core.Direction; import net.minecraft.server.level.ServerPlayer; import net.minecraft.world.item.ItemStack; import net.minecraftforge.fluids.FluidStack; import net.minecraftforge.fluids.FluidUtil; + import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -30,6 +33,7 @@ @ParametersAreNonnullByDefault public class EnderFluidLinkCover extends CoverAbstractEnderLink { + public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(EnderFluidLinkCover.class, CoverAbstractEnderLink.MANAGED_FIELD_HOLDER); public static final int TRANSFER_RATE = 8000; // mB/t @@ -116,7 +120,7 @@ public void onAttached(ItemStack itemStack, ServerPlayer player) { } ////////////////////////////////////// - // *********** GUI ************ // + // *********** GUI ************ // /// /////////////////////////////////// @@ -135,51 +139,51 @@ protected String getUITitle() { return "cover.ender_fluid_link.title"; } -// damn I can't make the list panel work in the server side -// private SelectableWidgetGroup createVisualTankWidget(VisualTank tank, int y) { -// final int TOTAL_WIDTH = 116; -// final int BUTTON_SIZE = 20; -// final int MARGIN = 2; -// -// int currentX = 0; -// int availableWidth = TOTAL_WIDTH - BUTTON_SIZE + MARGIN; -// -// SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(0, y, TOTAL_WIDTH, BUTTON_SIZE){ -// @Override -// public void drawInForeground(@NotNull GuiGraphics graphics, int mouseX, int mouseY, float partialTicks) { -// super.drawInForeground(graphics, mouseX, mouseY, partialTicks); -// if (super.isSelected) -// DrawerHelper.drawBorder(graphics, getPositionX(), getPositionY(), TOTAL_WIDTH, BUTTON_SIZE, 0xFFFFFFFF, 1); -// } -// }; -// var name = tank.getVirtualTank().getColorStr(); -// -// // Color block -// channelGroup.addWidget(new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) -// .setCurrentColor(tank.getVirtualTank().getColor())); -// currentX += BUTTON_SIZE + MARGIN; -// -// // Text box -// int textBoxWidth = availableWidth; -// textBoxWidth -= BUTTON_SIZE + MARGIN; -// if (tank.getFluidAmount() == 0) { -// textBoxWidth -= BUTTON_SIZE + MARGIN; -// } -// channelGroup.addWidget( -// new TextBoxWidget(currentX, 6, textBoxWidth, List.of(name)).setCenter(true)); -// currentX += textBoxWidth + MARGIN; -// -// // Tank slot -// channelGroup.addWidget(new TankWidget(tank, currentX, 0, -// BUTTON_SIZE, BUTTON_SIZE, false, false) -// .setBackground(GuiTextures.FLUID_SLOT)); -// currentX += BUTTON_SIZE + MARGIN; -// -// // Remove button (if tank is empty) -// if (tank.getFluidAmount() == 0) { -// channelGroup.addWidget(new ButtonWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE, -// GuiTextures.BUTTON_INT_CIRCUIT_MINUS, cd -> removeChannel(tank))); -// } -// return channelGroup; -// } + // damn I can't make the list panel work in the server side + // private SelectableWidgetGroup createVisualTankWidget(VisualTank tank, int y) { + // final int TOTAL_WIDTH = 116; + // final int BUTTON_SIZE = 20; + // final int MARGIN = 2; + // + // int currentX = 0; + // int availableWidth = TOTAL_WIDTH - BUTTON_SIZE + MARGIN; + // + // SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(0, y, TOTAL_WIDTH, BUTTON_SIZE){ + // @Override + // public void drawInForeground(@NotNull GuiGraphics graphics, int mouseX, int mouseY, float partialTicks) { + // super.drawInForeground(graphics, mouseX, mouseY, partialTicks); + // if (super.isSelected) + // DrawerHelper.drawBorder(graphics, getPositionX(), getPositionY(), TOTAL_WIDTH, BUTTON_SIZE, 0xFFFFFFFF, 1); + // } + // }; + // var name = tank.getVirtualTank().getColorStr(); + // + // // Color block + // channelGroup.addWidget(new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) + // .setCurrentColor(tank.getVirtualTank().getColor())); + // currentX += BUTTON_SIZE + MARGIN; + // + // // Text box + // int textBoxWidth = availableWidth; + // textBoxWidth -= BUTTON_SIZE + MARGIN; + // if (tank.getFluidAmount() == 0) { + // textBoxWidth -= BUTTON_SIZE + MARGIN; + // } + // channelGroup.addWidget( + // new TextBoxWidget(currentX, 6, textBoxWidth, List.of(name)).setCenter(true)); + // currentX += textBoxWidth + MARGIN; + // + // // Tank slot + // channelGroup.addWidget(new TankWidget(tank, currentX, 0, + // BUTTON_SIZE, BUTTON_SIZE, false, false) + // .setBackground(GuiTextures.FLUID_SLOT)); + // currentX += BUTTON_SIZE + MARGIN; + // + // // Remove button (if tank is empty) + // if (tank.getFluidAmount() == 0) { + // channelGroup.addWidget(new ButtonWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE, + // GuiTextures.BUTTON_INT_CIRCUIT_MINUS, cd -> removeChannel(tank))); + // } + // return channelGroup; + // } } diff --git a/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java b/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java index 1a9bfb1da7..f9af96131f 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java +++ b/src/main/java/com/gregtechceu/gtceu/common/data/GTCovers.java @@ -15,9 +15,11 @@ import com.gregtechceu.gtceu.common.cover.voiding.AdvancedItemVoidingCover; import com.gregtechceu.gtceu.common.cover.voiding.FluidVoidingCover; import com.gregtechceu.gtceu.common.cover.voiding.ItemVoidingCover; -import it.unimi.dsi.fastutil.ints.Int2ObjectFunction; + import net.minecraftforge.fml.ModLoader; +import it.unimi.dsi.fastutil.ints.Int2ObjectFunction; + import java.util.Arrays; import java.util.Locale; diff --git a/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java b/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java index 15ea030a3b..2346fb9b26 100644 --- a/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java +++ b/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java @@ -53,8 +53,7 @@ import com.gregtechceu.gtceu.integration.map.WaypointManager; import com.gregtechceu.gtceu.integration.map.cache.server.ServerCache; import com.gregtechceu.gtceu.utils.TaskHandler; -import com.tterrag.registrate.util.entry.BlockEntry; -import com.tterrag.registrate.util.entry.ItemEntry; + import net.minecraft.core.Direction; import net.minecraft.core.registries.Registries; import net.minecraft.nbt.CompoundTag; @@ -94,6 +93,9 @@ import net.minecraftforge.fml.common.Mod; import net.minecraftforge.items.IItemHandler; import net.minecraftforge.registries.MissingMappingsEvent; + +import com.tterrag.registrate.util.entry.BlockEntry; +import com.tterrag.registrate.util.entry.ItemEntry; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; From 180f7618bf9237b349ea5740a3b2c8c18a6e906b Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sat, 7 Dec 2024 00:02:24 +0800 Subject: [PATCH 03/14] use machine owner --- .../api/machine/MachineCoverContainer.java | 1 + .../api/misc/virtualregistry/EntryTypes.java | 4 +-- .../virtualregistry/VirtualEnderRegistry.java | 1 - .../misc/virtualregistry/VirtualEntry.java | 18 +++------- .../virtualregistry/VirtualRegistryMap.java | 4 ++- ...rLink.java => AbstractEnderLinkCover.java} | 34 ++++++++++++------- .../cover/ender/EnderFluidLinkCover.java | 21 +++++------- .../common/machine/owner/IMachineOwner.java | 3 ++ 8 files changed, 44 insertions(+), 42 deletions(-) rename src/main/java/com/gregtechceu/gtceu/common/cover/ender/{CoverAbstractEnderLink.java => AbstractEnderLinkCover.java} (90%) diff --git a/src/main/java/com/gregtechceu/gtceu/api/machine/MachineCoverContainer.java b/src/main/java/com/gregtechceu/gtceu/api/machine/MachineCoverContainer.java index 12d216c0ef..326eaa0c03 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/machine/MachineCoverContainer.java +++ b/src/main/java/com/gregtechceu/gtceu/api/machine/MachineCoverContainer.java @@ -40,6 +40,7 @@ public class MachineCoverContainer implements ICoverable, IEnhancedManaged { public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(MachineCoverContainer.class); @Getter private final FieldManagedStorage syncStorage = new FieldManagedStorage(this); + @Getter private final MetaMachine machine; @DescSynced @Persisted diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java index c2e3e3b560..9910f108a8 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/EntryTypes.java @@ -33,8 +33,8 @@ public static EntryTypes fromString(String name) { } @Nullable - public static EntryTypes fromLocation(String location) { - return TYPES_MAP.getOrDefault(new ResourceLocation(location), null); + public static EntryTypes fromLocation(ResourceLocation location) { + return TYPES_MAP.getOrDefault(location, null); } public static EntryTypes addEntryType(ResourceLocation location, Supplier supplier) { diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java index e38e3ef206..d76b54600b 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEnderRegistry.java @@ -35,7 +35,6 @@ public static VirtualEnderRegistry getInstance() { if (server != null) { data = server.overworld().getDataStorage() .computeIfAbsent(VirtualEnderRegistry::new, VirtualEnderRegistry::new, DATA_ID); - GTCEu.LOGGER.debug("VirtualEnderRegistry has been successfully loaded"); } } diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java index 0c4cf56a9c..40307265b7 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java @@ -4,20 +4,21 @@ import net.minecraftforge.common.util.INBTSerializable; import lombok.Getter; +import lombok.Setter; import org.jetbrains.annotations.NotNull; +@Getter public abstract class VirtualEntry implements INBTSerializable { public static final String DEFAULT_COLOR = "FFFFFFFF"; protected static final String COLOR_KEY = "color"; protected static final String DESC_KEY = "description"; - @Getter - private int color = 0xFFFFFFFF; - @Getter - private String colorStr = DEFAULT_COLOR; + @Setter @NotNull private String description = ""; + private int color = 0xFFFFFFFF; + private String colorStr = DEFAULT_COLOR; public abstract EntryTypes getType(); @@ -39,15 +40,6 @@ private int parseColor(String s) { return (int) tmp; } - @NotNull - public String getDescription() { - return this.description; - } - - public void setDescription(@NotNull String desc) { - this.description = desc; - } - @Override public boolean equals(Object o) { if (!(o instanceof VirtualEntry other)) return false; diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java index af026dca63..3d48f8b020 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualRegistryMap.java @@ -1,6 +1,7 @@ package com.gregtechceu.gtceu.api.misc.virtualregistry; import net.minecraft.nbt.CompoundTag; +import net.minecraft.resources.ResourceLocation; import net.minecraftforge.common.util.INBTSerializable; import org.jetbrains.annotations.NotNull; @@ -69,7 +70,8 @@ public Set getEntryNames(EntryTypes type) { @Override public void deserializeNBT(CompoundTag nbt) { for (String entryTypeString : nbt.getAllKeys()) { - EntryTypes type = entryTypeString.contains(":") ? EntryTypes.fromLocation(entryTypeString) : + EntryTypes type = entryTypeString.contains(":") ? + EntryTypes.fromLocation(ResourceLocation.tryParse(entryTypeString)) : EntryTypes.fromString(entryTypeString); if (type == null) continue; diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java similarity index 90% rename from src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java rename to src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index de8fb4558d..65bcc31237 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/CoverAbstractEnderLink.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -12,11 +12,13 @@ import com.gregtechceu.gtceu.api.gui.widget.EnumSelectorWidget; import com.gregtechceu.gtceu.api.gui.widget.ToggleButtonWidget; import com.gregtechceu.gtceu.api.machine.ConditionalSubscriptionHandler; +import com.gregtechceu.gtceu.api.machine.MachineCoverContainer; import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEntry; import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; import com.gregtechceu.gtceu.common.cover.data.ManualIOMode; +import com.gregtechceu.gtceu.common.machine.owner.IMachineOwner; import com.lowdragmc.lowdraglib.gui.widget.LabelWidget; import com.lowdragmc.lowdraglib.gui.widget.Widget; @@ -38,23 +40,21 @@ import java.util.UUID; import java.util.regex.Pattern; -public abstract class CoverAbstractEnderLink extends CoverBehavior +public abstract class AbstractEnderLinkCover extends CoverBehavior implements IUICover, IControllable { - public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(CoverAbstractEnderLink.class, + public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(AbstractEnderLinkCover.class, CoverBehavior.MANAGED_FIELD_HOLDER); public static final Pattern COLOR_INPUT_PATTERN = Pattern.compile("[0-9a-fA-F]*"); protected final ConditionalSubscriptionHandler subscriptionHandler; @Persisted @DescSynced - protected String channelName = VirtualEntry.DEFAULT_COLOR; + protected String color = VirtualEntry.DEFAULT_COLOR; @Persisted @DescSynced protected String description = VirtualEntry.DEFAULT_COLOR; - @Getter @Persisted - @DescSynced - protected UUID playerUUID = null; + protected IMachineOwner owner = null; @Getter @Setter @Persisted @@ -73,7 +73,7 @@ public abstract class CoverAbstractEnderLink extends Cov @RequireRerender protected IO io = IO.OUT; - public CoverAbstractEnderLink(CoverDefinition definition, ICoverable coverHolder, Direction attachedSide) { + public AbstractEnderLinkCover(CoverDefinition definition, ICoverable coverHolder, Direction attachedSide) { super(definition, coverHolder, attachedSide); subscriptionHandler = new ConditionalSubscriptionHandler(coverHolder, this::update, this::isSubscriptionActive); } @@ -100,12 +100,20 @@ public void onRemoved() { @Override public void onAttached(@NotNull ItemStack itemStack, @NotNull ServerPlayer player) { super.onAttached(itemStack, player); - playerUUID = player.getUUID(); + if (coverHolder instanceof MachineCoverContainer mcc) { + this.owner = mcc.getMachine().getHolder().getOwner(); + } } + protected final String getChannelName() { + return identifier() + this.color; + } + + protected abstract String identifier(); + protected void setChannelName(String name) { - beforeChannelNameChanging(this.channelName); - this.channelName = name; + beforeChannelNameChanging(getChannelName()); + this.color = name; } protected void beforeChannelNameChanging(String oldChannelName) { @@ -119,7 +127,7 @@ protected void beforeChannelNameChanging(String oldChannelName) { protected abstract void updateEntry(); public UUID getOwner() { - return isPrivate ? playerUUID : null; + return isPrivate ? owner.getPlayerUUID() : null; } protected void update() { @@ -186,7 +194,7 @@ public Widget createUIWidget() { int textInputWidth = channelGroupWidth - currentX - SMALL_WIDGET_WIDTH - 2; var confirmTextInputWidget = new ConfirmTextInputWidget(currentX, 0, textInputWidth, WIDGET_HEIGHT, - channelName, + this.color, text -> { if (text != null && !text.isEmpty()) { setChannelName(text); @@ -218,7 +226,7 @@ protected void buildAdditionalUI(WidgetGroup group) {} protected abstract String getUITitle(); protected int getColor() { - var colorString = this.channelName; + var colorString = this.color; colorString = String.format("%8s", colorString).replace(' ', '0'); if (colorString.length() > 8) { diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index 7af0abbd4e..de87f0b82a 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -21,8 +21,6 @@ import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; import net.minecraft.core.Direction; -import net.minecraft.server.level.ServerPlayer; -import net.minecraft.world.item.ItemStack; import net.minecraftforge.fluids.FluidStack; import net.minecraftforge.fluids.FluidUtil; @@ -32,10 +30,10 @@ import javax.annotation.ParametersAreNonnullByDefault; @ParametersAreNonnullByDefault -public class EnderFluidLinkCover extends CoverAbstractEnderLink { +public class EnderFluidLinkCover extends AbstractEnderLinkCover { public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(EnderFluidLinkCover.class, - CoverAbstractEnderLink.MANAGED_FIELD_HOLDER); + AbstractEnderLinkCover.MANAGED_FIELD_HOLDER); public static final int TRANSFER_RATE = 8000; // mB/t @Persisted @@ -63,13 +61,18 @@ protected EntryTypes getEntryType() { return EntryTypes.ENDER_FLUID; } + @Override + protected String identifier() { + return "EFLink#"; + } + @Override protected void updateEntry() { var reg = VirtualEnderRegistry.getInstance(); if (reg == null) return; - var tank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, this.channelName); + var tank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, getChannelName()); this.visualTank.setVirtualTank(tank); - this.visualTank.getVirtualTank().setColor(this.channelName); + this.visualTank.getVirtualTank().setColor(this.getColor()); markAsDirty(); markDirty("visualTank"); this.visualTank.setFluid(this.visualTank.getVirtualTank().getFluid()); @@ -108,12 +111,6 @@ private int doTransferFluids(int platformTransferLimit) { return 0; } - @Override - public void onAttached(ItemStack itemStack, ServerPlayer player) { - super.onAttached(itemStack, player); - playerUUID = player.getUUID(); - } - @Override public @NotNull ManagedFieldHolder getFieldHolder() { return MANAGED_FIELD_HOLDER; diff --git a/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java b/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java index 9f90afd18f..924c34a899 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java +++ b/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java @@ -9,6 +9,7 @@ import lombok.Getter; import java.util.List; +import java.util.UUID; import java.util.function.BooleanSupplier; public sealed interface IMachineOwner permits PlayerOwner, ArgonautsOwner, FTBOwner { @@ -21,6 +22,8 @@ public sealed interface IMachineOwner permits PlayerOwner, ArgonautsOwner, FTBOw void displayInfo(List compList); + UUID getPlayerUUID(); + static IMachineOwner create(CompoundTag tag) { MachineOwnerType type = MachineOwnerType.VALUES[tag.getInt("type")]; if (!type.isAvailable()) { From 6206b8a7359400afa121be265d4c45f79b01c4ec Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sat, 7 Dec 2024 00:47:27 +0800 Subject: [PATCH 04/14] fix crash --- .../cover/ender/AbstractEnderLinkCover.java | 2 +- .../common/data/GTSyncedFieldAccessors.java | 7 +++--- .../common/machine/owner/IMachineOwner.java | 4 ++-- .../gtceu/syncdata/MachineOwnerPayload.java | 23 +++++++++++++++++++ 4 files changed, 29 insertions(+), 7 deletions(-) create mode 100644 src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index 65bcc31237..eb989b9e3c 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -54,7 +54,7 @@ public abstract class AbstractEnderLinkCover extends Cov @DescSynced protected String description = VirtualEntry.DEFAULT_COLOR; @Persisted - protected IMachineOwner owner = null; + private IMachineOwner owner; @Getter @Setter @Persisted diff --git a/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java b/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java index 0216883d2e..c3ebe1af52 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java +++ b/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java @@ -2,10 +2,8 @@ import com.gregtechceu.gtceu.api.data.chemical.material.Material; import com.gregtechceu.gtceu.api.recipe.GTRecipe; -import com.gregtechceu.gtceu.syncdata.FluidStackPayload; -import com.gregtechceu.gtceu.syncdata.GTRecipePayload; -import com.gregtechceu.gtceu.syncdata.GTRecipeTypeAccessor; -import com.gregtechceu.gtceu.syncdata.MaterialPayload; +import com.gregtechceu.gtceu.common.machine.owner.IMachineOwner; +import com.gregtechceu.gtceu.syncdata.*; import com.lowdragmc.lowdraglib.syncdata.IAccessor; import com.lowdragmc.lowdraglib.syncdata.payload.FriendlyBufPayload; @@ -26,6 +24,7 @@ public class GTSyncedFieldAccessors { public static void init() { register(FriendlyBufPayload.class, FriendlyBufPayload::new, GT_RECIPE_TYPE_ACCESSOR, 1000); + registerSimple(MachineOwnerPayload.class, MachineOwnerPayload::new, IMachineOwner.class, 1); registerSimple(MaterialPayload.class, MaterialPayload::new, Material.class, 1); registerSimple(GTRecipePayload.class, GTRecipePayload::new, GTRecipe.class, 100); registerSimple(FluidStackPayload.class, FluidStackPayload::new, FluidStack.class, -1); diff --git a/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java b/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java index 924c34a899..280eda1475 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java +++ b/src/main/java/com/gregtechceu/gtceu/common/machine/owner/IMachineOwner.java @@ -64,12 +64,12 @@ enum MachineOwnerType { @Getter private final String name; - private MachineOwnerType(BooleanSupplier availabilitySupplier, String name) { + MachineOwnerType(BooleanSupplier availabilitySupplier, String name) { this.availabilitySupplier = availabilitySupplier; this.name = name; } - private MachineOwnerType() { + MachineOwnerType() { this.available = true; this.name = "Player"; } diff --git a/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java b/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java new file mode 100644 index 0000000000..8ffdf29cfe --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java @@ -0,0 +1,23 @@ +package com.gregtechceu.gtceu.syncdata; + +import com.gregtechceu.gtceu.common.machine.owner.IMachineOwner; + +import com.lowdragmc.lowdraglib.syncdata.payload.ObjectTypedPayload; + +import net.minecraft.nbt.CompoundTag; +import net.minecraft.nbt.Tag; + +import org.jetbrains.annotations.Nullable; + +public class MachineOwnerPayload extends ObjectTypedPayload { + + @Override + public @Nullable Tag serializeNBT() { + return payload.write(); + } + + @Override + public void deserializeNBT(Tag tag) { + payload.save((CompoundTag) tag); + } +} From 10df5b6e211f8c21c48a66b511893ef80191f867 Mon Sep 17 00:00:00 2001 From: Arborsm Date: Thu, 12 Dec 2024 21:40:38 +0800 Subject: [PATCH 05/14] fix weird fluid missing --- .../virtualregistry/entries/VirtualTank.java | 81 +------------------ .../virtualregistry/entries/VisualTank.java | 54 ------------- .../cover/ender/EnderFluidLinkCover.java | 17 ++-- .../common/data/GTSyncedFieldAccessors.java | 2 + .../gtceu/syncdata/VirtualTankAccessor.java | 31 +++++++ 5 files changed, 42 insertions(+), 143 deletions(-) delete mode 100644 src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java create mode 100644 src/main/java/com/gregtechceu/gtceu/syncdata/VirtualTankAccessor.java diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java index d89ff125e1..d18710b4b8 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java @@ -5,34 +5,24 @@ import net.minecraft.nbt.CompoundTag; import net.minecraftforge.fluids.FluidStack; -import net.minecraftforge.fluids.IFluidTank; -import net.minecraftforge.fluids.capability.IFluidHandler; import net.minecraftforge.fluids.capability.templates.FluidTank; -import lombok.Setter; +import lombok.Getter; import org.jetbrains.annotations.NotNull; -public class VirtualTank extends VirtualEntry implements IFluidTank, IFluidHandler { +public class VirtualTank extends VirtualEntry { public static final int DEFAULT_CAPACITY = 64000; // 64B protected static final String CAPACITY_KEY = "capacity"; protected static final String FLUID_KEY = "fluid"; @NotNull + @Getter private final FluidTank fluidTank; private int capacity; - @Setter - private Runnable onChange; public VirtualTank(int capacity) { this.capacity = capacity; - fluidTank = new FluidTank(this.capacity) { - - @Override - protected void onContentsChanged() { - super.onContentsChanged(); - VirtualTank.this.onContentsChanged(); - } - }; + fluidTank = new FluidTank(this.capacity); } public VirtualTank() { @@ -44,52 +34,10 @@ public EntryTypes getType() { return EntryTypes.ENDER_FLUID; } - @NotNull - @Override - public FluidStack getFluid() { - return this.fluidTank.getFluid(); - } - public void setFluid(FluidStack fluid) { this.fluidTank.setFluid(fluid); } - @Override - public int getFluidAmount() { - return this.fluidTank.getFluidAmount(); - } - - @Override - public int getCapacity() { - return this.capacity; - } - - @Override - public boolean isFluidValid(FluidStack fluidStack) { - return this.fluidTank.isFluidValid(fluidStack); - } - - @Override - public int getTanks() { - return this.fluidTank.getTanks(); - } - - @Override - public @NotNull FluidStack getFluidInTank(int i) { - return this.fluidTank.getFluidInTank(i); - } - - @Override - public int getTankCapacity(int i) { - if (i != 0) return 0; - return this.capacity; - } - - @Override - public boolean isFluidValid(int i, @NotNull FluidStack fluidStack) { - return this.fluidTank.isFluidValid(i, fluidStack); - } - @Override public boolean equals(Object o) { if (!(o instanceof VirtualTank other)) return false; @@ -120,25 +68,4 @@ public void deserializeNBT(CompoundTag nbt) { public boolean canRemove() { return this.fluidTank.isEmpty(); } - - @Override - public int fill(FluidStack fluidStack, FluidAction fluidAction) { - return this.fluidTank.fill(fluidStack, fluidAction); - } - - @NotNull - @Override - public FluidStack drain(FluidStack fluidStack, FluidAction doDrain) { - return this.fluidTank.drain(fluidStack, doDrain); - } - - @NotNull - @Override - public FluidStack drain(int amount, FluidAction fluidAction) { - return this.fluidTank.drain(amount, fluidAction); - } - - protected void onContentsChanged() { - if (onChange != null) onChange.run(); - } } diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java deleted file mode 100644 index 84ae73fe7b..0000000000 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VisualTank.java +++ /dev/null @@ -1,54 +0,0 @@ -package com.gregtechceu.gtceu.api.misc.virtualregistry.entries; - -import com.lowdragmc.lowdraglib.syncdata.ITagSerializable; - -import net.minecraft.nbt.CompoundTag; -import net.minecraftforge.common.util.INBTSerializable; -import net.minecraftforge.fluids.capability.templates.FluidTank; - -import lombok.Getter; -import lombok.Setter; -import lombok.experimental.Accessors; - -@Accessors(chain = true) -public class VisualTank extends FluidTank implements INBTSerializable, ITagSerializable { - - @Getter - private VirtualTank virtualTank; - @Setter - private Runnable onChange; - - public VisualTank(VirtualTank tank) { - super(VirtualTank.DEFAULT_CAPACITY); - setVirtualTank(tank); - } - - public VisualTank() { - super(VirtualTank.DEFAULT_CAPACITY); - setVirtualTank(new VirtualTank()); - } - - public void setVirtualTank(VirtualTank tank) { - virtualTank = tank; - setFluid(tank.getFluid()); - virtualTank.setOnChange(() -> setFluid(virtualTank.getFluid())); - } - - @Override - protected void onContentsChanged() { - super.onContentsChanged(); - virtualTank.setFluid(getFluid()); - if (onChange != null) onChange.run(); - } - - @Override - public CompoundTag serializeNBT() { - return virtualTank.serializeNBT(); - } - - @Override - public void deserializeNBT(CompoundTag nbt) { - virtualTank.deserializeNBT(nbt); - fluid = virtualTank.getFluid(); - } -} diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index de87f0b82a..2c63428c6b 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -10,13 +10,11 @@ import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; -import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VisualTank; import com.gregtechceu.gtceu.api.transfer.fluid.IFluidHandlerModifiable; import com.gregtechceu.gtceu.utils.GTTransferUtils; import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; -import com.lowdragmc.lowdraglib.syncdata.annotation.LazyManaged; import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; @@ -38,8 +36,7 @@ public class EnderFluidLinkCover extends AbstractEnderLinkCover { @Persisted @DescSynced - @LazyManaged - protected final VisualTank visualTank = new VisualTank(); + protected VirtualTank visualTank = new VirtualTank(); @Persisted @DescSynced protected final FilterHandler filterHandler; @@ -70,12 +67,8 @@ protected String identifier() { protected void updateEntry() { var reg = VirtualEnderRegistry.getInstance(); if (reg == null) return; - var tank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, getChannelName()); - this.visualTank.setVirtualTank(tank); - this.visualTank.getVirtualTank().setColor(this.getColor()); + this.visualTank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, getChannelName()); markAsDirty(); - markDirty("visualTank"); - this.visualTank.setFluid(this.visualTank.getVirtualTank().getFluid()); } @Override @@ -100,9 +93,9 @@ private int doTransferFluids(int platformTransferLimit) { if (ownFluidHandler != null) { return switch (io) { - case IN -> GTTransferUtils.transferFluidsFiltered(ownFluidHandler, visualTank.getVirtualTank(), + case IN -> GTTransferUtils.transferFluidsFiltered(ownFluidHandler, visualTank.getFluidTank(), filterHandler.getFilter(), platformTransferLimit); - case OUT -> GTTransferUtils.transferFluidsFiltered(visualTank.getVirtualTank(), ownFluidHandler, + case OUT -> GTTransferUtils.transferFluidsFiltered(visualTank.getFluidTank(), ownFluidHandler, filterHandler.getFilter(), platformTransferLimit); default -> 0; }; @@ -123,7 +116,7 @@ private int doTransferFluids(int platformTransferLimit) { @Override protected void buildAdditionalUI(WidgetGroup group) { - group.addWidget(new TankWidget(visualTank, 0, 146, 20, 20, 20, + group.addWidget(new TankWidget(visualTank.getFluidTank(), 0, 146, 20, 20, 20, true, true).setBackground(GuiTextures.FLUID_SLOT)); group.addWidget(filterHandler.createFilterSlotUI(117, 108)); diff --git a/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java b/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java index c3ebe1af52..b7d205ee27 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java +++ b/src/main/java/com/gregtechceu/gtceu/common/data/GTSyncedFieldAccessors.java @@ -7,6 +7,7 @@ import com.lowdragmc.lowdraglib.syncdata.IAccessor; import com.lowdragmc.lowdraglib.syncdata.payload.FriendlyBufPayload; +import com.lowdragmc.lowdraglib.syncdata.payload.NbtTagPayload; import net.minecraftforge.fluids.FluidStack; @@ -23,6 +24,7 @@ public class GTSyncedFieldAccessors { public static void init() { register(FriendlyBufPayload.class, FriendlyBufPayload::new, GT_RECIPE_TYPE_ACCESSOR, 1000); + register(NbtTagPayload.class, NbtTagPayload::new, VirtualTankAccessor.INSTANCE, 2); registerSimple(MachineOwnerPayload.class, MachineOwnerPayload::new, IMachineOwner.class, 1); registerSimple(MaterialPayload.class, MaterialPayload::new, Material.class, 1); diff --git a/src/main/java/com/gregtechceu/gtceu/syncdata/VirtualTankAccessor.java b/src/main/java/com/gregtechceu/gtceu/syncdata/VirtualTankAccessor.java new file mode 100644 index 0000000000..f469f0f5d1 --- /dev/null +++ b/src/main/java/com/gregtechceu/gtceu/syncdata/VirtualTankAccessor.java @@ -0,0 +1,31 @@ +package com.gregtechceu.gtceu.syncdata; + +import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; + +import com.lowdragmc.lowdraglib.syncdata.AccessorOp; +import com.lowdragmc.lowdraglib.syncdata.accessor.CustomObjectAccessor; +import com.lowdragmc.lowdraglib.syncdata.payload.ITypedPayload; +import com.lowdragmc.lowdraglib.syncdata.payload.NbtTagPayload; + +import net.minecraft.nbt.CompoundTag; + +public class VirtualTankAccessor extends CustomObjectAccessor { + + public static final VirtualTankAccessor INSTANCE = new VirtualTankAccessor(); + + protected VirtualTankAccessor() { + super(VirtualTank.class, true); + } + + @Override + public ITypedPayload serialize(AccessorOp op, VirtualTank value) { + return NbtTagPayload.of(value.serializeNBT()); + } + + @Override + public VirtualTank deserialize(AccessorOp op, ITypedPayload payload) { + var tank = new VirtualTank(); + tank.deserializeNBT((CompoundTag) payload.getPayload()); + return tank; + } +} From 96bc55dafd2fa1808ceb47ff054bd48bd39f40d1 Mon Sep 17 00:00:00 2001 From: Arborsm Date: Fri, 13 Dec 2024 02:03:50 +0800 Subject: [PATCH 06/14] yea,it syncs well now --- .../common/cover/ender/EnderFluidLinkCover.java | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index 2c63428c6b..c019392011 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -10,6 +10,7 @@ import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; +import com.gregtechceu.gtceu.api.transfer.fluid.CustomFluidTank; import com.gregtechceu.gtceu.api.transfer.fluid.IFluidHandlerModifiable; import com.gregtechceu.gtceu.utils.GTTransferUtils; @@ -39,6 +40,9 @@ public class EnderFluidLinkCover extends AbstractEnderLinkCover { protected VirtualTank visualTank = new VirtualTank(); @Persisted @DescSynced + protected final CustomFluidTank shownFluidTank = new CustomFluidTank(VirtualTank.DEFAULT_CAPACITY); + @Persisted + @DescSynced protected final FilterHandler filterHandler; protected int mBLeftToTransferLastSecond; @@ -46,6 +50,9 @@ public EnderFluidLinkCover(CoverDefinition definition, ICoverable coverHolder, D super(definition, coverHolder, attachedSide); this.mBLeftToTransferLastSecond = TRANSFER_RATE * 20; filterHandler = FilterHandlers.fluid(this); + shownFluidTank.setOnContentsChanged(() -> { + if (this.visualTank != null) this.visualTank.setFluid(shownFluidTank.getFluid().copy()); + }); } @Override @@ -68,6 +75,14 @@ protected void updateEntry() { var reg = VirtualEnderRegistry.getInstance(); if (reg == null) return; this.visualTank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, getChannelName()); + onShownFluidChanged(); + } + + private void onShownFluidChanged() { + if (visualTank != null) { + var fluid = visualTank.getFluidTank().getFluidInTank(0); + this.shownFluidTank.setFluid(fluid.copy()); + } markAsDirty(); } From 533722640372089b46b87aa471f9d5945a72b292 Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sat, 21 Dec 2024 00:46:32 +0800 Subject: [PATCH 07/14] why the sync list just not update before reopen the UI????? --- .../gregtechceu/gtceu/api/cover/IUICover.java | 7 +- .../gui/widget/ConfirmTextInputWidget.java | 9 +- .../misc/virtualregistry/VirtualEntry.java | 25 +- .../cover/ender/AbstractEnderLinkCover.java | 343 +++++++++++++----- .../cover/ender/EnderFluidLinkCover.java | 117 ++---- .../gtceu/syncdata/MachineOwnerPayload.java | 2 +- 6 files changed, 316 insertions(+), 187 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java b/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java index 5c4e316863..4ef09ebdfc 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java +++ b/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java @@ -41,11 +41,16 @@ default ModularUI createUI(Player entityPlayer) { var widget = createUIWidget(); var size = widget.getSize(); widget.setSelfPosition(new Position((176 - size.width) / 2, 0)); - return new ModularUI(176, size.height + 82, this, entityPlayer) + var modularUI = new ModularUI(176, size.height + 82, this, entityPlayer) .background(GuiTextures.BACKGROUND) .widget(widget) .widget(UITemplate.bindPlayerInventory(entityPlayer.getInventory(), GuiTextures.SLOT, 7, size.height, true)); + modularUI.registerCloseListener(this::onUIClosed); + return modularUI; + } + + default void onUIClosed() { } Widget createUIWidget(); diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java index a9ddc6b2cf..0dc49a9564 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java @@ -20,12 +20,10 @@ public class ConfirmTextInputWidget extends WidgetGroup { private final Consumer textResponder; private final Function validator; - @Getter - @Setter - private String text = ""; @Getter(AccessLevel.PRIVATE) @Setter(AccessLevel.PRIVATE) private String inputText = ""; + @Setter private String hoverText = ""; public ConfirmTextInputWidget(int x, int y, int width, int height, String text, Consumer textResponder, @@ -38,11 +36,6 @@ public ConfirmTextInputWidget(int x, int y, int width, int height, String text, } } - public ConfirmTextInputWidget setInputBoxTooltips(String text) { - this.hoverText = text; - return this; - } - @Override public void initWidget() { super.initWidget(); diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java index 40307265b7..0bf500f785 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java @@ -1,5 +1,6 @@ package com.gregtechceu.gtceu.api.misc.virtualregistry; +import com.lowdragmc.lowdraglib.syncdata.ITagSerializable; import net.minecraft.nbt.CompoundTag; import net.minecraftforge.common.util.INBTSerializable; @@ -8,7 +9,7 @@ import org.jetbrains.annotations.NotNull; @Getter -public abstract class VirtualEntry implements INBTSerializable { +public abstract class VirtualEntry implements INBTSerializable, ITagSerializable { public static final String DEFAULT_COLOR = "FFFFFFFF"; protected static final String COLOR_KEY = "color"; @@ -31,13 +32,23 @@ public void setColor(int color) { setColor(Integer.toHexString(color)); } - private int parseColor(String s) { - // stupid java not having actual unsigned ints - long tmp = Long.parseLong(s, 16); - if (tmp > 0x7FFFFFFF) { - tmp -= 0x100000000L; + public static int parseColor(String colorString) { + colorString = formatColorString(colorString); + + if (colorString.length() > 8) { + colorString = colorString.substring(colorString.length() - 8); } - return (int) tmp; + + int alpha = Integer.parseInt(colorString.substring(6, 8), 16); + int red = Integer.parseInt(colorString.substring(0, 2), 16); + int green = Integer.parseInt(colorString.substring(2, 4), 16); + int blue = Integer.parseInt(colorString.substring(4, 6), 16); + + return (alpha << 24) | (red << 16) | (green << 8) | blue; + } + + public static @NotNull String formatColorString(String colorString) { + return String.format("%8s", colorString).replace(' ', '0').toUpperCase(); } @Override diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index eb989b9e3c..4bd4becb1d 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -6,11 +6,9 @@ import com.gregtechceu.gtceu.api.cover.CoverBehavior; import com.gregtechceu.gtceu.api.cover.CoverDefinition; import com.gregtechceu.gtceu.api.cover.IUICover; +import com.gregtechceu.gtceu.api.cover.filter.FilterHandler; import com.gregtechceu.gtceu.api.gui.GuiTextures; -import com.gregtechceu.gtceu.api.gui.widget.ColorBlockWidget; -import com.gregtechceu.gtceu.api.gui.widget.ConfirmTextInputWidget; -import com.gregtechceu.gtceu.api.gui.widget.EnumSelectorWidget; -import com.gregtechceu.gtceu.api.gui.widget.ToggleButtonWidget; +import com.gregtechceu.gtceu.api.gui.widget.*; import com.gregtechceu.gtceu.api.machine.ConditionalSubscriptionHandler; import com.gregtechceu.gtceu.api.machine.MachineCoverContainer; import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; @@ -20,26 +18,29 @@ import com.gregtechceu.gtceu.common.cover.data.ManualIOMode; import com.gregtechceu.gtceu.common.machine.owner.IMachineOwner; -import com.lowdragmc.lowdraglib.gui.widget.LabelWidget; -import com.lowdragmc.lowdraglib.gui.widget.Widget; -import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; +import com.lowdragmc.lowdraglib.gui.editor.ColorPattern; +import com.lowdragmc.lowdraglib.gui.widget.*; import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; import com.lowdragmc.lowdraglib.syncdata.annotation.RequireRerender; import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; import net.minecraft.core.Direction; +import net.minecraft.network.FriendlyByteBuf; import net.minecraft.server.level.ServerPlayer; import net.minecraft.world.item.ItemStack; import lombok.Getter; -import lombok.Setter; +import org.apache.commons.lang3.mutable.MutableBoolean; +import org.jetbrains.annotations.Contract; import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; -import java.util.List; -import java.util.UUID; +import java.util.*; import java.util.regex.Pattern; +import java.util.stream.Stream; +@SuppressWarnings("SameParameterValue") public abstract class AbstractEnderLinkCover extends CoverBehavior implements IUICover, IControllable { @@ -49,14 +50,14 @@ public abstract class AbstractEnderLinkCover extends Cov protected final ConditionalSubscriptionHandler subscriptionHandler; @Persisted @DescSynced - protected String color = VirtualEntry.DEFAULT_COLOR; + protected String colorStr = VirtualEntry.DEFAULT_COLOR; @Persisted @DescSynced protected String description = VirtualEntry.DEFAULT_COLOR; @Persisted + @DescSynced private IMachineOwner owner; @Getter - @Setter @Persisted @DescSynced protected boolean isPrivate = false; @@ -72,6 +73,9 @@ public abstract class AbstractEnderLinkCover extends Cov @Getter @RequireRerender protected IO io = IO.OUT; + @DescSynced + boolean isAnyChanged = false; + protected VirtualEntryWidget virtualEntryWidget; public AbstractEnderLinkCover(CoverDefinition definition, ICoverable coverHolder, Direction attachedSide) { super(definition, coverHolder, attachedSide); @@ -94,6 +98,14 @@ public void onRemoved() { subscriptionHandler.unsubscribe(); } + protected abstract VirtualEntry getEntry(); + + protected abstract void setEntry(VirtualEntry entry); + + protected abstract Stream getEntries(); + + public abstract void clearEntries(); + @Override public abstract boolean canAttach(); @@ -101,30 +113,54 @@ public void onRemoved() { public void onAttached(@NotNull ItemStack itemStack, @NotNull ServerPlayer player) { super.onAttached(itemStack, player); if (coverHolder instanceof MachineCoverContainer mcc) { - this.owner = mcc.getMachine().getHolder().getOwner(); + var owner = mcc.getMachine().getHolder().getOwner(); + if (owner != null) this.owner = owner; } } + @Override + public void onUIClosed() { + if (virtualEntryWidget != null) + virtualEntryWidget = null; + clearEntries(); + } + protected final String getChannelName() { - return identifier() + this.color; + return identifier() + this.colorStr; + } + + protected final String getChannelName(VirtualEntry entry) { + return identifier() + entry.getColorStr(); } protected abstract String identifier(); protected void setChannelName(String name) { - beforeChannelNameChanging(getChannelName()); - this.color = name; + if (name == null || name.isEmpty()) return; + var reg = VirtualEnderRegistry.getInstance(); + if (reg == null) return; + reg.deleteEntryIf(getOwner(), getEntryType(), this.colorStr, VirtualEntry::canRemove); + this.colorStr = VirtualEntry.formatColorString(name); + setVirtualEntry(reg); } - protected void beforeChannelNameChanging(String oldChannelName) { + protected void setPrivate(boolean isPrivate) { + if (isPrivate == this.isPrivate) return; var reg = VirtualEnderRegistry.getInstance(); if (reg == null) return; - reg.deleteEntryIf(getOwner(), getEntryType(), oldChannelName, VirtualEntry::canRemove); + reg.deleteEntryIf(getOwner(), getEntryType(), this.colorStr, VirtualEntry::canRemove); + this.isPrivate = isPrivate; + setVirtualEntry(reg); } - protected abstract EntryTypes getEntryType(); + private void setVirtualEntry(VirtualEnderRegistry reg) { + setEntry(reg.getOrCreateEntry(getOwner(), getEntryType(), this.colorStr)); + getEntry().setColor(this.colorStr); + this.isAnyChanged = true; + subscriptionHandler.updateSubscription(); + } - protected abstract void updateEntry(); + protected abstract EntryTypes getEntryType(); public UUID getOwner() { return isPrivate ? owner.getPlayerUUID() : null; @@ -137,7 +173,12 @@ protected void update() { if (isWorkingEnabled()) { transfer(); } - updateEntry(); + + if (isAnyChanged) { + if (virtualEntryWidget != null) + virtualEntryWidget.update(); + isAnyChanged = false; + } subscriptionHandler.updateSubscription(); } @@ -155,94 +196,212 @@ public void setWorkingEnabled(boolean isWorkingAllowed) { public void setIo(IO io) { if (io == IO.IN || io == IO.OUT) { this.io = io; + subscriptionHandler.updateSubscription(); } } protected void setManualIOMode(ManualIOMode manualIOMode) { this.manualIOMode = manualIOMode; - coverHolder.markDirty(); + subscriptionHandler.updateSubscription(); } @Override public Widget createUIWidget() { - updateEntry(); - final int GROUP_WIDTH = 176; - final int WIDGET_HEIGHT = 20; - final int SMALL_WIDGET_WIDTH = 20; - final int GROUP_X = 10; - final int GROUP_Y = 20; - int channelGroupWidth = GROUP_WIDTH - GROUP_X * 2; - int currentX = 0; - - final var group = new WidgetGroup(0, 0, 176, 137); - final var channelGroup = new WidgetGroup(GROUP_X, GROUP_Y, channelGroupWidth, WIDGET_HEIGHT); - group.addWidget(new LabelWidget(10, 5, getUITitle())); - - var toggleButtonWidget = new ToggleButtonWidget(currentX, 0, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - GuiTextures.BUTTON_PUBLIC_PRIVATE, this::isPrivate, null); - toggleButtonWidget.setOnPressCallback((clickData, isPrivate) -> { - setPrivate(isPrivate); - toggleButtonWidget.setHoverTooltips(isPrivate ? - "cover.ender_link.permission.public" : "cover.ender_link.permission.private"); - }); - channelGroup.addWidget(toggleButtonWidget); - currentX += SMALL_WIDGET_WIDTH + 2; - - channelGroup.addWidget(new ColorBlockWidget(currentX, 0, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT) - .setColorSupplier(this::getColor)); - currentX += SMALL_WIDGET_WIDTH + 2; - - int textInputWidth = channelGroupWidth - currentX - SMALL_WIDGET_WIDTH - 2; - var confirmTextInputWidget = new ConfirmTextInputWidget(currentX, 0, textInputWidth, WIDGET_HEIGHT, - this.color, - text -> { - if (text != null && !text.isEmpty()) { - setChannelName(text); - } - }, - text -> { - if (text == null || !COLOR_INPUT_PATTERN.matcher(text).matches() || text.length() > 8) { - return VirtualTank.DEFAULT_COLOR; - } - return text; - }).setInputBoxTooltips(description); - channelGroup.addWidget(confirmTextInputWidget); - group.addWidget(channelGroup); - - group.addWidget(new ToggleButtonWidget(116, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - GuiTextures.BUTTON_POWER, this::isWorkingEnabled, this::setWorkingEnabled)); - group.addWidget(new EnumSelectorWidget<>(146, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - List.of(IO.IN, IO.OUT), io, this::setIo)); - group.addWidget(new EnumSelectorWidget<>(146, 107, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - ManualIOMode.VALUES, manualIOMode, this::setManualIOMode) - .setHoverTooltips("cover.universal.manual_import_export.mode.description")); - - buildAdditionalUI(group); - return group; - } - - protected void buildAdditionalUI(WidgetGroup group) {} - - protected abstract String getUITitle(); + virtualEntryWidget = new VirtualEntryWidget(this); + return virtualEntryWidget; + } - protected int getColor() { - var colorString = this.color; - colorString = String.format("%8s", colorString).replace(' ', '0'); + @Nullable + protected FilterHandler getFilterHandler(){ + return null; + } - if (colorString.length() > 8) { - colorString = colorString.substring(colorString.length() - 8); - } + protected abstract Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height); - int alpha = Integer.parseInt(colorString.substring(6, 8), 16); - int red = Integer.parseInt(colorString.substring(0, 2), 16); - int green = Integer.parseInt(colorString.substring(2, 4), 16); - int blue = Integer.parseInt(colorString.substring(4, 6), 16); + protected abstract String getUITitle(); - return (alpha << 24) | (red << 16) | (green << 8) | blue; + protected int getColorStr() { + return VirtualEntry.parseColor(this.colorStr); } @Override public @NotNull ManagedFieldHolder getFieldHolder() { return MANAGED_FIELD_HOLDER; } + + protected static class VirtualEntryWidget extends WidgetGroup { + private final AbstractEnderLinkCover cover; + + private static final int SMALL_WIDGET_WIDTH = 20; + private static final int WIDGET_HEIGHT = 20; + private static final int GROUP_WIDTH = 176; + private static final int TOTAL_WIDTH = 156; + private static final int BUTTON_SIZE = 16; + private final MutableBoolean showChannels; + private final WidgetGroup mainGroup; + private final DraggableScrollableWidgetGroup channelsGroup; + private final WidgetGroup mainChannelGroup; + + VirtualEntryWidget(AbstractEnderLinkCover cover) { + super(0, 0, GROUP_WIDTH, 137); + this.cover = cover; + this.showChannels = new MutableBoolean(false); + mainGroup = new WidgetGroup(0, 0, GROUP_WIDTH, 137); + channelsGroup = new DraggableScrollableWidgetGroup(0, 20, 170, 110) + .setYScrollBarWidth(2).setYBarStyle(null, ColorPattern.T_WHITE.rectTexture().setRadius(1)); + mainChannelGroup = new WidgetGroup(10, 20, 156, 20); + initWidgets(); + } + + public void update() { + var reg = VirtualEnderRegistry.getInstance(); + if (reg == null) return; + widgets.clear(); + mainGroup.widgets.clear(); + channelsGroup.widgets.clear(); + mainChannelGroup.widgets.clear(); + initWidgets(); + this.detectAndSendChanges(); + } + + private void initWidgets() { + int currentX = 0; + + this.addWidget(new LabelWidget(10, 5, cover.getUITitle())); + this.addWidget(createToggleButton()); + this.addWidget(mainGroup); + this.addWidget(channelsGroup.setVisible(false)); + + var toggleButtonWidget = createToggleButtonForPrivacy(currentX); + mainChannelGroup.addWidget(toggleButtonWidget); + currentX += SMALL_WIDGET_WIDTH + 2; + mainChannelGroup.addWidget(createColorBlockWidget(currentX)); + currentX += SMALL_WIDGET_WIDTH + 2; + mainChannelGroup.addWidget(createConfirmTextInputWidget(currentX)); + + mainGroup.addWidget(mainChannelGroup); + mainGroup.addWidget(createWorkingEnabledButton()); + addEnumSelectorWidgets(); + mainGroup.addWidget(cover.addVirtualEntryWidget(cover.getEntry(), 146, 20, 20, 20)); + + if (cover.getFilterHandler() != null) { + mainGroup.addWidget(cover.getFilterHandler().createFilterSlotUI(117, 108)); + mainGroup.addWidget(cover.getFilterHandler().createFilterConfigUI(10, 72, 156, 60)); + } + + addChannelWidgets(); + } + + @Contract(" -> new") + private @NotNull ToggleButtonWidget createToggleButton() { + return new ToggleButtonWidget(156, 5, 10, 10, GuiTextures.TOGGLE_BUTTON_BACK, + showChannels::getValue, cd -> { + showChannels.setValue(!showChannels.getValue()); + mainGroup.setVisible(showChannels.isFalse()); + channelsGroup.setVisible(showChannels.isTrue()); + }); + } + + private @NotNull ToggleButtonWidget createToggleButtonForPrivacy(int currentX) { + ToggleButtonWidget toggleButtonWidget = new ToggleButtonWidget(currentX, 0, SMALL_WIDGET_WIDTH, + WIDGET_HEIGHT, GuiTextures.BUTTON_PUBLIC_PRIVATE, cover::isPrivate, null); + toggleButtonWidget.setHoverTooltips(cover.isPrivate ? + "cover.ender_link.permission.public" : "cover.ender_link.permission.private"); + toggleButtonWidget.setOnPressCallback((clickData, isPrivate) -> { + cover.setPrivate(isPrivate); + cover.isAnyChanged = true; + }); + return toggleButtonWidget; + } + + private ColorBlockWidget createColorBlockWidget(int currentX) { + return new ColorBlockWidget(currentX, 0, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT) + .setColorSupplier(cover::getColorStr); + } + + private ConfirmTextInputWidget createConfirmTextInputWidget(int currentX) { + int GROUP_X = 10; + int textInputWidth = (GROUP_WIDTH - GROUP_X * 2) - currentX - SMALL_WIDGET_WIDTH - 2; + return new ConfirmTextInputWidget(currentX, 0, textInputWidth, WIDGET_HEIGHT, + cover.colorStr, + cover::setChannelName, + text -> { + if (text == null || !COLOR_INPUT_PATTERN.matcher(text).matches() || text.length() > 8) { + return VirtualTank.DEFAULT_COLOR; + } + return text; + }).setHoverText(cover.description); + } + + @Contract(" -> new") + private @NotNull ToggleButtonWidget createWorkingEnabledButton() { + return new ToggleButtonWidget(116, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + GuiTextures.BUTTON_POWER, cover::isWorkingEnabled, cover::setWorkingEnabled); + } + + private void addEnumSelectorWidgets() { + mainGroup.addWidget(new EnumSelectorWidget<>(146, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + List.of(IO.IN, IO.OUT), cover.io, cover::setIo)); + mainGroup.addWidget(new EnumSelectorWidget<>(146, 107, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, + ManualIOMode.VALUES, cover.manualIOMode, cover::setManualIOMode) + .setHoverTooltips("cover.universal.manual_import_export.mode.description")); + } + + private void addChannelWidgets() { + int y = 0; + SelectableWidgetGroup selectedWidget = null; + for (var entry : cover.getEntries().sorted(Comparator.comparing(VirtualEntry::getColorStr)).toList()) { + SelectableWidgetGroup channelWidget = createChannelWidget(entry, 10, y); + if (cover.getChannelName(entry).equals(cover.getChannelName())) { + selectedWidget = channelWidget; + } + channelsGroup.addWidget(channelWidget); + y += 22; + } + channelsGroup.setSelected(selectedWidget); + if (selectedWidget != null) selectedWidget.onSelected(); + } + + private @NotNull SelectableWidgetGroup createChannelWidget(@NotNull VirtualEntry entry, int x, int y) { + int currentX = 0; + int MARGIN = 2; + int availableWidth = TOTAL_WIDTH - (BUTTON_SIZE + MARGIN) * 2; + + TextBoxWidget textBoxWidget = new TextBoxWidget(BUTTON_SIZE + MARGIN, 4, availableWidth, List.of(entry.getColorStr())).setCenter(true); + SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(x, y, TOTAL_WIDTH, BUTTON_SIZE).setOnSelected(group -> { + if (cover.getChannelName().equals(cover.getChannelName(entry))) return; + writeClientAction(0, buffer -> { + // send new channel name to server + String newChannelColorStr = entry.getColorStr(); + buffer.writeUtf(newChannelColorStr); + }); + playButtonClickSound(); + }).setSelectedTexture(1, -1); + + // Color block + ColorBlockWidget colorBlockWidget = + new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE).setCurrentColor(entry.getColor()); + channelGroup.addWidget(colorBlockWidget); + currentX += BUTTON_SIZE + MARGIN; + + // Text box + channelGroup.addWidget(textBoxWidget); + currentX += availableWidth + MARGIN; + + // Slot + Widget slotWidget = cover.addVirtualEntryWidget(entry, currentX, 0, BUTTON_SIZE, BUTTON_SIZE); + channelGroup.addWidget(slotWidget); + + return channelGroup; + } + + @Override + public void handleClientAction(int id, FriendlyByteBuf buffer) { + super.handleClientAction(id, buffer); + if (id == 0) { + String newChannelColorStr = buffer.readUtf(); + cover.setChannelName(newChannelColorStr); + } + } + } } diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index c019392011..bf21584c17 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -9,12 +9,12 @@ import com.gregtechceu.gtceu.api.gui.widget.TankWidget; import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEntry; import com.gregtechceu.gtceu.api.misc.virtualregistry.entries.VirtualTank; -import com.gregtechceu.gtceu.api.transfer.fluid.CustomFluidTank; import com.gregtechceu.gtceu.api.transfer.fluid.IFluidHandlerModifiable; import com.gregtechceu.gtceu.utils.GTTransferUtils; -import com.lowdragmc.lowdraglib.gui.widget.WidgetGroup; +import com.lowdragmc.lowdraglib.gui.widget.*; import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; @@ -27,6 +27,9 @@ import org.jetbrains.annotations.Nullable; import javax.annotation.ParametersAreNonnullByDefault; +import java.util.ArrayList; +import java.util.List; +import java.util.stream.Stream; @ParametersAreNonnullByDefault public class EnderFluidLinkCover extends AbstractEnderLinkCover { @@ -35,12 +38,11 @@ public class EnderFluidLinkCover extends AbstractEnderLinkCover { AbstractEnderLinkCover.MANAGED_FIELD_HOLDER); public static final int TRANSFER_RATE = 8000; // mB/t - @Persisted @DescSynced - protected VirtualTank visualTank = new VirtualTank(); + protected final List tanks = new ArrayList<>(); @Persisted @DescSynced - protected final CustomFluidTank shownFluidTank = new CustomFluidTank(VirtualTank.DEFAULT_CAPACITY); + protected VirtualTank visualTank = new VirtualTank(); @Persisted @DescSynced protected final FilterHandler filterHandler; @@ -50,9 +52,31 @@ public EnderFluidLinkCover(CoverDefinition definition, ICoverable coverHolder, D super(definition, coverHolder, attachedSide); this.mBLeftToTransferLastSecond = TRANSFER_RATE * 20; filterHandler = FilterHandlers.fluid(this); - shownFluidTank.setOnContentsChanged(() -> { - if (this.visualTank != null) this.visualTank.setFluid(shownFluidTank.getFluid().copy()); - }); + } + + @Override + protected VirtualTank getEntry() { + return visualTank; + } + + @Override + protected void setEntry(VirtualEntry entry) { + visualTank = (VirtualTank) entry; + } + + @Override + protected Stream getEntries(){ + var reg = VirtualEnderRegistry.getInstance(); + if (reg == null) return Stream.empty(); + tanks.clear(); + reg.getEntryNames(getOwner(), EntryTypes.ENDER_FLUID).stream() + .map(name -> reg.getEntry(getOwner(), EntryTypes.ENDER_FLUID, name)).forEach(tanks::add); + return tanks.stream().map(t -> t); + } + + @Override + public void clearEntries() { + tanks.clear(); } @Override @@ -70,22 +94,6 @@ protected String identifier() { return "EFLink#"; } - @Override - protected void updateEntry() { - var reg = VirtualEnderRegistry.getInstance(); - if (reg == null) return; - this.visualTank = reg.getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, getChannelName()); - onShownFluidChanged(); - } - - private void onShownFluidChanged() { - if (visualTank != null) { - var fluid = visualTank.getFluidTank().getFluidInTank(0); - this.shownFluidTank.setFluid(fluid.copy()); - } - markAsDirty(); - } - @Override protected void transfer() { long timer = coverHolder.getOffsetTimer(); @@ -126,16 +134,12 @@ private int doTransferFluids(int platformTransferLimit) { ////////////////////////////////////// // *********** GUI ************ // - /// /////////////////////////////////// @Override - protected void buildAdditionalUI(WidgetGroup group) { - group.addWidget(new TankWidget(visualTank.getFluidTank(), 0, 146, 20, 20, 20, - true, true).setBackground(GuiTextures.FLUID_SLOT)); - - group.addWidget(filterHandler.createFilterSlotUI(117, 108)); - group.addWidget(filterHandler.createFilterConfigUI(10, 72, 156, 60)); + protected Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height){ + return new TankWidget(((VirtualTank)entry).getFluidTank(), 0, x, y, width, height, + true, true).setBackground(GuiTextures.FLUID_SLOT); } @NotNull @@ -144,51 +148,8 @@ protected String getUITitle() { return "cover.ender_fluid_link.title"; } - // damn I can't make the list panel work in the server side - // private SelectableWidgetGroup createVisualTankWidget(VisualTank tank, int y) { - // final int TOTAL_WIDTH = 116; - // final int BUTTON_SIZE = 20; - // final int MARGIN = 2; - // - // int currentX = 0; - // int availableWidth = TOTAL_WIDTH - BUTTON_SIZE + MARGIN; - // - // SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(0, y, TOTAL_WIDTH, BUTTON_SIZE){ - // @Override - // public void drawInForeground(@NotNull GuiGraphics graphics, int mouseX, int mouseY, float partialTicks) { - // super.drawInForeground(graphics, mouseX, mouseY, partialTicks); - // if (super.isSelected) - // DrawerHelper.drawBorder(graphics, getPositionX(), getPositionY(), TOTAL_WIDTH, BUTTON_SIZE, 0xFFFFFFFF, 1); - // } - // }; - // var name = tank.getVirtualTank().getColorStr(); - // - // // Color block - // channelGroup.addWidget(new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) - // .setCurrentColor(tank.getVirtualTank().getColor())); - // currentX += BUTTON_SIZE + MARGIN; - // - // // Text box - // int textBoxWidth = availableWidth; - // textBoxWidth -= BUTTON_SIZE + MARGIN; - // if (tank.getFluidAmount() == 0) { - // textBoxWidth -= BUTTON_SIZE + MARGIN; - // } - // channelGroup.addWidget( - // new TextBoxWidget(currentX, 6, textBoxWidth, List.of(name)).setCenter(true)); - // currentX += textBoxWidth + MARGIN; - // - // // Tank slot - // channelGroup.addWidget(new TankWidget(tank, currentX, 0, - // BUTTON_SIZE, BUTTON_SIZE, false, false) - // .setBackground(GuiTextures.FLUID_SLOT)); - // currentX += BUTTON_SIZE + MARGIN; - // - // // Remove button (if tank is empty) - // if (tank.getFluidAmount() == 0) { - // channelGroup.addWidget(new ButtonWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE, - // GuiTextures.BUTTON_INT_CIRCUIT_MINUS, cd -> removeChannel(tank))); - // } - // return channelGroup; - // } + @Override + protected FilterHandler getFilterHandler() { + return filterHandler; + } } diff --git a/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java b/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java index 8ffdf29cfe..ca7fcd15c7 100644 --- a/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java +++ b/src/main/java/com/gregtechceu/gtceu/syncdata/MachineOwnerPayload.java @@ -18,6 +18,6 @@ public class MachineOwnerPayload extends ObjectTypedPayload { @Override public void deserializeNBT(Tag tag) { - payload.save((CompoundTag) tag); + payload = IMachineOwner.create((CompoundTag) tag); } } From 7a4a4e8e8d05e0e9f974427d4e3ca1037f284d7f Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sat, 21 Dec 2024 20:53:16 +0800 Subject: [PATCH 08/14] all done > < --- .../gregtechceu/gtceu/api/cover/IUICover.java | 3 +- .../gui/widget/ConfirmTextInputWidget.java | 5 +- .../misc/virtualregistry/VirtualEntry.java | 10 +- .../cover/ender/AbstractEnderLinkCover.java | 346 ++++++++++-------- .../cover/ender/EnderFluidLinkCover.java | 28 +- .../gtceu/forge/ForgeCommonEventListener.java | 2 +- 6 files changed, 218 insertions(+), 176 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java b/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java index 4ef09ebdfc..7fcf5bac41 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java +++ b/src/main/java/com/gregtechceu/gtceu/api/cover/IUICover.java @@ -50,8 +50,7 @@ default ModularUI createUI(Player entityPlayer) { return modularUI; } - default void onUIClosed() { - } + default void onUIClosed() {} Widget createUIWidget(); } diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java index 0dc49a9564..b3d5ae19ef 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java @@ -23,8 +23,6 @@ public class ConfirmTextInputWidget extends WidgetGroup { @Getter(AccessLevel.PRIVATE) @Setter(AccessLevel.PRIVATE) private String inputText = ""; - @Setter - private String hoverText = ""; public ConfirmTextInputWidget(int x, int y, int width, int height, String text, Consumer textResponder, Function validator) { @@ -55,7 +53,6 @@ public void initWidget() { getSizeHeight() - 2, this::getInputText, this::setInputText) - .setValidator(validator) - .setHoverTooltips(hoverText)); + .setValidator(validator)); } } diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java index 0bf500f785..ad353ab8f9 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java @@ -1,14 +1,17 @@ package com.gregtechceu.gtceu.api.misc.virtualregistry; import com.lowdragmc.lowdraglib.syncdata.ITagSerializable; + import net.minecraft.nbt.CompoundTag; import net.minecraftforge.common.util.INBTSerializable; import lombok.Getter; import lombok.Setter; +import lombok.experimental.Accessors; import org.jetbrains.annotations.NotNull; @Getter +@Accessors(chain = true) public abstract class VirtualEntry implements INBTSerializable, ITagSerializable { public static final String DEFAULT_COLOR = "FFFFFFFF"; @@ -54,7 +57,8 @@ public static int parseColor(String colorString) { @Override public boolean equals(Object o) { if (!(o instanceof VirtualEntry other)) return false; - return this.getType() == other.getType() && this.color == other.color; + return this.getType() == other.getType() && this.color == other.color && + this.description.equals(other.description); } @Override @@ -63,7 +67,7 @@ public CompoundTag serializeNBT() { tag.putString(COLOR_KEY, this.colorStr); if (!description.isEmpty()) - this.description = tag.getString(DESC_KEY); + tag.putString(DESC_KEY, this.description); return tag; } @@ -73,7 +77,7 @@ public void deserializeNBT(CompoundTag nbt) { setColor(nbt.getString(COLOR_KEY)); if (nbt.contains(DESC_KEY)) - setDescription(nbt.getString(DESC_KEY)); + this.description = nbt.getString(DESC_KEY); } public abstract boolean canRemove(); diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index 4bd4becb1d..36993f63ca 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -8,7 +8,10 @@ import com.gregtechceu.gtceu.api.cover.IUICover; import com.gregtechceu.gtceu.api.cover.filter.FilterHandler; import com.gregtechceu.gtceu.api.gui.GuiTextures; -import com.gregtechceu.gtceu.api.gui.widget.*; +import com.gregtechceu.gtceu.api.gui.widget.ColorBlockWidget; +import com.gregtechceu.gtceu.api.gui.widget.ConfirmTextInputWidget; +import com.gregtechceu.gtceu.api.gui.widget.EnumSelectorWidget; +import com.gregtechceu.gtceu.api.gui.widget.ToggleButtonWidget; import com.gregtechceu.gtceu.api.machine.ConditionalSubscriptionHandler; import com.gregtechceu.gtceu.api.machine.MachineCoverContainer; import com.gregtechceu.gtceu.api.misc.virtualregistry.EntryTypes; @@ -19,12 +22,15 @@ import com.gregtechceu.gtceu.common.machine.owner.IMachineOwner; import com.lowdragmc.lowdraglib.gui.editor.ColorPattern; +import com.lowdragmc.lowdraglib.gui.texture.IGuiTexture; +import com.lowdragmc.lowdraglib.gui.texture.TextTexture; import com.lowdragmc.lowdraglib.gui.widget.*; import com.lowdragmc.lowdraglib.syncdata.annotation.DescSynced; import com.lowdragmc.lowdraglib.syncdata.annotation.Persisted; import com.lowdragmc.lowdraglib.syncdata.annotation.RequireRerender; import com.lowdragmc.lowdraglib.syncdata.field.ManagedFieldHolder; +import net.minecraft.ChatFormatting; import net.minecraft.core.Direction; import net.minecraft.network.FriendlyByteBuf; import net.minecraft.server.level.ServerPlayer; @@ -38,7 +44,6 @@ import java.util.*; import java.util.regex.Pattern; -import java.util.stream.Stream; @SuppressWarnings("SameParameterValue") public abstract class AbstractEnderLinkCover extends CoverBehavior @@ -47,65 +52,46 @@ public abstract class AbstractEnderLinkCover extends Cov public static final ManagedFieldHolder MANAGED_FIELD_HOLDER = new ManagedFieldHolder(AbstractEnderLinkCover.class, CoverBehavior.MANAGED_FIELD_HOLDER); public static final Pattern COLOR_INPUT_PATTERN = Pattern.compile("[0-9a-fA-F]*"); + protected final ConditionalSubscriptionHandler subscriptionHandler; + @Persisted @DescSynced protected String colorStr = VirtualEntry.DEFAULT_COLOR; - @Persisted - @DescSynced - protected String description = VirtualEntry.DEFAULT_COLOR; - @Persisted - @DescSynced - private IMachineOwner owner; @Getter @Persisted @DescSynced - protected boolean isPrivate = false; + protected Permissions permission = Permissions.PUBLIC; @Persisted @Getter protected boolean isWorkingEnabled = true; + @Getter @Persisted @DescSynced - @Getter protected ManualIOMode manualIOMode = ManualIOMode.DISABLED; + @Getter @Persisted @DescSynced - @Getter @RequireRerender protected IO io = IO.OUT; + protected VirtualEntryWidget virtualEntryWidget; @DescSynced boolean isAnyChanged = false; - protected VirtualEntryWidget virtualEntryWidget; + @Persisted + @DescSynced + private IMachineOwner owner; public AbstractEnderLinkCover(CoverDefinition definition, ICoverable coverHolder, Direction attachedSide) { super(definition, coverHolder, attachedSide); subscriptionHandler = new ConditionalSubscriptionHandler(coverHolder, this::update, this::isSubscriptionActive); } - protected boolean isSubscriptionActive() { - return isWorkingEnabled(); - } - @Override public void onLoad() { super.onLoad(); subscriptionHandler.initialize(coverHolder.getLevel()); } - @Override - public void onRemoved() { - super.onRemoved(); - subscriptionHandler.unsubscribe(); - } - - protected abstract VirtualEntry getEntry(); - - protected abstract void setEntry(VirtualEntry entry); - - protected abstract Stream getEntries(); - - public abstract void clearEntries(); - @Override public abstract boolean canAttach(); @@ -118,43 +104,87 @@ public void onAttached(@NotNull ItemStack itemStack, @NotNull ServerPlayer playe } } + @Override + public void onUnload() { + super.onUnload(); + subscriptionHandler.unsubscribe(); + if (!isRemote()) { + VirtualEnderRegistry.getInstance() + .deleteEntryIf(getOwner(), getEntryType(), getChannelName(), VirtualEntry::canRemove); + } + } + @Override public void onUIClosed() { - if (virtualEntryWidget != null) - virtualEntryWidget = null; - clearEntries(); + virtualEntryWidget = null; } - protected final String getChannelName() { - return identifier() + this.colorStr; + @Override + public void setWorkingEnabled(boolean isWorkingAllowed) { + if (this.isWorkingEnabled != isWorkingAllowed) { + this.isWorkingEnabled = isWorkingAllowed; + subscriptionHandler.updateSubscription(); + } } - protected final String getChannelName(VirtualEntry entry) { - return identifier() + entry.getColorStr(); + @Override + public Widget createUIWidget() { + virtualEntryWidget = new VirtualEntryWidget(this); + return virtualEntryWidget; + } + + @Override + public @NotNull ManagedFieldHolder getFieldHolder() { + return MANAGED_FIELD_HOLDER; + } + + public void setIo(IO io) { + if (io == IO.IN || io == IO.OUT) { + this.io = io; + subscriptionHandler.updateSubscription(); + } + } + + public UUID getOwner() { + return permission == Permissions.PRIVATE ? owner.getPlayerUUID() : null; + } + + protected boolean isSubscriptionActive() { + return isWorkingEnabled(); } protected abstract String identifier(); + protected abstract VirtualEntry getEntry(); + + protected abstract void setEntry(VirtualEntry entry); + + protected final String getChannelName() { + return identifier() + this.colorStr; + } + protected void setChannelName(String name) { - if (name == null || name.isEmpty()) return; - var reg = VirtualEnderRegistry.getInstance(); - if (reg == null) return; - reg.deleteEntryIf(getOwner(), getEntryType(), this.colorStr, VirtualEntry::canRemove); + if (isRemote()) return; + VirtualEnderRegistry.getInstance().deleteEntryIf(getOwner(), getEntryType(), getChannelName(), + VirtualEntry::canRemove); this.colorStr = VirtualEntry.formatColorString(name); - setVirtualEntry(reg); + setVirtualEntry(); } - protected void setPrivate(boolean isPrivate) { - if (isPrivate == this.isPrivate) return; - var reg = VirtualEnderRegistry.getInstance(); - if (reg == null) return; - reg.deleteEntryIf(getOwner(), getEntryType(), this.colorStr, VirtualEntry::canRemove); - this.isPrivate = isPrivate; - setVirtualEntry(reg); + protected final String getChannelName(VirtualEntry entry) { + return identifier() + entry.getColorStr(); + } + + protected void setPermission(Permissions permission) { + if (isRemote()) return; + VirtualEnderRegistry.getInstance().deleteEntryIf(getOwner(), getEntryType(), getChannelName(), + VirtualEntry::canRemove); + this.permission = permission; + setVirtualEntry(); } - private void setVirtualEntry(VirtualEnderRegistry reg) { - setEntry(reg.getOrCreateEntry(getOwner(), getEntryType(), this.colorStr)); + protected void setVirtualEntry() { + setEntry(VirtualEnderRegistry.getInstance().getOrCreateEntry(getOwner(), getEntryType(), getChannelName())); getEntry().setColor(this.colorStr); this.isAnyChanged = true; subscriptionHandler.updateSubscription(); @@ -162,57 +192,39 @@ private void setVirtualEntry(VirtualEnderRegistry reg) { protected abstract EntryTypes getEntryType(); - public UUID getOwner() { - return isPrivate ? owner.getPlayerUUID() : null; - } - protected void update() { long timer = coverHolder.getOffsetTimer(); if (timer % 5 != 0) return; - - if (isWorkingEnabled()) { + if (isWorkingEnabled() && !isRemote()) { + if (!VirtualEnderRegistry.getInstance().hasEntry(getOwner(), getEntryType(), getChannelName())) { + var entry = VirtualEnderRegistry.getInstance().getOrCreateEntry(getOwner(), getEntryType(), + getChannelName()); + entry.setColor(this.colorStr); + } + var entry = VirtualEnderRegistry.getInstance().getOrCreateEntry(getOwner(), getEntryType(), + getChannelName()); + if (!entry.equals(getEntry())) { + setEntry(entry); + } transfer(); } if (isAnyChanged) { - if (virtualEntryWidget != null) - virtualEntryWidget.update(); + if (virtualEntryWidget != null) virtualEntryWidget.update(); isAnyChanged = false; } - subscriptionHandler.updateSubscription(); } protected abstract void transfer(); - @Override - public void setWorkingEnabled(boolean isWorkingAllowed) { - if (this.isWorkingEnabled != isWorkingAllowed) { - this.isWorkingEnabled = isWorkingAllowed; - subscriptionHandler.updateSubscription(); - } - } - - public void setIo(IO io) { - if (io == IO.IN || io == IO.OUT) { - this.io = io; - subscriptionHandler.updateSubscription(); - } - } - protected void setManualIOMode(ManualIOMode manualIOMode) { this.manualIOMode = manualIOMode; subscriptionHandler.updateSubscription(); } - @Override - public Widget createUIWidget() { - virtualEntryWidget = new VirtualEntryWidget(this); - return virtualEntryWidget; - } - @Nullable - protected FilterHandler getFilterHandler(){ + protected FilterHandler getFilterHandler() { return null; } @@ -224,23 +236,17 @@ protected int getColorStr() { return VirtualEntry.parseColor(this.colorStr); } - @Override - public @NotNull ManagedFieldHolder getFieldHolder() { - return MANAGED_FIELD_HOLDER; - } - protected static class VirtualEntryWidget extends WidgetGroup { - private final AbstractEnderLinkCover cover; - private static final int SMALL_WIDGET_WIDTH = 20; - private static final int WIDGET_HEIGHT = 20; + private static final int WIDGET_BOARD = 20; private static final int GROUP_WIDTH = 176; private static final int TOTAL_WIDTH = 156; private static final int BUTTON_SIZE = 16; + private final AbstractEnderLinkCover cover; private final MutableBoolean showChannels; private final WidgetGroup mainGroup; - private final DraggableScrollableWidgetGroup channelsGroup; private final WidgetGroup mainChannelGroup; + private final DraggableScrollableWidgetGroup channelsGroup; // client only VirtualEntryWidget(AbstractEnderLinkCover cover) { super(0, 0, GROUP_WIDTH, 137); @@ -254,8 +260,7 @@ protected static class VirtualEntryWidget extends WidgetGroup { } public void update() { - var reg = VirtualEnderRegistry.getInstance(); - if (reg == null) return; + if (isRemote()) return; widgets.clear(); mainGroup.widgets.clear(); channelsGroup.widgets.clear(); @@ -274,83 +279,75 @@ private void initWidgets() { var toggleButtonWidget = createToggleButtonForPrivacy(currentX); mainChannelGroup.addWidget(toggleButtonWidget); - currentX += SMALL_WIDGET_WIDTH + 2; + currentX += WIDGET_BOARD + 2; mainChannelGroup.addWidget(createColorBlockWidget(currentX)); - currentX += SMALL_WIDGET_WIDTH + 2; + currentX += WIDGET_BOARD + 2; mainChannelGroup.addWidget(createConfirmTextInputWidget(currentX)); mainGroup.addWidget(mainChannelGroup); mainGroup.addWidget(createWorkingEnabledButton()); addEnumSelectorWidgets(); - mainGroup.addWidget(cover.addVirtualEntryWidget(cover.getEntry(), 146, 20, 20, 20)); + mainGroup.addWidget( + cover.addVirtualEntryWidget(cover.getEntry(), 146, WIDGET_BOARD, WIDGET_BOARD, WIDGET_BOARD)); if (cover.getFilterHandler() != null) { mainGroup.addWidget(cover.getFilterHandler().createFilterSlotUI(117, 108)); mainGroup.addWidget(cover.getFilterHandler().createFilterConfigUI(10, 72, 156, 60)); } - - addChannelWidgets(); } @Contract(" -> new") private @NotNull ToggleButtonWidget createToggleButton() { - return new ToggleButtonWidget(156, 5, 10, 10, GuiTextures.TOGGLE_BUTTON_BACK, - showChannels::getValue, cd -> { - showChannels.setValue(!showChannels.getValue()); - mainGroup.setVisible(showChannels.isFalse()); - channelsGroup.setVisible(showChannels.isTrue()); - }); + return new ToggleButtonWidget(156, 5, 10, 10, GuiTextures.TOGGLE_BUTTON_BACK, showChannels::getValue, + cd -> { + showChannels.setValue(!showChannels.getValue()); + mainGroup.setVisible(showChannels.isFalse()); + channelsGroup.setVisible(showChannels.isTrue()); + sendChannelList(); + }); } - private @NotNull ToggleButtonWidget createToggleButtonForPrivacy(int currentX) { - ToggleButtonWidget toggleButtonWidget = new ToggleButtonWidget(currentX, 0, SMALL_WIDGET_WIDTH, - WIDGET_HEIGHT, GuiTextures.BUTTON_PUBLIC_PRIVATE, cover::isPrivate, null); - toggleButtonWidget.setHoverTooltips(cover.isPrivate ? - "cover.ender_link.permission.public" : "cover.ender_link.permission.private"); - toggleButtonWidget.setOnPressCallback((clickData, isPrivate) -> { - cover.setPrivate(isPrivate); - cover.isAnyChanged = true; - }); - return toggleButtonWidget; + @Contract("_ -> new") + private @NotNull Widget createToggleButtonForPrivacy(int currentX) { + return new EnumSelectorWidget<>(currentX, 0, + WIDGET_BOARD, WIDGET_BOARD, Permissions.values(), cover.permission, cover::setPermission); } private ColorBlockWidget createColorBlockWidget(int currentX) { - return new ColorBlockWidget(currentX, 0, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT) - .setColorSupplier(cover::getColorStr); + return new ColorBlockWidget(currentX, 0, WIDGET_BOARD, WIDGET_BOARD).setColorSupplier(cover::getColorStr); } private ConfirmTextInputWidget createConfirmTextInputWidget(int currentX) { int GROUP_X = 10; - int textInputWidth = (GROUP_WIDTH - GROUP_X * 2) - currentX - SMALL_WIDGET_WIDTH - 2; - return new ConfirmTextInputWidget(currentX, 0, textInputWidth, WIDGET_HEIGHT, - cover.colorStr, - cover::setChannelName, - text -> { + int textInputWidth = (GROUP_WIDTH - GROUP_X * 2) - currentX - WIDGET_BOARD - 2; + return new ConfirmTextInputWidget(currentX, 0, textInputWidth, WIDGET_BOARD, cover.colorStr, + cover::setChannelName, text -> { if (text == null || !COLOR_INPUT_PATTERN.matcher(text).matches() || text.length() > 8) { return VirtualTank.DEFAULT_COLOR; } return text; - }).setHoverText(cover.description); + }); } @Contract(" -> new") private @NotNull ToggleButtonWidget createWorkingEnabledButton() { - return new ToggleButtonWidget(116, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - GuiTextures.BUTTON_POWER, cover::isWorkingEnabled, cover::setWorkingEnabled); + return new ToggleButtonWidget(116, 82, WIDGET_BOARD, WIDGET_BOARD, GuiTextures.BUTTON_POWER, + cover::isWorkingEnabled, cover::setWorkingEnabled); } private void addEnumSelectorWidgets() { - mainGroup.addWidget(new EnumSelectorWidget<>(146, 82, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - List.of(IO.IN, IO.OUT), cover.io, cover::setIo)); - mainGroup.addWidget(new EnumSelectorWidget<>(146, 107, SMALL_WIDGET_WIDTH, WIDGET_HEIGHT, - ManualIOMode.VALUES, cover.manualIOMode, cover::setManualIOMode) + mainGroup.addWidget(new EnumSelectorWidget<>(146, 82, WIDGET_BOARD, WIDGET_BOARD, List.of(IO.IN, IO.OUT), + cover.io, cover::setIo)); + mainGroup.addWidget(new EnumSelectorWidget<>(146, 107, WIDGET_BOARD, WIDGET_BOARD, ManualIOMode.VALUES, + cover.manualIOMode, cover::setManualIOMode) .setHoverTooltips("cover.universal.manual_import_export.mode.description")); } - private void addChannelWidgets() { - int y = 0; + private void addChannelWidgets(List entries) { + channelsGroup.clearAllWidgets(); + int y = 1; SelectableWidgetGroup selectedWidget = null; - for (var entry : cover.getEntries().sorted(Comparator.comparing(VirtualEntry::getColorStr)).toList()) { + for (var entry : entries.stream().sorted(Comparator.comparing(VirtualEntry::getColorStr)).toList()) { SelectableWidgetGroup channelWidget = createChannelWidget(entry, 10, y); if (cover.getChannelName(entry).equals(cover.getChannelName())) { selectedWidget = channelWidget; @@ -360,6 +357,7 @@ private void addChannelWidgets() { } channelsGroup.setSelected(selectedWidget); if (selectedWidget != null) selectedWidget.onSelected(); + channelsGroup.setClientSideWidget(); } private @NotNull SelectableWidgetGroup createChannelWidget(@NotNull VirtualEntry entry, int x, int y) { @@ -367,26 +365,34 @@ private void addChannelWidgets() { int MARGIN = 2; int availableWidth = TOTAL_WIDTH - (BUTTON_SIZE + MARGIN) * 2; - TextBoxWidget textBoxWidget = new TextBoxWidget(BUTTON_SIZE + MARGIN, 4, availableWidth, List.of(entry.getColorStr())).setCenter(true); - SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(x, y, TOTAL_WIDTH, BUTTON_SIZE).setOnSelected(group -> { - if (cover.getChannelName().equals(cover.getChannelName(entry))) return; - writeClientAction(0, buffer -> { - // send new channel name to server - String newChannelColorStr = entry.getColorStr(); - buffer.writeUtf(newChannelColorStr); - }); - playButtonClickSound(); - }).setSelectedTexture(1, -1); + var des = entry.getDescription(); + TextBoxWidget textBoxWidget = new TextBoxWidget(BUTTON_SIZE + MARGIN, + !des.isEmpty() ? 0 : 4, availableWidth, List.of(entry.getColorStr())).setCenter(true); + SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(x, y, TOTAL_WIDTH, BUTTON_SIZE) + .setOnSelected(group -> { + if (cover.getChannelName().equals(cover.getChannelName(entry))) return; + writeClientAction(0, buffer -> { + // send new channel name to server + String newChannelColorStr = entry.getColorStr(); + buffer.writeUtf(newChannelColorStr); + }); + playButtonClickSound(); + }).setSelectedTexture(1, -1); // Color block - ColorBlockWidget colorBlockWidget = - new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE).setCurrentColor(entry.getColor()); + ColorBlockWidget colorBlockWidget = new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) + .setCurrentColor(entry.getColor()); channelGroup.addWidget(colorBlockWidget); currentX += BUTTON_SIZE + MARGIN; // Text box channelGroup.addWidget(textBoxWidget); currentX += availableWidth + MARGIN; + if (!des.isEmpty()) { + var desText = new TextTexture(ChatFormatting.DARK_GRAY + des).setDropShadow(false); + desText.setType(TextTexture.TextType.ROLL).setRollSpeed(0.7f); + channelGroup.addWidget(new ImageWidget(BUTTON_SIZE + MARGIN, 10, availableWidth, 8, desText)); + } // Slot Widget slotWidget = cover.addVirtualEntryWidget(entry, currentX, 0, BUTTON_SIZE, BUTTON_SIZE); @@ -395,13 +401,67 @@ private void addChannelWidgets() { return channelGroup; } + private void sendChannelList() { + writeClientAction(100, buffer -> buffer.writeBoolean(showChannels.isTrue())); + } + @Override public void handleClientAction(int id, FriendlyByteBuf buffer) { super.handleClientAction(id, buffer); if (id == 0) { String newChannelColorStr = buffer.readUtf(); cover.setChannelName(newChannelColorStr); + } else if (id == 100) { + if (!buffer.readBoolean()) return; + var entries = VirtualEnderRegistry.getInstance().getEntryNames(cover.getOwner(), EntryTypes.ENDER_FLUID) + .stream().map(name -> VirtualEnderRegistry.getInstance().getEntry(cover.getOwner(), + EntryTypes.ENDER_FLUID, name)) + .sorted(Comparator.comparing(VirtualEntry::getColorStr)); + writeUpdateInfo(101, buf -> { + var list = entries.toList(); + buf.writeVarInt(list.size()); + for (var entry : list) { + buf.writeNbt(entry.serializeNBT()); + } + }); + } + } + + @Override + public void readUpdateInfo(int id, FriendlyByteBuf buffer) { + super.readUpdateInfo(id, buffer); + if (id == 101) { + int size = buffer.readVarInt(); + List entries = new ArrayList<>(); + for (int i = 0; i < size; i++) { + VirtualEntry entry = cover.getEntryType().createInstance(); + entry.deserializeNBT(Objects.requireNonNull(buffer.readNbt())); + entries.add(entry); + } + addChannelWidgets(entries); } } } + + protected enum Permissions implements EnumSelectorWidget.SelectableEnum { + + PUBLIC, + PRIVATE; + + @Override + public @NotNull String getTooltip() { + return switch (this) { + case PUBLIC -> "cover.ender_fluid_link.private.tooltip.enabled"; + case PRIVATE -> "cover.ender_fluid_link.private.tooltip.disabled"; + }; + } + + @Override + public @NotNull IGuiTexture getIcon() { + return switch (this) { + case PUBLIC -> GuiTextures.BUTTON_PUBLIC_PRIVATE.getSubTexture(0, 0, 1, 0.5); + case PRIVATE -> GuiTextures.BUTTON_PUBLIC_PRIVATE.getSubTexture(0, 0.5, 1, 0.5); + }; + } + } } diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index bf21584c17..309b306ff4 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -27,9 +27,6 @@ import org.jetbrains.annotations.Nullable; import javax.annotation.ParametersAreNonnullByDefault; -import java.util.ArrayList; -import java.util.List; -import java.util.stream.Stream; @ParametersAreNonnullByDefault public class EnderFluidLinkCover extends AbstractEnderLinkCover { @@ -38,11 +35,9 @@ public class EnderFluidLinkCover extends AbstractEnderLinkCover { AbstractEnderLinkCover.MANAGED_FIELD_HOLDER); public static final int TRANSFER_RATE = 8000; // mB/t - @DescSynced - protected final List tanks = new ArrayList<>(); @Persisted @DescSynced - protected VirtualTank visualTank = new VirtualTank(); + protected VirtualTank visualTank; @Persisted @DescSynced protected final FilterHandler filterHandler; @@ -52,6 +47,8 @@ public EnderFluidLinkCover(CoverDefinition definition, ICoverable coverHolder, D super(definition, coverHolder, attachedSide); this.mBLeftToTransferLastSecond = TRANSFER_RATE * 20; filterHandler = FilterHandlers.fluid(this); + if (!isRemote()) visualTank = VirtualEnderRegistry.getInstance() + .getOrCreateEntry(getOwner(), EntryTypes.ENDER_FLUID, getChannelName()); } @Override @@ -64,21 +61,6 @@ protected void setEntry(VirtualEntry entry) { visualTank = (VirtualTank) entry; } - @Override - protected Stream getEntries(){ - var reg = VirtualEnderRegistry.getInstance(); - if (reg == null) return Stream.empty(); - tanks.clear(); - reg.getEntryNames(getOwner(), EntryTypes.ENDER_FLUID).stream() - .map(name -> reg.getEntry(getOwner(), EntryTypes.ENDER_FLUID, name)).forEach(tanks::add); - return tanks.stream().map(t -> t); - } - - @Override - public void clearEntries() { - tanks.clear(); - } - @Override public boolean canAttach() { return FluidUtil.getFluidHandler(coverHolder.getLevel(), coverHolder.getPos(), attachedSide).isPresent(); @@ -137,8 +119,8 @@ private int doTransferFluids(int platformTransferLimit) { /// /////////////////////////////////// @Override - protected Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height){ - return new TankWidget(((VirtualTank)entry).getFluidTank(), 0, x, y, width, height, + protected Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height) { + return new TankWidget(((VirtualTank) entry).getFluidTank(), 0, x, y, width, height, true, true).setBackground(GuiTextures.FLUID_SLOT); } diff --git a/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java b/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java index 07baea52c0..8e5fb2f738 100644 --- a/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java +++ b/src/main/java/com/gregtechceu/gtceu/forge/ForgeCommonEventListener.java @@ -20,8 +20,8 @@ import com.gregtechceu.gtceu.api.item.armor.ArmorComponentItem; import com.gregtechceu.gtceu.api.machine.MetaMachine; import com.gregtechceu.gtceu.api.machine.feature.IInteractedMachine; -import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; import com.gregtechceu.gtceu.api.misc.forge.FilteredFluidHandlerItemStack; +import com.gregtechceu.gtceu.api.misc.virtualregistry.VirtualEnderRegistry; import com.gregtechceu.gtceu.api.pattern.MultiblockWorldSavedData; import com.gregtechceu.gtceu.api.registry.GTRegistries; import com.gregtechceu.gtceu.common.capability.EnvironmentalHazardSavedData; From 21cb3bc44835ecfba0d2bde7af0843d412182947 Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sat, 21 Dec 2024 21:58:04 +0800 Subject: [PATCH 09/14] add texture --- .../gtceu/api/gui/GuiTextures.java | 4 ++++ .../gui/widget/ConfirmTextInputWidget.java | 3 +-- .../cover/ender/AbstractEnderLinkCover.java | 21 ++++++++++++------ .../textures/gui/widget/button_check.png | Bin 0 -> 454 bytes .../gtceu/textures/gui/widget/button_list.png | Bin 0 -> 402 bytes 5 files changed, 19 insertions(+), 9 deletions(-) create mode 100644 src/main/resources/assets/gtceu/textures/gui/widget/button_check.png create mode 100644 src/main/resources/assets/gtceu/textures/gui/widget/button_list.png diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/GuiTextures.java b/src/main/java/com/gregtechceu/gtceu/api/gui/GuiTextures.java index da93638216..9f7b6a4d21 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/GuiTextures.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/GuiTextures.java @@ -129,6 +129,10 @@ public class GuiTextures { public static final ResourceTexture BUTTON_LEFT = new ResourceTexture("gtceu:textures/gui/widget/left.png"); public static final ResourceTexture BUTTON_PUBLIC_PRIVATE = new ResourceTexture( "gtceu:textures/gui/widget/button_public_private.png"); + public static final ResourceTexture BUTTON_CHECK = new ResourceTexture( + "gtceu:textures/gui/widget/button_check.png"); + public static final ResourceTexture BUTTON_LIST = new ResourceTexture( + "gtceu:textures/gui/widget/button_list.png"); public static final ResourceTexture BUTTON_RIGHT = new ResourceTexture("gtceu:textures/gui/widget/right.png"); public static final ResourceTexture BUTTON_SILK_TOUCH_MODE = new ResourceTexture( "gtceu:textures/gui/widget/button_silk_touch_mode.png"); diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java index b3d5ae19ef..0cad7bf5c6 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java @@ -44,8 +44,7 @@ public void initWidget() { getSizeHeight(), pressed -> textResponder.accept(inputText)) .setButtonTexture( - new GuiTextureGroup(GuiTextures.VANILLA_BUTTON, - GuiTextures.CLIPBOARD_BUTTON.getSubTexture(0, 0.25, 1, 0.25)))); + new GuiTextureGroup(GuiTextures.VANILLA_BUTTON, GuiTextures.BUTTON_CHECK))); this.addWidget(new TextFieldWidget( 1, 1, diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index 36993f63ca..49c8d8a92d 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -22,6 +22,7 @@ import com.gregtechceu.gtceu.common.machine.owner.IMachineOwner; import com.lowdragmc.lowdraglib.gui.editor.ColorPattern; +import com.lowdragmc.lowdraglib.gui.texture.GuiTextureGroup; import com.lowdragmc.lowdraglib.gui.texture.IGuiTexture; import com.lowdragmc.lowdraglib.gui.texture.TextTexture; import com.lowdragmc.lowdraglib.gui.widget.*; @@ -284,6 +285,9 @@ private void initWidgets() { currentX += WIDGET_BOARD + 2; mainChannelGroup.addWidget(createConfirmTextInputWidget(currentX)); + mainChannelGroup.addWidget(new ConfirmTextInputWidget(0, WIDGET_BOARD + 2, GROUP_WIDTH - WIDGET_BOARD, + WIDGET_BOARD, cover.getEntry().getDescription(), cover.getEntry()::setDescription, t -> t)); + mainGroup.addWidget(mainChannelGroup); mainGroup.addWidget(createWorkingEnabledButton()); addEnumSelectorWidgets(); @@ -298,13 +302,16 @@ private void initWidgets() { @Contract(" -> new") private @NotNull ToggleButtonWidget createToggleButton() { - return new ToggleButtonWidget(156, 5, 10, 10, GuiTextures.TOGGLE_BUTTON_BACK, showChannels::getValue, - cd -> { - showChannels.setValue(!showChannels.getValue()); - mainGroup.setVisible(showChannels.isFalse()); - channelsGroup.setVisible(showChannels.isTrue()); - sendChannelList(); - }); + return (ToggleButtonWidget) new ToggleButtonWidget(156, 5, 12, 12, showChannels::getValue, cd -> { + showChannels.setValue(!showChannels.getValue()); + mainGroup.setVisible(showChannels.isFalse()); + channelsGroup.setVisible(showChannels.isTrue()); + sendChannelList(); + }).setTexture( + new GuiTextureGroup(GuiTextures.TOGGLE_BUTTON_BACK.getSubTexture(0, 0, 1, 0.5), + GuiTextures.BUTTON_LIST), + new GuiTextureGroup(GuiTextures.TOGGLE_BUTTON_BACK.getSubTexture(0, 0.5, 1, 0.5), + GuiTextures.BUTTON_LIST)); } @Contract("_ -> new") diff --git a/src/main/resources/assets/gtceu/textures/gui/widget/button_check.png b/src/main/resources/assets/gtceu/textures/gui/widget/button_check.png new file mode 100644 index 0000000000000000000000000000000000000000..7c3435aefb9c4eedb6c217461087e08096505151 GIT binary patch literal 454 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbKJV{wqX6T`Z5GB1G~mUKs7M+SzC z{oH>NS%G|>0G|+7<~nBP9n8#@AWa5Er*lE-N`m}?|NsBb;Gnhg3y{xQ;1OBOz`%DH zgc*%FBlnrvV1|u_AoC(M_WMl&SA_~aPY-a(BX93wDkO0IW{V*EM zQU;(GCa^QG096!MXrq(i9*Y1ek#4Fo9JDSy}*DP+f)w1|Zp&SHD@D zx|LG}Wcqr#IEH8h*Pd|{I$*%Tr8$xGp6!o$zo4HmUz1QxvX&q9iy!t)x7$D3u`~F*C13&(AeP!Bo#s z&*=9a=50VV+fpMu(>y)37&w3&Rt70XRt82O%L|C5p=^+AG#Ht|;!HrcAtMvmbx}Ze zW;+X5JPXJM0qby9h8N5T8qHD$pwt9*1{R=710!Pt#sv^lK{m23fS5D|$OZu>pt($7 zl|hykKo(S&p@9KNmUXs|&X3~jD}hW$PZ!4!3;$$^f&&~&C3SRT|2MyQe7xNF(2X4j z=30N3jN8AD`5L#mLr4hg8cr3) Date: Sun, 22 Dec 2024 15:45:07 +0800 Subject: [PATCH 10/14] fix issues --- .../misc/virtualregistry/VirtualEntry.java | 6 +- .../virtualregistry/entries/VirtualTank.java | 2 +- .../cover/ender/AbstractEnderLinkCover.java | 77 +++++++++++++------ 3 files changed, 57 insertions(+), 28 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java index ad353ab8f9..f4bc95b609 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/VirtualEntry.java @@ -42,7 +42,7 @@ public static int parseColor(String colorString) { colorString = colorString.substring(colorString.length() - 8); } - int alpha = Integer.parseInt(colorString.substring(6, 8), 16); + int alpha = 255; // make alpha 100% int red = Integer.parseInt(colorString.substring(0, 2), 16); int green = Integer.parseInt(colorString.substring(2, 4), 16); int blue = Integer.parseInt(colorString.substring(4, 6), 16); @@ -80,5 +80,7 @@ public void deserializeNBT(CompoundTag nbt) { this.description = nbt.getString(DESC_KEY); } - public abstract boolean canRemove(); + public boolean canRemove() { + return this.description.isEmpty(); + } } diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java index d18710b4b8..183a7e8df9 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java @@ -66,6 +66,6 @@ public void deserializeNBT(CompoundTag nbt) { @Override public boolean canRemove() { - return this.fluidTank.isEmpty(); + return super.canRemove() && this.fluidTank.isEmpty(); } } diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index 49c8d8a92d..e2cf4e284e 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -196,15 +196,14 @@ protected void setVirtualEntry() { protected void update() { long timer = coverHolder.getOffsetTimer(); if (timer % 5 != 0) return; + if (isWorkingEnabled() && !isRemote()) { - if (!VirtualEnderRegistry.getInstance().hasEntry(getOwner(), getEntryType(), getChannelName())) { - var entry = VirtualEnderRegistry.getInstance().getOrCreateEntry(getOwner(), getEntryType(), - getChannelName()); - entry.setColor(this.colorStr); - } var entry = VirtualEnderRegistry.getInstance().getOrCreateEntry(getOwner(), getEntryType(), getChannelName()); - if (!entry.equals(getEntry())) { + if (!entry.getColorStr().equals(this.colorStr)) { + entry.setColor(this.colorStr); + } + if (!getEntry().equals(entry)) { setEntry(entry); } transfer(); @@ -233,7 +232,7 @@ protected void setManualIOMode(ManualIOMode manualIOMode) { protected abstract String getUITitle(); - protected int getColorStr() { + protected int getColor() { return VirtualEntry.parseColor(this.colorStr); } @@ -286,7 +285,8 @@ private void initWidgets() { mainChannelGroup.addWidget(createConfirmTextInputWidget(currentX)); mainChannelGroup.addWidget(new ConfirmTextInputWidget(0, WIDGET_BOARD + 2, GROUP_WIDTH - WIDGET_BOARD, - WIDGET_BOARD, cover.getEntry().getDescription(), cover.getEntry()::setDescription, t -> t)); + WIDGET_BOARD, cover.getEntry().getDescription(), cover.getEntry()::setDescription, + t -> t == null ? "" : t)); mainGroup.addWidget(mainChannelGroup); mainGroup.addWidget(createWorkingEnabledButton()); @@ -302,11 +302,11 @@ private void initWidgets() { @Contract(" -> new") private @NotNull ToggleButtonWidget createToggleButton() { - return (ToggleButtonWidget) new ToggleButtonWidget(156, 5, 12, 12, showChannels::getValue, cd -> { + return (ToggleButtonWidget) new ToggleButtonWidget(146, 3, 12, 12, showChannels::getValue, cd -> { showChannels.setValue(!showChannels.getValue()); mainGroup.setVisible(showChannels.isFalse()); channelsGroup.setVisible(showChannels.isTrue()); - sendChannelList(); + requestUpdate(); }).setTexture( new GuiTextureGroup(GuiTextures.TOGGLE_BUTTON_BACK.getSubTexture(0, 0, 1, 0.5), GuiTextures.BUTTON_LIST), @@ -321,7 +321,7 @@ private void initWidgets() { } private ColorBlockWidget createColorBlockWidget(int currentX) { - return new ColorBlockWidget(currentX, 0, WIDGET_BOARD, WIDGET_BOARD).setColorSupplier(cover::getColorStr); + return new ColorBlockWidget(currentX, 0, WIDGET_BOARD, WIDGET_BOARD).setColorSupplier(cover::getColor); } private ConfirmTextInputWidget createConfirmTextInputWidget(int currentX) { @@ -370,21 +370,28 @@ private void addChannelWidgets(List entries) { private @NotNull SelectableWidgetGroup createChannelWidget(@NotNull VirtualEntry entry, int x, int y) { int currentX = 0; int MARGIN = 2; - int availableWidth = TOTAL_WIDTH - (BUTTON_SIZE + MARGIN) * 2; + int availableWidth = TOTAL_WIDTH - (BUTTON_SIZE + MARGIN) * 3; + final MutableBoolean canSelect = new MutableBoolean(false); var des = entry.getDescription(); TextBoxWidget textBoxWidget = new TextBoxWidget(BUTTON_SIZE + MARGIN, !des.isEmpty() ? 0 : 4, availableWidth, List.of(entry.getColorStr())).setCenter(true); - SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(x, y, TOTAL_WIDTH, BUTTON_SIZE) - .setOnSelected(group -> { - if (cover.getChannelName().equals(cover.getChannelName(entry))) return; - writeClientAction(0, buffer -> { - // send new channel name to server - String newChannelColorStr = entry.getColorStr(); - buffer.writeUtf(newChannelColorStr); - }); - playButtonClickSound(); - }).setSelectedTexture(1, -1); + SelectableWidgetGroup channelGroup = new SelectableWidgetGroup(x, y, TOTAL_WIDTH, BUTTON_SIZE) { + + @Override + public boolean allowSelected(double mouseX, double mouseY, int button) { + return canSelect.getValue() && super.allowSelected(mouseX, mouseY, button); + } + }; + channelGroup.setOnSelected(group -> { + if (cover.getChannelName().equals(cover.getChannelName(entry))) return; + writeClientAction(0, buffer -> { + // send new channel name to server + String newChannelColorStr = entry.getColorStr(); + buffer.writeUtf(newChannelColorStr); + }); + playButtonClickSound(); + }).setSelectedTexture(1, -1); // Color block ColorBlockWidget colorBlockWidget = new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) @@ -404,11 +411,27 @@ private void addChannelWidgets(List entries) { // Slot Widget slotWidget = cover.addVirtualEntryWidget(entry, currentX, 0, BUTTON_SIZE, BUTTON_SIZE); channelGroup.addWidget(slotWidget); + currentX += BUTTON_SIZE + MARGIN; + + // Delete button + channelGroup.addWidget( + new ButtonWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE, GuiTextures.BUTTON_CLEAR_GRID, press -> { + writeClientAction(200, buffer -> buffer.writeUtf(cover.getChannelName(entry))); + requestUpdate(); + }) { + + @Override + public boolean isMouseOverElement(double mouseX, double mouseY) { + var isOver = super.isMouseOverElement(mouseX, mouseY); + if (canSelect.getValue() == isOver) canSelect.setValue(!isOver); + return isOver; + } + }); return channelGroup; } - private void sendChannelList() { + private void requestUpdate() { writeClientAction(100, buffer -> buffer.writeBoolean(showChannels.isTrue())); } @@ -431,6 +454,10 @@ public void handleClientAction(int id, FriendlyByteBuf buffer) { buf.writeNbt(entry.serializeNBT()); } }); + } else if (id == 200) { + String channelName = buffer.readUtf(); + VirtualEnderRegistry.getInstance().deleteEntry(cover.getOwner(), EntryTypes.ENDER_FLUID, channelName); + cover.setVirtualEntry(); } } @@ -458,8 +485,8 @@ protected enum Permissions implements EnumSelectorWidget.SelectableEnum { @Override public @NotNull String getTooltip() { return switch (this) { - case PUBLIC -> "cover.ender_fluid_link.private.tooltip.enabled"; - case PRIVATE -> "cover.ender_fluid_link.private.tooltip.disabled"; + case PUBLIC -> "cover.ender_fluid_link.private.tooltip.disabled"; + case PRIVATE -> "cover.ender_fluid_link.private.tooltip.enabled"; }; } From 185ae12f78bd95246fc830a0f69c7366b544efdc Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sun, 22 Dec 2024 16:53:26 +0800 Subject: [PATCH 11/14] add tooltip --- .../resources/assets/gtceu/lang/en_ud.json | 4 ++++ .../resources/assets/gtceu/lang/en_us.json | 4 ++++ .../api/gui/widget/ConfirmTextInputWidget.java | 5 ++++- .../cover/ender/AbstractEnderLinkCover.java | 17 +++++++++-------- .../gtceu/data/lang/LangHandler.java | 4 ++++ 5 files changed, 25 insertions(+), 9 deletions(-) diff --git a/src/generated/resources/assets/gtceu/lang/en_ud.json b/src/generated/resources/assets/gtceu/lang/en_ud.json index 18580338c0..43462b0be5 100644 --- a/src/generated/resources/assets/gtceu/lang/en_ud.json +++ b/src/generated/resources/assets/gtceu/lang/en_ud.json @@ -1958,6 +1958,10 @@ "cover.ender_fluid_link.private.tooltip.disabled.1": "ɹǝʌoɔ ǝɥʇ pǝɔɐןd ʎןןɐuıbıɹo oɥʍ ɹǝʎɐןd ǝɥʇ sǝsn ǝpoɯ ǝʇɐʌıɹԀ", "cover.ender_fluid_link.private.tooltip.enabled": "ǝpoɯ ʞuɐʇ ɔıןqnd oʇ ɥɔʇıʍS", "cover.ender_fluid_link.title": "ʞuıꞀ pınןℲ ɹǝpuƎ", + "cover.ender_fluid_link.tooltip.channel_description": "ʇxǝʇ ʇnduı ɥʇıʍ uoıʇdıɹɔsǝp ןǝuuɐɥɔ ʇǝS", + "cover.ender_fluid_link.tooltip.channel_name": "ʇxǝʇ ʇnduı ɥʇıʍ ǝɯɐu ןǝuuɐɥɔ ʇǝS", + "cover.ender_fluid_link.tooltip.clear_button": "uoıʇdıɹɔsǝp ןǝuuɐɥɔ ɹɐǝןƆ", + "cover.ender_fluid_link.tooltip.list_button": "ʇsıן ןǝuuɐɥɔ ʍoɥS", "cover.filter.blacklist.disabled": "ʇsıןǝʇıɥM", "cover.filter.blacklist.enabled": "ʇsıןʞɔɐןᗺ", "cover.filter.mode.filter_both": "ʇɔɐɹʇxƎ/ʇɹǝsuI ɹǝʇןıℲ", diff --git a/src/generated/resources/assets/gtceu/lang/en_us.json b/src/generated/resources/assets/gtceu/lang/en_us.json index b3fdb619c0..0c3fa2c889 100644 --- a/src/generated/resources/assets/gtceu/lang/en_us.json +++ b/src/generated/resources/assets/gtceu/lang/en_us.json @@ -1958,6 +1958,10 @@ "cover.ender_fluid_link.private.tooltip.disabled.1": "Private mode uses the player who originally placed the cover", "cover.ender_fluid_link.private.tooltip.enabled": "Switch to public tank mode", "cover.ender_fluid_link.title": "Ender Fluid Link", + "cover.ender_fluid_link.tooltip.channel_description": "Set channel description with input text", + "cover.ender_fluid_link.tooltip.channel_name": "Set channel name with input text", + "cover.ender_fluid_link.tooltip.clear_button": "Clear channel description", + "cover.ender_fluid_link.tooltip.list_button": "Show channel list", "cover.filter.blacklist.disabled": "Whitelist", "cover.filter.blacklist.enabled": "Blacklist", "cover.filter.mode.filter_both": "Filter Insert/Extract", diff --git a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java index 0cad7bf5c6..80d7a969cc 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java +++ b/src/main/java/com/gregtechceu/gtceu/api/gui/widget/ConfirmTextInputWidget.java @@ -23,6 +23,8 @@ public class ConfirmTextInputWidget extends WidgetGroup { @Getter(AccessLevel.PRIVATE) @Setter(AccessLevel.PRIVATE) private String inputText = ""; + @Setter + private String tooltip = ""; public ConfirmTextInputWidget(int x, int y, int width, int height, String text, Consumer textResponder, Function validator) { @@ -52,6 +54,7 @@ public void initWidget() { getSizeHeight() - 2, this::getInputText, this::setInputText) - .setValidator(validator)); + .setValidator(validator) + .setHoverTooltips(tooltip)); } } diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index e2cf4e284e..a4ede79e7c 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -286,7 +286,7 @@ private void initWidgets() { mainChannelGroup.addWidget(new ConfirmTextInputWidget(0, WIDGET_BOARD + 2, GROUP_WIDTH - WIDGET_BOARD, WIDGET_BOARD, cover.getEntry().getDescription(), cover.getEntry()::setDescription, - t -> t == null ? "" : t)); + t -> t == null ? "" : t).setTooltip("cover.ender_fluid_link.tooltip.channel_description")); mainGroup.addWidget(mainChannelGroup); mainGroup.addWidget(createWorkingEnabledButton()); @@ -311,7 +311,8 @@ private void initWidgets() { new GuiTextureGroup(GuiTextures.TOGGLE_BUTTON_BACK.getSubTexture(0, 0, 1, 0.5), GuiTextures.BUTTON_LIST), new GuiTextureGroup(GuiTextures.TOGGLE_BUTTON_BACK.getSubTexture(0, 0.5, 1, 0.5), - GuiTextures.BUTTON_LIST)); + GuiTextures.BUTTON_LIST)) + .setHoverTooltips("cover.ender_fluid_link.tooltip.list_button"); } @Contract("_ -> new") @@ -333,7 +334,7 @@ private ConfirmTextInputWidget createConfirmTextInputWidget(int currentX) { return VirtualTank.DEFAULT_COLOR; } return text; - }); + }).setTooltip("cover.ender_fluid_link.tooltip.channel_name"); } @Contract(" -> new") @@ -395,7 +396,7 @@ public boolean allowSelected(double mouseX, double mouseY, int button) { // Color block ColorBlockWidget colorBlockWidget = new ColorBlockWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE) - .setCurrentColor(entry.getColor()); + .setCurrentColor(VirtualEntry.parseColor(entry.getColorStr())); channelGroup.addWidget(colorBlockWidget); currentX += BUTTON_SIZE + MARGIN; @@ -413,7 +414,7 @@ public boolean allowSelected(double mouseX, double mouseY, int button) { channelGroup.addWidget(slotWidget); currentX += BUTTON_SIZE + MARGIN; - // Delete button + // Clear Description button channelGroup.addWidget( new ButtonWidget(currentX, 0, BUTTON_SIZE, BUTTON_SIZE, GuiTextures.BUTTON_CLEAR_GRID, press -> { writeClientAction(200, buffer -> buffer.writeUtf(cover.getChannelName(entry))); @@ -426,7 +427,7 @@ public boolean isMouseOverElement(double mouseX, double mouseY) { if (canSelect.getValue() == isOver) canSelect.setValue(!isOver); return isOver; } - }); + }.appendHoverTooltips("cover.ender_fluid_link.tooltip.clear_button")); return channelGroup; } @@ -456,8 +457,8 @@ public void handleClientAction(int id, FriendlyByteBuf buffer) { }); } else if (id == 200) { String channelName = buffer.readUtf(); - VirtualEnderRegistry.getInstance().deleteEntry(cover.getOwner(), EntryTypes.ENDER_FLUID, channelName); - cover.setVirtualEntry(); + VirtualEnderRegistry.getInstance().getEntry(cover.getOwner(), EntryTypes.ENDER_FLUID, channelName) + .setDescription(""); } } diff --git a/src/main/java/com/gregtechceu/gtceu/data/lang/LangHandler.java b/src/main/java/com/gregtechceu/gtceu/data/lang/LangHandler.java index ecd18e26a5..d0bb2f59f4 100644 --- a/src/main/java/com/gregtechceu/gtceu/data/lang/LangHandler.java +++ b/src/main/java/com/gregtechceu/gtceu/data/lang/LangHandler.java @@ -443,6 +443,10 @@ public static void init(RegistrateLangProvider provider) { provider.add("cover.ender_fluid_link.title", "Ender Fluid Link"); provider.add("cover.ender_fluid_link.iomode.enabled", "I/O Enabled"); provider.add("cover.ender_fluid_link.iomode.disabled", "I/O Disabled"); + provider.add("cover.ender_fluid_link.tooltip.channel_description", "Set channel description with input text"); + provider.add("cover.ender_fluid_link.tooltip.channel_name", "Set channel name with input text"); + provider.add("cover.ender_fluid_link.tooltip.list_button", "Show channel list"); + provider.add("cover.ender_fluid_link.tooltip.clear_button", "Clear channel description"); multilineLang(provider, "cover.ender_fluid_link.private.tooltip.disabled", "Switch to private tank mode\nPrivate mode uses the player who originally placed the cover"); provider.add("cover.ender_fluid_link.private.tooltip.enabled", "Switch to public tank mode"); From e72a09039828d17e3db26d84941496587c138ae8 Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sun, 22 Dec 2024 18:19:11 +0800 Subject: [PATCH 12/14] fix after removed still runs --- .../cover/ender/AbstractEnderLinkCover.java | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index a4ede79e7c..783489e489 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -105,6 +105,16 @@ public void onAttached(@NotNull ItemStack itemStack, @NotNull ServerPlayer playe } } + @Override + public void onRemoved() { + super.onRemoved(); + subscriptionHandler.unsubscribe(); + if (!isRemote()) { + VirtualEnderRegistry.getInstance() + .deleteEntryIf(getOwner(), getEntryType(), getChannelName(), VirtualEntry::canRemove); + } + } + @Override public void onUnload() { super.onUnload(); @@ -271,12 +281,15 @@ public void update() { private void initWidgets() { int currentX = 0; + final var titleGroup = new WidgetGroup(10, 5, GROUP_WIDTH, 20); - this.addWidget(new LabelWidget(10, 5, cover.getUITitle())); - this.addWidget(createToggleButton()); + this.addWidget(titleGroup); this.addWidget(mainGroup); this.addWidget(channelsGroup.setVisible(false)); + titleGroup.addWidget(createToggleButton()); + titleGroup.addWidget(new LabelWidget(15, 3, cover.getUITitle())); + var toggleButtonWidget = createToggleButtonForPrivacy(currentX); mainChannelGroup.addWidget(toggleButtonWidget); currentX += WIDGET_BOARD + 2; @@ -302,7 +315,7 @@ private void initWidgets() { @Contract(" -> new") private @NotNull ToggleButtonWidget createToggleButton() { - return (ToggleButtonWidget) new ToggleButtonWidget(146, 3, 12, 12, showChannels::getValue, cd -> { + return (ToggleButtonWidget) new ToggleButtonWidget(0, 0, 12, 12, showChannels::getValue, cd -> { showChannels.setValue(!showChannels.getValue()); mainGroup.setVisible(showChannels.isFalse()); channelsGroup.setVisible(showChannels.isTrue()); From 90b519d287b8863fdc03ed5ea5a6454b705a32eb Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sun, 22 Dec 2024 20:32:15 +0800 Subject: [PATCH 13/14] larger fluid capacity and api issue --- .../gtceu/api/misc/virtualregistry/entries/VirtualTank.java | 2 +- .../gtceu/common/cover/ender/AbstractEnderLinkCover.java | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java index 183a7e8df9..b142de09b9 100644 --- a/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java +++ b/src/main/java/com/gregtechceu/gtceu/api/misc/virtualregistry/entries/VirtualTank.java @@ -12,7 +12,7 @@ public class VirtualTank extends VirtualEntry { - public static final int DEFAULT_CAPACITY = 64000; // 64B + public static final int DEFAULT_CAPACITY = 160_000; // 160B for per second transfer protected static final String CAPACITY_KEY = "capacity"; protected static final String FLUID_KEY = "fluid"; @NotNull diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index 783489e489..60d341351d 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -457,9 +457,9 @@ public void handleClientAction(int id, FriendlyByteBuf buffer) { cover.setChannelName(newChannelColorStr); } else if (id == 100) { if (!buffer.readBoolean()) return; - var entries = VirtualEnderRegistry.getInstance().getEntryNames(cover.getOwner(), EntryTypes.ENDER_FLUID) + var entries = VirtualEnderRegistry.getInstance().getEntryNames(cover.getOwner(), cover.getEntryType()) .stream().map(name -> VirtualEnderRegistry.getInstance().getEntry(cover.getOwner(), - EntryTypes.ENDER_FLUID, name)) + cover.getEntryType(), name)) .sorted(Comparator.comparing(VirtualEntry::getColorStr)); writeUpdateInfo(101, buf -> { var list = entries.toList(); @@ -470,7 +470,7 @@ public void handleClientAction(int id, FriendlyByteBuf buffer) { }); } else if (id == 200) { String channelName = buffer.readUtf(); - VirtualEnderRegistry.getInstance().getEntry(cover.getOwner(), EntryTypes.ENDER_FLUID, channelName) + VirtualEnderRegistry.getInstance().getEntry(cover.getOwner(), cover.getEntryType(), channelName) .setDescription(""); } } From 355e221b6ff769854a156d3e9eb967bee9800ae8 Mon Sep 17 00:00:00 2001 From: Arborsm Date: Sun, 22 Dec 2024 20:44:43 +0800 Subject: [PATCH 14/14] another api support --- .../gtceu/common/cover/ender/AbstractEnderLinkCover.java | 7 ++++--- .../gtceu/common/cover/ender/EnderFluidLinkCover.java | 6 +++--- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java index 60d341351d..ba303a92ce 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/AbstractEnderLinkCover.java @@ -238,7 +238,8 @@ protected void setManualIOMode(ManualIOMode manualIOMode) { return null; } - protected abstract Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height); + protected abstract Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height, + boolean canClick); protected abstract String getUITitle(); @@ -305,7 +306,7 @@ private void initWidgets() { mainGroup.addWidget(createWorkingEnabledButton()); addEnumSelectorWidgets(); mainGroup.addWidget( - cover.addVirtualEntryWidget(cover.getEntry(), 146, WIDGET_BOARD, WIDGET_BOARD, WIDGET_BOARD)); + cover.addVirtualEntryWidget(cover.getEntry(), 146, WIDGET_BOARD, WIDGET_BOARD, WIDGET_BOARD, true)); if (cover.getFilterHandler() != null) { mainGroup.addWidget(cover.getFilterHandler().createFilterSlotUI(117, 108)); @@ -423,7 +424,7 @@ public boolean allowSelected(double mouseX, double mouseY, int button) { } // Slot - Widget slotWidget = cover.addVirtualEntryWidget(entry, currentX, 0, BUTTON_SIZE, BUTTON_SIZE); + Widget slotWidget = cover.addVirtualEntryWidget(entry, currentX, 0, BUTTON_SIZE, BUTTON_SIZE, false); channelGroup.addWidget(slotWidget); currentX += BUTTON_SIZE + MARGIN; diff --git a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java index 309b306ff4..724a52cd72 100644 --- a/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java +++ b/src/main/java/com/gregtechceu/gtceu/common/cover/ender/EnderFluidLinkCover.java @@ -119,9 +119,9 @@ private int doTransferFluids(int platformTransferLimit) { /// /////////////////////////////////// @Override - protected Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height) { - return new TankWidget(((VirtualTank) entry).getFluidTank(), 0, x, y, width, height, - true, true).setBackground(GuiTextures.FLUID_SLOT); + protected Widget addVirtualEntryWidget(VirtualEntry entry, int x, int y, int width, int height, boolean canClick) { + return new TankWidget(((VirtualTank) entry).getFluidTank(), 0, x, y, width, height, canClick, canClick) + .setBackground(GuiTextures.FLUID_SLOT); } @NotNull