diff --git a/src/generated/resources/assets/anvilcraft/lang/en_ud.json b/src/generated/resources/assets/anvilcraft/lang/en_ud.json index 9f083e793..61ee5d09b 100644 --- a/src/generated/resources/assets/anvilcraft/lang/en_ud.json +++ b/src/generated/resources/assets/anvilcraft/lang/en_ud.json @@ -376,6 +376,7 @@ "block.anvilcraft.mob_amber_block": "qoW ɥʇıʍ ɹǝqɯⱯ ɟo ʞɔoןᗺ", "block.anvilcraft.multiphase_matter_block": "ɹǝʇʇɐW ǝsɐɥdıʇןnW ɟo ʞɔoןᗺ", "block.anvilcraft.negative_matter_block": "ɹǝʇʇɐW ǝʌıʇɐbǝN ɟo ʞɔoןᗺ", + "block.anvilcraft.neoforge": "ǝbɹoɟoǝN", "block.anvilcraft.nesting_shulker_box": "xoᗺ ɹǝʞןnɥS buıʇsǝN", "block.anvilcraft.nether_dust": "ʇsnᗡ ɹǝɥʇǝN", "block.anvilcraft.neutron_irradiator": "ɹoʇɐıpɐɹɹI uoɹʇnǝN", diff --git a/src/generated/resources/assets/anvilcraft/lang/en_us.json b/src/generated/resources/assets/anvilcraft/lang/en_us.json index 37047d82b..cca9e4b8a 100644 --- a/src/generated/resources/assets/anvilcraft/lang/en_us.json +++ b/src/generated/resources/assets/anvilcraft/lang/en_us.json @@ -376,6 +376,7 @@ "block.anvilcraft.mob_amber_block": "Block of Amber with Mob", "block.anvilcraft.multiphase_matter_block": "Block of Multiphase Matter", "block.anvilcraft.negative_matter_block": "Block of Negative Matter", + "block.anvilcraft.neoforge": "Neoforge", "block.anvilcraft.nesting_shulker_box": "Nesting Shulker Box", "block.anvilcraft.nether_dust": "Nether Dust", "block.anvilcraft.neutron_irradiator": "Neutron Irradiator", diff --git a/src/generated/resources/assets/anvilcraft/models/item/neoforge.json b/src/generated/resources/assets/anvilcraft/models/item/neoforge.json new file mode 100644 index 000000000..9cfe1c512 --- /dev/null +++ b/src/generated/resources/assets/anvilcraft/models/item/neoforge.json @@ -0,0 +1,3 @@ +{ + "parent": "anvilcraft:block/neoforge" +} \ No newline at end of file diff --git a/src/generated/resources/data/anvilcraft/advancement/recipes/misc/neoforge.json b/src/generated/resources/data/anvilcraft/advancement/recipes/misc/neoforge.json new file mode 100644 index 000000000..caf32dfb9 --- /dev/null +++ b/src/generated/resources/data/anvilcraft/advancement/recipes/misc/neoforge.json @@ -0,0 +1,43 @@ +{ + "parent": "minecraft:recipes/root", + "criteria": { + "has_cake_block": { + "conditions": { + "items": [ + { + "items": "anvilcraft:cake_block" + } + ] + }, + "trigger": "minecraft:inventory_changed" + }, + "has_creamy_bread_roll": { + "conditions": { + "items": [ + { + "items": "anvilcraft:creamy_bread_roll" + } + ] + }, + "trigger": "minecraft:inventory_changed" + }, + "has_the_recipe": { + "conditions": { + "recipe": "anvilcraft:neoforge" + }, + "trigger": "minecraft:recipe_unlocked" + } + }, + "requirements": [ + [ + "has_the_recipe", + "has_cake_block", + "has_creamy_bread_roll" + ] + ], + "rewards": { + "recipes": [ + "anvilcraft:neoforge" + ] + } +} \ No newline at end of file diff --git a/src/generated/resources/data/anvilcraft/loot_table/blocks/neoforge.json b/src/generated/resources/data/anvilcraft/loot_table/blocks/neoforge.json new file mode 100644 index 000000000..464b51d64 --- /dev/null +++ b/src/generated/resources/data/anvilcraft/loot_table/blocks/neoforge.json @@ -0,0 +1,21 @@ +{ + "type": "minecraft:block", + "pools": [ + { + "bonus_rolls": 0.0, + "conditions": [ + { + "condition": "minecraft:survives_explosion" + } + ], + "entries": [ + { + "type": "minecraft:item", + "name": "anvilcraft:neoforge" + } + ], + "rolls": 1.0 + } + ], + "random_sequence": "anvilcraft:blocks/neoforge" +} \ No newline at end of file diff --git a/src/generated/resources/data/anvilcraft/recipe/neoforge.json b/src/generated/resources/data/anvilcraft/recipe/neoforge.json new file mode 100644 index 000000000..598cbd560 --- /dev/null +++ b/src/generated/resources/data/anvilcraft/recipe/neoforge.json @@ -0,0 +1,21 @@ +{ + "type": "minecraft:crafting_shaped", + "category": "misc", + "key": { + "A": { + "item": "anvilcraft:cake_block" + }, + "B": { + "item": "anvilcraft:creamy_bread_roll" + } + }, + "pattern": [ + "AAA", + " B ", + "BBB" + ], + "result": { + "count": 1, + "id": "anvilcraft:neoforge" + } +} \ No newline at end of file diff --git a/src/generated/resources/data/anvilcraft/tags/block/cant_broken_anvil.json b/src/generated/resources/data/anvilcraft/tags/block/cant_broken_anvil.json index a01809110..18a5ca1a3 100644 --- a/src/generated/resources/data/anvilcraft/tags/block/cant_broken_anvil.json +++ b/src/generated/resources/data/anvilcraft/tags/block/cant_broken_anvil.json @@ -2,6 +2,7 @@ "values": [ "anvilcraft:spectral_anvil", "anvilcraft:royal_anvil", + "anvilcraft:neoforge", "anvilcraft:frost_anvil", "anvilcraft:ember_anvil", "anvilcraft:transcendence_anvil" diff --git a/src/generated/resources/data/anvilcraft/tags/block/non_magnetic.json b/src/generated/resources/data/anvilcraft/tags/block/non_magnetic.json index 1227ae3c7..cd4d0a72a 100644 --- a/src/generated/resources/data/anvilcraft/tags/block/non_magnetic.json +++ b/src/generated/resources/data/anvilcraft/tags/block/non_magnetic.json @@ -1,5 +1,6 @@ { "values": [ - "anvilcraft:spectral_anvil" + "anvilcraft:spectral_anvil", + "anvilcraft:neoforge" ] } \ No newline at end of file diff --git a/src/generated/resources/data/minecraft/tags/block/anvil.json b/src/generated/resources/data/minecraft/tags/block/anvil.json index a01809110..18a5ca1a3 100644 --- a/src/generated/resources/data/minecraft/tags/block/anvil.json +++ b/src/generated/resources/data/minecraft/tags/block/anvil.json @@ -2,6 +2,7 @@ "values": [ "anvilcraft:spectral_anvil", "anvilcraft:royal_anvil", + "anvilcraft:neoforge", "anvilcraft:frost_anvil", "anvilcraft:ember_anvil", "anvilcraft:transcendence_anvil" diff --git a/src/generated/resources/data/minecraft/tags/item/anvil.json b/src/generated/resources/data/minecraft/tags/item/anvil.json index a01809110..18a5ca1a3 100644 --- a/src/generated/resources/data/minecraft/tags/item/anvil.json +++ b/src/generated/resources/data/minecraft/tags/item/anvil.json @@ -2,6 +2,7 @@ "values": [ "anvilcraft:spectral_anvil", "anvilcraft:royal_anvil", + "anvilcraft:neoforge", "anvilcraft:frost_anvil", "anvilcraft:ember_anvil", "anvilcraft:transcendence_anvil" diff --git a/src/main/java/dev/dubhe/anvilcraft/block/NeoforgeBlock.java b/src/main/java/dev/dubhe/anvilcraft/block/NeoforgeBlock.java new file mode 100644 index 000000000..952c7dedd --- /dev/null +++ b/src/main/java/dev/dubhe/anvilcraft/block/NeoforgeBlock.java @@ -0,0 +1,149 @@ +package dev.dubhe.anvilcraft.block; + +import com.mojang.serialization.MapCodec; +import dev.dubhe.anvilcraft.inventory.NeoforgeMenu; +import net.minecraft.core.BlockPos; +import net.minecraft.core.Direction; +import net.minecraft.network.chat.Component; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.stats.Stats; +import net.minecraft.world.InteractionResult; +import net.minecraft.world.MenuProvider; +import net.minecraft.world.SimpleMenuProvider; +import net.minecraft.world.damagesource.DamageSource; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.entity.EntityType; +import net.minecraft.world.entity.MobSpawnType; +import net.minecraft.world.entity.item.FallingBlockEntity; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.inventory.ContainerLevelAccess; +import net.minecraft.world.item.context.BlockPlaceContext; +import net.minecraft.world.level.BlockGetter; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.block.Blocks; +import net.minecraft.world.level.block.FallingBlock; +import net.minecraft.world.level.block.HorizontalDirectionalBlock; +import net.minecraft.world.level.block.Rotation; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.level.block.state.StateDefinition; +import net.minecraft.world.level.block.state.properties.DirectionProperty; +import net.minecraft.world.level.gameevent.GameEvent; +import net.minecraft.world.level.pathfinder.PathComputationType; +import net.minecraft.world.phys.BlockHitResult; +import net.minecraft.world.phys.shapes.CollisionContext; +import net.minecraft.world.phys.shapes.Shapes; +import net.minecraft.world.phys.shapes.VoxelShape; +import org.jetbrains.annotations.Nullable; + +public class NeoforgeBlock extends FallingBlock { + public static final DirectionProperty FACING = HorizontalDirectionalBlock.FACING; + private static final VoxelShape BASE = Block.box(2.0, 0.0, 2.0, 14.0, 4.0, 14.0); + private static final VoxelShape X_LEG1 = Block.box(4.0, 4.0, 5.0, 12.0, 10.0, 11.0); + private static final VoxelShape X_TOP = Block.box(0.0, 10.0, 3.0, 16.0, 16.0, 13.0); + private static final VoxelShape Z_LEG1 = Block.box(5.0, 4.0, 4.0, 11.0, 10.0, 12.0); + private static final VoxelShape Z_TOP = Block.box(3.0, 10.0, 0.0, 13.0, 16.0, 16.0); + private static final VoxelShape X_AXIS_AABB = Shapes.or(BASE, X_LEG1, X_TOP); + private static final VoxelShape Z_AXIS_AABB = Shapes.or(BASE, Z_LEG1, Z_TOP); + public static final Component CONTAINER_TITLE = Component.translatable("container.repair"); + + @Override + protected MapCodec codec() { + return simpleCodec(NeoforgeBlock::new); + } + + public NeoforgeBlock(Properties properties) { + super(properties); + this.registerDefaultState(this.getStateDefinition().any() + .setValue(FACING, Direction.NORTH)); + } + + @Override + public @Nullable BlockState getStateForPlacement(BlockPlaceContext context) { + return this.defaultBlockState().setValue(FACING, context.getHorizontalDirection().getClockWise()); + } + + @Override + protected InteractionResult useWithoutItem(BlockState state, Level level, BlockPos pos, Player player, BlockHitResult hitResult) { + if (level.isClientSide()) { + return InteractionResult.SUCCESS; + } else { + player.openMenu(state.getMenuProvider(level, pos)); + player.awardStat(Stats.INTERACT_WITH_ANVIL); + return InteractionResult.CONSUME; + } + } + + @Override + protected @Nullable MenuProvider getMenuProvider(BlockState state, Level level, BlockPos pos) { + return new SimpleMenuProvider( + (syncId, inventory, player) -> + new NeoforgeMenu(syncId, inventory, ContainerLevelAccess.create(level, pos)), + CONTAINER_TITLE); + } + + @Override + protected VoxelShape getShape(BlockState state, BlockGetter level, BlockPos pos, CollisionContext context) { + Direction direction = state.getValue(FACING); + return direction.getAxis() == Direction.Axis.X ? X_AXIS_AABB : Z_AXIS_AABB; + } + + @Override + public void falling(FallingBlockEntity entity) { + entity.setHurtsEntities(2.0f, 20); + } + + @Override + public void onLand(Level level, BlockPos pos, BlockState state, BlockState replaceableState, FallingBlockEntity fallingBlock) { + if (!fallingBlock.isSilent()) { + level.levelEvent(1031, pos, 0); + } + } + + @Override + public void onBrokenAfterFall(Level level, BlockPos pos, FallingBlockEntity fallingBlock) { + if (!fallingBlock.isSilent()) { + level.levelEvent(1029, pos, 0); + } + } + + public static void damage(Level level, BlockPos pos) { + level.setBlockAndUpdate(pos, Blocks.AIR.defaultBlockState()); + level.levelEvent(1029, pos, 0); + if (EntityType.FOX.spawn( + (ServerLevel) level, + null, null, + pos, + MobSpawnType.SPAWN_EGG, + true, + false + ) != null) { + level.gameEvent(null, GameEvent.ENTITY_PLACE, pos); + } + } + + @Override + public DamageSource getFallDamageSource(Entity entity) { + return entity.damageSources().anvil(entity); + } + + @Override + protected BlockState rotate(BlockState state, Rotation rotation) { + return state.setValue(FACING, rotation.rotate(state.getValue(FACING))); + } + + @Override + protected void createBlockStateDefinition(StateDefinition.Builder builder) { + builder.add(FACING); + } + + @Override + protected boolean isPathfindable(BlockState state, PathComputationType pathComputationType) { + return false; + } + + @Override + public int getDustColor(BlockState state, BlockGetter level, BlockPos pos) { + return state.getMapColor(level, pos).col; + } +} diff --git a/src/main/java/dev/dubhe/anvilcraft/event/anvil/AnvilEventListener.java b/src/main/java/dev/dubhe/anvilcraft/event/anvil/AnvilEventListener.java index 199c4f1db..f4ca0c8e8 100644 --- a/src/main/java/dev/dubhe/anvilcraft/event/anvil/AnvilEventListener.java +++ b/src/main/java/dev/dubhe/anvilcraft/event/anvil/AnvilEventListener.java @@ -9,8 +9,10 @@ import dev.dubhe.anvilcraft.api.event.AnvilEvent; import dev.dubhe.anvilcraft.block.EmberAnvilBlock; import dev.dubhe.anvilcraft.block.FrostAnvilBlock; +import dev.dubhe.anvilcraft.block.NeoforgeBlock; import dev.dubhe.anvilcraft.block.RoyalAnvilBlock; import dev.dubhe.anvilcraft.block.TranscendenceAnvilBlock; +import dev.dubhe.anvilcraft.init.block.ModBlocks; import dev.dubhe.anvilcraft.init.recipe.ModRecipeTriggers; import dev.dubhe.anvilcraft.recipe.anvil.outcome.DamageAnvil; import dev.dubhe.anvilcraft.util.AnvilUtil; @@ -60,6 +62,7 @@ public static void onLand(AnvilEvent.OnLand event) { } Level level = event.getLevel(); BlockPos pos = event.getPos(); + final BlockState blockState = level.getBlockState(pos); MinecraftServer server = level.getServer(); if (null == server) return; TriggerUtil.anvilOnGround(level, pos); @@ -77,6 +80,13 @@ public static void onLand(AnvilEvent.OnLand event) { return; } } + if (blockState.is(ModBlocks.NEOFORGE)) { + if (event.getFallDistance() > 1) { + if (level.random.nextDouble() < 0.01) { + NeoforgeBlock.damage(level, pos); + } + } + } } public static void handleNeoAnvilRecipe(AnvilEvent.OnLand event) { diff --git a/src/main/java/dev/dubhe/anvilcraft/init/block/ModBlocks.java b/src/main/java/dev/dubhe/anvilcraft/init/block/ModBlocks.java index cc74adb80..a7974c360 100644 --- a/src/main/java/dev/dubhe/anvilcraft/init/block/ModBlocks.java +++ b/src/main/java/dev/dubhe/anvilcraft/init/block/ModBlocks.java @@ -84,6 +84,7 @@ import dev.dubhe.anvilcraft.block.MineralFountainBlock; import dev.dubhe.anvilcraft.block.MobAmberBlock; import dev.dubhe.anvilcraft.block.NegativeMatterBlock; +import dev.dubhe.anvilcraft.block.NeoforgeBlock; import dev.dubhe.anvilcraft.block.NestingShulkerBoxBlock; import dev.dubhe.anvilcraft.block.NeutronIrradiatorBlock; import dev.dubhe.anvilcraft.block.ObsidianCauldron; @@ -444,6 +445,28 @@ public class ModBlocks { .tag(BlockTags.ANVIL, ModBlockTags.CANT_BROKEN_ANVIL, BlockTags.MINEABLE_WITH_PICKAXE, BlockTags.NEEDS_IRON_TOOL) .register(); + public static final BlockEntry NEOFORGE = REGISTRATE + .block("neoforge", NeoforgeBlock::new) + .initialProperties(() -> Blocks.CAKE) + .blockstate(DataGenUtil::noExtraModelOrState) + .item() + .tag(ItemTags.ANVIL) + .build() + .tag(BlockTags.ANVIL, ModBlockTags.NON_MAGNETIC, ModBlockTags.CANT_BROKEN_ANVIL) + .recipe((ctx, provider) -> { + ShapedRecipeBuilder.shaped(RecipeCategory.MISC, ctx.get()) + .pattern("AAA") + .pattern(" B ") + .pattern("BBB") + .define('A', ModBlocks.CAKE_BLOCK) + .define('B', ModFoodItems.CREAMY_BREAD_ROLL) + .unlockedBy(AnvilCraftDatagen.hasItem(ModBlocks.CAKE_BLOCK), AnvilCraftDatagen.has(ModBlocks.CAKE_BLOCK)) + .unlockedBy(AnvilCraftDatagen.hasItem(ModFoodItems.CREAMY_BREAD_ROLL), + AnvilCraftDatagen.has(ModFoodItems.CREAMY_BREAD_ROLL)) + .save(provider); + }) + .register(); + public static final BlockEntry ROYAL_GRINDSTONE = REGISTRATE.block("royal_grindstone", RoyalGrindstoneBlock::new) .recipe((ctx, provider) -> { SmithingTransformRecipeBuilder.smithing( @@ -2985,7 +3008,6 @@ public class ModBlocks { }) .register(); - public static final BlockEntry RESIN_BLOCK = REGISTRATE.block("resin_block", ResinBlock::new) .lang("Block of Resin") .initialProperties(() -> Blocks.SLIME_BLOCK) diff --git a/src/main/java/dev/dubhe/anvilcraft/inventory/NeoforgeMenu.java b/src/main/java/dev/dubhe/anvilcraft/inventory/NeoforgeMenu.java new file mode 100644 index 000000000..dc67a2778 --- /dev/null +++ b/src/main/java/dev/dubhe/anvilcraft/inventory/NeoforgeMenu.java @@ -0,0 +1,24 @@ +package dev.dubhe.anvilcraft.inventory; + +import dev.dubhe.anvilcraft.block.NeoforgeBlock; +import net.minecraft.world.entity.player.Inventory; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.inventory.AnvilMenu; +import net.minecraft.world.inventory.ContainerLevelAccess; +import net.minecraft.world.item.ItemStack; + +public class NeoforgeMenu extends AnvilMenu { + public NeoforgeMenu(int containerId, Inventory playerInventory, ContainerLevelAccess access) { + super(containerId, playerInventory, access); + } + + @Override + protected void onTake(Player player, ItemStack stack) { + super.onTake(player, stack); + this.access.execute((level, pos) -> { + if (level.random.nextDouble() < 0.01) { + NeoforgeBlock.damage(level, pos); + } + }); + } +} diff --git a/src/main/resources/assets/anvilcraft/blockstates/neoforge.json b/src/main/resources/assets/anvilcraft/blockstates/neoforge.json new file mode 100644 index 000000000..a8ec7eb16 --- /dev/null +++ b/src/main/resources/assets/anvilcraft/blockstates/neoforge.json @@ -0,0 +1,19 @@ +{ + "variants": { + "facing=east": { + "model": "anvilcraft:block/neoforge", + "y": 270 + }, + "facing=north": { + "model": "anvilcraft:block/neoforge", + "y": 180 + }, + "facing=south": { + "model": "anvilcraft:block/neoforge" + }, + "facing=west": { + "model": "anvilcraft:block/neoforge", + "y": 90 + } + } +} \ No newline at end of file