From 7da7dddafa9f2e7894d8363de1787e4a09f58fbe Mon Sep 17 00:00:00 2001 From: IM23a-spirgif Date: Tue, 10 Jun 2025 14:46:49 +0200 Subject: [PATCH] Added Stalinium Cache block with shared party inventory functionality. Updated loot tables, block entities, menus, and localized translations. Bumped version to 0.2.0. --- gradle.properties | 2 +- .../krituximon/stalinium/block/ModBlocks.java | 5 ++ .../block/custom/StaliniumCacheBlock.java | 82 +++++++++++++++++++ .../block/custom/StaliniumPressBlock.java | 1 - .../block/entity/ModBlockEntities.java | 8 ++ .../entity/StaliniumCacheBlockEntity.java | 70 ++++++++++++++++ .../datagen/ModBlockLootTableProvider.java | 1 + .../stalinium/screen/ModMenuTypes.java | 27 ++++-- .../assets/stalinium/lang/en_us.json | 5 +- 9 files changed, 190 insertions(+), 11 deletions(-) create mode 100644 src/main/java/net/krituximon/stalinium/block/custom/StaliniumCacheBlock.java create mode 100644 src/main/java/net/krituximon/stalinium/block/entity/StaliniumCacheBlockEntity.java diff --git a/gradle.properties b/gradle.properties index c55df21..f95dd66 100644 --- a/gradle.properties +++ b/gradle.properties @@ -36,7 +36,7 @@ mod_name=Stalinium # The license of the mod. Review your options at https://choosealicense.com/. All Rights Reserved is the default. mod_license=MIT # The mod version. See https://semver.org/ -mod_version=0.1.7 +mod_version=0.2.0 # The group ID for the mod. It is only important when publishing as an artifact to a Maven repository. # This should match the base package used for the mod sources. # See https://maven.apache.org/guides/mini/guide-naming-conventions.html diff --git a/src/main/java/net/krituximon/stalinium/block/ModBlocks.java b/src/main/java/net/krituximon/stalinium/block/ModBlocks.java index 23099cb..fa49bdd 100644 --- a/src/main/java/net/krituximon/stalinium/block/ModBlocks.java +++ b/src/main/java/net/krituximon/stalinium/block/ModBlocks.java @@ -2,6 +2,7 @@ package net.krituximon.stalinium.block; import net.krituximon.stalinium.Stalinium; import net.krituximon.stalinium.block.custom.CompressedBedrock; +import net.krituximon.stalinium.block.custom.StaliniumCacheBlock; import net.krituximon.stalinium.block.custom.StaliniumPressBlock; import net.krituximon.stalinium.item.ModItems; import net.minecraft.util.valueproviders.UniformInt; @@ -46,6 +47,10 @@ public class ModBlocks { public static final DeferredBlock STALINIUM_PRESS = registerBlock("stalinium_press", () -> new StaliniumPressBlock(BlockBehaviour.Properties.of())); + public static final DeferredBlock STALINIUM_CACHE = registerBlock( + "stalinium_cache", + () -> new StaliniumCacheBlock(Block.Properties.of())); + private static DeferredBlock registerBlock(String name, Supplier block) { DeferredBlock toReturn = BLOCKS.register(name, block); registerBlockItem(name, toReturn); diff --git a/src/main/java/net/krituximon/stalinium/block/custom/StaliniumCacheBlock.java b/src/main/java/net/krituximon/stalinium/block/custom/StaliniumCacheBlock.java new file mode 100644 index 0000000..fc1b2aa --- /dev/null +++ b/src/main/java/net/krituximon/stalinium/block/custom/StaliniumCacheBlock.java @@ -0,0 +1,82 @@ +package net.krituximon.stalinium.block.custom; + +import com.mojang.serialization.MapCodec; +import net.krituximon.stalinium.block.entity.ModBlockEntities; +import net.krituximon.stalinium.block.entity.StaliniumCacheBlockEntity; +import net.minecraft.core.BlockPos; +import net.minecraft.network.chat.Component; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.*; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.inventory.ChestMenu; +import net.minecraft.world.item.ItemStack; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.block.BaseEntityBlock; +import net.minecraft.world.level.block.RenderShape; +import net.minecraft.world.level.block.entity.BlockEntity; +import net.minecraft.world.level.block.entity.BlockEntityTicker; +import net.minecraft.world.level.block.entity.BlockEntityType; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.phys.BlockHitResult; + +import org.jetbrains.annotations.Nullable; + +public class StaliniumCacheBlock extends BaseEntityBlock { + // 1) supply a real codec so the block actually constructs from your registry + public static final MapCodec CODEC = + simpleCodec(StaliniumCacheBlock::new); + + public StaliniumCacheBlock(Properties props) { + super(props); + } + + @Override + protected MapCodec codec() { + return CODEC; + } + + @Nullable + @Override + public BlockEntity newBlockEntity(BlockPos pos, BlockState state) { + return ModBlockEntities.STALINIUM_CACHE_BE.get().create(pos, state); + } + + @Override + protected RenderShape getRenderShape(BlockState state) { + return RenderShape.MODEL; + } + + @Override + protected ItemInteractionResult useItemOn(ItemStack stack, BlockState state, Level level, + BlockPos pos, Player player, InteractionHand hand, + BlockHitResult hit) { + if (!level.isClientSide() && player instanceof ServerPlayer sp) { + var container = StaliniumCacheBlockEntity.getPartyInventory(sp); + sp.openMenu(new SimpleMenuProvider( + (id, inv, p) -> ChestMenu.threeRows(id, inv, container), + Component.translatable("container.stalinium.cache") + ), pos); + } + return ItemInteractionResult.sidedSuccess(level.isClientSide()); + } + + + @Override + @SuppressWarnings("unchecked") + public BlockEntityTicker getTicker( + Level level, BlockState state, BlockEntityType type) { + return null; + } + + @Override + public void onRemove(BlockState oldSt, Level world, BlockPos pos, + BlockState newSt, boolean moving) { + if (!oldSt.is(newSt.getBlock())) { + var be = world.getBlockEntity(pos); + if (be instanceof StaliniumCacheBlockEntity cache) { + cache.drops(); + } + } + super.onRemove(oldSt, world, pos, newSt, moving); + } +} \ No newline at end of file diff --git a/src/main/java/net/krituximon/stalinium/block/custom/StaliniumPressBlock.java b/src/main/java/net/krituximon/stalinium/block/custom/StaliniumPressBlock.java index ccaf466..7b3b949 100644 --- a/src/main/java/net/krituximon/stalinium/block/custom/StaliniumPressBlock.java +++ b/src/main/java/net/krituximon/stalinium/block/custom/StaliniumPressBlock.java @@ -64,7 +64,6 @@ public class StaliniumPressBlock extends BaseEntityBlock { throw new IllegalStateException("Our Container provider is missing!"); } } - return ItemInteractionResult.sidedSuccess(pLevel.isClientSide()); } diff --git a/src/main/java/net/krituximon/stalinium/block/entity/ModBlockEntities.java b/src/main/java/net/krituximon/stalinium/block/entity/ModBlockEntities.java index 5c53798..f2ac715 100644 --- a/src/main/java/net/krituximon/stalinium/block/entity/ModBlockEntities.java +++ b/src/main/java/net/krituximon/stalinium/block/entity/ModBlockEntities.java @@ -19,6 +19,14 @@ public class ModBlockEntities { BLOCK_ENTITIES.register("stalinium_press_be", () -> BlockEntityType.Builder.of( StaliniumPressBlockEntity::new, ModBlocks.STALINIUM_PRESS.get()).build(null)); + public static final Supplier> STALINIUM_CACHE_BE = + BLOCK_ENTITIES.register("stalinium_cache", () -> + BlockEntityType.Builder.of( + StaliniumCacheBlockEntity::new, + ModBlocks.STALINIUM_CACHE.get() + ).build(null) + ); + public static void register(IEventBus eventBus) { BLOCK_ENTITIES.register(eventBus); } diff --git a/src/main/java/net/krituximon/stalinium/block/entity/StaliniumCacheBlockEntity.java b/src/main/java/net/krituximon/stalinium/block/entity/StaliniumCacheBlockEntity.java new file mode 100644 index 0000000..b11530f --- /dev/null +++ b/src/main/java/net/krituximon/stalinium/block/entity/StaliniumCacheBlockEntity.java @@ -0,0 +1,70 @@ +// StaliniumCacheBlockEntity.java + +package net.krituximon.stalinium.block.entity; + +import net.krituximon.stalinium.event.ComradeHandler; +import net.minecraft.core.BlockPos; +import net.minecraft.core.HolderLookup; +import net.minecraft.core.registries.Registries; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.network.protocol.Packet; +import net.minecraft.network.protocol.game.ClientGamePacketListener; +import net.minecraft.network.protocol.game.ClientboundBlockEntityDataPacket; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.world.Containers; +import net.minecraft.world.SimpleContainer; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.inventory.ContainerData; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.block.entity.BlockEntity; +import net.minecraft.world.level.block.entity.BlockEntityType; +import net.minecraft.world.level.block.state.BlockState; + +import javax.annotation.Nullable; +import java.util.Map; +import java.util.Optional; +import java.util.UUID; +import java.util.concurrent.ConcurrentHashMap; + +public class StaliniumCacheBlockEntity extends BlockEntity { + private static final int SIZE = 27; + + // each party → shared 27‐slot inventory + private static final Map PARTY_INVENTORIES = new ConcurrentHashMap<>(); + + public StaliniumCacheBlockEntity(BlockPos pos, BlockState state) { + super(ModBlockEntities.STALINIUM_CACHE_BE.get(), pos, state); + } + + /** + * Grab (or create) the shared SimpleContainer for this player's party + */ + public static SimpleContainer getPartyInventory(Player who) { + Optional opt = ComradeHandler.findPartyOf(who.getUUID()); + UUID key = opt.map(p -> p.leader).orElse(who.getUUID()); + return PARTY_INVENTORIES.computeIfAbsent(key, __ -> new SimpleContainer(SIZE)); + } + + /** Drop everything, using that same shared container */ + public void drops() { + SimpleContainer inv = getPartyInventory((ServerPlayer) null); + // actually, we don't know "who" here—just drop all slots + SimpleContainer tmp = new SimpleContainer(SIZE); + for (int i = 0; i < SIZE; i++) { + tmp.setItem(i, inv.getItem(i)); + } + Containers.dropContents(level, worldPosition, tmp); + } + + @Override + protected void saveAdditional(CompoundTag tag, HolderLookup.Provider prov) { + super.saveAdditional(tag, prov); + } + + @Override + @Nullable + public Packet getUpdatePacket() { + return ClientboundBlockEntityDataPacket.create(this); + } +} diff --git a/src/main/java/net/krituximon/stalinium/datagen/ModBlockLootTableProvider.java b/src/main/java/net/krituximon/stalinium/datagen/ModBlockLootTableProvider.java index 9aeac33..81fd240 100644 --- a/src/main/java/net/krituximon/stalinium/datagen/ModBlockLootTableProvider.java +++ b/src/main/java/net/krituximon/stalinium/datagen/ModBlockLootTableProvider.java @@ -38,6 +38,7 @@ public class ModBlockLootTableProvider extends BlockLootSubProvider { dropSelf(ModBlocks.STALINIUM_BLOCK.get()); dropSelf(ModBlocks.COMPRESSED_BEDROCK.get()); dropSelf(ModBlocks.STALINIUM_PRESS.get()); + dropSelf(ModBlocks.STALINIUM_CACHE.get()); } diff --git a/src/main/java/net/krituximon/stalinium/screen/ModMenuTypes.java b/src/main/java/net/krituximon/stalinium/screen/ModMenuTypes.java index e917d3c..a79afdf 100644 --- a/src/main/java/net/krituximon/stalinium/screen/ModMenuTypes.java +++ b/src/main/java/net/krituximon/stalinium/screen/ModMenuTypes.java @@ -3,7 +3,9 @@ package net.krituximon.stalinium.screen; import net.krituximon.stalinium.Stalinium; import net.krituximon.stalinium.screen.custom.StaliniumPressMenu; import net.minecraft.core.registries.Registries; +import net.minecraft.world.SimpleContainer; import net.minecraft.world.inventory.AbstractContainerMenu; +import net.minecraft.world.inventory.ChestMenu; import net.minecraft.world.inventory.MenuType; import net.neoforged.bus.api.IEventBus; import net.neoforged.neoforge.common.extensions.IMenuTypeExtension; @@ -15,15 +17,24 @@ public class ModMenuTypes { public static final DeferredRegister> MENUS = DeferredRegister.create(Registries.MENU, Stalinium.MODID); - public static final DeferredHolder, MenuType> STALINIUM_PRESS_MENU = - registerMenuType("stalinium_press_menu", StaliniumPressMenu::new); - - private static DeferredHolder, MenuType> registerMenuType(String name, - IContainerFactory factory) { - return MENUS.register(name, () -> IMenuTypeExtension.create(factory)); + @SuppressWarnings("unchecked") + private static DeferredHolder, MenuType> + registerMenuType(String name, IContainerFactory factory) { + return (DeferredHolder, MenuType>) (Object) MENUS.register(name, () -> IMenuTypeExtension.create(factory)); } - public static void register(IEventBus eventBus) { - MENUS.register(eventBus); + // press menu + public static final DeferredHolder,MenuType> + STALINIUM_PRESS_MENU = registerMenuType("stalinium_press_menu", StaliniumPressMenu::new); + + // cache menu — *also* use registerMenuType so the generics line up: + public static final DeferredHolder,MenuType> + STALINIUM_CACHE_MENU = registerMenuType( + "stalinium_cache", + (windowId, inv, buf) -> ChestMenu.threeRows(windowId, inv, new SimpleContainer(27)) + ); + + public static void register(IEventBus bus) { + MENUS.register(bus); } } \ No newline at end of file diff --git a/src/main/resources/assets/stalinium/lang/en_us.json b/src/main/resources/assets/stalinium/lang/en_us.json index f005216..60be96d 100644 --- a/src/main/resources/assets/stalinium/lang/en_us.json +++ b/src/main/resources/assets/stalinium/lang/en_us.json @@ -19,6 +19,7 @@ "block.stalinium.stalinium_ore": "Stalinium Ore", "block.stalinium.compressed_bedrock": "Compressed Bedrock", "block.stalinium.stalinium_press": "Stalinium Press", + "block.stalinium.stalinium_cache": "Stalinium Cache", "creativetab.stalinium.stalinium": "Stalinium", @@ -61,5 +62,7 @@ "item.minecraft.lingering_potion.effect.weapons_grade_vodka": "Lingering Weapons Grade Vodka", "item.minecraft.tipped_arrow.effect.weapons_grade_vodka": "Arrow of Weapons Grade Vodka", - "item.stalinium.stalinium_smithing_template": "Stalinium Upgrade Template" + "item.stalinium.stalinium_smithing_template": "Stalinium Upgrade Template", + + "container.stalinium.cache": "Stalinium Cache" }