From f620227e358a54ee69c4607051fc5d76d04caa35 Mon Sep 17 00:00:00 2001 From: Sollace Date: Thu, 25 May 2023 11:56:18 +0100 Subject: [PATCH] flowering zap leaves are now a separate block --- .../block/BaseZapAppleLeavesBlock.java | 133 +++++++++++++++++ .../unicopia/block/UBlocks.java | 1 + .../unicopia/block/ZapAppleLeavesBlock.java | 139 +----------------- .../block/ZapAppleLeavesPlaceholderBlock.java | 4 +- .../unicopia/client/URenderers.java | 4 - .../server/world/ZapAppleStageStore.java | 18 ++- .../blockstates/flowering_zap_leaves.json | 7 + .../resources/assets/unicopia/lang/en_us.json | 1 + .../unicopia/models/item/zap_leaves.json | 10 +- .../blocks/flowering_zap_leaves.json | 116 +++++++++++++++ 10 files changed, 280 insertions(+), 153 deletions(-) create mode 100644 src/main/java/com/minelittlepony/unicopia/block/BaseZapAppleLeavesBlock.java create mode 100644 src/main/resources/assets/unicopia/blockstates/flowering_zap_leaves.json create mode 100644 src/main/resources/data/unicopia/loot_tables/blocks/flowering_zap_leaves.json diff --git a/src/main/java/com/minelittlepony/unicopia/block/BaseZapAppleLeavesBlock.java b/src/main/java/com/minelittlepony/unicopia/block/BaseZapAppleLeavesBlock.java new file mode 100644 index 00000000..0c256c1f --- /dev/null +++ b/src/main/java/com/minelittlepony/unicopia/block/BaseZapAppleLeavesBlock.java @@ -0,0 +1,133 @@ +package com.minelittlepony.unicopia.block; + +import org.jetbrains.annotations.Nullable; + +import com.minelittlepony.unicopia.entity.player.Pony; +import com.minelittlepony.unicopia.server.world.ZapAppleStageStore; + +import net.minecraft.block.*; +import net.minecraft.entity.player.PlayerEntity; +import net.minecraft.server.world.ServerWorld; +import net.minecraft.sound.BlockSoundGroup; +import net.minecraft.util.math.*; +import net.minecraft.util.math.random.Random; +import net.minecraft.world.*; + +public class BaseZapAppleLeavesBlock extends LeavesBlock implements TintedBlock { + + BaseZapAppleLeavesBlock() { + super(Settings.of(Material.LEAVES) + .strength(500, 1200) + .ticksRandomly() + .sounds(BlockSoundGroup.AZALEA_LEAVES) + .nonOpaque() + .allowsSpawning(UBlocks::canSpawnOnLeaves) + .suffocates(UBlocks::never) + .blockVision(UBlocks::never) + ); + } + + @Override + public boolean hasRandomTicks(BlockState state) { + return !state.get(PERSISTENT); + } + + @Override + public void randomTick(BlockState state, ServerWorld world, BlockPos pos, Random random) { + super.randomTick(state, world, pos, random); + tryAdvanceStage(state, world, pos, random); + } + + @Override + public void scheduledTick(BlockState state, ServerWorld world, BlockPos pos, Random random) { + super.scheduledTick(state, world, pos, random); + tryAdvanceStage(state, world, pos, random); + world.scheduleBlockTick(pos, this, 1); + } + + private void tryAdvanceStage(BlockState state, ServerWorld world, BlockPos pos, Random random) { + if (state.get(PERSISTENT)) { + return; + } + + ZapAppleStageStore store = ZapAppleStageStore.get(world); + ZapAppleStageStore.Stage newStage = store.getStage(); + if (!world.isDay() && getStage(state).mustChangeIntoInstantly(newStage)) { + world.setBlockState(pos, newStage.getNewState(state)); + onStageChanged(store, newStage, world, state, pos, random); + } + } + + protected ZapAppleStageStore.Stage getStage(BlockState state) { + return ZapAppleStageStore.Stage.FLOWERING; + } + + @Override + protected boolean shouldDecay(BlockState state) { + return false; + } + + @Deprecated + @Override + public float calcBlockBreakingDelta(BlockState state, PlayerEntity player, BlockView world, BlockPos pos) { + if (state.get(PERSISTENT)) { + return Blocks.OAK_LEAVES.calcBlockBreakingDelta(Blocks.OAK_LEAVES.getDefaultState(), player, world, pos); + } + + float delta = super.calcBlockBreakingDelta(state, player, world, pos); + + if (Pony.of(player).getSpecies().canUseEarth()) { + delta *= 50; + } + + if (getStage(state) == ZapAppleStageStore.Stage.RIPE) { + delta *= 5; + } + + return MathHelper.clamp(delta, 0, 0.9F); + } + + @Override + public void onBlockBreakStart(BlockState state, World world, BlockPos pos, PlayerEntity player) { + ZapBlock.triggerLightning(state, world, pos, player); + } + + @Override + public int getTint(BlockState state, @Nullable BlockRenderView world, @Nullable BlockPos pos, int foliageColor) { + + if (pos == null) { + return 0x4C7EFA; + } + + return TintedBlock.blend(TintedBlock.rotate(foliageColor, 2), 0x0000FF, 0.3F); + } + + static void onStageChanged(ZapAppleStageStore store, ZapAppleStageStore.Stage stage, ServerWorld world, BlockState state, BlockPos pos, Random random) { + boolean mustFruit = Random.create(state.getRenderingSeed(pos)).nextInt(5) < 2; + BlockState below = world.getBlockState(pos.down()); + + if (world.isAir(pos.down())) { + if (stage == ZapAppleStageStore.Stage.FRUITING && mustFruit) { + world.setBlockState(pos.down(), UBlocks.ZAP_BULB.getDefaultState(), Block.NOTIFY_ALL); + store.triggerLightningStrike(pos); + } + } + + if (stage != ZapAppleStageStore.Stage.HIBERNATING && world.getRandom().nextInt(10) == 0) { + store.triggerLightningStrike(pos); + } + + if (stage == ZapAppleStageStore.Stage.RIPE) { + if (below.isOf(UBlocks.ZAP_BULB)) { + world.setBlockState(pos.down(), UBlocks.ZAP_APPLE.getDefaultState(), Block.NOTIFY_ALL); + store.playMoonEffect(pos); + } + } + + if (mustFruit && stage == ZapAppleStageStore.Stage.HIBERNATING) { + if (below.isOf(UBlocks.ZAP_APPLE) || below.isOf(UBlocks.ZAP_BULB)) { + world.setBlockState(pos.down(), Blocks.AIR.getDefaultState()); + } + } + } +} diff --git a/src/main/java/com/minelittlepony/unicopia/block/UBlocks.java b/src/main/java/com/minelittlepony/unicopia/block/UBlocks.java index 0c4cdade..903e04b5 100644 --- a/src/main/java/com/minelittlepony/unicopia/block/UBlocks.java +++ b/src/main/java/com/minelittlepony/unicopia/block/UBlocks.java @@ -45,6 +45,7 @@ public interface UBlocks { Block STRIPPED_ZAP_WOOD = register("stripped_zap_wood", new ZapAppleLogBlock(Blocks.STRIPPED_OAK_WOOD, MapColor.GRAY, MapColor.GRAY), ItemGroups.BUILDING_BLOCKS); Block ZAP_LEAVES = register("zap_leaves", new ZapAppleLeavesBlock(), ItemGroups.NATURAL); + Block FLOWERING_ZAP_LEAVES = register("flowering_zap_leaves", new BaseZapAppleLeavesBlock(), ItemGroups.NATURAL); Block ZAP_LEAVES_PLACEHOLDER = register("zap_leaves_placeholder", new ZapAppleLeavesPlaceholderBlock()); Block ZAP_BULB = register("zap_bulb", new FruitBlock(FabricBlockSettings.of(Material.GOURD, MapColor.GRAY).strength(500, 1200).sounds(BlockSoundGroup.AZALEA_LEAVES), Direction.DOWN, ZAP_LEAVES, FruitBlock.DEFAULT_SHAPE, false)); Block ZAP_APPLE = register("zap_apple", new FruitBlock(FabricBlockSettings.of(Material.GOURD, MapColor.GRAY).sounds(BlockSoundGroup.AZALEA_LEAVES), Direction.DOWN, ZAP_LEAVES, FruitBlock.DEFAULT_SHAPE, false)); diff --git a/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesBlock.java b/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesBlock.java index f99bd33e..573e30d3 100644 --- a/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesBlock.java +++ b/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesBlock.java @@ -1,153 +1,26 @@ package com.minelittlepony.unicopia.block; -import org.jetbrains.annotations.Nullable; - -import com.minelittlepony.unicopia.entity.player.Pony; import com.minelittlepony.unicopia.server.world.ZapAppleStageStore; import net.minecraft.block.*; -import net.minecraft.entity.player.PlayerEntity; -import net.minecraft.item.ItemPlacementContext; -import net.minecraft.item.ItemStack; -import net.minecraft.server.world.ServerWorld; -import net.minecraft.sound.BlockSoundGroup; import net.minecraft.state.StateManager; import net.minecraft.state.property.*; -import net.minecraft.util.math.*; -import net.minecraft.util.math.random.Random; -import net.minecraft.world.*; -public class ZapAppleLeavesBlock extends LeavesBlock implements TintedBlock { +public class ZapAppleLeavesBlock extends BaseZapAppleLeavesBlock { public static final EnumProperty STAGE = EnumProperty.of("stage", ZapAppleStageStore.Stage.class); ZapAppleLeavesBlock() { - super(Settings.of(Material.LEAVES) - .strength(500, 1200) - .ticksRandomly() - .sounds(BlockSoundGroup.AZALEA_LEAVES) - .nonOpaque() - .allowsSpawning(UBlocks::canSpawnOnLeaves) - .suffocates(UBlocks::never) - .blockVision(UBlocks::never) - ); setDefaultState(getDefaultState().with(STAGE, ZapAppleStageStore.Stage.HIBERNATING)); } + @Override + protected ZapAppleStageStore.Stage getStage(BlockState state) { + return state.get(STAGE); + } + @Override protected void appendProperties(StateManager.Builder builder) { super.appendProperties(builder); builder.add(STAGE); } - - @Override - public boolean hasRandomTicks(BlockState state) { - return !state.get(PERSISTENT); - } - - @Override - public void randomTick(BlockState state, ServerWorld world, BlockPos pos, Random random) { - super.randomTick(state, world, pos, random); - tryAdvanceStage(state, world, pos, random); - } - - @Override - public void scheduledTick(BlockState state, ServerWorld world, BlockPos pos, Random random) { - super.scheduledTick(state, world, pos, random); - tryAdvanceStage(state, world, pos, random); - world.scheduleBlockTick(pos, this, 1); - } - - private void tryAdvanceStage(BlockState state, ServerWorld world, BlockPos pos, Random random) { - if (state.get(PERSISTENT)) { - return; - } - - ZapAppleStageStore store = ZapAppleStageStore.get(world); - ZapAppleStageStore.Stage newStage = store.getStage(); - if (!world.isDay() && state.get(STAGE).mustChangeIntoInstantly(newStage)) { - world.setBlockState(pos, newStage == ZapAppleStageStore.Stage.HIBERNATING ? UBlocks.ZAP_LEAVES_PLACEHOLDER.getDefaultState() : state.with(STAGE, newStage)); - onStageChanged(store, newStage, world, state, pos, random); - } - } - - @Override - protected boolean shouldDecay(BlockState state) { - return false; - } - - @Override - public ItemStack getPickStack(BlockView world, BlockPos pos, BlockState state) { - ItemStack stack = super.getPickStack(world, pos, state); - stack.setDamage(Math.max(0, state.get(STAGE).ordinal() - 1)); - return stack; - } - - @Override - public BlockState getPlacementState(ItemPlacementContext ctx) { - return super.getPlacementState(ctx).with(STAGE, ZapAppleStageStore.Stage.byId(ctx.getStack().getDamage() + 1)); - } - - static void onStageChanged(ZapAppleStageStore store, ZapAppleStageStore.Stage stage, ServerWorld world, BlockState state, BlockPos pos, Random random) { - boolean mustFruit = Random.create(state.getRenderingSeed(pos)).nextInt(5) < 2; - BlockState below = world.getBlockState(pos.down()); - - if (world.isAir(pos.down())) { - if (stage == ZapAppleStageStore.Stage.FRUITING && mustFruit) { - world.setBlockState(pos.down(), UBlocks.ZAP_BULB.getDefaultState(), Block.NOTIFY_ALL); - store.triggerLightningStrike(pos); - } - } - - if (stage != ZapAppleStageStore.Stage.HIBERNATING && world.getRandom().nextInt(10) == 0) { - store.triggerLightningStrike(pos); - } - - if (stage == ZapAppleStageStore.Stage.RIPE) { - if (below.isOf(UBlocks.ZAP_BULB)) { - world.setBlockState(pos.down(), UBlocks.ZAP_APPLE.getDefaultState(), Block.NOTIFY_ALL); - store.playMoonEffect(pos); - } - } - - if (mustFruit && stage == ZapAppleStageStore.Stage.HIBERNATING) { - if (below.isOf(UBlocks.ZAP_APPLE) || below.isOf(UBlocks.ZAP_BULB)) { - world.setBlockState(pos.down(), Blocks.AIR.getDefaultState()); - } - } - } - - @Override - public void onBlockBreakStart(BlockState state, World world, BlockPos pos, PlayerEntity player) { - ZapBlock.triggerLightning(state, world, pos, player); - } - - @Override - public int getTint(BlockState state, @Nullable BlockRenderView world, @Nullable BlockPos pos, int foliageColor) { - - if (pos == null) { - return 0x4C7EFA; - } - - return TintedBlock.blend(TintedBlock.rotate(foliageColor, 2), 0x0000FF, 0.3F); - } - - @Deprecated - @Override - public float calcBlockBreakingDelta(BlockState state, PlayerEntity player, BlockView world, BlockPos pos) { - if (state.get(PERSISTENT)) { - return Blocks.OAK_LEAVES.calcBlockBreakingDelta(Blocks.OAK_LEAVES.getDefaultState(), player, world, pos); - } - - float delta = super.calcBlockBreakingDelta(state, player, world, pos); - - if (Pony.of(player).getSpecies().canUseEarth()) { - delta *= 50; - } - - if (state.get(STAGE) == ZapAppleStageStore.Stage.RIPE) { - delta *= 5; - } - - return MathHelper.clamp(delta, 0, 0.9F); - } } diff --git a/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesPlaceholderBlock.java b/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesPlaceholderBlock.java index c73abc36..5b23dcde 100644 --- a/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesPlaceholderBlock.java +++ b/src/main/java/com/minelittlepony/unicopia/block/ZapAppleLeavesPlaceholderBlock.java @@ -26,8 +26,8 @@ public class ZapAppleLeavesPlaceholderBlock extends AirBlock { ZapAppleStageStore store = ZapAppleStageStore.get(world); ZapAppleStageStore.Stage newStage = store.getStage(); if (!world.isDay() && ZapAppleStageStore.Stage.HIBERNATING.mustChangeIntoInstantly(newStage)) { - world.setBlockState(pos, UBlocks.ZAP_LEAVES.getDefaultState().with(ZapAppleLeavesBlock.STAGE, newStage)); - ZapAppleLeavesBlock.onStageChanged(store, newStage, world, state, pos, random); + world.setBlockState(pos, newStage.getNewState(state)); + BaseZapAppleLeavesBlock.onStageChanged(store, newStage, world, state, pos, random); } world.scheduleBlockTick(pos, this, 1); diff --git a/src/main/java/com/minelittlepony/unicopia/client/URenderers.java b/src/main/java/com/minelittlepony/unicopia/client/URenderers.java index 23fa07b8..30b2baf3 100644 --- a/src/main/java/com/minelittlepony/unicopia/client/URenderers.java +++ b/src/main/java/com/minelittlepony/unicopia/client/URenderers.java @@ -20,7 +20,6 @@ import com.minelittlepony.unicopia.item.ChameleonItem; import com.minelittlepony.unicopia.item.EnchantableItem; import com.minelittlepony.unicopia.item.UItems; import com.minelittlepony.unicopia.particle.UParticles; -import com.minelittlepony.unicopia.server.world.ZapAppleStageStore; import net.fabricmc.fabric.api.blockrenderlayer.v1.BlockRenderLayerMap; import net.fabricmc.fabric.api.client.particle.v1.ParticleFactoryRegistry; @@ -120,9 +119,6 @@ public interface URenderers { ModelPredicateProviderRegistry.register(UItems.GEMSTONE, new Identifier("affinity"), (stack, world, entity, seed) -> { return EnchantableItem.isEnchanted(stack) ? EnchantableItem.getSpellKey(stack).getAffinity().getAlignment() : 0; }); - ModelPredicateProviderRegistry.register(UBlocks.ZAP_LEAVES.asItem(), new Identifier("flowering"), (stack, world, entity, seed) -> { - return ZapAppleStageStore.Stage.byStack(stack) == ZapAppleStageStore.Stage.FLOWERING ? 1 : 0; - }); ColorProviderRegistry.ITEM.register((stack, i) -> { return i > 0 || !EnchantableItem.isEnchanted(stack) ? -1 : EnchantableItem.getSpellKey(stack).getColor(); }, UItems.GEMSTONE); diff --git a/src/main/java/com/minelittlepony/unicopia/server/world/ZapAppleStageStore.java b/src/main/java/com/minelittlepony/unicopia/server/world/ZapAppleStageStore.java index 82c47433..1565a4ab 100644 --- a/src/main/java/com/minelittlepony/unicopia/server/world/ZapAppleStageStore.java +++ b/src/main/java/com/minelittlepony/unicopia/server/world/ZapAppleStageStore.java @@ -4,13 +4,15 @@ import java.util.Locale; import java.util.stream.StreamSupport; import com.minelittlepony.unicopia.Unicopia; +import com.minelittlepony.unicopia.block.UBlocks; +import com.minelittlepony.unicopia.block.ZapAppleLeavesBlock; import com.minelittlepony.unicopia.particle.ParticleUtils; import com.minelittlepony.unicopia.particle.UParticles; import com.minelittlepony.unicopia.util.Tickable; +import net.minecraft.block.BlockState; import net.minecraft.entity.EntityType; import net.minecraft.entity.LightningEntity; -import net.minecraft.item.ItemStack; import net.minecraft.nbt.*; import net.minecraft.sound.SoundCategory; import net.minecraft.sound.SoundEvents; @@ -154,10 +156,6 @@ public class ZapAppleStageStore extends PersistentState implements Tickable { return VALUES[MathHelper.clamp(id, 0, VALUES.length)]; } - public static Stage byStack(ItemStack stack) { - return byId(stack.getDamage() + 1); - } - public boolean mustChangeInto(Stage to) { return this != to && (getNext() == to || this == HIBERNATING || to == HIBERNATING); } @@ -166,6 +164,16 @@ public class ZapAppleStageStore extends PersistentState implements Tickable { return this != to && (this == HIBERNATING || to == HIBERNATING); } + public BlockState getNewState(BlockState currentState) { + if (this == ZapAppleStageStore.Stage.HIBERNATING) { + return UBlocks.ZAP_LEAVES_PLACEHOLDER.getDefaultState(); + } + if (this == ZapAppleStageStore.Stage.FLOWERING) { + return UBlocks.FLOWERING_ZAP_LEAVES.getDefaultState(); + } + return currentState.withIfExists(ZapAppleLeavesBlock.STAGE, this); + } + @Override public String asString() { return name().toLowerCase(Locale.ROOT); diff --git a/src/main/resources/assets/unicopia/blockstates/flowering_zap_leaves.json b/src/main/resources/assets/unicopia/blockstates/flowering_zap_leaves.json new file mode 100644 index 00000000..8122824c --- /dev/null +++ b/src/main/resources/assets/unicopia/blockstates/flowering_zap_leaves.json @@ -0,0 +1,7 @@ +{ + "variants": { + "": { + "model": "unicopia:block/flowering_zap_leaves" + } + } +} diff --git a/src/main/resources/assets/unicopia/lang/en_us.json b/src/main/resources/assets/unicopia/lang/en_us.json index 09be9e94..d0026a7f 100644 --- a/src/main/resources/assets/unicopia/lang/en_us.json +++ b/src/main/resources/assets/unicopia/lang/en_us.json @@ -138,6 +138,7 @@ "block.unicopia.stripped_zap_log": "Stripped Zap Apple Log", "block.unicopia.stripped_zap_wood": "Stripped Zap Apple Wood", "block.unicopia.zap_leaves": "Zap Apple Leaves", + "block.unicopia.flowering_zap_leaves": "Flowering Zap Apple Leaves", "block.unicopia.zap_apple": "Zap Apple", "block.unicopia.zap_bulb": "Unripened Zap Apple", "block.unicopia.palm_sapling": "Palm Sapling", diff --git a/src/main/resources/assets/unicopia/models/item/zap_leaves.json b/src/main/resources/assets/unicopia/models/item/zap_leaves.json index 3b2ce617..6a481c2e 100644 --- a/src/main/resources/assets/unicopia/models/item/zap_leaves.json +++ b/src/main/resources/assets/unicopia/models/item/zap_leaves.json @@ -1,11 +1,3 @@ { - "parent": "unicopia:block/zap_leaves", - "overrides": [ - { - "predicate": { - "flowering": 1 - }, - "model": "unicopia:item/flowering_zap_leaves" - } - ] + "parent": "unicopia:block/zap_leaves" } \ No newline at end of file diff --git a/src/main/resources/data/unicopia/loot_tables/blocks/flowering_zap_leaves.json b/src/main/resources/data/unicopia/loot_tables/blocks/flowering_zap_leaves.json new file mode 100644 index 00000000..fca666d6 --- /dev/null +++ b/src/main/resources/data/unicopia/loot_tables/blocks/flowering_zap_leaves.json @@ -0,0 +1,116 @@ +{ + "type": "minecraft:block", + "pools": [ + { + "bonus_rolls": 0.0, + "entries": [ + { + "type": "minecraft:alternatives", + "children": [ + { + "type": "minecraft:item", + "conditions": [ + { + "condition": "minecraft:alternative", + "terms": [ + { + "condition": "minecraft:match_tool", + "predicate": { + "items": [ + "minecraft:shears" + ] + } + }, + { + "condition": "minecraft:match_tool", + "predicate": { + "enchantments": [ + { + "enchantment": "minecraft:silk_touch", + "levels": { + "min": 1 + } + } + ] + } + } + ] + } + ], + "name": "unicopia:flowering_zap_leaves" + } + ] + } + ], + "rolls": 1.0 + }, + { + "bonus_rolls": 0.0, + "conditions": [ + { + "condition": "minecraft:inverted", + "term": { + "condition": "minecraft:alternative", + "terms": [ + { + "condition": "minecraft:match_tool", + "predicate": { + "items": [ + "minecraft:shears" + ] + } + }, + { + "condition": "minecraft:match_tool", + "predicate": { + "enchantments": [ + { + "enchantment": "minecraft:silk_touch", + "levels": { + "min": 1 + } + } + ] + } + } + ] + } + } + ], + "entries": [ + { + "type": "minecraft:item", + "conditions": [ + { + "chances": [ + 0.02, + 0.022222223, + 0.025, + 0.033333335, + 0.1 + ], + "condition": "minecraft:table_bonus", + "enchantment": "minecraft:fortune" + } + ], + "functions": [ + { + "add": false, + "count": { + "type": "minecraft:uniform", + "max": 2.0, + "min": 1.0 + }, + "function": "minecraft:set_count" + }, + { + "function": "minecraft:explosion_decay" + } + ], + "name": "minecraft:stick" + } + ], + "rolls": 1.0 + } + ] +} \ No newline at end of file