Removed old End Caves (temporary), added new Caves and Cave API (WIP)
This commit is contained in:
parent
2135fe50b5
commit
231794363b
14 changed files with 384 additions and 28 deletions
8
src/main/java/ru/betterend/interfaces/IBiomeArray.java
Normal file
8
src/main/java/ru/betterend/interfaces/IBiomeArray.java
Normal file
|
@ -0,0 +1,8 @@
|
|||
package ru.betterend.interfaces;
|
||||
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
|
||||
public interface IBiomeArray {
|
||||
public void setBiome(Biome biome, BlockPos pos);
|
||||
}
|
46
src/main/java/ru/betterend/mixin/common/BiomeArrayMixin.java
Normal file
46
src/main/java/ru/betterend/mixin/common/BiomeArrayMixin.java
Normal file
|
@ -0,0 +1,46 @@
|
|||
package ru.betterend.mixin.common;
|
||||
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.MathHelper;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.source.BiomeArray;
|
||||
import ru.betterend.interfaces.IBiomeArray;
|
||||
|
||||
@Mixin(BiomeArray.class)
|
||||
public class BiomeArrayMixin implements IBiomeArray {
|
||||
@Final
|
||||
@Shadow
|
||||
private Biome[] data;
|
||||
|
||||
@Final
|
||||
@Shadow
|
||||
private static int HORIZONTAL_SECTION_COUNT;
|
||||
|
||||
@Final
|
||||
@Shadow
|
||||
public static int HORIZONTAL_BIT_MASK;
|
||||
|
||||
@Final
|
||||
@Shadow
|
||||
public static int VERTICAL_BIT_MASK;
|
||||
|
||||
@Override
|
||||
public void setBiome(Biome biome, BlockPos pos) {
|
||||
int biomeX = pos.getX() >> 2;
|
||||
int biomeY = pos.getY() >> 2;
|
||||
int biomeZ = pos.getZ() >> 2;
|
||||
int index = be_getArrayIndex(biomeX, biomeY, biomeZ);
|
||||
data[index] = biome;
|
||||
}
|
||||
|
||||
private int be_getArrayIndex(int biomeX, int biomeY, int biomeZ) {
|
||||
int i = biomeX & HORIZONTAL_BIT_MASK;
|
||||
int j = MathHelper.clamp(biomeY, 0, VERTICAL_BIT_MASK);
|
||||
int k = biomeZ & HORIZONTAL_BIT_MASK;
|
||||
return j << HORIZONTAL_SECTION_COUNT + HORIZONTAL_SECTION_COUNT | k << HORIZONTAL_SECTION_COUNT | i;
|
||||
}
|
||||
}
|
|
@ -4,6 +4,7 @@ import java.io.InputStream;
|
|||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Random;
|
||||
import java.util.Set;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
@ -45,7 +46,9 @@ import ru.betterend.world.biome.BiomeSulphurSprings;
|
|||
import ru.betterend.world.biome.BiomeUmbrellaJungle;
|
||||
import ru.betterend.world.biome.DragonGraveyardsBiome;
|
||||
import ru.betterend.world.biome.DryShrublandBiome;
|
||||
import ru.betterend.world.biome.EmptyEndCaveBiome;
|
||||
import ru.betterend.world.biome.EndBiome;
|
||||
import ru.betterend.world.biome.EndCaveBiome;
|
||||
import ru.betterend.world.biome.GlowingGrasslandsBiome;
|
||||
import ru.betterend.world.generator.BELayerRandomSource;
|
||||
import ru.betterend.world.generator.BiomePicker;
|
||||
|
@ -59,6 +62,7 @@ public class EndBiomes {
|
|||
|
||||
public static final BiomePicker LAND_BIOMES = new BiomePicker();
|
||||
public static final BiomePicker VOID_BIOMES = new BiomePicker();
|
||||
public static final BiomePicker CAVE_BIOMES = new BiomePicker();
|
||||
public static final List<EndBiome> SUBBIOMES = Lists.newArrayList();
|
||||
private static final JsonObject EMPTY_JSON = new JsonObject();
|
||||
|
||||
|
@ -93,6 +97,9 @@ public class EndBiomes {
|
|||
// Better End Void
|
||||
public static final EndBiome ICE_STARFIELD = registerBiome(new BiomeIceStarfield(), BiomeType.VOID);
|
||||
|
||||
// Better End Caves
|
||||
public static final EndCaveBiome EMPTY_CAVE = registerCaveBiome(new EmptyEndCaveBiome());
|
||||
|
||||
public static void register() {}
|
||||
|
||||
public static void mutateRegistry(Registry<Biome> biomeRegistry) {
|
||||
|
@ -100,6 +107,7 @@ public class EndBiomes {
|
|||
|
||||
LAND_BIOMES.clearMutables();
|
||||
VOID_BIOMES.clearMutables();
|
||||
CAVE_BIOMES.clearMutables();
|
||||
|
||||
if (FABRIC_VOID.isEmpty()) {
|
||||
loadFabricAPIBiomes();
|
||||
|
@ -144,16 +152,9 @@ public class EndBiomes {
|
|||
Integrations.addBiomes();
|
||||
Configs.BIOME_CONFIG.saveChanges();
|
||||
|
||||
LAND_BIOMES.rebuild();
|
||||
VOID_BIOMES.rebuild();
|
||||
|
||||
LAND_BIOMES.getBiomes().forEach((endBiome) -> {
|
||||
endBiome.updateActualBiomes(biomeRegistry);
|
||||
});
|
||||
|
||||
VOID_BIOMES.getBiomes().forEach((endBiome) -> {
|
||||
endBiome.updateActualBiomes(biomeRegistry);
|
||||
});
|
||||
rebuildPicker(LAND_BIOMES, biomeRegistry);
|
||||
rebuildPicker(VOID_BIOMES, biomeRegistry);
|
||||
rebuildPicker(CAVE_BIOMES, biomeRegistry);
|
||||
|
||||
SUBBIOMES.forEach((endBiome) -> {
|
||||
endBiome.updateActualBiomes(biomeRegistry);
|
||||
|
@ -162,6 +163,13 @@ public class EndBiomes {
|
|||
CLIENT.clear();
|
||||
}
|
||||
|
||||
private static void rebuildPicker(BiomePicker picker, Registry<Biome> biomeRegistry) {
|
||||
picker.rebuild();
|
||||
picker.getBiomes().forEach((endBiome) -> {
|
||||
endBiome.updateActualBiomes(biomeRegistry);
|
||||
});
|
||||
}
|
||||
|
||||
private static void loadFabricAPIBiomes() {
|
||||
WeightedBiomePicker picker = InternalBiomeData.getEndBiomesMap().get(BiomeKeys.SMALL_END_ISLANDS);
|
||||
LayerRandomnessSource random = new BELayerRandomSource();
|
||||
|
@ -343,10 +351,12 @@ public class EndBiomes {
|
|||
}
|
||||
|
||||
private static void addToPicker(EndBiome biome, BiomeType type) {
|
||||
if (type == BiomeType.LAND)
|
||||
if (type == BiomeType.LAND) {
|
||||
LAND_BIOMES.addBiome(biome);
|
||||
else
|
||||
}
|
||||
else {
|
||||
VOID_BIOMES.addBiome(biome);
|
||||
}
|
||||
}
|
||||
|
||||
private static void registerBiomeDirectly(EndBiome biome) {
|
||||
|
@ -400,4 +410,21 @@ public class EndBiomes {
|
|||
result.addAll(SUBBIOMES);
|
||||
return result;
|
||||
}
|
||||
|
||||
public static EndCaveBiome registerCaveBiome(EndCaveBiome biome) {
|
||||
registerBiomeDirectly(biome);
|
||||
if (Configs.BIOME_CONFIG.getBoolean(biome.getID(), "enabled", true)) {
|
||||
CAVE_BIOMES.addBiome(biome);
|
||||
ID_MAP.put(biome.getID(), biome);
|
||||
}
|
||||
return biome;
|
||||
}
|
||||
|
||||
public static EndCaveBiome getCaveBiome(Random random) {
|
||||
return (EndCaveBiome) CAVE_BIOMES.getBiome(random);
|
||||
}
|
||||
|
||||
public static boolean hasBiome(Identifier biomeID) {
|
||||
return ID_MAP.containsKey(biomeID);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -13,7 +13,6 @@ import ru.betterend.BetterEnd;
|
|||
import ru.betterend.world.biome.BiomeDefinition;
|
||||
import ru.betterend.world.biome.EndBiome;
|
||||
import ru.betterend.world.features.BlueVineFeature;
|
||||
import ru.betterend.world.features.CavePlantFeature;
|
||||
import ru.betterend.world.features.CharniaFeature;
|
||||
import ru.betterend.world.features.CrashedShipFeature;
|
||||
import ru.betterend.world.features.DoublePlantFeature;
|
||||
|
@ -44,12 +43,12 @@ import ru.betterend.world.features.terrain.GeyserFeature;
|
|||
import ru.betterend.world.features.terrain.IceStarFeature;
|
||||
import ru.betterend.world.features.terrain.ObsidianBoulderFeature;
|
||||
import ru.betterend.world.features.terrain.ObsidianPillarBasementFeature;
|
||||
import ru.betterend.world.features.terrain.RoundCaveFeature;
|
||||
import ru.betterend.world.features.terrain.SpireFeature;
|
||||
import ru.betterend.world.features.terrain.SulphurHillFeature;
|
||||
import ru.betterend.world.features.terrain.SulphuricCaveFeature;
|
||||
import ru.betterend.world.features.terrain.SulphuricLakeFeature;
|
||||
import ru.betterend.world.features.terrain.SurfaceVentFeature;
|
||||
import ru.betterend.world.features.terrain.caves.RoundCaveFeature;
|
||||
import ru.betterend.world.features.trees.DragonTreeFeature;
|
||||
import ru.betterend.world.features.trees.GiganticAmaranitaFeature;
|
||||
import ru.betterend.world.features.trees.HelixTreeFeature;
|
||||
|
@ -85,7 +84,6 @@ public class EndFeatures {
|
|||
public static final EndFeature CREEPING_MOSS = new EndFeature("creeping_moss", new SinglePlantFeature(EndBlocks.CREEPING_MOSS, 5), 5);
|
||||
public static final EndFeature BLUE_VINE = new EndFeature("blue_vine", new BlueVineFeature(), 1);
|
||||
public static final EndFeature CHORUS_GRASS = new EndFeature("chorus_grass", new SinglePlantFeature(EndBlocks.CHORUS_GRASS, 4), 5);
|
||||
public static final EndFeature CAVE_GRASS = new EndFeature("cave_grass", new CavePlantFeature(EndBlocks.CAVE_GRASS, 7), 7);
|
||||
public static final EndFeature CRYSTAL_GRASS = new EndFeature("crystal_grass", new SinglePlantFeature(EndBlocks.CRYSTAL_GRASS, 8, false), 5);
|
||||
public static final EndFeature SHADOW_PLANT = new EndFeature("shadow_plant", new SinglePlantFeature(EndBlocks.SHADOW_PLANT, 6), 9);
|
||||
public static final EndFeature MURKWEED = new EndFeature("murkweed", new SinglePlantFeature(EndBlocks.MURKWEED, 3), 2);
|
||||
|
@ -161,7 +159,6 @@ public class EndFeatures {
|
|||
public static final EndFeature END_LAKE = EndFeature.makeLakeFeature("end_lake", new EndLakeFeature(), 4);
|
||||
public static final EndFeature END_LAKE_RARE = EndFeature.makeLakeFeature("end_lake_rare", new EndLakeFeature(), 40);
|
||||
public static final EndFeature ROUND_CAVE = EndFeature.makeRawGenFeature("round_cave", new RoundCaveFeature(), 2);
|
||||
public static final EndFeature ROUND_CAVE_RARE = EndFeature.makeRawGenFeature("round_cave_rare", new RoundCaveFeature(), 25);
|
||||
public static final EndFeature SPIRE = EndFeature.makeRawGenFeature("spire", new SpireFeature(), 2);
|
||||
public static final EndFeature FLOATING_SPIRE = EndFeature.makeRawGenFeature("floating_spire", new FloatingSpireFeature(), 8);
|
||||
public static final EndFeature GEYSER = EndFeature.makeRawGenFeature("geyser", new GeyserFeature(), 8);
|
||||
|
@ -215,8 +212,7 @@ public class EndFeatures {
|
|||
addFeature(CRASHED_SHIP, features);
|
||||
|
||||
if (EndBiomes.getBiome(id).hasCaves()) {
|
||||
addFeature(ROUND_CAVE_RARE, features);
|
||||
addFeature(CAVE_GRASS, features);
|
||||
addFeature(ROUND_CAVE, features);
|
||||
}
|
||||
|
||||
EndBiome endBiome = EndBiomes.getBiome(id);
|
||||
|
@ -233,8 +229,7 @@ public class EndFeatures {
|
|||
def.addFeature(CRASHED_SHIP);
|
||||
|
||||
if (def.hasCaves()) {
|
||||
def.addFeature(ROUND_CAVE_RARE);
|
||||
def.addFeature(CAVE_GRASS);
|
||||
def.addFeature(ROUND_CAVE);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -67,6 +67,7 @@ public class BiomeDefinition {
|
|||
private final Identifier id;
|
||||
private float genChance = 1F;
|
||||
private boolean hasCaves = true;
|
||||
private boolean isCaveBiome = false;
|
||||
|
||||
private ConfiguredSurfaceBuilder<?> surface;
|
||||
|
||||
|
@ -74,6 +75,11 @@ public class BiomeDefinition {
|
|||
this.id = BetterEnd.makeID(name);
|
||||
}
|
||||
|
||||
public BiomeDefinition setCaveBiome() {
|
||||
isCaveBiome = true;
|
||||
return this;
|
||||
}
|
||||
|
||||
public BiomeDefinition setSurface(Block block) {
|
||||
setSurface(SurfaceBuilder.DEFAULT.withConfig(new TernarySurfaceConfig(
|
||||
block.getDefaultState(),
|
||||
|
@ -249,7 +255,7 @@ public class BiomeDefinition {
|
|||
|
||||
return new Biome.Builder()
|
||||
.precipitation(Precipitation.NONE)
|
||||
.category(Category.THEEND)
|
||||
.category(isCaveBiome ? Category.NONE : Category.THEEND)
|
||||
.depth(0.1F)
|
||||
.scale(0.2F)
|
||||
.temperature(2.0F)
|
||||
|
|
|
@ -0,0 +1,18 @@
|
|||
package ru.betterend.world.biome;
|
||||
|
||||
import ru.betterend.registry.EndBlocks;
|
||||
import ru.betterend.registry.EndParticles;
|
||||
import ru.betterend.registry.EndSounds;
|
||||
|
||||
public class EmptyEndCaveBiome extends EndCaveBiome {
|
||||
public EmptyEndCaveBiome() {
|
||||
super(new BiomeDefinition("empty_end_cave")
|
||||
.setFogColor(255, 184, 71)
|
||||
.setFogDensity(2.0F)
|
||||
.setPlantsColor(219, 115, 38)
|
||||
.setWaterAndFogColor(145, 108, 72)
|
||||
.setMusic(EndSounds.MUSIC_FOREST)
|
||||
.setParticles(EndParticles.AMBER_SPHERE, 0.001F)
|
||||
.setSurface(EndBlocks.AMBER_MOSS));
|
||||
}
|
||||
}
|
|
@ -190,8 +190,7 @@ public class EndBiome {
|
|||
if (edge != null) {
|
||||
edge.updateActualBiomes(biomeRegistry);
|
||||
}
|
||||
Biome biome = biomeRegistry.get(mcID);
|
||||
this.actualBiome = biome;
|
||||
this.actualBiome = biomeRegistry.get(mcID);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
33
src/main/java/ru/betterend/world/biome/EndCaveBiome.java
Normal file
33
src/main/java/ru/betterend/world/biome/EndCaveBiome.java
Normal file
|
@ -0,0 +1,33 @@
|
|||
package ru.betterend.world.biome;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Random;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
import net.minecraft.world.gen.feature.Feature;
|
||||
|
||||
public class EndCaveBiome extends EndBiome {
|
||||
private List<Feature<?>> floorFeatures = Lists.newArrayList();
|
||||
private List<Feature<?>> ceilFeatures = Lists.newArrayList();
|
||||
|
||||
public EndCaveBiome(BiomeDefinition definition) {
|
||||
super(definition.setCaveBiome());
|
||||
}
|
||||
|
||||
public void addFloorFeature(Feature<?> feature) {
|
||||
floorFeatures.add(feature);
|
||||
}
|
||||
|
||||
public void addCeilFeature(Feature<?> feature) {
|
||||
ceilFeatures.add(feature);
|
||||
}
|
||||
|
||||
public Feature<?> getFloorFeature(Random random) {
|
||||
return floorFeatures.isEmpty() ? null : floorFeatures.get(random.nextInt(floorFeatures.size()));
|
||||
}
|
||||
|
||||
public Feature<?> getCeilFeature(Random random) {
|
||||
return ceilFeatures.isEmpty() ? null : ceilFeatures.get(random.nextInt(ceilFeatures.size()));
|
||||
}
|
||||
}
|
|
@ -32,6 +32,7 @@ import ru.betterend.util.sdf.primitive.SDFSphere;
|
|||
import ru.betterend.world.features.DefaultFeature;
|
||||
import ru.betterend.world.generator.GeneratorOptions;
|
||||
|
||||
@Deprecated
|
||||
public class RoundCaveFeature extends DefaultFeature {
|
||||
private static final BlockState CAVE_AIR = Blocks.CAVE_AIR.getDefaultState();
|
||||
|
||||
|
|
|
@ -0,0 +1,134 @@
|
|||
package ru.betterend.world.features.terrain.caves;
|
||||
|
||||
import java.util.Random;
|
||||
import java.util.Set;
|
||||
|
||||
import com.google.common.collect.Sets;
|
||||
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.block.Blocks;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.BlockPos.Mutable;
|
||||
import net.minecraft.world.Heightmap;
|
||||
import net.minecraft.world.StructureWorldAccess;
|
||||
import net.minecraft.world.gen.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.gen.feature.DefaultFeatureConfig;
|
||||
import ru.betterend.interfaces.IBiomeArray;
|
||||
import ru.betterend.registry.EndBiomes;
|
||||
import ru.betterend.registry.EndTags;
|
||||
import ru.betterend.util.BlocksHelper;
|
||||
import ru.betterend.util.MHelper;
|
||||
import ru.betterend.world.biome.EndCaveBiome;
|
||||
import ru.betterend.world.features.DefaultFeature;
|
||||
import ru.betterend.world.generator.GeneratorOptions;
|
||||
|
||||
public abstract class EndCaveFeature extends DefaultFeature {
|
||||
protected static final BlockState CAVE_AIR = Blocks.CAVE_AIR.getDefaultState();
|
||||
protected static final BlockState END_STONE = Blocks.END_STONE.getDefaultState();
|
||||
protected static final BlockState WATER = Blocks.WATER.getDefaultState();
|
||||
|
||||
@Override
|
||||
public boolean generate(StructureWorldAccess world, ChunkGenerator chunkGenerator, Random random, BlockPos pos, DefaultFeatureConfig config) {
|
||||
if (!(GeneratorOptions.useNewGenerator() && GeneratorOptions.noRingVoid()) || pos.getX() * pos.getX() + pos.getZ() * pos.getZ() <= 22500) {
|
||||
return false;
|
||||
}
|
||||
|
||||
int radius = MHelper.randRange(10, 30, random);
|
||||
BlockPos center = findPos(world, pos, radius, random);
|
||||
|
||||
if (center == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
EndCaveBiome biome = EndBiomes.getCaveBiome(random);
|
||||
Set<BlockPos> caveBlocks = generate(world, center, radius, random);
|
||||
if (biome != null && !caveBlocks.isEmpty()) {
|
||||
setBiomes(world, biome, caveBlocks);
|
||||
Set<BlockPos> floorPositions = Sets.newHashSet();
|
||||
Set<BlockPos> ceilPositions = Sets.newHashSet();
|
||||
Mutable mut = new Mutable();
|
||||
caveBlocks.forEach((bpos) -> {
|
||||
mut.set(bpos);
|
||||
if (world.getBlockState(mut).getMaterial().isReplaceable()) {
|
||||
mut.setY(bpos.getY() - 1);
|
||||
if (world.getBlockState(mut).isIn(EndTags.GEN_TERRAIN)) {
|
||||
floorPositions.add(mut.toImmutable());
|
||||
}
|
||||
mut.setY(bpos.getY() + 1);
|
||||
if (world.getBlockState(mut).isIn(EndTags.GEN_TERRAIN)) {
|
||||
ceilPositions.add(mut.toImmutable());
|
||||
}
|
||||
}
|
||||
});
|
||||
BlockState surfaceBlock = biome.getBiome().getGenerationSettings().getSurfaceConfig().getTopMaterial();
|
||||
placeFloor(world, biome, floorPositions, random, surfaceBlock);
|
||||
placeCeil(world, biome, ceilPositions, random);
|
||||
}
|
||||
fixBlocks(world, center, radius);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
protected abstract Set<BlockPos> generate(StructureWorldAccess world, BlockPos center, int radius, Random random);
|
||||
|
||||
protected void placeFloor(StructureWorldAccess world, EndCaveBiome biome, Set<BlockPos> floorPositions, Random random, BlockState surfaceBlock) {
|
||||
floorPositions.forEach((pos) -> {
|
||||
BlocksHelper.setWithoutUpdate(world, pos, surfaceBlock);
|
||||
});
|
||||
}
|
||||
|
||||
protected void placeCeil(StructureWorldAccess world, EndCaveBiome biome, Set<BlockPos> ceilPositions, Random random) {
|
||||
|
||||
}
|
||||
|
||||
protected void setBiomes(StructureWorldAccess world, EndCaveBiome biome, Set<BlockPos> blocks) {
|
||||
blocks.forEach((pos) -> setBiome(world, pos, biome));
|
||||
}
|
||||
|
||||
private void setBiome(StructureWorldAccess world, BlockPos pos, EndCaveBiome biome) {
|
||||
IBiomeArray array = (IBiomeArray) world.getChunk(pos).getBiomeArray();
|
||||
if (array != null) {
|
||||
array.setBiome(biome.getActualBiome(), pos);
|
||||
}
|
||||
}
|
||||
|
||||
private BlockPos findPos(StructureWorldAccess world, BlockPos pos, int radius, Random random) {
|
||||
int top = world.getTopY(Heightmap.Type.WORLD_SURFACE_WG, pos.getX(), pos.getZ());
|
||||
Mutable bpos = new Mutable();
|
||||
bpos.setX(pos.getX());
|
||||
bpos.setZ(pos.getZ());
|
||||
bpos.setY(top - 1);
|
||||
|
||||
BlockState state = world.getBlockState(bpos);
|
||||
while (!state.isIn(EndTags.GEN_TERRAIN) && bpos.getY() > 5) {
|
||||
bpos.setY(bpos.getY() - 1);
|
||||
state = world.getBlockState(bpos);
|
||||
}
|
||||
if (bpos.getY() < 10) {
|
||||
return null;
|
||||
}
|
||||
top = (int) (bpos.getY() - (radius * 1.3F + 5));
|
||||
|
||||
while (state.isIn(EndTags.GEN_TERRAIN) || !state.getFluidState().isEmpty() && bpos.getY() > 5) {
|
||||
bpos.setY(bpos.getY() - 1);
|
||||
state = world.getBlockState(bpos);
|
||||
}
|
||||
int bottom = (int) (bpos.getY() + radius * 1.3F + 5);
|
||||
|
||||
if (top <= bottom) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return new BlockPos(pos.getX(), MHelper.randRange(bottom, top, random), pos.getZ());
|
||||
}
|
||||
|
||||
private void fixBlocks(StructureWorldAccess world, BlockPos pos, int radius) {
|
||||
int x1 = pos.getX() - radius - 5;
|
||||
int y1 = pos.getY() - radius - 5;
|
||||
int z1 = pos.getZ() - radius - 5;
|
||||
int x2 = pos.getX() + radius + 5;
|
||||
int y2 = pos.getY() + radius + 5;
|
||||
int z2 = pos.getZ() + radius + 5;
|
||||
BlocksHelper.fixBlocks(world, new BlockPos(x1, y1, z1), new BlockPos(x2, y2, z2));
|
||||
}
|
||||
}
|
|
@ -0,0 +1,85 @@
|
|||
package ru.betterend.world.features.terrain.caves;
|
||||
|
||||
import java.util.Random;
|
||||
import java.util.Set;
|
||||
|
||||
import com.google.common.collect.Sets;
|
||||
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.block.Material;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.BlockPos.Mutable;
|
||||
import net.minecraft.world.StructureWorldAccess;
|
||||
import ru.betterend.noise.OpenSimplexNoise;
|
||||
import ru.betterend.registry.EndTags;
|
||||
import ru.betterend.util.BlocksHelper;
|
||||
import ru.betterend.util.MHelper;
|
||||
|
||||
public class RoundCaveFeature extends EndCaveFeature {
|
||||
@Override
|
||||
protected Set<BlockPos> generate(StructureWorldAccess world, BlockPos center, int radius, Random random) {
|
||||
OpenSimplexNoise noise = new OpenSimplexNoise(MHelper.getSeed(534, center.getX(), center.getZ()));
|
||||
|
||||
int x1 = center.getX() - radius - 5;
|
||||
int z1 = center.getZ() - radius - 5;
|
||||
int x2 = center.getX() + radius + 5;
|
||||
int z2 = center.getZ() + radius + 5;
|
||||
int y1 = MHelper.floor(center.getY() - (radius + 5) / 1.6);
|
||||
int y2 = MHelper.floor(center.getY() + (radius + 5) / 1.6);
|
||||
|
||||
double hr = radius * 0.75;
|
||||
double nr = radius * 0.25;
|
||||
|
||||
BlockState state;
|
||||
Mutable bpos = new Mutable();
|
||||
Set<BlockPos> blocks = Sets.newHashSet();
|
||||
for (int x = x1; x <= x2; x++) {
|
||||
int xsq = x - center.getX();
|
||||
xsq *= xsq;
|
||||
bpos.setX(x);
|
||||
for (int z = z1; z <= z2; z++) {
|
||||
int zsq = z - center.getZ();
|
||||
zsq *= zsq;
|
||||
bpos.setZ(z);
|
||||
for (int y = y1; y <= y2; y++) {
|
||||
int ysq = y - center.getY();
|
||||
ysq *= 1.6;
|
||||
ysq *= ysq;
|
||||
bpos.setY(y);
|
||||
double r = noise.eval(x * 0.1, y * 0.1, z * 0.1) * nr + hr;
|
||||
//double r2 = r + 5;
|
||||
double dist = xsq + ysq + zsq;
|
||||
if (dist < r * r) {
|
||||
state = world.getBlockState(bpos);
|
||||
if (isReplaceable(state)) {
|
||||
BlocksHelper.setWithoutUpdate(world, bpos, CAVE_AIR);
|
||||
blocks.add(bpos.toImmutable());
|
||||
|
||||
while (state.getMaterial().equals(Material.LEAVES)) {
|
||||
BlocksHelper.setWithoutUpdate(world, bpos, CAVE_AIR);
|
||||
bpos.setY(bpos.getY() + 1);
|
||||
state = world.getBlockState(bpos);
|
||||
}
|
||||
|
||||
bpos.setY(y - 1);
|
||||
while (state.getMaterial().equals(Material.LEAVES)) {
|
||||
BlocksHelper.setWithoutUpdate(world, bpos, CAVE_AIR);
|
||||
bpos.setY(bpos.getY() - 1);
|
||||
state = world.getBlockState(bpos);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return blocks;
|
||||
}
|
||||
|
||||
private boolean isReplaceable(BlockState state) {
|
||||
return state.isIn(EndTags.GEN_TERRAIN)
|
||||
|| state.getMaterial().isReplaceable()
|
||||
|| state.getMaterial().equals(Material.PLANT)
|
||||
|| state.getMaterial().equals(Material.LEAVES);
|
||||
}
|
||||
}
|
|
@ -10,7 +10,6 @@ import net.minecraft.util.math.noise.SimplexNoiseSampler;
|
|||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.util.registry.RegistryLookupCodec;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.Biome.Category;
|
||||
import net.minecraft.world.biome.BiomeKeys;
|
||||
import net.minecraft.world.biome.source.BiomeSource;
|
||||
import net.minecraft.world.biome.source.TheEndBiomeSource;
|
||||
|
@ -61,7 +60,7 @@ public class BetterEndBiomeSource extends BiomeSource {
|
|||
private static List<Biome> getBiomes(Registry<Biome> biomeRegistry) {
|
||||
List<Biome> list = Lists.newArrayList();
|
||||
biomeRegistry.forEach((biome) -> {
|
||||
if (biome.getCategory() == Category.THEEND) {
|
||||
if (EndBiomes.hasBiome(biomeRegistry.getId(biome))) {
|
||||
list.add(biome);
|
||||
}
|
||||
});
|
||||
|
|
|
@ -32,12 +32,13 @@ public class BiomePicker {
|
|||
|
||||
public void clearMutables() {
|
||||
maxChance = maxChanceUnmutable;
|
||||
for (int i = biomes.size() - 1; i >= biomeCount; i--)
|
||||
for (int i = biomes.size() - 1; i >= biomeCount; i--) {
|
||||
biomes.remove(i);
|
||||
}
|
||||
}
|
||||
|
||||
public EndBiome getBiome(Random random) {
|
||||
return tree.getBiome(random.nextFloat() * maxChance);
|
||||
return biomes.isEmpty() ? null : tree.getBiome(random.nextFloat() * maxChance);
|
||||
}
|
||||
|
||||
public List<EndBiome> getBiomes() {
|
||||
|
@ -59,6 +60,9 @@ public class BiomePicker {
|
|||
}
|
||||
|
||||
public void rebuild() {
|
||||
if (biomes.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
maxChance = maxChanceUnmutable;
|
||||
for (int i = biomeCount; i < biomes.size(); i++) {
|
||||
maxChance = biomes.get(i).mutateGenChance(maxChance);
|
||||
|
|
|
@ -33,6 +33,7 @@
|
|||
"SlimeEntityMixin",
|
||||
"AnvilBlockMixin",
|
||||
"BrewingAccessor",
|
||||
"BiomeArrayMixin",
|
||||
"EntityMixin"
|
||||
],
|
||||
"injectors": {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue