diff --git a/src/main/java/ru/betterend/blocks/BlockTerrain.java b/src/main/java/ru/betterend/blocks/BlockTerrain.java index d97c8938..e47e1905 100644 --- a/src/main/java/ru/betterend/blocks/BlockTerrain.java +++ b/src/main/java/ru/betterend/blocks/BlockTerrain.java @@ -10,6 +10,7 @@ import net.minecraft.block.Block; import net.minecraft.block.BlockState; import net.minecraft.block.Blocks; import net.minecraft.block.MaterialColor; +import net.minecraft.block.SnowBlock; import net.minecraft.enchantment.EnchantmentHelper; import net.minecraft.enchantment.Enchantments; import net.minecraft.entity.player.PlayerEntity; @@ -24,7 +25,10 @@ import net.minecraft.util.ActionResult; import net.minecraft.util.Hand; import net.minecraft.util.hit.BlockHitResult; import net.minecraft.util.math.BlockPos; +import net.minecraft.util.math.Direction; import net.minecraft.world.World; +import net.minecraft.world.WorldView; +import net.minecraft.world.chunk.light.ChunkLightProvider; import ru.betterend.blocks.basis.BlockBase; public class BlockTerrain extends BlockBase { @@ -64,8 +68,21 @@ public class BlockTerrain extends BlockBase { @Override public void randomTick(BlockState state, ServerWorld world, BlockPos pos, Random random) { - if (random.nextInt(16) == 0 && world.getBlockState(pos.up()).getMaterial().blocksLight()) { + if (random.nextInt(16) == 0 && !canSurvive(state, world, pos)) { world.setBlockState(pos, Blocks.END_STONE.getDefaultState()); } } + + public static boolean canSurvive(BlockState state, WorldView worldView, BlockPos pos) { + BlockPos blockPos = pos.up(); + BlockState blockState = worldView.getBlockState(blockPos); + if (blockState.isOf(Blocks.SNOW) && (Integer)blockState.get(SnowBlock.LAYERS) == 1) { + return true; + } else if (blockState.getFluidState().getLevel() == 8) { + return false; + } else { + int i = ChunkLightProvider.getRealisticOpacity(worldView, state, pos, blockState, blockPos, Direction.UP, blockState.getOpacity(worldView, blockPos)); + return i < 5; + } + } } diff --git a/src/main/java/ru/betterend/blocks/InfusionPedestal.java b/src/main/java/ru/betterend/blocks/InfusionPedestal.java index 8301b4be..cc65f2fd 100644 --- a/src/main/java/ru/betterend/blocks/InfusionPedestal.java +++ b/src/main/java/ru/betterend/blocks/InfusionPedestal.java @@ -3,7 +3,6 @@ package ru.betterend.blocks; import net.minecraft.block.Blocks; import net.minecraft.block.entity.BlockEntity; import net.minecraft.world.BlockView; - import ru.betterend.blocks.basis.BlockPedestal; import ru.betterend.blocks.entities.InfusionPedestalEntity; diff --git a/src/main/java/ru/betterend/blocks/entities/render/PedestalItemRenderer.java b/src/main/java/ru/betterend/blocks/entities/render/PedestalItemRenderer.java index bc2632d3..67f78c17 100644 --- a/src/main/java/ru/betterend/blocks/entities/render/PedestalItemRenderer.java +++ b/src/main/java/ru/betterend/blocks/entities/render/PedestalItemRenderer.java @@ -2,7 +2,6 @@ package ru.betterend.blocks.entities.render; import net.fabricmc.api.EnvType; import net.fabricmc.api.Environment; - import net.minecraft.block.BlockState; import net.minecraft.client.MinecraftClient; import net.minecraft.client.render.RenderLayer; @@ -20,7 +19,6 @@ import net.minecraft.item.Items; import net.minecraft.util.DyeColor; import net.minecraft.util.Identifier; import net.minecraft.util.math.MathHelper; - import ru.betterend.blocks.EternalPedestal; import ru.betterend.blocks.basis.BlockPedestal; import ru.betterend.blocks.entities.PedestalBlockEntity; diff --git a/src/main/java/ru/betterend/registry/EndBiomes.java b/src/main/java/ru/betterend/registry/EndBiomes.java index ceacfb58..bded0d14 100644 --- a/src/main/java/ru/betterend/registry/EndBiomes.java +++ b/src/main/java/ru/betterend/registry/EndBiomes.java @@ -77,8 +77,9 @@ public class EndBiomes { biomeRegistry.forEach((biome) -> { if (biome.getCategory() == Category.THEEND) { - if (!MUTABLE.containsKey(biome) && !biomeRegistry.getId(biome).getNamespace().equals("minecraft")) { - EndBiome endBiome = new EndBiome(biome, 1, 1); + Identifier id = biomeRegistry.getId(biome); + if (!MUTABLE.containsKey(biome) && !ID_MAP.containsKey(id)) { + EndBiome endBiome = new EndBiome(id, biome, 1, 1); LAND_BIOMES.addBiomeMutable(endBiome); KEYS.put(endBiome, biomeRegistry.getKey(biome).get()); } @@ -118,7 +119,7 @@ public class EndBiomes { * @return registered {@link EndBiome} */ public static EndBiome registerBiome(Biome biome, BiomeType type, float fogDensity, float genChance) { - EndBiome endBiome = new EndBiome(biome, fogDensity, genChance); + EndBiome endBiome = new EndBiome(BuiltinRegistries.BIOME.getId(biome), biome, fogDensity, genChance); addToPicker(endBiome, type); makeLink(endBiome); return endBiome; @@ -144,10 +145,11 @@ public class EndBiomes { * @return registered {@link EndBiome} */ public static EndBiome registerSubBiome(Biome biome, EndBiome parent, float fogDensity, float genChance) { - EndBiome endBiome = new EndBiome(biome, fogDensity, genChance); + EndBiome endBiome = new EndBiome(BuiltinRegistries.BIOME.getId(biome), biome, fogDensity, genChance); parent.addSubBiome(endBiome); makeLink(endBiome); SUBBIOMES.add(endBiome); + ID_MAP.put(endBiome.getID(), endBiome); return endBiome; } @@ -162,6 +164,7 @@ public class EndBiomes { parent.addSubBiome(biome); makeLink(biome); SUBBIOMES.add(biome); + ID_MAP.put(biome.getID(), biome); return biome; } diff --git a/src/main/java/ru/betterend/registry/EndFeatures.java b/src/main/java/ru/betterend/registry/EndFeatures.java index f1bf93ca..874d0fb4 100644 --- a/src/main/java/ru/betterend/registry/EndFeatures.java +++ b/src/main/java/ru/betterend/registry/EndFeatures.java @@ -9,6 +9,7 @@ import net.minecraft.util.Identifier; import net.minecraft.world.biome.Biome; import net.minecraft.world.gen.GenerationStep; import net.minecraft.world.gen.feature.ConfiguredFeature; +import ru.betterend.world.biome.EndBiome; import ru.betterend.world.features.BlueVineFeature; import ru.betterend.world.features.CavePlantFeature; import ru.betterend.world.features.DoublePlantFeature; @@ -103,6 +104,12 @@ public class EndFeatures { addFeature(ENDER_ORE, features); addFeature(ROUND_CAVE_RARE, features); addFeature(CAVE_GRASS, features); + + EndBiome endBiome = EndBiomes.getBiome(id); + EndFeature feature = endBiome.getStructuresFeature(); + if (feature != null) { + addFeature(feature, features); + } } private static void addFeature(EndFeature feature, List>>> features) { diff --git a/src/main/java/ru/betterend/util/JsonFactory.java b/src/main/java/ru/betterend/util/JsonFactory.java index 94c80e98..2b28a5c3 100644 --- a/src/main/java/ru/betterend/util/JsonFactory.java +++ b/src/main/java/ru/betterend/util/JsonFactory.java @@ -1,88 +1,102 @@ -package ru.betterend.util; - -import java.io.File; -import java.io.FileReader; -import java.io.FileWriter; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.io.Reader; - -import com.google.gson.Gson; -import com.google.gson.GsonBuilder; -import com.google.gson.JsonElement; -import com.google.gson.JsonObject; - -import net.minecraft.resource.Resource; -import ru.betterend.BetterEnd; - -public class JsonFactory { - - public final static Gson GSON = new GsonBuilder().setPrettyPrinting().create(); - - public static JsonObject getJsonObject(String path) throws IOException { - try (InputStream is = JsonFactory.class.getResourceAsStream(path)) { - Reader reader = new InputStreamReader(is); - JsonObject jsonObject = loadJson(reader).getAsJsonObject(); - if (jsonObject == null) { - return new JsonObject(); - } - return jsonObject; - } - } - - public static JsonObject getJsonObject(Resource jsonSource) { - if (jsonSource != null) { - try (InputStream is = jsonSource.getInputStream()) { - Reader reader = new InputStreamReader(is); - JsonObject jsonObject = loadJson(reader).getAsJsonObject(); - if (jsonObject == null) { - return new JsonObject(); - } - return jsonObject; - } catch (IOException ex) { - BetterEnd.LOGGER.catching(ex); - return new JsonObject(); - } - } - - return new JsonObject(); - } - - public static JsonObject getJsonObject(File jsonFile) { - if (jsonFile.exists()) { - JsonObject jsonObject = loadJson(jsonFile).getAsJsonObject(); - if (jsonObject == null) { - return new JsonObject(); - } - return jsonObject; - } - - return new JsonObject(); - } - - public static JsonElement loadJson(File jsonFile) { - if (jsonFile.exists()) { - try (Reader reader = new FileReader(jsonFile)) { - return loadJson(reader); - } catch (Exception ex) { - BetterEnd.LOGGER.catching(ex); - } - } - return null; - } - - public static JsonElement loadJson(Reader reader) { - return GSON.fromJson(reader, JsonElement.class); - } - - public static void storeJson(File jsonFile, JsonElement jsonObject) { - try(FileWriter writer = new FileWriter(jsonFile)) { - String json = GSON.toJson(jsonObject); - writer.write(json); - writer.flush(); - } catch (IOException ex) { - BetterEnd.LOGGER.catching(ex); - } - } -} +package ru.betterend.util; + +import java.io.File; +import java.io.FileReader; +import java.io.FileWriter; +import java.io.IOException; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.io.Reader; + +import com.google.gson.Gson; +import com.google.gson.GsonBuilder; +import com.google.gson.JsonElement; +import com.google.gson.JsonObject; + +import net.minecraft.resource.Resource; +import ru.betterend.BetterEnd; + +public class JsonFactory { + + public final static Gson GSON = new GsonBuilder().setPrettyPrinting().create(); + + public static JsonObject getJsonObject(String path) throws IOException { + try (InputStream is = JsonFactory.class.getResourceAsStream(path)) { + Reader reader = new InputStreamReader(is); + JsonObject jsonObject = loadJson(reader).getAsJsonObject(); + if (jsonObject == null) { + return new JsonObject(); + } + return jsonObject; + } + } + + public static JsonObject getJsonObject(Resource jsonSource) { + if (jsonSource != null) { + try (InputStream is = jsonSource.getInputStream()) { + Reader reader = new InputStreamReader(is); + JsonObject jsonObject = loadJson(reader).getAsJsonObject(); + if (jsonObject == null) { + return new JsonObject(); + } + return jsonObject; + } catch (IOException ex) { + BetterEnd.LOGGER.catching(ex); + return new JsonObject(); + } + } + + return new JsonObject(); + } + + public static JsonObject getJsonObject(InputStream stream) { + try { + Reader reader = new InputStreamReader(stream); + JsonObject jsonObject = loadJson(reader).getAsJsonObject(); + if (jsonObject == null) { + return new JsonObject(); + } + return jsonObject; + } catch (Exception ex) { + BetterEnd.LOGGER.catching(ex); + return new JsonObject(); + } + } + + public static JsonObject getJsonObject(File jsonFile) { + if (jsonFile.exists()) { + JsonObject jsonObject = loadJson(jsonFile).getAsJsonObject(); + if (jsonObject == null) { + return new JsonObject(); + } + return jsonObject; + } + + return new JsonObject(); + } + + public static JsonElement loadJson(File jsonFile) { + if (jsonFile.exists()) { + try (Reader reader = new FileReader(jsonFile)) { + return loadJson(reader); + } catch (Exception ex) { + BetterEnd.LOGGER.catching(ex); + } + } + return null; + } + + public static JsonElement loadJson(Reader reader) { + return GSON.fromJson(reader, JsonElement.class); + } + + public static void storeJson(File jsonFile, JsonElement jsonObject) { + try(FileWriter writer = new FileWriter(jsonFile)) { + String json = GSON.toJson(jsonObject); + writer.write(json); + writer.flush(); + } catch (IOException ex) { + BetterEnd.LOGGER.catching(ex); + } + } +} diff --git a/src/main/java/ru/betterend/util/StructureHelper.java b/src/main/java/ru/betterend/util/StructureHelper.java index d669b843..a9bf2b40 100644 --- a/src/main/java/ru/betterend/util/StructureHelper.java +++ b/src/main/java/ru/betterend/util/StructureHelper.java @@ -9,7 +9,6 @@ import net.minecraft.block.Blocks; import net.minecraft.block.Material; import net.minecraft.nbt.CompoundTag; import net.minecraft.nbt.NbtIo; -import net.minecraft.server.MinecraftServer; import net.minecraft.structure.Structure; import net.minecraft.structure.StructurePlacementData; import net.minecraft.tag.BlockTags; @@ -30,15 +29,17 @@ public class StructureHelper { public static Structure readStructure(Identifier resource) { String ns = resource.getNamespace(); String nm = resource.getPath(); - + return readStructure("/data/" + ns + "/structures/" + nm + ".nbt"); + } + + public static Structure readStructure(String path) { try { - InputStream inputstream = MinecraftServer.class.getResourceAsStream("/data/" + ns + "/structures/" + nm + ".nbt"); + InputStream inputstream = StructureHelper.class.getResourceAsStream(path); return readStructureFromStream(inputstream); } catch (IOException e) { e.printStackTrace(); } - return null; } diff --git a/src/main/java/ru/betterend/world/biome/EndBiome.java b/src/main/java/ru/betterend/world/biome/EndBiome.java index 0177e532..fb1eef89 100644 --- a/src/main/java/ru/betterend/world/biome/EndBiome.java +++ b/src/main/java/ru/betterend/world/biome/EndBiome.java @@ -1,15 +1,23 @@ package ru.betterend.world.biome; +import java.io.InputStream; import java.util.List; import java.util.Random; import com.google.common.collect.Lists; +import com.google.gson.JsonArray; +import com.google.gson.JsonObject; +import net.minecraft.structure.Structure; import net.minecraft.util.Identifier; import net.minecraft.util.math.BlockPos; -import net.minecraft.util.registry.BuiltinRegistries; import net.minecraft.world.WorldAccess; import net.minecraft.world.biome.Biome; +import ru.betterend.util.JsonFactory; +import ru.betterend.util.StructureHelper; +import ru.betterend.world.features.EndFeature; +import ru.betterend.world.features.ListFeature; +import ru.betterend.world.features.ListFeature.StructureInfo; public class EndBiome { protected List subbiomes = Lists.newArrayList(); @@ -25,19 +33,22 @@ public class EndBiome { protected float genChance = 1; private final float fogDensity; + private EndFeature structuresFeature; public EndBiome(BiomeDefinition definition) { biome = definition.build(); mcID = definition.getID(); fogDensity = definition.getFodDensity(); genChanceUnmutable = definition.getGenChance(); + readStructureList(); } - public EndBiome(Biome biome, float fogDensity, float genChance) { + public EndBiome(Identifier id, Biome biome, float fogDensity, float genChance) { this.biome = biome; - this.mcID = BuiltinRegistries.BIOME.getId(biome); + this.mcID = id; this.fogDensity = fogDensity; this.genChanceUnmutable = genChance; + readStructureList(); } public void genSurfColumn(WorldAccess world, BlockPos pos, Random random) { @@ -116,4 +127,33 @@ public class EndBiome { public float getFogDensity() { return fogDensity; } + + protected void readStructureList() { + String ns = mcID.getNamespace(); + String nm = mcID.getPath(); + + String path = "/data/" + ns + "/structures/biome/" + nm + "/"; + InputStream inputstream = StructureHelper.class.getResourceAsStream(path + "structures.json"); + if (inputstream != null) { + JsonObject obj = JsonFactory.getJsonObject(inputstream); + JsonArray enties = obj.getAsJsonArray("structures"); + if (enties != null) { + List list = Lists.newArrayList(); + enties.forEach((entry) -> { + JsonObject e = entry.getAsJsonObject(); + Structure structure = StructureHelper.readStructure(path + e.get("nbt").getAsString() + ".nbt"); + boolean adjustTerrain = e.get("adjustTerrain").getAsBoolean(); + int offsetY = e.get("offsetY").getAsInt(); + list.add(new StructureInfo(structure, offsetY, adjustTerrain)); + }); + if (!list.isEmpty()) { + structuresFeature = EndFeature.makeChansedFeature(nm + "_structures", new ListFeature(list), 50); + } + } + } + } + + public EndFeature getStructuresFeature() { + return structuresFeature; + } } diff --git a/src/main/java/ru/betterend/world/features/ListFeature.java b/src/main/java/ru/betterend/world/features/ListFeature.java new file mode 100644 index 00000000..e6da5d8b --- /dev/null +++ b/src/main/java/ru/betterend/world/features/ListFeature.java @@ -0,0 +1,63 @@ +package ru.betterend.world.features; + +import java.util.List; +import java.util.Random; + +import net.minecraft.structure.Structure; +import net.minecraft.util.BlockMirror; +import net.minecraft.util.BlockRotation; +import net.minecraft.util.math.BlockPos; +import net.minecraft.world.StructureWorldAccess; +import ru.betterend.registry.EndTags; + +public class ListFeature extends NBTStructureFeature { + private final List list; + private StructureInfo selected; + + public ListFeature(List list) { + this.list = list; + } + + @Override + protected Structure getStructure(StructureWorldAccess world, BlockPos pos, Random random) { + selected = list.get(random.nextInt(list.size())); + return selected.structure; + } + + @Override + protected boolean canSpawn(StructureWorldAccess world, BlockPos pos, Random random) { + return pos.getY() > 58 && world.getBlockState(pos.down()).isIn(EndTags.GEN_TERRAIN); + } + + @Override + protected BlockRotation getRotation(StructureWorldAccess world, BlockPos pos, Random random) { + return BlockRotation.random(random); + } + + @Override + protected BlockMirror getMirror(StructureWorldAccess world, BlockPos pos, Random random) { + return BlockMirror.values()[random.nextInt(3)]; + } + + @Override + protected int getYOffset(Structure structure, StructureWorldAccess world, BlockPos pos, Random random) { + return selected.offsetY; + } + + @Override + protected boolean adjustSurface(StructureWorldAccess world, BlockPos pos, Random random) { + return selected.adjustTerrain; + } + + public static final class StructureInfo { + public final boolean adjustTerrain; + public final Structure structure; + public final int offsetY; + + public StructureInfo(Structure structure, int offsetY, boolean adjustTerrain) { + this.adjustTerrain = adjustTerrain; + this.structure = structure; + this.offsetY = offsetY; + } + } +} diff --git a/src/main/java/ru/betterend/world/features/NBTStructureFeature.java b/src/main/java/ru/betterend/world/features/NBTStructureFeature.java index 4fee674b..e1f9ff4d 100644 --- a/src/main/java/ru/betterend/world/features/NBTStructureFeature.java +++ b/src/main/java/ru/betterend/world/features/NBTStructureFeature.java @@ -4,8 +4,8 @@ import java.io.IOException; import java.io.InputStream; import java.util.Random; +import net.minecraft.block.Block; import net.minecraft.block.BlockState; -import net.minecraft.block.Blocks; import net.minecraft.nbt.CompoundTag; import net.minecraft.nbt.NbtIo; import net.minecraft.server.MinecraftServer; @@ -16,19 +16,24 @@ import net.minecraft.util.BlockRotation; import net.minecraft.util.Identifier; import net.minecraft.util.math.BlockBox; import net.minecraft.util.math.BlockPos; +import net.minecraft.util.math.Direction; import net.minecraft.util.math.BlockPos.Mutable; import net.minecraft.world.StructureWorldAccess; +import net.minecraft.world.biome.Biome; import net.minecraft.world.gen.chunk.ChunkGenerator; import net.minecraft.world.gen.feature.DefaultFeatureConfig; +import net.minecraft.world.gen.surfacebuilder.SurfaceConfig; +import ru.betterend.registry.EndBiomes; +import ru.betterend.registry.EndTags; import ru.betterend.util.BlocksHelper; import ru.betterend.world.processors.DestructionStructureProcessor; public abstract class NBTStructureFeature extends DefaultFeature { protected static final DestructionStructureProcessor DESTRUCTION = new DestructionStructureProcessor(); - protected abstract Structure getStructure(); + protected abstract Structure getStructure(StructureWorldAccess world, BlockPos pos, Random random); - protected abstract boolean canSpawn(StructureWorldAccess world, BlockPos pos); + protected abstract boolean canSpawn(StructureWorldAccess world, BlockPos pos, Random random); protected abstract BlockRotation getRotation(StructureWorldAccess world, BlockPos pos, Random random); @@ -36,14 +41,37 @@ public abstract class NBTStructureFeature extends DefaultFeature { protected abstract int getYOffset(Structure structure, StructureWorldAccess world, BlockPos pos, Random random); - protected abstract boolean hasErosion(); - - protected abstract boolean hasTerrainOverlay(); - - protected abstract void addProcessors(StructurePlacementData placementData, Random random); + protected abstract boolean adjustSurface(StructureWorldAccess world, BlockPos pos, Random random); protected BlockPos getGround(StructureWorldAccess world, BlockPos center) { - return getPosOnSurface(world, center); + Biome biome = world.getBiome(center); + Identifier id = EndBiomes.getBiomeID(biome); + if (id.getNamespace().contains("moutain") || id.getNamespace().contains("lake")) { + int y = getAverageY(world, center); + return new BlockPos(center.getX(), y, center.getZ()); + } + else { + int y = getAverageYWG(world, center); + return new BlockPos(center.getX(), y, center.getZ()); + } + } + + protected int getAverageY(StructureWorldAccess world, BlockPos center) { + int y = getYOnSurface(world, center.getX(), center.getZ()); + y += getYOnSurface(world, center.getX() - 2, center.getZ() - 2); + y += getYOnSurface(world, center.getX() + 2, center.getZ() - 2); + y += getYOnSurface(world, center.getX() - 2, center.getZ() + 2); + y += getYOnSurface(world, center.getX() + 2, center.getZ() + 2); + return y / 5; + } + + protected int getAverageYWG(StructureWorldAccess world, BlockPos center) { + int y = getYOnSurfaceWG(world, center.getX(), center.getZ()); + y += getYOnSurfaceWG(world, center.getX() - 2, center.getZ() - 2); + y += getYOnSurfaceWG(world, center.getX() + 2, center.getZ() - 2); + y += getYOnSurfaceWG(world, center.getX() - 2, center.getZ() + 2); + y += getYOnSurfaceWG(world, center.getX() + 2, center.getZ() + 2); + return y / 5; } @Override @@ -51,11 +79,12 @@ public abstract class NBTStructureFeature extends DefaultFeature { center = new BlockPos(((center.getX() >> 4) << 4) | 8, 128, ((center.getZ() >> 4) << 4) | 8); center = getGround(world, center); - if (!canSpawn(world, center)) { + if (!canSpawn(world, center, random)) { return false; } - Structure structure = getStructure(); + int posY = center.getY() + 1; + Structure structure = getStructure(world, center, random); BlockRotation rotation = getRotation(world, center, random); BlockMirror mirror = getMirror(world, center, random); BlockPos offset = Structure.transformAround(structure.getSize(), mirror, rotation, BlockPos.ORIGIN); @@ -63,44 +92,39 @@ public abstract class NBTStructureFeature extends DefaultFeature { BlockBox bounds = makeBox(center); StructurePlacementData placementData = new StructurePlacementData().setRotation(rotation).setMirror(mirror).setBoundingBox(bounds); - addProcessors(placementData, random); - structure.place(world, center.add(-offset.getX() * 0.5, 0, -offset.getZ() * 0.5), placementData, random); + center = center.add(-offset.getX() * 0.5, 1, -offset.getZ() * 0.5); + structure.place(world, center, placementData, random); - int x1 = center.getX(); - int y1 = center.getX(); - int z1 = center.getX(); - int x2 = x1 + offset.getX(); - int y2 = y1 + offset.getY(); - int z2 = z1 + offset.getZ(); - - boolean erosion = hasErosion(); - boolean overlay = hasTerrainOverlay(); - - if (erosion || overlay) { + if (adjustSurface(world, center, random)) { Mutable mut = new Mutable(); + int x1 = center.getX(); + int z1 = center.getZ(); + int x2 = x1 + offset.getX(); + int z2 = z1 + offset.getZ(); + + int surfMax = posY - 1; for (int x = x1; x <= x2; x++) { mut.setX(x); for (int z = z1; z <= z2; z++) { mut.setZ(z); - for (int y = y1; y <= y2; y++) { - mut.setY(y); - if (bounds.contains(mut)) { - if (overlay) { - if (world.getBlockState(mut).isOf(Blocks.END_STONE) && world.isAir(mut.up())) { - BlockState terrain = world.getBiome(mut).getGenerationSettings().getSurfaceConfig().getTopMaterial(); - BlocksHelper.setWithoutUpdate(world, mut, terrain); - } + mut.setY(posY); + BlockState state = world.getBlockState(mut); + if (!state.isIn(EndTags.GEN_TERRAIN) && Block.sideCoversSmallSquare(world, mut, Direction.DOWN)) { + for (int i = 0; i < 10; i--) { + mut.setY(mut.getY() - 1); + BlockState stateSt = world.getBlockState(mut); + if (!stateSt.isIn(EndTags.GEN_TERRAIN) && stateSt.getMaterial().isReplaceable()) { + SurfaceConfig config = world.getBiome(mut).getGenerationSettings().getSurfaceConfig(); + boolean isTop = mut.getY() == surfMax && state.getMaterial().blocksLight(); + BlockState top = isTop ? config.getTopMaterial() : config.getUnderMaterial(); + BlocksHelper.setWithoutUpdate(world, mut, top); } - if (erosion) { - mut.setY(mut.getY() - 1); - int down = BlocksHelper.downRay(world, mut, 32); - if (down > 0) { - mut.setY(mut.getY() + 1); - BlockState state = world.getBlockState(mut); - BlocksHelper.setWithoutUpdate(world, mut, AIR); - mut.setY(mut.getY() - down); - BlocksHelper.setWithoutUpdate(world, mut, state); + else { + if (stateSt.isIn(EndTags.END_GROUND) && state.getMaterial().blocksLight()) { + SurfaceConfig config = world.getBiome(mut).getGenerationSettings().getSurfaceConfig(); + BlocksHelper.setWithoutUpdate(world, mut, config.getUnderMaterial()); } + break; } } } diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/fallen_log_1.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/fallen_log_1.nbt new file mode 100644 index 00000000..aab1b13a Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/fallen_log_1.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/fallen_log_2.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/fallen_log_2.nbt new file mode 100644 index 00000000..40c21ace Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/fallen_log_2.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_1.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_1.nbt new file mode 100644 index 00000000..1ed06c7c Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_1.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_2.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_2.nbt new file mode 100644 index 00000000..92f2f896 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_2.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_3.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_3.nbt new file mode 100644 index 00000000..56514f7c Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_3.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_4.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_4.nbt new file mode 100644 index 00000000..48a358d1 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_4.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_5.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_5.nbt new file mode 100644 index 00000000..83ccf5a1 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_5.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_6.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_6.nbt new file mode 100644 index 00000000..6f1e11cb Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_6.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_7.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_7.nbt new file mode 100644 index 00000000..25a72062 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_7.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_8.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_8.nbt new file mode 100644 index 00000000..b4791e3a Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/ruins_8.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/small_mansion.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/small_mansion.nbt new file mode 100644 index 00000000..0af440e5 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/small_mansion.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/structures.json b/src/main/resources/data/betterend/structures/biome/shadow_forest/structures.json new file mode 100644 index 00000000..fbf3ccdf --- /dev/null +++ b/src/main/resources/data/betterend/structures/biome/shadow_forest/structures.json @@ -0,0 +1,17 @@ +{ + "structures": [ + { "nbt": "stump_1", "offsetY": 0, "adjustTerrain": false }, + { "nbt": "stump_2", "offsetY": 0, "adjustTerrain": false }, + { "nbt": "fallen_log_1", "offsetY": 0, "adjustTerrain": false }, + { "nbt": "fallen_log_2", "offsetY": 0, "adjustTerrain": false }, + { "nbt": "ruins_1", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_2", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_3", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_4", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_5", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_6", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_7", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "ruins_8", "offsetY": 0, "adjustTerrain": true }, + { "nbt": "small_mansion", "offsetY": -1, "adjustTerrain": false } + ] +} \ No newline at end of file diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/stump_1.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/stump_1.nbt new file mode 100644 index 00000000..b6dcea63 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/stump_1.nbt differ diff --git a/src/main/resources/data/betterend/structures/biome/shadow_forest/stump_2.nbt b/src/main/resources/data/betterend/structures/biome/shadow_forest/stump_2.nbt new file mode 100644 index 00000000..2b2b93f9 Binary files /dev/null and b/src/main/resources/data/betterend/structures/biome/shadow_forest/stump_2.nbt differ