From 82505652ebb18ef7481470dbd4f30c9e2b000824 Mon Sep 17 00:00:00 2001 From: shedaniel Date: Thu, 8 Jun 2023 12:49:18 +0800 Subject: [PATCH] Update to 1.20 and support Forge --- .../event/events/common/LootEvent.java | 14 +- fabric/build.gradle | 4 +- forge/build.gradle | 2 +- .../event/forge/EventHandlerImplClient.java | 22 +-- .../event/forge/EventHandlerImplCommon.java | 9 +- .../LootTableModificationContextImpl.java | 37 ++++- .../mixin/forge/MixinFallingBlockEntity.java | 2 +- .../mixin/forge/MixinLootDataManager.java | 43 ++++++ .../forge/ParticleProviderRegistryImpl.java | 4 +- .../forge/CreativeTabRegistryImpl.java | 131 ++++++++---------- .../main/resources/architectury.mixins.json | 3 +- gradle.properties | 14 +- settings.gradle | 4 +- 13 files changed, 177 insertions(+), 112 deletions(-) create mode 100644 forge/src/main/java/dev/architectury/mixin/forge/MixinLootDataManager.java diff --git a/common/src/main/java/dev/architectury/event/events/common/LootEvent.java b/common/src/main/java/dev/architectury/event/events/common/LootEvent.java index fc60cf84..89752311 100644 --- a/common/src/main/java/dev/architectury/event/events/common/LootEvent.java +++ b/common/src/main/java/dev/architectury/event/events/common/LootEvent.java @@ -25,6 +25,7 @@ import net.minecraft.resources.ResourceLocation; import net.minecraft.world.level.storage.loot.LootDataManager; import net.minecraft.world.level.storage.loot.LootPool; import org.jetbrains.annotations.ApiStatus; +import org.jetbrains.annotations.Nullable; /** * Events related to loot tables and loot generation. @@ -65,13 +66,14 @@ public interface LootEvent { /** * Modifies a loot table. * - * @param lootDataManager the {@link LootDataManager} instance containing all loot tables - * @param id the loot table ID - * @param context the context used to modify the loot table - * @param builtin if {@code true}, the loot table is built-in; - * if {@code false}, it is from a user data pack + * @param lootDataManager the {@link LootDataManager} instance containing all loot tables, + * may be {@code null} + * @param id the loot table ID + * @param context the context used to modify the loot table + * @param builtin if {@code true}, the loot table is built-in; + * if {@code false}, it is from a user data pack */ - void modifyLootTable(LootDataManager lootDataManager, ResourceLocation id, LootTableModificationContext context, boolean builtin); + void modifyLootTable(@Nullable LootDataManager lootDataManager, ResourceLocation id, LootTableModificationContext context, boolean builtin); } /** diff --git a/fabric/build.gradle b/fabric/build.gradle index 552a2878..32578fdd 100644 --- a/fabric/build.gradle +++ b/fabric/build.gradle @@ -113,7 +113,7 @@ unifiedPublishing { displayName = "[Fabric $rootProject.supported_version] v$project.version" releaseType = "$rootProject.artifact_type" changelog = releaseChangelog() - gameVersions = [] + gameVersions = ["1.20"] gameLoaders = ["fabric", "quilt"] mainPublication renameJarForPublication relations { @@ -138,7 +138,7 @@ unifiedPublishing { token = MODRINTH_TOKEN id = rootProject.modrinth_id version = "$project.version+$project.name" - gameVersions.addAll project.minecraft_version + // gameVersions.addAll project.minecraft_version } } } diff --git a/forge/build.gradle b/forge/build.gradle index e35d1f2e..8f931182 100644 --- a/forge/build.gradle +++ b/forge/build.gradle @@ -126,7 +126,7 @@ unifiedPublishing { displayName = "[Forge $rootProject.supported_version] v$project.version" releaseType = "$rootProject.artifact_type" changelog = releaseChangelog() - gameVersions = ["1.19.4"] + gameVersions = ["1.20"] gameLoaders = ["forge"] mainPublication renameJarForPublication diff --git a/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplClient.java b/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplClient.java index 659283f8..c9345d25 100644 --- a/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplClient.java +++ b/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplClient.java @@ -19,7 +19,6 @@ package dev.architectury.event.forge; -import com.mojang.blaze3d.vertex.PoseStack; import dev.architectury.event.CompoundEventResult; import dev.architectury.event.EventResult; import dev.architectury.event.events.client.ClientChatEvent; @@ -29,6 +28,7 @@ import dev.architectury.impl.ScreenAccessImpl; import dev.architectury.impl.TooltipEventColorContextImpl; import dev.architectury.impl.TooltipEventPositionContextImpl; import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.GuiGraphics; import net.minecraft.client.gui.screens.Screen; import net.minecraft.client.multiplayer.ClientLevel; import net.minecraft.network.chat.Component; @@ -59,7 +59,7 @@ public class EventHandlerImplClient { @SubscribeEvent(priority = EventPriority.HIGH) public static void eventRenderGameOverlayEvent(RenderGuiEvent.Post event) { - ClientGuiEvent.RENDER_HUD.invoker().renderHud(event.getPoseStack(), event.getPartialTick()); + ClientGuiEvent.RENDER_HUD.invoker().renderHud(event.getGuiGraphics(), event.getPartialTick()); } @SubscribeEvent(priority = EventPriority.HIGH) @@ -137,24 +137,24 @@ public class EventHandlerImplClient { @SubscribeEvent(priority = EventPriority.HIGH) public static void eventDrawScreenEvent(ScreenEvent.Render.Pre event) { - if (ClientGuiEvent.RENDER_PRE.invoker().render(event.getScreen(), event.getPoseStack(), event.getMouseX(), event.getMouseY(), event.getPartialTick()).isFalse()) { + if (ClientGuiEvent.RENDER_PRE.invoker().render(event.getScreen(), event.getGuiGraphics(), event.getMouseX(), event.getMouseY(), event.getPartialTick()).isFalse()) { event.setCanceled(true); } } @SubscribeEvent(priority = EventPriority.HIGH) public static void eventDrawScreenEvent(ScreenEvent.Render.Post event) { - ClientGuiEvent.RENDER_POST.invoker().render(event.getScreen(), event.getPoseStack(), event.getMouseX(), event.getMouseY(), event.getPartialTick()); + ClientGuiEvent.RENDER_POST.invoker().render(event.getScreen(), event.getGuiGraphics(), event.getMouseX(), event.getMouseY(), event.getPartialTick()); } @SubscribeEvent(priority = EventPriority.HIGH) public static void eventContainerScreenEvent(ContainerScreenEvent.Render.Background event) { - ClientGuiEvent.RENDER_CONTAINER_BACKGROUND.invoker().render(event.getContainerScreen(), event.getPoseStack(), event.getMouseX(), event.getMouseY(), Minecraft.getInstance().getDeltaFrameTime()); + ClientGuiEvent.RENDER_CONTAINER_BACKGROUND.invoker().render(event.getContainerScreen(), event.getGuiGraphics(), event.getMouseX(), event.getMouseY(), Minecraft.getInstance().getDeltaFrameTime()); } @SubscribeEvent(priority = EventPriority.HIGH) public static void eventContainerScreenEvent(ContainerScreenEvent.Render.Foreground event) { - ClientGuiEvent.RENDER_CONTAINER_FOREGROUND.invoker().render(event.getContainerScreen(), event.getPoseStack(), event.getMouseX(), event.getMouseY(), Minecraft.getInstance().getDeltaFrameTime()); + ClientGuiEvent.RENDER_CONTAINER_FOREGROUND.invoker().render(event.getContainerScreen(), event.getGuiGraphics(), event.getMouseX(), event.getMouseY(), Minecraft.getInstance().getDeltaFrameTime()); } @SubscribeEvent(priority = EventPriority.HIGH) @@ -177,18 +177,18 @@ public class EventHandlerImplClient { @SubscribeEvent(priority = EventPriority.HIGH) public static void eventRenderTooltipEvent(RenderTooltipEvent.Pre event) { - PoseStack stack = event.getPoseStack(); + GuiGraphics graphics = event.getGraphics(); ClientTooltipEvent.additionalContexts().setItem(event.getItemStack()); try { - if (ClientTooltipEvent.RENDER_PRE.invoker().renderTooltip(stack, event.getComponents(), event.getX(), event.getY()).isFalse()) { + if (ClientTooltipEvent.RENDER_PRE.invoker().renderTooltip(graphics, event.getComponents(), event.getX(), event.getY()).isFalse()) { event.setCanceled(true); return; } TooltipEventPositionContextImpl positionContext = tooltipPositionContext.get(); positionContext.reset(event.getX(), event.getY()); - ClientTooltipEvent.RENDER_MODIFY_POSITION.invoker().renderTooltip(stack, positionContext); + ClientTooltipEvent.RENDER_MODIFY_POSITION.invoker().renderTooltip(graphics, positionContext); event.setX(positionContext.getTooltipX()); event.setY(positionContext.getTooltipY()); } finally { @@ -198,7 +198,7 @@ public class EventHandlerImplClient { @SubscribeEvent(priority = EventPriority.HIGH) public static void eventRenderTooltipEvent(RenderTooltipEvent.Color event) { - PoseStack stack = event.getPoseStack(); + GuiGraphics graphics = event.getGraphics(); ClientTooltipEvent.additionalContexts().setItem(event.getItemStack()); try { @@ -207,7 +207,7 @@ public class EventHandlerImplClient { colorContext.setBackgroundColor(event.getBackgroundStart()); colorContext.setOutlineGradientTopColor(event.getBorderStart()); colorContext.setOutlineGradientBottomColor(event.getBorderEnd()); - // ClientTooltipEvent.RENDER_MODIFY_COLOR.invoker().renderTooltip(stack, event.getX(), event.getY(), colorContext); + // ClientTooltipEvent.RENDER_MODIFY_COLOR.invoker().renderTooltip(graphics, event.getX(), event.getY(), colorContext); event.setBackground(colorContext.getBackgroundColor()); event.setBorderEnd(colorContext.getOutlineGradientBottomColor()); event.setBorderStart(colorContext.getOutlineGradientTopColor()); diff --git a/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplCommon.java b/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplCommon.java index 5d26a85b..617a0bcb 100644 --- a/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplCommon.java +++ b/forge/src/main/java/dev/architectury/event/forge/EventHandlerImplCommon.java @@ -30,6 +30,7 @@ import net.minecraft.server.level.ServerPlayer; import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.Level; import net.minecraft.world.level.LevelAccessor; +import net.minecraft.world.level.storage.loot.LootDataManager; import net.minecraftforge.event.CommandEvent; import net.minecraftforge.event.LootTableLoadEvent; import net.minecraftforge.event.RegisterCommandsEvent; @@ -61,7 +62,11 @@ import net.minecraftforge.fml.LogicalSide; import net.minecraftforge.fml.event.lifecycle.FMLCommonSetupEvent; import net.minecraftforge.server.ServerLifecycleHooks; +import java.lang.ref.WeakReference; + public class EventHandlerImplCommon { + public static WeakReference lootDataManagerRef = null; + @SubscribeEvent(priority = EventPriority.HIGH) public static void event(ServerTickEvent event) { if (event.phase == Phase.START) @@ -418,12 +423,12 @@ public class EventHandlerImplCommon { @SubscribeEvent(priority = EventPriority.HIGH) public static void event(LootTableLoadEvent event) { - LootEvent.MODIFY_LOOT_TABLE.invoker().modifyLootTable(event.getLootTableManager(), event.getName(), new LootTableModificationContextImpl(event.getTable()), true); + LootEvent.MODIFY_LOOT_TABLE.invoker().modifyLootTable(lootDataManagerRef == null ? null : lootDataManagerRef.get(), event.getName(), new LootTableModificationContextImpl(event.getTable()), true); } @SubscribeEvent(priority = EventPriority.HIGH) public static void event(AttackEntityEvent event) { - EventResult result = PlayerEvent.ATTACK_ENTITY.invoker().attack(event.getEntity(), event.getEntity().level, event.getTarget(), event.getEntity().getUsedItemHand(), null); + EventResult result = PlayerEvent.ATTACK_ENTITY.invoker().attack(event.getEntity(), event.getEntity().level(), event.getTarget(), event.getEntity().getUsedItemHand(), null); if (result.isFalse()) { event.setCanceled(true); } diff --git a/forge/src/main/java/dev/architectury/event/forge/LootTableModificationContextImpl.java b/forge/src/main/java/dev/architectury/event/forge/LootTableModificationContextImpl.java index b8eff2ea..db262cae 100644 --- a/forge/src/main/java/dev/architectury/event/forge/LootTableModificationContextImpl.java +++ b/forge/src/main/java/dev/architectury/event/forge/LootTableModificationContextImpl.java @@ -22,16 +22,51 @@ package dev.architectury.event.forge; import dev.architectury.event.events.common.LootEvent; import net.minecraft.world.level.storage.loot.LootPool; import net.minecraft.world.level.storage.loot.LootTable; +import net.minecraftforge.fml.util.ObfuscationReflectionHelper; + +import java.lang.reflect.Field; +import java.util.List; final class LootTableModificationContextImpl implements LootEvent.LootTableModificationContext { private final LootTable table; + private final List pools; LootTableModificationContextImpl(LootTable table) { this.table = table; + + // This field has the type changed to List by Forge + // Since this is rather unsafe, we are making sure 100% we are getting it + List pools = null; + try { + pools = ObfuscationReflectionHelper.getPrivateValue(LootTable.class, table, "f_79109_"); + } catch (ObfuscationReflectionHelper.UnableToFindFieldException ignored) { + for (Field field : LootTable.class.getDeclaredFields()) { + if (field.getType().equals(List.class)) { + // This is probably the field + field.setAccessible(true); + try { + pools = (List) field.get(table); + } catch (IllegalAccessException e) { + throw new RuntimeException(e); + } + } + } + + if (pools == null) { + throw new RuntimeException("Unable to find pools field in LootTable!"); + } + } + + this.pools = pools; } @Override public void addPool(LootPool pool) { - table.addPool(pool); + this.pools.add(pool); + } + + @Override + public void addPool(LootPool.Builder pool) { + this.pools.add(pool.build()); } } diff --git a/forge/src/main/java/dev/architectury/mixin/forge/MixinFallingBlockEntity.java b/forge/src/main/java/dev/architectury/mixin/forge/MixinFallingBlockEntity.java index b968f332..99610e6f 100644 --- a/forge/src/main/java/dev/architectury/mixin/forge/MixinFallingBlockEntity.java +++ b/forge/src/main/java/dev/architectury/mixin/forge/MixinFallingBlockEntity.java @@ -47,6 +47,6 @@ public abstract class MixinFallingBlockEntity extends Entity { target = "Lnet/minecraft/world/level/block/Fallable;onLand(Lnet/minecraft/world/level/Level;Lnet/minecraft/core/BlockPos;Lnet/minecraft/world/level/block/state/BlockState;Lnet/minecraft/world/level/block/state/BlockState;Lnet/minecraft/world/entity/item/FallingBlockEntity;)V"), locals = LocalCapture.CAPTURE_FAILHARD) public void handleLand(CallbackInfo ci, Block block, BlockPos blockPos2, boolean bl, boolean bl2, double d, BlockState blockState) { - BlockEvent.FALLING_LAND.invoker().onLand(this.level, blockPos2, this.blockState, blockState, (FallingBlockEntity) (Object) this); + BlockEvent.FALLING_LAND.invoker().onLand(this.level(), blockPos2, this.blockState, blockState, (FallingBlockEntity) (Object) this); } } diff --git a/forge/src/main/java/dev/architectury/mixin/forge/MixinLootDataManager.java b/forge/src/main/java/dev/architectury/mixin/forge/MixinLootDataManager.java new file mode 100644 index 00000000..bea92674 --- /dev/null +++ b/forge/src/main/java/dev/architectury/mixin/forge/MixinLootDataManager.java @@ -0,0 +1,43 @@ +/* + * This file is part of architectury. + * Copyright (C) 2020, 2021, 2022 architectury + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +package dev.architectury.mixin.forge; + +import dev.architectury.event.forge.EventHandlerImplCommon; +import net.minecraft.server.packs.resources.PreparableReloadListener; +import net.minecraft.server.packs.resources.ResourceManager; +import net.minecraft.util.profiling.ProfilerFiller; +import net.minecraft.world.level.storage.loot.LootDataManager; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; + +import java.lang.ref.WeakReference; +import java.util.concurrent.CompletableFuture; +import java.util.concurrent.Executor; + +@Mixin(LootDataManager.class) +public class MixinLootDataManager { + @Inject(method = "reload", at = @At("HEAD")) + private void reload(PreparableReloadListener.PreparationBarrier arg, ResourceManager arg2, ProfilerFiller arg3, + ProfilerFiller arg4, Executor executor, Executor executor2, CallbackInfoReturnable> cir) { + EventHandlerImplCommon.lootDataManagerRef = new WeakReference<>((LootDataManager) (Object) this); + } +} diff --git a/forge/src/main/java/dev/architectury/registry/client/particle/forge/ParticleProviderRegistryImpl.java b/forge/src/main/java/dev/architectury/registry/client/particle/forge/ParticleProviderRegistryImpl.java index ad3641ce..b081a03e 100644 --- a/forge/src/main/java/dev/architectury/registry/client/particle/forge/ParticleProviderRegistryImpl.java +++ b/forge/src/main/java/dev/architectury/registry/client/particle/forge/ParticleProviderRegistryImpl.java @@ -127,12 +127,12 @@ public class ParticleProviderRegistryImpl { return new ParticleProviderRegistrar() { @Override public void register(ParticleType type, ParticleProvider provider) { - event.register(type, provider); + event.registerSpecial(type, provider); } @Override public void register(ParticleType type, ParticleEngine.SpriteParticleRegistration registration) { - event.register(type, registration); + event.registerSpriteSet(type, registration); } }; } diff --git a/forge/src/main/java/dev/architectury/registry/forge/CreativeTabRegistryImpl.java b/forge/src/main/java/dev/architectury/registry/forge/CreativeTabRegistryImpl.java index c44c8f1c..7a3eedce 100644 --- a/forge/src/main/java/dev/architectury/registry/forge/CreativeTabRegistryImpl.java +++ b/forge/src/main/java/dev/architectury/registry/forge/CreativeTabRegistryImpl.java @@ -25,15 +25,16 @@ import com.google.common.collect.MultimapBuilder; import dev.architectury.forge.ArchitecturyForge; import dev.architectury.registry.CreativeTabOutput; import dev.architectury.registry.CreativeTabRegistry; -import dev.architectury.registry.CreativeTabRegistry.TabSupplier; -import net.minecraft.network.chat.Component; +import dev.architectury.registry.registries.DeferredSupplier; +import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.core.registries.Registries; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.item.CreativeModeTab; import net.minecraft.world.item.ItemStack; import net.minecraftforge.api.distmarker.Dist; import net.minecraftforge.common.CreativeModeTabRegistry; import net.minecraftforge.common.util.MutableHashedLinkedMap; -import net.minecraftforge.event.CreativeModeTabEvent; +import net.minecraftforge.event.BuildCreativeModeTabContentsEvent; import net.minecraftforge.eventbus.api.SubscribeEvent; import net.minecraftforge.fml.common.Mod; import org.apache.logging.log4j.LogManager; @@ -49,9 +50,7 @@ import java.util.function.Supplier; public class CreativeTabRegistryImpl { private static final Logger LOGGER = LogManager.getLogger(CreativeTabRegistryImpl.class); - @Nullable - private static List> registerListeners = new ArrayList<>(); - private static final List> BUILD_CONTENTS_LISTENERS = new ArrayList<>(); + private static final List> BUILD_CONTENTS_LISTENERS = new ArrayList<>(); private static final Multimap> APPENDS = MultimapBuilder.hashKeys().arrayListValues().build(); static { @@ -61,7 +60,7 @@ public class CreativeTabRegistryImpl { .map(Supplier::get) .toList()); if (keyEntry.getKey() instanceof TabKey.SupplierTabKey supplierTabKey) { - if (Objects.equals(CreativeModeTabRegistry.getName(event.getTab()), supplierTabKey.supplier().getName())) { + if (Objects.equals(CreativeModeTabRegistry.getName(event.getTab()), supplierTabKey.supplier().getId())) { for (ItemStack stack : stacks.get()) { event.getEntries().put(stack, CreativeModeTab.TabVisibility.PARENT_AND_SEARCH_TABS); } @@ -78,67 +77,34 @@ public class CreativeTabRegistryImpl { } @SubscribeEvent - public static void event(CreativeModeTabEvent.Register event) { - if (registerListeners != null) { - for (Consumer listener : registerListeners) { - listener.accept(event); - } - registerListeners = null; - } else { - LOGGER.warn("Creative tab listeners were already registered!"); - } - } - - @SubscribeEvent - public static void event(CreativeModeTabEvent.BuildContents event) { - for (Consumer listener : BUILD_CONTENTS_LISTENERS) { + public static void event(BuildCreativeModeTabContentsEvent event) { + for (Consumer listener : BUILD_CONTENTS_LISTENERS) { listener.accept(event); } } - public static TabSupplier create(ResourceLocation name, Consumer callback) { - if (registerListeners == null) { - throw new IllegalStateException("Creative tab listeners were already registered!"); - } - CreativeModeTab[] tab = new CreativeModeTab[1]; - registerListeners.add(register -> { - tab[0] = register.registerCreativeModeTab(name, builder -> { - builder.title(Component.translatable("itemGroup.%s.%s".formatted(name.getNamespace(), name.getPath()))); - callback.accept(builder); - }); - }); - return new TabSupplier() { - @Override - public ResourceLocation getName() { - return name; - } - - @Override - public CreativeModeTab get() { - if (tab[0] == null) { - throw new IllegalStateException("Creative tab %s was not registered yet!".formatted(name)); - } - - return tab[0]; - } - - @Override - public boolean isPresent() { - return tab[0] != null; - } - }; + @ApiStatus.Experimental + public static CreativeModeTab create(Consumer callback) { + CreativeModeTab.Builder builder = CreativeModeTab.builder(); + callback.accept(builder); + return builder.build(); } @ApiStatus.Experimental - public static TabSupplier ofBuiltin(CreativeModeTab tab) { - ResourceLocation location = CreativeModeTabRegistry.getName(tab); - if (location == null) { - throw new IllegalArgumentException("Tab %s is not registered!".formatted(tab)); + public static DeferredSupplier ofBuiltin(CreativeModeTab tab) { + ResourceLocation key = BuiltInRegistries.CREATIVE_MODE_TAB.getKey(tab); + if (key == null) { + throw new IllegalArgumentException("Builtin tab %s is not registered!".formatted(tab)); } - return new TabSupplier() { + return new DeferredSupplier<>() { @Override - public ResourceLocation getName() { - return location; + public ResourceLocation getRegistryId() { + return Registries.CREATIVE_MODE_TAB.location(); + } + + @Override + public ResourceLocation getId() { + return BuiltInRegistries.CREATIVE_MODE_TAB.getKey(tab); } @Override @@ -154,37 +120,50 @@ public class CreativeTabRegistryImpl { } @ApiStatus.Experimental - public static TabSupplier defer(ResourceLocation name) { - return new TabSupplier() { + public static DeferredSupplier defer(ResourceLocation name) { + return new DeferredSupplier<>() { + @Nullable + private CreativeModeTab tab; + @Override - public ResourceLocation getName() { + public ResourceLocation getRegistryId() { + return Registries.CREATIVE_MODE_TAB.location(); + } + + @Override + public ResourceLocation getId() { return name; } @Override - public boolean isPresent() { - return CreativeModeTabRegistry.getTab(name) != null; + public CreativeModeTab get() { + resolve(); + if (tab == null) + throw new IllegalStateException("Creative tab %s was not registered yet!".formatted(name)); + return tab; } @Override - public CreativeModeTab get() { - CreativeModeTab tab = CreativeModeTabRegistry.getTab(name); - if (tab == null) { - throw new IllegalStateException("Creative tab %s was not registered yet!".formatted(name)); - } else { - return tab; + public boolean isPresent() { + resolve(); + return tab != null; + } + + private void resolve() { + if (this.tab == null) { + this.tab = BuiltInRegistries.CREATIVE_MODE_TAB.get(name); } } }; } - public static void modify(TabSupplier tab, CreativeTabRegistry.ModifyTabCallback filler) { + public static void modify(DeferredSupplier tab, CreativeTabRegistry.ModifyTabCallback filler) { BUILD_CONTENTS_LISTENERS.add(event -> { if (tab.isPresent()) { if (event.getTab().equals(tab.get())) { filler.accept(event.getFlags(), wrapTabOutput(event.getEntries()), event.hasPermissions()); } - } else if (Objects.equals(CreativeModeTabRegistry.getName(event.getTab()), tab.getName())) { + } else if (Objects.equals(CreativeModeTabRegistry.getName(event.getTab()), tab.getId())) { filler.accept(event.getFlags(), wrapTabOutput(event.getEntries()), event.hasPermissions()); } }); @@ -213,22 +192,22 @@ public class CreativeTabRegistryImpl { } @ApiStatus.Experimental - public static void appendStack(TabSupplier tab, Supplier item) { + public static void appendStack(DeferredSupplier tab, Supplier item) { APPENDS.put(new TabKey.SupplierTabKey(tab), item); } private interface TabKey { - record SupplierTabKey(TabSupplier supplier) implements TabKey { + record SupplierTabKey(DeferredSupplier supplier) implements TabKey { @Override public boolean equals(Object o) { if (this == o) return true; if (!(o instanceof SupplierTabKey that)) return false; - return Objects.equals(supplier.getName(), that.supplier.getName()); + return Objects.equals(supplier.getId(), that.supplier.getId()); } @Override public int hashCode() { - return Objects.hash(supplier.getName()); + return Objects.hash(supplier.getId()); } } diff --git a/forge/src/main/resources/architectury.mixins.json b/forge/src/main/resources/architectury.mixins.json index f2ee348f..4242d539 100644 --- a/forge/src/main/resources/architectury.mixins.json +++ b/forge/src/main/resources/architectury.mixins.json @@ -13,7 +13,8 @@ "MixinEntitySpawnExtension", "MixinFallingBlockEntity", "MixinItemExtension", - "MixinLevelEvent" + "MixinLevelEvent", + "MixinLootDataManager" ], "injectors": { "defaultRequire": 1 diff --git a/gradle.properties b/gradle.properties index 1a83a1f6..4987a239 100644 --- a/gradle.properties +++ b/gradle.properties @@ -1,10 +1,10 @@ org.gradle.jvmargs=-Xmx6G org.gradle.daemon=false -platforms=fabric +platforms=fabric,forge -minecraft_version=1.20-pre5 -supported_version=1.20-pre5 +minecraft_version=1.20 +supported_version=1.20 artifact_type=beta @@ -13,11 +13,11 @@ archives_base_name_snapshot=architectury-snapshot base_version=9.0 maven_group=dev.architectury -fabric_loader_version=0.14.20 -fabric_api_version=0.81.3+1.20 -mod_menu_version=5.0.2 +fabric_loader_version=0.14.21 +fabric_api_version=0.83.0+1.20 +mod_menu_version=7.0.0 -forge_version=45.0.24 +forge_version=46.0.1 curseforge_id=419699 modrinth_id=lhGA9TYQ diff --git a/settings.gradle b/settings.gradle index 0f4b94fd..8bfde812 100644 --- a/settings.gradle +++ b/settings.gradle @@ -13,9 +13,9 @@ if (JavaVersion.current().ordinal() + 1 < 17) { include("common") include("fabric") -//include("forge") +include("forge") include("testmod-common") include("testmod-fabric") -//include("testmod-forge") +include("testmod-forge") rootProject.name = "architectury"