More updates to new BoneMealAPI
This commit is contained in:
parent
5b99e0be53
commit
5faf0ef134
18 changed files with 411 additions and 155 deletions
|
@ -15,6 +15,7 @@ import org.betterx.bclib.api.v2.levelgen.surface.rules.Conditions;
|
||||||
import org.betterx.bclib.api.v2.poi.PoiManager;
|
import org.betterx.bclib.api.v2.poi.PoiManager;
|
||||||
import org.betterx.bclib.api.v3.levelgen.features.blockpredicates.BlockPredicates;
|
import org.betterx.bclib.api.v3.levelgen.features.blockpredicates.BlockPredicates;
|
||||||
import org.betterx.bclib.api.v3.levelgen.features.placement.PlacementModifiers;
|
import org.betterx.bclib.api.v3.levelgen.features.placement.PlacementModifiers;
|
||||||
|
import org.betterx.bclib.api.v3.tag.BCLBlockTags;
|
||||||
import org.betterx.bclib.commands.CommandRegistry;
|
import org.betterx.bclib.commands.CommandRegistry;
|
||||||
import org.betterx.bclib.config.Configs;
|
import org.betterx.bclib.config.Configs;
|
||||||
import org.betterx.bclib.networking.VersionChecker;
|
import org.betterx.bclib.networking.VersionChecker;
|
||||||
|
@ -61,6 +62,7 @@ public class BCLib implements ModInitializer {
|
||||||
AnvilRecipe.register();
|
AnvilRecipe.register();
|
||||||
Conditions.registerAll();
|
Conditions.registerAll();
|
||||||
CommandRegistry.register();
|
CommandRegistry.register();
|
||||||
|
BCLBlockTags.ensureStaticallyLoaded();
|
||||||
PoiManager.registerAll();
|
PoiManager.registerAll();
|
||||||
|
|
||||||
DataExchangeAPI.registerDescriptors(List.of(
|
DataExchangeAPI.registerDescriptors(List.of(
|
||||||
|
|
|
@ -25,6 +25,7 @@ public class BonemealAPI {
|
||||||
private static final Set<Block> TERRAIN_TO_SPREAD = Sets.newHashSet();
|
private static final Set<Block> TERRAIN_TO_SPREAD = Sets.newHashSet();
|
||||||
private static final Set<Block> TERRAIN = Sets.newHashSet();
|
private static final Set<Block> TERRAIN = Sets.newHashSet();
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addSpreadableBlock(Block spreadableBlock, Block surfaceForSpread) {
|
public static void addSpreadableBlock(Block spreadableBlock, Block surfaceForSpread) {
|
||||||
SPREADABLE_BLOCKS.put(spreadableBlock, surfaceForSpread);
|
SPREADABLE_BLOCKS.put(spreadableBlock, surfaceForSpread);
|
||||||
TERRAIN_TO_SPREAD.add(surfaceForSpread);
|
TERRAIN_TO_SPREAD.add(surfaceForSpread);
|
||||||
|
@ -35,38 +36,53 @@ public class BonemealAPI {
|
||||||
return TERRAIN.contains(block);
|
return TERRAIN.contains(block);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static boolean isSpreadableTerrain(Block block) {
|
public static boolean isSpreadableTerrain(Block block) {
|
||||||
return TERRAIN_TO_SPREAD.contains(block);
|
return TERRAIN_TO_SPREAD.contains(block);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static Block getSpreadable(Block block) {
|
public static Block getSpreadable(Block block) {
|
||||||
return SPREADABLE_BLOCKS.get(block);
|
return SPREADABLE_BLOCKS.get(block);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(Block plant, Block... terrain) {
|
public static void addLandGrass(Block plant, Block... terrain) {
|
||||||
addLandGrass(makeConsumer(plant), terrain);
|
addLandGrass(makeConsumer(plant), terrain);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(BiConsumer<Level, BlockPos> plant, Block... terrain) {
|
public static void addLandGrass(BiConsumer<Level, BlockPos> plant, Block... terrain) {
|
||||||
for (Block block : terrain) {
|
for (Block block : terrain) {
|
||||||
addLandGrass(plant, block, 1F);
|
addLandGrass(plant, block, 1F);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This API is deprecated, please use the new {@link org.betterx.bclib.api.v3.bonemeal.BonemealAPI}.
|
||||||
|
*
|
||||||
|
* @param biome
|
||||||
|
* @param plant
|
||||||
|
* @param terrain
|
||||||
|
*/
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(ResourceLocation biome, Block plant, Block... terrain) {
|
public static void addLandGrass(ResourceLocation biome, Block plant, Block... terrain) {
|
||||||
addLandGrass(biome, makeConsumer(plant), terrain);
|
addLandGrass(biome, makeConsumer(plant), terrain);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(ResourceLocation biome, BiConsumer<Level, BlockPos> plant, Block... terrain) {
|
public static void addLandGrass(ResourceLocation biome, BiConsumer<Level, BlockPos> plant, Block... terrain) {
|
||||||
for (Block block : terrain) {
|
for (Block block : terrain) {
|
||||||
addLandGrass(biome, plant, block, 1F);
|
addLandGrass(biome, plant, block, 1F);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(Block plant, Block terrain, float chance) {
|
public static void addLandGrass(Block plant, Block terrain, float chance) {
|
||||||
addLandGrass(makeConsumer(plant), terrain, chance);
|
addLandGrass(makeConsumer(plant), terrain, chance);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(BiConsumer<Level, BlockPos> plant, Block terrain, float chance) {
|
public static void addLandGrass(BiConsumer<Level, BlockPos> plant, Block terrain, float chance) {
|
||||||
WeightedList<BiConsumer<Level, BlockPos>> list = LAND_GRASS_TYPES.get(terrain);
|
WeightedList<BiConsumer<Level, BlockPos>> list = LAND_GRASS_TYPES.get(terrain);
|
||||||
if (list == null) {
|
if (list == null) {
|
||||||
|
@ -77,10 +93,12 @@ public class BonemealAPI {
|
||||||
list.add(plant, chance);
|
list.add(plant, chance);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(ResourceLocation biome, Block plant, Block terrain, float chance) {
|
public static void addLandGrass(ResourceLocation biome, Block plant, Block terrain, float chance) {
|
||||||
addLandGrass(biome, makeConsumer(plant), terrain, chance);
|
addLandGrass(biome, makeConsumer(plant), terrain, chance);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static void addLandGrass(
|
public static void addLandGrass(
|
||||||
ResourceLocation biome,
|
ResourceLocation biome,
|
||||||
BiConsumer<Level, BlockPos> plant,
|
BiConsumer<Level, BlockPos> plant,
|
||||||
|
@ -159,6 +177,7 @@ public class BonemealAPI {
|
||||||
list.add(plant, chance);
|
list.add(plant, chance);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated(forRemoval = true)
|
||||||
public static BiConsumer<Level, BlockPos> getLandGrass(
|
public static BiConsumer<Level, BlockPos> getLandGrass(
|
||||||
ResourceLocation biomeID,
|
ResourceLocation biomeID,
|
||||||
Block terrain,
|
Block terrain,
|
||||||
|
|
|
@ -0,0 +1,76 @@
|
||||||
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
|
import net.minecraft.core.BlockPos;
|
||||||
|
import net.minecraft.server.level.ServerLevel;
|
||||||
|
import net.minecraft.util.RandomSource;
|
||||||
|
import net.minecraft.util.random.SimpleWeightedRandomList;
|
||||||
|
import net.minecraft.world.level.BlockGetter;
|
||||||
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
|
import net.minecraft.world.level.levelgen.feature.stateproviders.WeightedStateProvider;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
abstract class BlockSpreader implements BonemealBlockSpreader {
|
||||||
|
protected abstract boolean isValidSource(BlockState state);
|
||||||
|
protected abstract boolean hasCustomBehaviour(BlockState state);
|
||||||
|
|
||||||
|
public boolean isValidBonemealSpreadTarget(
|
||||||
|
BlockGetter blockGetter,
|
||||||
|
BlockPos blockPos,
|
||||||
|
BlockState blockState,
|
||||||
|
boolean bl
|
||||||
|
) {
|
||||||
|
if (!blockGetter.getBlockState(blockPos.above()).propagatesSkylightDown(blockGetter, blockPos)) {
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
for (BlockPos testPos : BlockPos.betweenClosed(
|
||||||
|
blockPos.offset(-1, -1, -1),
|
||||||
|
blockPos.offset(1, 1, 1)
|
||||||
|
)) {
|
||||||
|
BlockState state = blockGetter.getBlockState(testPos);
|
||||||
|
if (isValidSource(state))
|
||||||
|
if (hasCustomBehaviour(state))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean performBonemealSpread(
|
||||||
|
ServerLevel serverLevel,
|
||||||
|
RandomSource randomSource,
|
||||||
|
BlockPos blockPos,
|
||||||
|
BlockState blockState
|
||||||
|
) {
|
||||||
|
final Map<BlockState, Integer> sourceBlocks = new HashMap<>();
|
||||||
|
|
||||||
|
for (BlockPos testPos : BlockPos.betweenClosed(
|
||||||
|
blockPos.offset(-1, -1, -1),
|
||||||
|
blockPos.offset(1, 1, 1)
|
||||||
|
)) {
|
||||||
|
BlockState state = serverLevel.getBlockState(testPos);
|
||||||
|
if (isValidSource(state)) {
|
||||||
|
sourceBlocks.compute(state, (k, v) -> {
|
||||||
|
if (v == null) return 1;
|
||||||
|
return v + 1;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
SimpleWeightedRandomList.Builder<BlockState> builder = new SimpleWeightedRandomList.Builder<>();
|
||||||
|
for (Map.Entry<BlockState, Integer> e : sourceBlocks.entrySet()) {
|
||||||
|
builder.add(e.getKey(), e.getValue());
|
||||||
|
}
|
||||||
|
WeightedStateProvider provider = new WeightedStateProvider(builder.build());
|
||||||
|
|
||||||
|
BlockState bl = provider.getState(randomSource, blockPos);
|
||||||
|
if (bl != null) {
|
||||||
|
serverLevel.setBlock(blockPos, bl, 3);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
144
src/main/java/org/betterx/bclib/api/v3/bonemeal/BonemealAPI.java
Normal file
144
src/main/java/org/betterx/bclib/api/v3/bonemeal/BonemealAPI.java
Normal file
|
@ -0,0 +1,144 @@
|
||||||
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
|
import org.betterx.bclib.api.v3.levelgen.features.BCLConfigureFeature;
|
||||||
|
import org.betterx.bclib.api.v3.tag.BCLBlockTags;
|
||||||
|
|
||||||
|
import net.minecraft.core.BlockPos;
|
||||||
|
import net.minecraft.server.level.ServerLevel;
|
||||||
|
import net.minecraft.tags.TagKey;
|
||||||
|
import net.minecraft.world.item.ItemStack;
|
||||||
|
import net.minecraft.world.level.Level;
|
||||||
|
import net.minecraft.world.level.block.Block;
|
||||||
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
|
import net.minecraft.world.level.levelgen.feature.Feature;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
import org.jetbrains.annotations.ApiStatus;
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
public class BonemealAPI {
|
||||||
|
public static BonemealAPI INSTANCE = new BonemealAPI();
|
||||||
|
private final Map<TagKey<Block>, BonemealBlockSpreader> taggedSpreaders;
|
||||||
|
private final Map<Block, FeatureSpreader> featureSpreaders;
|
||||||
|
|
||||||
|
private BonemealAPI() {
|
||||||
|
taggedSpreaders = new HashMap<>();
|
||||||
|
featureSpreaders = new HashMap<>();
|
||||||
|
|
||||||
|
addSpreadableBlocks(BCLBlockTags.BONEMEAL_TARGET_NETHERRACK, NetherrackSpreader.INSTANCE);
|
||||||
|
addSpreadableBlocks(BCLBlockTags.BONEMEAL_TARGET_END_STONE, EndStoneSpreader.INSTANCE);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Bonemeal can be used to spread vegetation to neighbouring blocks.
|
||||||
|
* <p>
|
||||||
|
* This method allows you to register a block (the type that was clicked with bonemeal) with
|
||||||
|
* a {@link BCLConfigureFeature} that will be placed on the bonemeald block
|
||||||
|
* <p>
|
||||||
|
* You can achieve the same behaviour by implementing {@link BonemealNyliumLike} on your custom
|
||||||
|
* BlockClass. This is mainly intended for vanilla Blocks where you need to add bonemeal
|
||||||
|
* behaviour
|
||||||
|
*
|
||||||
|
* @param target The block-type
|
||||||
|
* @param spreadableFeature the feature to place
|
||||||
|
*/
|
||||||
|
public void addSpreadableFeatures(
|
||||||
|
Block target,
|
||||||
|
@NotNull BCLConfigureFeature<? extends Feature<?>, ?> spreadableFeature
|
||||||
|
) {
|
||||||
|
featureSpreaders.put(target, new FeatureSpreader(target, spreadableFeature));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Bonemeal can be used to spread for example Nylium to Netherrack.
|
||||||
|
* <p>
|
||||||
|
* In this example, Netherrack is the target block which will get replaced by one of the source blocks (like
|
||||||
|
* Warped or Crimson Nylium. You can register Tag-Combinations to easily add your own behaviour for custom
|
||||||
|
* blocks.
|
||||||
|
* <p>
|
||||||
|
* When a Block with the Target-Tag
|
||||||
|
*
|
||||||
|
* @param targetTag If you click a Block with the given Tag using Bonemeal, you will replace it with
|
||||||
|
* a block from the sourceTag
|
||||||
|
* @param sourceTag Blocks with this Tag can replace the Target block if they are in a 3x3 Neighborhood
|
||||||
|
* centered around the target Block.
|
||||||
|
*/
|
||||||
|
public void addSpreadableBlocks(@NotNull TagKey<Block> targetTag, @NotNull TagKey<Block> sourceTag) {
|
||||||
|
taggedSpreaders.put(targetTag, new TaggedBonemealBlockSpreader(sourceTag));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* See {@link #addSpreadableBlocks(TagKey, TagKey)} for Details.
|
||||||
|
*
|
||||||
|
* @param targetTag If you click a Block with the given Tag using Bonemeal, you will replace it with
|
||||||
|
* * a block from the sourceTag
|
||||||
|
* @param spreader The {@link BonemealBlockSpreader}-Object that is called when a corresponding target-Block
|
||||||
|
* is clicked with Bone-Meal
|
||||||
|
*/
|
||||||
|
public void addSpreadableBlocks(@NotNull TagKey<Block> targetTag, @NotNull BonemealBlockSpreader spreader) {
|
||||||
|
taggedSpreaders.put(targetTag, spreader);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* When a block is clicked with Bonemeal, this method will be called with the state of the given Block.
|
||||||
|
* <p>
|
||||||
|
* If the Method returs a valid {@link BonemealBlockSpreader}-Instance, it will override the default behaviour
|
||||||
|
* for the BoneMeal, otherwise the vanilla action will be performed.
|
||||||
|
*
|
||||||
|
* @param state The {@link BlockState} you need to test
|
||||||
|
* @return A valid spreader instance, or {@code null}
|
||||||
|
*/
|
||||||
|
@ApiStatus.Internal
|
||||||
|
public BonemealBlockSpreader blockSpreaderForState(@NotNull BlockState state) {
|
||||||
|
for (var e : taggedSpreaders.entrySet()) {
|
||||||
|
if (state.is(e.getKey())) {
|
||||||
|
return e.getValue();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@ApiStatus.Internal
|
||||||
|
public FeatureSpreader featureSpreaderForState(@NotNull BlockState state) {
|
||||||
|
return featureSpreaders.get(state.getBlock());
|
||||||
|
}
|
||||||
|
|
||||||
|
@ApiStatus.Internal
|
||||||
|
public boolean runSpreaders(ItemStack itemStack, Level level, BlockPos blockPos) {
|
||||||
|
BlockState blockState = level.getBlockState(blockPos);
|
||||||
|
BonemealBlockSpreader spreader = org.betterx.bclib.api.v3.bonemeal.BonemealAPI
|
||||||
|
.INSTANCE
|
||||||
|
.blockSpreaderForState(blockState);
|
||||||
|
|
||||||
|
if (spreader != null) {
|
||||||
|
if (spreader.isValidBonemealSpreadTarget(level, blockPos, blockState, level.isClientSide)) {
|
||||||
|
if (level instanceof ServerLevel) {
|
||||||
|
if (spreader.performBonemealSpread((ServerLevel) level, level.random, blockPos, blockState)) {
|
||||||
|
itemStack.shrink(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
FeatureSpreader fSpreader = org.betterx.bclib.api.v3.bonemeal.BonemealAPI
|
||||||
|
.INSTANCE
|
||||||
|
.featureSpreaderForState(blockState);
|
||||||
|
|
||||||
|
if (fSpreader != null) {
|
||||||
|
if (fSpreader.isValidBonemealTarget(level, blockPos, blockState, level.isClientSide)) {
|
||||||
|
if (level instanceof ServerLevel) {
|
||||||
|
if (fSpreader.isBonemealSuccess(level, level.random, blockPos, blockState)) {
|
||||||
|
fSpreader.performBonemeal((ServerLevel) level, level.random, blockPos, blockState);
|
||||||
|
}
|
||||||
|
itemStack.shrink(1);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
|
@ -6,7 +6,7 @@ import net.minecraft.util.RandomSource;
|
||||||
import net.minecraft.world.level.BlockGetter;
|
import net.minecraft.world.level.BlockGetter;
|
||||||
import net.minecraft.world.level.block.state.BlockState;
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
|
|
||||||
public interface BonemealSpreader {
|
public interface BonemealBlockSpreader {
|
||||||
boolean isValidBonemealSpreadTarget(BlockGetter blockGetter, BlockPos blockPos, BlockState blockState, boolean bl);
|
boolean isValidBonemealSpreadTarget(BlockGetter blockGetter, BlockPos blockPos, BlockState blockState, boolean bl);
|
||||||
|
|
||||||
|
|
|
@ -16,11 +16,11 @@ import net.minecraft.world.level.levelgen.placement.PlacedFeature;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
public interface BonemealGrassLike extends BonemealableBlock {
|
public interface BonemealGrassLike extends BonemealableBlock {
|
||||||
BlockState growableCoverState(); //Blocks.GRASS.defaultBlockState();
|
BlockState getGrowableCoverState(); //Blocks.GRASS.defaultBlockState();
|
||||||
Block hostBlock(); //this
|
Block getHostBlock(); //this
|
||||||
|
|
||||||
Holder<PlacedFeature> coverFeature(); //VegetationPlacements.GRASS_BONEMEAL
|
Holder<PlacedFeature> getCoverFeature(); //VegetationPlacements.GRASS_BONEMEAL
|
||||||
List<ConfiguredFeature<?, ?>> flowerFeatures(); /*serverLevel.getBiome(currentPos)
|
List<ConfiguredFeature<?, ?>> getFlowerFeatures(); /*serverLevel.getBiome(currentPos)
|
||||||
.value()
|
.value()
|
||||||
.getGenerationSettings()
|
.getGenerationSettings()
|
||||||
.getFlowerFeatures();*/
|
.getFlowerFeatures();*/
|
||||||
|
@ -52,7 +52,7 @@ public interface BonemealGrassLike extends BonemealableBlock {
|
||||||
|
|
||||||
default void performBonemeal(ServerLevel serverLevel, RandomSource random, BlockPos pos, BlockState state) {
|
default void performBonemeal(ServerLevel serverLevel, RandomSource random, BlockPos pos, BlockState state) {
|
||||||
final BlockPos above = pos.above();
|
final BlockPos above = pos.above();
|
||||||
final BlockState growableState = growableCoverState();
|
final BlockState growableState = getGrowableCoverState();
|
||||||
|
|
||||||
outerLoop:
|
outerLoop:
|
||||||
for (int bonemealAttempt = 0; bonemealAttempt < 128; ++bonemealAttempt) {
|
for (int bonemealAttempt = 0; bonemealAttempt < 128; ++bonemealAttempt) {
|
||||||
|
@ -64,7 +64,7 @@ public interface BonemealGrassLike extends BonemealableBlock {
|
||||||
(random.nextInt(3) - 1) * random.nextInt(3) / 2,
|
(random.nextInt(3) - 1) * random.nextInt(3) / 2,
|
||||||
random.nextInt(3) - 1
|
random.nextInt(3) - 1
|
||||||
);
|
);
|
||||||
if (!serverLevel.getBlockState(currentPos.below()).is(hostBlock())
|
if (!serverLevel.getBlockState(currentPos.below()).is(getHostBlock())
|
||||||
|| serverLevel.getBlockState(currentPos)
|
|| serverLevel.getBlockState(currentPos)
|
||||||
.isCollisionShapeFullBlock(serverLevel, currentPos)) {
|
.isCollisionShapeFullBlock(serverLevel, currentPos)) {
|
||||||
continue outerLoop;
|
continue outerLoop;
|
||||||
|
@ -84,14 +84,14 @@ public interface BonemealGrassLike extends BonemealableBlock {
|
||||||
if (currentState.isAir()) {
|
if (currentState.isAir()) {
|
||||||
Holder<PlacedFeature> boneFeature;
|
Holder<PlacedFeature> boneFeature;
|
||||||
if (canGrowFlower(random)) {
|
if (canGrowFlower(random)) {
|
||||||
List<ConfiguredFeature<?, ?>> list = flowerFeatures();
|
List<ConfiguredFeature<?, ?>> list = getFlowerFeatures();
|
||||||
if (list.isEmpty()) {
|
if (list.isEmpty()) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
boneFeature = ((RandomPatchConfiguration) list.get(0).config()).feature();
|
boneFeature = ((RandomPatchConfiguration) list.get(0).config()).feature();
|
||||||
} else {
|
} else {
|
||||||
boneFeature = coverFeature();
|
boneFeature = getCoverFeature();
|
||||||
}
|
}
|
||||||
|
|
||||||
boneFeature.value()
|
boneFeature.value()
|
||||||
|
|
|
@ -1,7 +1,8 @@
|
||||||
package org.betterx.bclib.api.v3.bonemeal;
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
|
import org.betterx.bclib.api.v3.levelgen.features.BCLConfigureFeature;
|
||||||
|
|
||||||
import net.minecraft.core.BlockPos;
|
import net.minecraft.core.BlockPos;
|
||||||
import net.minecraft.core.Holder;
|
|
||||||
import net.minecraft.server.level.ServerLevel;
|
import net.minecraft.server.level.ServerLevel;
|
||||||
import net.minecraft.util.RandomSource;
|
import net.minecraft.util.RandomSource;
|
||||||
import net.minecraft.world.level.BlockGetter;
|
import net.minecraft.world.level.BlockGetter;
|
||||||
|
@ -9,12 +10,12 @@ import net.minecraft.world.level.Level;
|
||||||
import net.minecraft.world.level.block.Block;
|
import net.minecraft.world.level.block.Block;
|
||||||
import net.minecraft.world.level.block.BonemealableBlock;
|
import net.minecraft.world.level.block.BonemealableBlock;
|
||||||
import net.minecraft.world.level.block.state.BlockState;
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
import net.minecraft.world.level.levelgen.feature.Feature;
|
||||||
import net.minecraft.world.level.levelgen.placement.PlacedFeature;
|
|
||||||
|
|
||||||
|
//adapted from NyliumBlock
|
||||||
public interface BonemealNyliumLike extends BonemealableBlock {
|
public interface BonemealNyliumLike extends BonemealableBlock {
|
||||||
Block hostBlock(); //this
|
Block getHostBlock(); //this
|
||||||
Holder<PlacedFeature> coverFeature();
|
BCLConfigureFeature<? extends Feature<?>, ?> getCoverFeature();
|
||||||
|
|
||||||
default boolean isValidBonemealTarget(
|
default boolean isValidBonemealTarget(
|
||||||
BlockGetter blockGetter,
|
BlockGetter blockGetter,
|
||||||
|
@ -41,12 +42,11 @@ public interface BonemealNyliumLike extends BonemealableBlock {
|
||||||
BlockState blockState
|
BlockState blockState
|
||||||
) {
|
) {
|
||||||
final BlockState currentState = serverLevel.getBlockState(blockPos);
|
final BlockState currentState = serverLevel.getBlockState(blockPos);
|
||||||
final BlockPos above = blockPos.above();
|
if (currentState.is(getHostBlock())) {
|
||||||
final ChunkGenerator generator = serverLevel.getChunkSource().getGenerator();
|
BCLConfigureFeature<? extends Feature<?>, ?> feature = getCoverFeature();
|
||||||
if (currentState.is(hostBlock())) {
|
if (feature != null) {
|
||||||
coverFeature()
|
feature.placeInWorld(serverLevel, blockPos.above(), randomSource, true);
|
||||||
.value()
|
}
|
||||||
.place(serverLevel, generator, randomSource, above);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,31 +1,12 @@
|
||||||
package org.betterx.bclib.api.v3.bonemeal;
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
import net.minecraft.core.BlockPos;
|
import org.betterx.bclib.api.v3.tag.BCLBlockTags;
|
||||||
import net.minecraft.server.level.ServerLevel;
|
|
||||||
import net.minecraft.util.RandomSource;
|
|
||||||
import net.minecraft.world.level.BlockGetter;
|
|
||||||
import net.minecraft.world.level.block.state.BlockState;
|
|
||||||
|
|
||||||
public class EndStoneSpreader implements BonemealSpreader {
|
public class EndStoneSpreader extends TaggedBonemealBlockSpreader {
|
||||||
public static final EndStoneSpreader INSTANCE = new EndStoneSpreader();
|
static final EndStoneSpreader INSTANCE = new EndStoneSpreader();
|
||||||
|
|
||||||
@Override
|
protected EndStoneSpreader() {
|
||||||
public boolean isValidBonemealSpreadTarget(
|
super(BCLBlockTags.BONEMEAL_SOURCE_END_STONE);
|
||||||
BlockGetter blockGetter,
|
|
||||||
BlockPos blockPos,
|
|
||||||
BlockState blockState,
|
|
||||||
boolean bl
|
|
||||||
) {
|
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean performBonemealSpread(
|
|
||||||
ServerLevel serverLevel,
|
|
||||||
RandomSource randomSource,
|
|
||||||
BlockPos blockPos,
|
|
||||||
BlockState blockState
|
|
||||||
) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,40 @@
|
||||||
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
|
import org.betterx.bclib.api.v3.levelgen.features.BCLConfigureFeature;
|
||||||
|
|
||||||
|
import net.minecraft.core.BlockPos;
|
||||||
|
import net.minecraft.world.level.BlockGetter;
|
||||||
|
import net.minecraft.world.level.block.Block;
|
||||||
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
|
import net.minecraft.world.level.levelgen.feature.Feature;
|
||||||
|
|
||||||
|
public class FeatureSpreader implements BonemealNyliumLike {
|
||||||
|
public final BCLConfigureFeature<? extends Feature<?>, ?> spreadableFeature;
|
||||||
|
public final Block hostBlock;
|
||||||
|
|
||||||
|
public FeatureSpreader(Block hostBlock, BCLConfigureFeature<? extends Feature<?>, ?> spreadableFeature) {
|
||||||
|
this.spreadableFeature = spreadableFeature;
|
||||||
|
this.hostBlock = hostBlock;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isValidBonemealTarget(
|
||||||
|
BlockGetter blockGetter,
|
||||||
|
BlockPos blockPos,
|
||||||
|
BlockState blockState,
|
||||||
|
boolean bl
|
||||||
|
) {
|
||||||
|
return spreadableFeature != null
|
||||||
|
&& BonemealNyliumLike.super.isValidBonemealTarget(blockGetter, blockPos, blockState, bl);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Block getHostBlock() {
|
||||||
|
return hostBlock;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public BCLConfigureFeature<? extends Feature<?>, ?> getCoverFeature() {
|
||||||
|
return spreadableFeature;
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,81 +1,18 @@
|
||||||
package org.betterx.bclib.api.v3.bonemeal;
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
import org.betterx.bclib.util.WeightedList;
|
import org.betterx.bclib.api.v3.tag.BCLBlockTags;
|
||||||
import org.betterx.worlds.together.tag.v3.CommonBlockTags;
|
|
||||||
|
|
||||||
import net.minecraft.core.BlockPos;
|
|
||||||
import net.minecraft.server.level.ServerLevel;
|
|
||||||
import net.minecraft.util.RandomSource;
|
|
||||||
import net.minecraft.world.level.BlockGetter;
|
|
||||||
import net.minecraft.world.level.block.Block;
|
|
||||||
import net.minecraft.world.level.block.Blocks;
|
import net.minecraft.world.level.block.Blocks;
|
||||||
import net.minecraft.world.level.block.state.BlockState;
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
|
|
||||||
import java.util.HashMap;
|
public class NetherrackSpreader extends TaggedBonemealBlockSpreader {
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
public class NetherrackSpreader implements BonemealSpreader {
|
|
||||||
public static final NetherrackSpreader INSTANCE = new NetherrackSpreader();
|
public static final NetherrackSpreader INSTANCE = new NetherrackSpreader();
|
||||||
|
|
||||||
public boolean isValidBonemealSpreadTarget(
|
protected NetherrackSpreader() {
|
||||||
BlockGetter blockGetter,
|
super(BCLBlockTags.BONEMEAL_SOURCE_NETHERRACK);
|
||||||
BlockPos blockPos,
|
|
||||||
BlockState blockState,
|
|
||||||
boolean bl
|
|
||||||
) {
|
|
||||||
if (!blockGetter.getBlockState(blockPos.above()).propagatesSkylightDown(blockGetter, blockPos)) {
|
|
||||||
return false;
|
|
||||||
} else {
|
|
||||||
for (BlockPos testPos : BlockPos.betweenClosed(
|
|
||||||
blockPos.offset(-1, -1, -1),
|
|
||||||
blockPos.offset(1, 1, 1)
|
|
||||||
)) {
|
|
||||||
if (blockGetter.getBlockState(testPos).is(CommonBlockTags.NETHERRACK_SPREADABLE))
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected boolean hasCustomBehaviour(BlockState state) {
|
||||||
public boolean performBonemealSpread(
|
return !state.is(Blocks.WARPED_NYLIUM) && !state.is(Blocks.CRIMSON_NYLIUM);
|
||||||
ServerLevel serverLevel,
|
|
||||||
RandomSource randomSource,
|
|
||||||
BlockPos blockPos,
|
|
||||||
BlockState blockState
|
|
||||||
) {
|
|
||||||
Map<Block, Integer> sourceBlocks = new HashMap<>();
|
|
||||||
boolean hasNonVanilla = false;
|
|
||||||
for (BlockPos testPos : BlockPos.betweenClosed(
|
|
||||||
blockPos.offset(-1, -1, -1),
|
|
||||||
blockPos.offset(1, 1, 1)
|
|
||||||
)) {
|
|
||||||
BlockState state = serverLevel.getBlockState(testPos);
|
|
||||||
if (serverLevel.getBlockState(testPos).is(CommonBlockTags.NETHERRACK_SPREADABLE)) {
|
|
||||||
sourceBlocks.compute(state.getBlock(), (k, v) -> {
|
|
||||||
if (v == null) return 1;
|
|
||||||
return v + 1;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!state.is(Blocks.WARPED_NYLIUM) && state.is(Blocks.CRIMSON_NYLIUM)) {
|
|
||||||
hasNonVanilla = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (hasNonVanilla) {
|
|
||||||
WeightedList<Block> list = new WeightedList<>();
|
|
||||||
for (Map.Entry<Block, Integer> e : sourceBlocks.entrySet()) {
|
|
||||||
list.add(e.getKey(), e.getValue());
|
|
||||||
}
|
|
||||||
Block bl = list.get(randomSource);
|
|
||||||
if (bl != null) {
|
|
||||||
serverLevel.setBlock(blockPos, bl.defaultBlockState(), 3);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,23 @@
|
||||||
|
package org.betterx.bclib.api.v3.bonemeal;
|
||||||
|
|
||||||
|
import net.minecraft.tags.TagKey;
|
||||||
|
import net.minecraft.world.level.block.Block;
|
||||||
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
|
|
||||||
|
class TaggedBonemealBlockSpreader extends BlockSpreader {
|
||||||
|
public final TagKey<Block> blockTag;
|
||||||
|
|
||||||
|
public TaggedBonemealBlockSpreader(TagKey<Block> blockTag) {
|
||||||
|
this.blockTag = blockTag;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected boolean isValidSource(BlockState state) {
|
||||||
|
return state.is(blockTag);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected boolean hasCustomBehaviour(BlockState state) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
|
@ -55,7 +55,11 @@ public class BCLConfigureFeature<F extends Feature<FC>, FC extends FeatureConfig
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean placeInWorld(ServerLevel level, BlockPos pos, RandomSource random) {
|
public boolean placeInWorld(ServerLevel level, BlockPos pos, RandomSource random) {
|
||||||
return placeInWorld(getFeature(), getConfiguration(), level, pos, random);
|
return placeInWorld(level, pos, random, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean placeInWorld(ServerLevel level, BlockPos pos, RandomSource random, boolean unchanged) {
|
||||||
|
return placeUnboundInWorld(getFeature(), getConfiguration(), level, pos, random, unchanged);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static boolean placeUnboundInWorld(
|
private static boolean placeUnboundInWorld(
|
||||||
|
@ -63,16 +67,19 @@ public class BCLConfigureFeature<F extends Feature<FC>, FC extends FeatureConfig
|
||||||
FeatureConfiguration config,
|
FeatureConfiguration config,
|
||||||
ServerLevel level,
|
ServerLevel level,
|
||||||
BlockPos pos,
|
BlockPos pos,
|
||||||
RandomSource random
|
RandomSource random,
|
||||||
|
boolean asIs
|
||||||
) {
|
) {
|
||||||
if (config instanceof RandomPatchConfiguration rnd) {
|
if (!asIs) {
|
||||||
var configured = rnd.feature().value().feature().value();
|
if (config instanceof RandomPatchConfiguration rnd) {
|
||||||
feature = configured.feature();
|
var configured = rnd.feature().value().feature().value();
|
||||||
config = configured.config();
|
feature = configured.feature();
|
||||||
}
|
config = configured.config();
|
||||||
|
}
|
||||||
|
|
||||||
if (feature instanceof UserGrowableFeature growable) {
|
if (feature instanceof UserGrowableFeature growable) {
|
||||||
return growable.grow(level, pos, random, config);
|
return growable.grow(level, pos, random, config);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
FeaturePlaceContext context = new FeaturePlaceContext(
|
FeaturePlaceContext context = new FeaturePlaceContext(
|
||||||
|
@ -92,7 +99,7 @@ public class BCLConfigureFeature<F extends Feature<FC>, FC extends FeatureConfig
|
||||||
BlockPos pos,
|
BlockPos pos,
|
||||||
RandomSource random
|
RandomSource random
|
||||||
) {
|
) {
|
||||||
return placeUnboundInWorld(feature, FeatureConfiguration.NONE, level, pos, random);
|
return placeUnboundInWorld(feature, FeatureConfiguration.NONE, level, pos, random, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static <FC extends FeatureConfiguration> boolean placeInWorld(
|
public static <FC extends FeatureConfiguration> boolean placeInWorld(
|
||||||
|
@ -102,6 +109,6 @@ public class BCLConfigureFeature<F extends Feature<FC>, FC extends FeatureConfig
|
||||||
BlockPos pos,
|
BlockPos pos,
|
||||||
RandomSource random
|
RandomSource random
|
||||||
) {
|
) {
|
||||||
return placeUnboundInWorld(feature, config, level, pos, random);
|
return placeUnboundInWorld(feature, config, level, pos, random, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -140,6 +140,15 @@ public abstract class BCLFeatureBuilder<F extends Feature<FC>, FC extends Featur
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static NetherForrestVegetation startBonemealNetherVegetation(
|
||||||
|
ResourceLocation featureID
|
||||||
|
) {
|
||||||
|
return new NetherForrestVegetation(
|
||||||
|
featureID,
|
||||||
|
(NetherForestVegetationFeature) Feature.NETHER_FOREST_VEGETATION
|
||||||
|
).spreadHeight(1).spreadWidth(3);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
public static WithTemplates startWithTemplates(
|
public static WithTemplates startWithTemplates(
|
||||||
ResourceLocation featureID
|
ResourceLocation featureID
|
||||||
|
@ -671,7 +680,7 @@ public abstract class BCLFeatureBuilder<F extends Feature<FC>, FC extends Featur
|
||||||
// is meant to prevent that...
|
// is meant to prevent that...
|
||||||
if (NoneFeatureConfiguration.NONE != null)
|
if (NoneFeatureConfiguration.NONE != null)
|
||||||
return (FC) NoneFeatureConfiguration.NONE;
|
return (FC) NoneFeatureConfiguration.NONE;
|
||||||
|
|
||||||
return (FC) NoneFeatureConfiguration.INSTANCE;
|
return (FC) NoneFeatureConfiguration.INSTANCE;
|
||||||
}
|
}
|
||||||
return configuration;
|
return configuration;
|
||||||
|
|
|
@ -420,4 +420,11 @@ abstract class CommonPlacedFeatureBuilder<F extends Feature<FC>, FC extends Feat
|
||||||
public BCLFeatureBuilder.RandomPatch inRandomPatch(ResourceLocation id) {
|
public BCLFeatureBuilder.RandomPatch inRandomPatch(ResourceLocation id) {
|
||||||
return BCLFeatureBuilder.startRandomPatch(id, build());
|
return BCLFeatureBuilder.startRandomPatch(id, build());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public BCLFeatureBuilder.RandomPatch randomBonemealDistribution(ResourceLocation id) {
|
||||||
|
return inRandomPatch(id)
|
||||||
|
.tries(9)
|
||||||
|
.spreadXZ(3)
|
||||||
|
.spreadY(1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
31
src/main/java/org/betterx/bclib/api/v3/tag/BCLBlockTags.java
Normal file
31
src/main/java/org/betterx/bclib/api/v3/tag/BCLBlockTags.java
Normal file
|
@ -0,0 +1,31 @@
|
||||||
|
package org.betterx.bclib.api.v3.tag;
|
||||||
|
|
||||||
|
import org.betterx.worlds.together.tag.v3.TagManager;
|
||||||
|
|
||||||
|
import net.minecraft.tags.TagKey;
|
||||||
|
import net.minecraft.world.level.block.Block;
|
||||||
|
import net.minecraft.world.level.block.Blocks;
|
||||||
|
|
||||||
|
import org.jetbrains.annotations.ApiStatus;
|
||||||
|
|
||||||
|
public class BCLBlockTags {
|
||||||
|
public static final TagKey<Block> BONEMEAL_SOURCE_NETHERRACK = TagManager.BLOCKS.makeTogetherTag(
|
||||||
|
"bonemeal/source/netherrack"
|
||||||
|
);
|
||||||
|
public static final TagKey<Block> BONEMEAL_TARGET_NETHERRACK = TagManager.BLOCKS.makeTogetherTag(
|
||||||
|
"bonemeal/target/netherrack"
|
||||||
|
);
|
||||||
|
public static final TagKey<Block> BONEMEAL_SOURCE_END_STONE = TagManager.BLOCKS.makeTogetherTag(
|
||||||
|
"bonemeal/source/end_stone"
|
||||||
|
);
|
||||||
|
public static final TagKey<Block> BONEMEAL_TARGET_END_STONE = TagManager.BLOCKS.makeTogetherTag(
|
||||||
|
"bonemeal/target/end_stone"
|
||||||
|
);
|
||||||
|
|
||||||
|
@ApiStatus.Internal
|
||||||
|
public static void ensureStaticallyLoaded() {
|
||||||
|
TagManager.BLOCKS.add(BONEMEAL_SOURCE_NETHERRACK, Blocks.WARPED_NYLIUM, Blocks.CRIMSON_NYLIUM);
|
||||||
|
TagManager.BLOCKS.add(BONEMEAL_TARGET_NETHERRACK, Blocks.NETHERRACK);
|
||||||
|
TagManager.BLOCKS.add(BONEMEAL_TARGET_END_STONE, Blocks.END_STONE);
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,16 +2,12 @@ package org.betterx.bclib.mixin.common;
|
||||||
|
|
||||||
import org.betterx.bclib.api.v2.BonemealAPI;
|
import org.betterx.bclib.api.v2.BonemealAPI;
|
||||||
import org.betterx.bclib.api.v2.levelgen.biomes.BiomeAPI;
|
import org.betterx.bclib.api.v2.levelgen.biomes.BiomeAPI;
|
||||||
import org.betterx.bclib.api.v3.bonemeal.BonemealSpreader;
|
|
||||||
import org.betterx.bclib.api.v3.bonemeal.EndStoneSpreader;
|
|
||||||
import org.betterx.bclib.api.v3.bonemeal.NetherrackSpreader;
|
|
||||||
import org.betterx.bclib.util.BlocksHelper;
|
import org.betterx.bclib.util.BlocksHelper;
|
||||||
import org.betterx.bclib.util.MHelper;
|
import org.betterx.bclib.util.MHelper;
|
||||||
|
|
||||||
import net.minecraft.core.BlockPos;
|
import net.minecraft.core.BlockPos;
|
||||||
import net.minecraft.core.BlockPos.MutableBlockPos;
|
import net.minecraft.core.BlockPos.MutableBlockPos;
|
||||||
import net.minecraft.core.Vec3i;
|
import net.minecraft.core.Vec3i;
|
||||||
import net.minecraft.server.level.ServerLevel;
|
|
||||||
import net.minecraft.world.InteractionResult;
|
import net.minecraft.world.InteractionResult;
|
||||||
import net.minecraft.world.item.BoneMealItem;
|
import net.minecraft.world.item.BoneMealItem;
|
||||||
import net.minecraft.world.item.ItemStack;
|
import net.minecraft.world.item.ItemStack;
|
||||||
|
@ -71,32 +67,17 @@ public class BoneMealItemMixin {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Inject(method = "growCrop", at = @At("HEAD"), cancellable = true)
|
@Inject(method = "growCrop", at = @At("HEAD"), cancellable = true)
|
||||||
private static void growCrop(
|
private static void bcl_growCrop(
|
||||||
ItemStack itemStack,
|
ItemStack itemStack,
|
||||||
Level level,
|
Level level,
|
||||||
BlockPos blockPos,
|
BlockPos blockPos,
|
||||||
CallbackInfoReturnable<Boolean> cir
|
CallbackInfoReturnable<Boolean> cir
|
||||||
) {
|
) {
|
||||||
BlockState blockState = level.getBlockState(blockPos);
|
if (org.betterx.bclib.api.v3.bonemeal.BonemealAPI
|
||||||
BonemealSpreader spreader = null;
|
.INSTANCE
|
||||||
|
.runSpreaders(itemStack, level, blockPos)
|
||||||
if (blockState.is(Blocks.NETHERRACK)) {
|
) {
|
||||||
spreader = NetherrackSpreader.INSTANCE;
|
cir.setReturnValue(true);
|
||||||
} else if (blockState.is(Blocks.END_STONE)) {
|
|
||||||
spreader = EndStoneSpreader.INSTANCE;
|
|
||||||
} else if (blockState.getBlock() instanceof BonemealSpreader s) {
|
|
||||||
spreader = s;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (spreader != null) {
|
|
||||||
if (spreader.isValidBonemealSpreadTarget(level, blockPos, blockState, level.isClientSide)) {
|
|
||||||
if (level instanceof ServerLevel) {
|
|
||||||
if (spreader.performBonemealSpread((ServerLevel) level, level.random, blockPos, blockState)) {
|
|
||||||
itemStack.shrink(1);
|
|
||||||
cir.setReturnValue(true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -35,12 +35,7 @@ public class CommonBlockTags {
|
||||||
public static final TagKey<Block> TERRAIN = TagManager.BLOCKS.makeCommonTag("terrain");
|
public static final TagKey<Block> TERRAIN = TagManager.BLOCKS.makeCommonTag("terrain");
|
||||||
public static final TagKey<Block> NETHER_TERRAIN = TagManager.BLOCKS.makeCommonTag("nether_terrain");
|
public static final TagKey<Block> NETHER_TERRAIN = TagManager.BLOCKS.makeCommonTag("nether_terrain");
|
||||||
|
|
||||||
public static final TagKey<Block> NETHERRACK_SPREADABLE = TagManager.BLOCKS.makeCommonTag(
|
|
||||||
"netherrack_spreadable");
|
|
||||||
|
|
||||||
static void prepareTags() {
|
static void prepareTags() {
|
||||||
TagManager.BLOCKS.add(NETHERRACK_SPREADABLE, Blocks.WARPED_NYLIUM, Blocks.CRIMSON_NYLIUM);
|
|
||||||
|
|
||||||
TagManager.BLOCKS.add(SCULK_LIKE, Blocks.SCULK);
|
TagManager.BLOCKS.add(SCULK_LIKE, Blocks.SCULK);
|
||||||
TagManager.BLOCKS.addOtherTags(DRAGON_IMMUNE, BlockTags.DRAGON_IMMUNE);
|
TagManager.BLOCKS.addOtherTags(DRAGON_IMMUNE, BlockTags.DRAGON_IMMUNE);
|
||||||
|
|
||||||
|
|
|
@ -205,6 +205,10 @@ public class TagRegistry<T> {
|
||||||
return creatTagKey(new ResourceLocation("c", name));
|
return creatTagKey(new ResourceLocation("c", name));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public TagKey<T> makeTogetherTag(String name) {
|
||||||
|
return creatTagKey(WorldsTogether.makeID(name));
|
||||||
|
}
|
||||||
|
|
||||||
public void addUntyped(TagKey<T> tagID, ResourceLocation... elements) {
|
public void addUntyped(TagKey<T> tagID, ResourceLocation... elements) {
|
||||||
if (isFrozen) WorldsTogether.LOGGER.warning("Adding Tag " + tagID + " after the API was frozen.");
|
if (isFrozen) WorldsTogether.LOGGER.warning("Adding Tag " + tagID + " after the API was frozen.");
|
||||||
Set<TagEntry> set = getSetForTag(tagID);
|
Set<TagEntry> set = getSetForTag(tagID);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue