diff --git a/src/main/java/com/dfsek/terra/Terra.java b/src/main/java/com/dfsek/terra/Terra.java
index 7abcf65b2..459bf8f1f 100644
--- a/src/main/java/com/dfsek/terra/Terra.java
+++ b/src/main/java/com/dfsek/terra/Terra.java
@@ -33,7 +33,6 @@ import com.dfsek.terra.config.loaders.palette.CarverPaletteLoader;
import com.dfsek.terra.config.loaders.palette.PaletteHolderLoader;
import com.dfsek.terra.config.loaders.palette.PaletteLayerLoader;
import com.dfsek.terra.debug.Debug;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import com.dfsek.terra.generation.config.NoiseBuilder;
import com.dfsek.terra.generation.items.flora.FloraLayer;
import com.dfsek.terra.generation.items.flora.TerraFlora;
diff --git a/src/main/java/com/dfsek/terra/TerraWorld.java b/src/main/java/com/dfsek/terra/TerraWorld.java
index 8e9812f84..1e1046ae0 100644
--- a/src/main/java/com/dfsek/terra/TerraWorld.java
+++ b/src/main/java/com/dfsek/terra/TerraWorld.java
@@ -9,7 +9,6 @@ import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.base.ConfigPackTemplate;
import com.dfsek.terra.config.builder.biomegrid.BiomeGridBuilder;
import com.dfsek.terra.debug.Debug;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import org.bukkit.Bukkit;
import org.bukkit.World;
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/BukkitBlockData.java b/src/main/java/com/dfsek/terra/api/bukkit/BukkitBlockData.java
deleted file mode 100644
index 73701d1ea..000000000
--- a/src/main/java/com/dfsek/terra/api/bukkit/BukkitBlockData.java
+++ /dev/null
@@ -1,17 +0,0 @@
-package com.dfsek.terra.api.bukkit;
-
-import com.dfsek.terra.api.generic.BlockData;
-
-public class BukkitBlockData implements BlockData {
- private final org.bukkit.block.data.BlockData delegate;
-
- public BukkitBlockData(org.bukkit.block.data.BlockData delegate) {
- this.delegate = delegate;
- }
-
-
- @Override
- public org.bukkit.block.data.BlockData getHandle() {
- return delegate;
- }
-}
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/BukkitWorldHandle.java b/src/main/java/com/dfsek/terra/api/bukkit/BukkitWorldHandle.java
index b28ee2585..a804889ba 100644
--- a/src/main/java/com/dfsek/terra/api/bukkit/BukkitWorldHandle.java
+++ b/src/main/java/com/dfsek/terra/api/bukkit/BukkitWorldHandle.java
@@ -1,9 +1,17 @@
package com.dfsek.terra.api.bukkit;
+import com.dfsek.terra.api.bukkit.world.block.BukkitBlockData;
+import com.dfsek.terra.api.bukkit.world.block.BukkitMaterialData;
+import com.dfsek.terra.api.bukkit.world.block.data.BukkitStairs;
+import com.dfsek.terra.api.bukkit.world.block.data.BukkitWaterlogged;
import com.dfsek.terra.api.generic.world.WorldHandle;
+import com.dfsek.terra.api.generic.world.block.BlockData;
+import com.dfsek.terra.api.generic.world.block.MaterialData;
+import com.dfsek.terra.api.generic.world.block.data.Waterlogged;
import org.bukkit.Bukkit;
import org.bukkit.Material;
import org.bukkit.block.Block;
+import org.bukkit.block.data.type.Stairs;
public class BukkitWorldHandle implements WorldHandle {
@@ -23,7 +31,15 @@ public class BukkitWorldHandle implements WorldHandle {
}
@Override
- public com.dfsek.terra.api.generic.BlockData createBlockData(String data) {
+ public BlockData createBlockData(String data) {
+ org.bukkit.block.data.BlockData bukkitData = Bukkit.createBlockData(data);
+ if(bukkitData instanceof Stairs) return new BukkitStairs(bukkitData);
+ if(bukkitData instanceof Waterlogged) return new BukkitWaterlogged(bukkitData);
return new BukkitBlockData(Bukkit.createBlockData(data));
}
+
+ @Override
+ public MaterialData createMaterialData(String data) {
+ return new BukkitMaterialData(Material.matchMaterial(data));
+ }
}
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/generator/BukkitChunkGenerator.java b/src/main/java/com/dfsek/terra/api/bukkit/generator/BukkitChunkGenerator.java
index 7b0d3362c..a2cf7d3ab 100644
--- a/src/main/java/com/dfsek/terra/api/bukkit/generator/BukkitChunkGenerator.java
+++ b/src/main/java/com/dfsek/terra/api/bukkit/generator/BukkitChunkGenerator.java
@@ -1,9 +1,9 @@
package com.dfsek.terra.api.bukkit.generator;
import com.dfsek.terra.api.bukkit.BukkitBiomeGrid;
-import com.dfsek.terra.api.bukkit.BukkitBlockData;
import com.dfsek.terra.api.bukkit.BukkitWorld;
-import com.dfsek.terra.api.generic.BlockData;
+import com.dfsek.terra.api.bukkit.world.block.BukkitBlockData;
+import com.dfsek.terra.api.generic.world.block.BlockData;
import org.bukkit.World;
import org.bukkit.generator.ChunkGenerator;
import org.jetbrains.annotations.NotNull;
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/BukkitBlock.java b/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitBlock.java
similarity index 77%
rename from src/main/java/com/dfsek/terra/api/bukkit/BukkitBlock.java
rename to src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitBlock.java
index d635b63b8..10a9ca888 100644
--- a/src/main/java/com/dfsek/terra/api/bukkit/BukkitBlock.java
+++ b/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitBlock.java
@@ -1,7 +1,7 @@
-package com.dfsek.terra.api.bukkit;
+package com.dfsek.terra.api.bukkit.world.block;
-import com.dfsek.terra.api.generic.BlockData;
-import com.dfsek.terra.api.generic.world.Block;
+import com.dfsek.terra.api.generic.world.block.Block;
+import com.dfsek.terra.api.generic.world.block.BlockData;
public class BukkitBlock implements Block {
private final org.bukkit.block.Block delegate;
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitBlockData.java b/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitBlockData.java
new file mode 100644
index 000000000..98d6e54c7
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitBlockData.java
@@ -0,0 +1,37 @@
+package com.dfsek.terra.api.bukkit.world.block;
+
+import com.dfsek.terra.api.generic.world.block.BlockData;
+import com.dfsek.terra.api.generic.world.block.MaterialData;
+
+public class BukkitBlockData implements BlockData {
+ private final org.bukkit.block.data.BlockData delegate;
+
+ public BukkitBlockData(org.bukkit.block.data.BlockData delegate) {
+ this.delegate = delegate;
+ }
+
+
+ @Override
+ public org.bukkit.block.data.BlockData getHandle() {
+ return delegate;
+ }
+
+ @Override
+ public MaterialData getMaterial() {
+ return new BukkitMaterialData(delegate.getMaterial());
+ }
+
+ @Override
+ public boolean matches(MaterialData materialData) {
+ return delegate.getMaterial().equals(((BukkitMaterialData) materialData).getHandle());
+ }
+
+ @Override
+ public BukkitBlockData clone() {
+ try {
+ return (BukkitBlockData) super.clone();
+ } catch(CloneNotSupportedException e) {
+ throw new Error(e);
+ }
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitMaterialData.java b/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitMaterialData.java
new file mode 100644
index 000000000..6185ea8bd
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/bukkit/world/block/BukkitMaterialData.java
@@ -0,0 +1,33 @@
+package com.dfsek.terra.api.bukkit.world.block;
+
+import com.dfsek.terra.api.generic.world.block.BlockData;
+import com.dfsek.terra.api.generic.world.block.MaterialData;
+import org.bukkit.Material;
+
+public class BukkitMaterialData implements MaterialData {
+ private final Material delegate;
+
+ public BukkitMaterialData(Material delegate) {
+ this.delegate = delegate;
+ }
+
+ @Override
+ public boolean matches(MaterialData other) {
+ return ((BukkitMaterialData) other).getHandle().equals(delegate);
+ }
+
+ @Override
+ public boolean matches(BlockData other) {
+ return ((BukkitMaterialData) other.getMaterial()).getHandle().equals(delegate);
+ }
+
+ @Override
+ public Material getHandle() {
+ return delegate;
+ }
+
+ @Override
+ public int hashCode() {
+ return delegate.hashCode();
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitEnumAdapter.java b/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitEnumAdapter.java
new file mode 100644
index 000000000..8410578b3
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitEnumAdapter.java
@@ -0,0 +1,153 @@
+package com.dfsek.terra.api.bukkit.world.block.data;
+
+import com.dfsek.terra.api.generic.world.block.BlockFace;
+import com.dfsek.terra.api.generic.world.block.data.Bisected;
+import com.dfsek.terra.api.generic.world.block.data.Stairs;
+
+public final class BukkitEnumAdapter {
+ public static Stairs.Shape fromBukkitStair(org.bukkit.block.data.type.Stairs.Shape shape) {
+ switch(shape) {
+ case STRAIGHT:
+ return Stairs.Shape.STRAIGHT;
+ case INNER_LEFT:
+ return Stairs.Shape.INNER_LEFT;
+ case OUTER_LEFT:
+ return Stairs.Shape.OUTER_LEFT;
+ case INNER_RIGHT:
+ return Stairs.Shape.INNER_RIGHT;
+ case OUTER_RIGHT:
+ return Stairs.Shape.OUTER_RIGHT;
+ default:
+ throw new IllegalStateException();
+ }
+ }
+
+ public static org.bukkit.block.data.type.Stairs.Shape fromTerraStair(Stairs.Shape shape) {
+ switch(shape) {
+ case STRAIGHT:
+ return org.bukkit.block.data.type.Stairs.Shape.STRAIGHT;
+ case INNER_LEFT:
+ return org.bukkit.block.data.type.Stairs.Shape.INNER_LEFT;
+ case OUTER_LEFT:
+ return org.bukkit.block.data.type.Stairs.Shape.OUTER_LEFT;
+ case INNER_RIGHT:
+ return org.bukkit.block.data.type.Stairs.Shape.INNER_RIGHT;
+ case OUTER_RIGHT:
+ return org.bukkit.block.data.type.Stairs.Shape.OUTER_RIGHT;
+ default:
+ throw new IllegalStateException();
+ }
+ }
+
+ public static Bisected.Half fromBukkitHalf(org.bukkit.block.data.Bisected.Half half) {
+ switch(half) {
+ case BOTTOM:
+ return Bisected.Half.BOTTOM;
+ case TOP:
+ return Bisected.Half.TOP;
+ default:
+ throw new IllegalStateException();
+ }
+ }
+
+ public static org.bukkit.block.data.Bisected.Half fromTerraHalf(Bisected.Half half) {
+ switch(half) {
+ case TOP:
+ return org.bukkit.block.data.Bisected.Half.TOP;
+ case BOTTOM:
+ return org.bukkit.block.data.Bisected.Half.BOTTOM;
+ default:
+ throw new IllegalStateException();
+ }
+ }
+
+ public static BlockFace fromBukkitBlockFace(org.bukkit.block.BlockFace face) {
+ switch(face) {
+ case DOWN:
+ return BlockFace.DOWN;
+ case UP:
+ return BlockFace.UP;
+ case NORTH_WEST:
+ return BlockFace.NORTH_WEST;
+ case NORTH_EAST:
+ return BlockFace.NORTH_EAST;
+ case SOUTH_EAST:
+ return BlockFace.SOUTH_EAST;
+ case SOUTH_WEST:
+ return BlockFace.SOUTH_WEST;
+ case NORTH_NORTH_WEST:
+ return BlockFace.NORTH_NORTH_WEST;
+ case WEST_NORTH_WEST:
+ return BlockFace.WEST_NORTH_WEST;
+ case WEST_SOUTH_WEST:
+ return BlockFace.WEST_SOUTH_WEST;
+ case SOUTH_SOUTH_WEST:
+ return BlockFace.SOUTH_SOUTH_WEST;
+ case EAST_NORTH_EAST:
+ return BlockFace.EAST_NORTH_EAST;
+ case WEST:
+ return BlockFace.WEST;
+ case SOUTH:
+ return BlockFace.SOUTH;
+ case EAST:
+ return BlockFace.EAST;
+ case NORTH:
+ return BlockFace.NORTH;
+ case SELF:
+ return BlockFace.SELF;
+ case EAST_SOUTH_EAST:
+ return BlockFace.EAST_SOUTH_EAST;
+ case NORTH_NORTH_EAST:
+ return BlockFace.NORTH_NORTH_EAST;
+ case SOUTH_SOUTH_EAST:
+ return BlockFace.SOUTH_SOUTH_EAST;
+ default:
+ throw new IllegalStateException();
+ }
+ }
+
+ public static org.bukkit.block.BlockFace fromTerraBlockFace(BlockFace face) {
+ switch(face) {
+ case DOWN:
+ return org.bukkit.block.BlockFace.DOWN;
+ case UP:
+ return org.bukkit.block.BlockFace.UP;
+ case NORTH_WEST:
+ return org.bukkit.block.BlockFace.NORTH_WEST;
+ case NORTH_EAST:
+ return org.bukkit.block.BlockFace.NORTH_EAST;
+ case SOUTH_EAST:
+ return org.bukkit.block.BlockFace.SOUTH_EAST;
+ case SOUTH_WEST:
+ return org.bukkit.block.BlockFace.SOUTH_WEST;
+ case NORTH_NORTH_WEST:
+ return org.bukkit.block.BlockFace.NORTH_NORTH_WEST;
+ case WEST_NORTH_WEST:
+ return org.bukkit.block.BlockFace.WEST_NORTH_WEST;
+ case WEST_SOUTH_WEST:
+ return org.bukkit.block.BlockFace.WEST_SOUTH_WEST;
+ case SOUTH_SOUTH_WEST:
+ return org.bukkit.block.BlockFace.SOUTH_SOUTH_WEST;
+ case EAST_NORTH_EAST:
+ return org.bukkit.block.BlockFace.EAST_NORTH_EAST;
+ case WEST:
+ return org.bukkit.block.BlockFace.WEST;
+ case SOUTH:
+ return org.bukkit.block.BlockFace.SOUTH;
+ case EAST:
+ return org.bukkit.block.BlockFace.EAST;
+ case NORTH:
+ return org.bukkit.block.BlockFace.NORTH;
+ case SELF:
+ return org.bukkit.block.BlockFace.SELF;
+ case EAST_SOUTH_EAST:
+ return org.bukkit.block.BlockFace.EAST_SOUTH_EAST;
+ case NORTH_NORTH_EAST:
+ return org.bukkit.block.BlockFace.NORTH_NORTH_EAST;
+ case SOUTH_SOUTH_EAST:
+ return org.bukkit.block.BlockFace.SOUTH_SOUTH_EAST;
+ default:
+ throw new IllegalStateException();
+ }
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitStairs.java b/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitStairs.java
new file mode 100644
index 000000000..27ed177ea
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitStairs.java
@@ -0,0 +1,55 @@
+package com.dfsek.terra.api.bukkit.world.block.data;
+
+import com.dfsek.terra.api.bukkit.world.block.BukkitBlockData;
+import com.dfsek.terra.api.generic.world.block.BlockFace;
+import com.dfsek.terra.api.generic.world.block.data.Stairs;
+import org.bukkit.block.data.BlockData;
+
+public class BukkitStairs extends BukkitBlockData implements Stairs {
+ private final org.bukkit.block.data.type.Stairs stairs;
+
+ public BukkitStairs(BlockData delegate) {
+ super(delegate);
+ this.stairs = (org.bukkit.block.data.type.Stairs) delegate;
+ }
+
+ @Override
+ public Shape getShape() {
+ return BukkitEnumAdapter.fromBukkitStair(stairs.getShape());
+ }
+
+ @Override
+ public void setShape(Shape shape) {
+ stairs.setShape(BukkitEnumAdapter.fromTerraStair(shape));
+ }
+
+ @Override
+ public Half getHalf() {
+ return BukkitEnumAdapter.fromBukkitHalf(stairs.getHalf());
+ }
+
+ @Override
+ public void setHalf(Half half) {
+ stairs.setHalf(BukkitEnumAdapter.fromTerraHalf(half));
+ }
+
+ @Override
+ public BlockFace getFacing() {
+ return BukkitEnumAdapter.fromBukkitBlockFace(stairs.getFacing());
+ }
+
+ @Override
+ public void setFacing(BlockFace facing) {
+ stairs.setFacing(BukkitEnumAdapter.fromTerraBlockFace(facing));
+ }
+
+ @Override
+ public boolean isWaterlogged() {
+ return stairs.isWaterlogged();
+ }
+
+ @Override
+ public void setWaterlogged(boolean waterlogged) {
+ stairs.setWaterlogged(waterlogged);
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitWaterlogged.java b/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitWaterlogged.java
new file mode 100644
index 000000000..25ee1cc80
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/bukkit/world/block/data/BukkitWaterlogged.java
@@ -0,0 +1,23 @@
+package com.dfsek.terra.api.bukkit.world.block.data;
+
+import com.dfsek.terra.api.bukkit.world.block.BukkitBlockData;
+import com.dfsek.terra.api.generic.world.block.data.Waterlogged;
+import org.bukkit.block.data.BlockData;
+
+public class BukkitWaterlogged extends BukkitBlockData implements Waterlogged {
+ private boolean waterlogged;
+
+ public BukkitWaterlogged(BlockData delegate) {
+ super(delegate);
+ }
+
+ @Override
+ public boolean isWaterlogged() {
+ return waterlogged;
+ }
+
+ @Override
+ public void setWaterlogged(boolean waterlogged) {
+ this.waterlogged = waterlogged;
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/gaea/biome/Generator.java b/src/main/java/com/dfsek/terra/api/gaea/biome/Generator.java
index a878a2253..d11d26623 100644
--- a/src/main/java/com/dfsek/terra/api/gaea/biome/Generator.java
+++ b/src/main/java/com/dfsek/terra/api/gaea/biome/Generator.java
@@ -1,32 +1,20 @@
package com.dfsek.terra.api.gaea.biome;
-import com.dfsek.terra.api.gaea.math.FastNoiseLite;
import com.dfsek.terra.api.gaea.math.Interpolator;
import com.dfsek.terra.api.gaea.world.palette.Palette;
-import org.bukkit.World;
-import org.bukkit.block.data.BlockData;
+import com.dfsek.terra.api.generic.world.World;
+import com.dfsek.terra.api.generic.world.block.BlockData;
public abstract class Generator {
- /**
- * Gets the 2D noise at a pair of coordinates using the provided FastNoiseLite instance.
- *
- * @param gen - The FastNoiseLite instance to use.
- * @param x - The x coordinate.
- * @param z - The z coordinate.
- * @return double - Noise value at the specified coordinates.
- */
- public abstract double getNoise(FastNoiseLite gen, World w, int x, int z);
-
/**
* Gets the 3D noise at a pair of coordinates using the provided FastNoiseLite instance.
*
- * @param gen - The FastNoiseLite instance to use.
- * @param x - The x coordinate.
- * @param y - The y coordinate.
- * @param z - The z coordinate.
+ * @param x - The x coordinate.
+ * @param y - The y coordinate.
+ * @param z - The z coordinate.
* @return double - Noise value at the specified coordinates.
*/
- public abstract double getNoise(FastNoiseLite gen, World w, int x, int y, int z);
+ public abstract double getNoise(World w, int x, int y, int z);
/**
* Gets the BlocPalette to generate the biome with.
diff --git a/src/main/java/com/dfsek/terra/api/gaea/generation/GaeaChunkGenerator.java b/src/main/java/com/dfsek/terra/api/gaea/generation/GaeaChunkGenerator.java
index 99edab779..dee2b3026 100644
--- a/src/main/java/com/dfsek/terra/api/gaea/generation/GaeaChunkGenerator.java
+++ b/src/main/java/com/dfsek/terra/api/gaea/generation/GaeaChunkGenerator.java
@@ -1,7 +1,6 @@
package com.dfsek.terra.api.gaea.generation;
import com.dfsek.terra.api.gaea.biome.Biome;
-import com.dfsek.terra.api.gaea.math.ChunkInterpolator;
import com.dfsek.terra.api.gaea.math.FastNoiseLite;
import com.dfsek.terra.api.gaea.profiler.ProfileFuture;
import com.dfsek.terra.api.gaea.profiler.WorldProfiler;
diff --git a/src/main/java/com/dfsek/terra/api/gaea/generation/GenerationPopulator.java b/src/main/java/com/dfsek/terra/api/gaea/generation/GenerationPopulator.java
index 76cab5215..57ac2cb0a 100644
--- a/src/main/java/com/dfsek/terra/api/gaea/generation/GenerationPopulator.java
+++ b/src/main/java/com/dfsek/terra/api/gaea/generation/GenerationPopulator.java
@@ -1,6 +1,5 @@
package com.dfsek.terra.api.gaea.generation;
-import com.dfsek.terra.api.gaea.math.ChunkInterpolator;
import org.bukkit.World;
import org.bukkit.generator.ChunkGenerator;
diff --git a/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator.java b/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator.java
deleted file mode 100644
index 9f8b34a46..000000000
--- a/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator.java
+++ /dev/null
@@ -1,32 +0,0 @@
-package com.dfsek.terra.api.gaea.math;
-
-import com.dfsek.terra.api.gaea.biome.BiomeGrid;
-import org.bukkit.World;
-
-public interface ChunkInterpolator {
- double getNoise(double x, double z);
-
- double getNoise(double x, double y, double z);
-
- enum InterpolationType {
- /**
- * 2D (Bilinear) interpolation
- */
- BILINEAR {
- @Override
- public com.dfsek.terra.api.gaea.math.ChunkInterpolator getInstance(World w, int chunkX, int chunkZ, BiomeGrid grid, FastNoiseLite noise) {
- return new ChunkInterpolator2(w, chunkX, chunkZ, grid, noise);
- }
- },
- /**
- * 3D (Trilinear) interpolation
- */
- TRILINEAR {
- @Override
- public com.dfsek.terra.api.gaea.math.ChunkInterpolator getInstance(World w, int chunkX, int chunkZ, BiomeGrid grid, FastNoiseLite noise) {
- return new ChunkInterpolator3(w, chunkX, chunkZ, grid, noise);
- }
- };
- public abstract com.dfsek.terra.api.gaea.math.ChunkInterpolator getInstance(World w, int chunkX, int chunkZ, BiomeGrid grid, FastNoiseLite noise);
- }
-}
diff --git a/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator2.java b/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator2.java
deleted file mode 100644
index 9191eadd0..000000000
--- a/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator2.java
+++ /dev/null
@@ -1,72 +0,0 @@
-package com.dfsek.terra.api.gaea.math;
-
-import com.dfsek.terra.api.gaea.biome.BiomeGrid;
-import com.dfsek.terra.api.gaea.biome.Generator;
-import com.dfsek.terra.api.gaea.generation.GenerationPhase;
-import org.bukkit.World;
-
-/**
- * Class to abstract away the 16 Interpolators needed to generate a chunk.
- * Contains method to get interpolated noise at a coordinate within the chunk.
- */
-public class ChunkInterpolator2 implements ChunkInterpolator {
- private final Interpolator[][] interpGrid = new Interpolator[4][4];
-
- private final int xOrigin;
- private final int zOrigin;
- private final FastNoiseLite noise;
- private final World w;
-
- /**
- * Instantiates a ChunkInterpolator at a pair of chunk coordinates, with a BiomeGrid and FastNoiseLite instance.
- *
- * @param chunkX X coordinate of the chunk.
- * @param chunkZ Z coordinate of the chunk.
- * @param grid BiomeGrid to use for noise fetching.
- * @param noise FastNoiseLite instance to use.
- */
- public ChunkInterpolator2(World w, int chunkX, int chunkZ, BiomeGrid grid, FastNoiseLite noise) {
- this.xOrigin = chunkX << 4;
- this.zOrigin = chunkZ << 4;
- this.noise = noise;
- this.w = w;
- Generator[][] gridTemp = new Generator[8][8];
- for(int x = - 2; x < 6; x++) {
- for(int z = - 2; z < 6; z++) {
- gridTemp[x + 2][z + 2] = grid.getBiome(xOrigin + (x << 2), zOrigin + (z << 2), GenerationPhase.BASE).getGenerator();
- }
- }
- for(byte x = 0; x < 4; x++) {
- for(byte z = 0; z < 4; z++) {
- interpGrid[x][z] = new Interpolator(biomeAvg(x, z, gridTemp),
- biomeAvg(x + 1, z, gridTemp),
- biomeAvg(x, z + 1, gridTemp),
- biomeAvg(x + 1, z + 1, gridTemp), gridTemp[x+1][z+1].getInterpolationType());
- }
- }
- }
-
- private double biomeAvg(int x, int z, Generator[][] g) {
- return (g[x + 3][z + 2].getNoise(noise, w, (x << 2) + xOrigin, (z << 2) + zOrigin)
- + g[x + 1][z + 2].getNoise(noise, w, (x << 2) + xOrigin, (z << 2) + zOrigin)
- + g[x + 2][z + 3].getNoise(noise, w, (x << 2) + xOrigin, (z << 2) + zOrigin)
- + g[x + 2][z + 1].getNoise(noise, w, (x << 2) + xOrigin, (z << 2) + zOrigin)) / 4D;
- }
-
- /**
- * Gets the noise at a pair of internal chunk coordinates.
- *
- * @param x The internal X coordinate (0-15).
- * @param z The internal Z coordinate (0-15).
- * @return double - The interpolated noise at the coordinates.
- */
- @Override
- public double getNoise(double x, double z) {
- return interpGrid[((int) x) / 4][((int) z) / 4].bilerp((x % 4) / 4, (z % 4) / 4);
- }
-
- @Override
- public double getNoise(double x, double y, double z) {
- return getNoise(x, z);
- }
-}
diff --git a/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator3.java b/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator3.java
index 9bd1d06cf..95547e132 100644
--- a/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator3.java
+++ b/src/main/java/com/dfsek/terra/api/gaea/math/ChunkInterpolator3.java
@@ -3,19 +3,18 @@ package com.dfsek.terra.api.gaea.math;
import com.dfsek.terra.api.gaea.biome.BiomeGrid;
import com.dfsek.terra.api.gaea.biome.Generator;
import com.dfsek.terra.api.gaea.generation.GenerationPhase;
+import com.dfsek.terra.api.generic.world.World;
import net.jafama.FastMath;
-import org.bukkit.World;
/**
* Class to abstract away the 16 Interpolators needed to generate a chunk.
* Contains method to get interpolated noise at a coordinate within the chunk.
*/
-public class ChunkInterpolator3 implements ChunkInterpolator {
+public class ChunkInterpolator3 {
private final Interpolator3[][][] interpGrid = new Interpolator3[4][64][4];
private final Generator[][] gens = new Generator[7][7];
private final boolean[][] needsBiomeInterp = new boolean[5][5];
private final double[][][] noiseStorage = new double[7][7][65];
- private final FastNoiseLite noise;
private final int xOrigin;
private final int zOrigin;
private final World w;
@@ -26,17 +25,15 @@ public class ChunkInterpolator3 implements ChunkInterpolator {
* @param chunkX X coordinate of the chunk.
* @param chunkZ Z coordinate of the chunk.
* @param grid BiomeGrid to use for noise fetching.
- * @param noise FastNoiseLite instance to use.
*/
- public ChunkInterpolator3(World w, int chunkX, int chunkZ, BiomeGrid grid, FastNoiseLite noise) {
+ public ChunkInterpolator3(World w, int chunkX, int chunkZ, BiomeGrid grid) {
this.xOrigin = chunkX << 4;
this.zOrigin = chunkZ << 4;
- this.noise = noise;
this.w = w;
- for(int x = - 1; x < 6; x++) {
- for(int z = - 1; z < 6; z++) {
+ for(int x = -1; x < 6; x++) {
+ for(int z = -1; z < 6; z++) {
gens[x + 1][z + 1] = grid.getBiome(xOrigin + (x << 2), zOrigin + (z << 2), GenerationPhase.BASE).getGenerator();
}
}
@@ -87,7 +84,7 @@ public class ChunkInterpolator3 implements ChunkInterpolator {
for(byte x = - 1; x < 6; x++) {
for(byte z = - 1; z < 6; z++) {
for(int y = 0; y < 64; y++) {
- noiseStorage[x + 1][z + 1][y] = gens[x + 1][z + 1].getNoise(noise, w, (x << 2) + xOrigin, y << 2, (z << 2) + zOrigin);
+ noiseStorage[x + 1][z + 1][y] = gens[x + 1][z + 1].getNoise(w, (x << 2) + xOrigin, y << 2, (z << 2) + zOrigin);
}
}
}
@@ -114,11 +111,6 @@ public class ChunkInterpolator3 implements ChunkInterpolator {
}
}
- @Override
- public double getNoise(double x, double z) {
- return getNoise(x, 0, z);
- }
-
/**
* Gets the noise at a pair of internal chunk coordinates.
*
@@ -126,7 +118,6 @@ public class ChunkInterpolator3 implements ChunkInterpolator {
* @param z The internal Z coordinate (0-15).
* @return double - The interpolated noise at the coordinates.
*/
- @Override
public double getNoise(double x, double y, double z) {
return interpGrid[reRange(((int) x) / 4, 3)][reRange(((int) y) / 4, 63)][reRange(((int) z) / 4, 3)].trilerp((x % 4) / 4, (y % 4) / 4, (z % 4) / 4);
}
diff --git a/src/main/java/com/dfsek/terra/api/generic/BlockData.java b/src/main/java/com/dfsek/terra/api/generic/BlockData.java
deleted file mode 100644
index 64d031c61..000000000
--- a/src/main/java/com/dfsek/terra/api/generic/BlockData.java
+++ /dev/null
@@ -1,4 +0,0 @@
-package com.dfsek.terra.api.generic;
-
-public interface BlockData extends Handle {
-}
diff --git a/src/main/java/com/dfsek/terra/api/generic/generator/ChunkGenerator.java b/src/main/java/com/dfsek/terra/api/generic/generator/ChunkGenerator.java
index 8eda98c94..a7261ff68 100644
--- a/src/main/java/com/dfsek/terra/api/generic/generator/ChunkGenerator.java
+++ b/src/main/java/com/dfsek/terra/api/generic/generator/ChunkGenerator.java
@@ -1,8 +1,8 @@
package com.dfsek.terra.api.generic.generator;
-import com.dfsek.terra.api.generic.BlockData;
import com.dfsek.terra.api.generic.world.BiomeGrid;
import com.dfsek.terra.api.generic.world.World;
+import com.dfsek.terra.api.generic.world.block.BlockData;
import org.jetbrains.annotations.NotNull;
import java.util.List;
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/World.java b/src/main/java/com/dfsek/terra/api/generic/world/World.java
index fc1df9474..99b3f1242 100644
--- a/src/main/java/com/dfsek/terra/api/generic/world/World.java
+++ b/src/main/java/com/dfsek/terra/api/generic/world/World.java
@@ -4,4 +4,6 @@ import com.dfsek.terra.api.generic.Handle;
public interface World extends Handle {
long getSeed();
+
+ int getMaxHeight();
}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/WorldHandle.java b/src/main/java/com/dfsek/terra/api/generic/world/WorldHandle.java
index bf59124ff..9936e42c7 100644
--- a/src/main/java/com/dfsek/terra/api/generic/world/WorldHandle.java
+++ b/src/main/java/com/dfsek/terra/api/generic/world/WorldHandle.java
@@ -1,5 +1,6 @@
package com.dfsek.terra.api.generic.world;
+import com.dfsek.terra.api.generic.world.block.MaterialData;
import org.bukkit.Material;
import org.bukkit.block.Block;
import org.bukkit.block.data.BlockData;
@@ -14,5 +15,7 @@ public interface WorldHandle {
Material getType(Block block);
- com.dfsek.terra.api.generic.BlockData createBlockData(String data);
+ com.dfsek.terra.api.generic.world.block.BlockData createBlockData(String data);
+
+ MaterialData createMaterialData(String data);
}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/Block.java b/src/main/java/com/dfsek/terra/api/generic/world/block/Block.java
similarity index 66%
rename from src/main/java/com/dfsek/terra/api/generic/world/Block.java
rename to src/main/java/com/dfsek/terra/api/generic/world/block/Block.java
index c78a707e0..691c1080f 100644
--- a/src/main/java/com/dfsek/terra/api/generic/world/Block.java
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/Block.java
@@ -1,6 +1,5 @@
-package com.dfsek.terra.api.generic.world;
+package com.dfsek.terra.api.generic.world.block;
-import com.dfsek.terra.api.generic.BlockData;
import com.dfsek.terra.api.generic.Handle;
public interface Block extends Handle {
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/BlockData.java b/src/main/java/com/dfsek/terra/api/generic/world/block/BlockData.java
new file mode 100644
index 000000000..50200660d
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/BlockData.java
@@ -0,0 +1,9 @@
+package com.dfsek.terra.api.generic.world.block;
+
+import com.dfsek.terra.api.generic.Handle;
+
+public interface BlockData extends Handle, Cloneable {
+ MaterialData getMaterial();
+
+ boolean matches(MaterialData materialData);
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/BlockFace.java b/src/main/java/com/dfsek/terra/api/generic/world/block/BlockFace.java
new file mode 100644
index 000000000..6a16eea70
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/BlockFace.java
@@ -0,0 +1,148 @@
+package com.dfsek.terra.api.generic.world.block;
+
+import com.dfsek.terra.api.generic.world.vector.Vector3;
+import org.jetbrains.annotations.NotNull;
+
+public enum BlockFace {
+ NORTH(0, 0, -1),
+ EAST(1, 0, 0),
+ SOUTH(0, 0, 1),
+ WEST(-1, 0, 0),
+ UP(0, 1, 0),
+ DOWN(0, -1, 0),
+ NORTH_EAST(NORTH, EAST),
+ NORTH_WEST(NORTH, WEST),
+ SOUTH_EAST(SOUTH, EAST),
+ SOUTH_WEST(SOUTH, WEST),
+ WEST_NORTH_WEST(WEST, NORTH_WEST),
+ NORTH_NORTH_WEST(NORTH, NORTH_WEST),
+ NORTH_NORTH_EAST(NORTH, NORTH_EAST),
+ EAST_NORTH_EAST(EAST, NORTH_EAST),
+ EAST_SOUTH_EAST(EAST, SOUTH_EAST),
+ SOUTH_SOUTH_EAST(SOUTH, SOUTH_EAST),
+ SOUTH_SOUTH_WEST(SOUTH, SOUTH_WEST),
+ WEST_SOUTH_WEST(WEST, SOUTH_WEST),
+ SELF(0, 0, 0);
+
+ private final int modX;
+ private final int modY;
+ private final int modZ;
+
+ BlockFace(final int modX, final int modY, final int modZ) {
+ this.modX = modX;
+ this.modY = modY;
+ this.modZ = modZ;
+ }
+
+ BlockFace(final BlockFace face1, final BlockFace face2) {
+ this.modX = face1.getModX() + face2.getModX();
+ this.modY = face1.getModY() + face2.getModY();
+ this.modZ = face1.getModZ() + face2.getModZ();
+ }
+
+ /**
+ * Get the amount of X-coordinates to modify to get the represented block
+ *
+ * @return Amount of X-coordinates to modify
+ */
+ public int getModX() {
+ return modX;
+ }
+
+ /**
+ * Get the amount of Y-coordinates to modify to get the represented block
+ *
+ * @return Amount of Y-coordinates to modify
+ */
+ public int getModY() {
+ return modY;
+ }
+
+ /**
+ * Get the amount of Z-coordinates to modify to get the represented block
+ *
+ * @return Amount of Z-coordinates to modify
+ */
+ public int getModZ() {
+ return modZ;
+ }
+
+ /**
+ * Gets the normal vector corresponding to this block face.
+ *
+ * @return the normal vector
+ */
+ @NotNull
+ public Vector3 getDirection() {
+ Vector3 direction = new Vector3(modX, modY, modZ);
+ if(modX != 0 || modY != 0 || modZ != 0) {
+ direction.normalize();
+ }
+ return direction;
+ }
+
+ @NotNull
+ public org.bukkit.block.BlockFace getOppositeFace() {
+ switch(this) {
+ case NORTH:
+ return org.bukkit.block.BlockFace.SOUTH;
+
+ case SOUTH:
+ return org.bukkit.block.BlockFace.NORTH;
+
+ case EAST:
+ return org.bukkit.block.BlockFace.WEST;
+
+ case WEST:
+ return org.bukkit.block.BlockFace.EAST;
+
+ case UP:
+ return org.bukkit.block.BlockFace.DOWN;
+
+ case DOWN:
+ return org.bukkit.block.BlockFace.UP;
+
+ case NORTH_EAST:
+ return org.bukkit.block.BlockFace.SOUTH_WEST;
+
+ case NORTH_WEST:
+ return org.bukkit.block.BlockFace.SOUTH_EAST;
+
+ case SOUTH_EAST:
+ return org.bukkit.block.BlockFace.NORTH_WEST;
+
+ case SOUTH_WEST:
+ return org.bukkit.block.BlockFace.NORTH_EAST;
+
+ case WEST_NORTH_WEST:
+ return org.bukkit.block.BlockFace.EAST_SOUTH_EAST;
+
+ case NORTH_NORTH_WEST:
+ return org.bukkit.block.BlockFace.SOUTH_SOUTH_EAST;
+
+ case NORTH_NORTH_EAST:
+ return org.bukkit.block.BlockFace.SOUTH_SOUTH_WEST;
+
+ case EAST_NORTH_EAST:
+ return org.bukkit.block.BlockFace.WEST_SOUTH_WEST;
+
+ case EAST_SOUTH_EAST:
+ return org.bukkit.block.BlockFace.WEST_NORTH_WEST;
+
+ case SOUTH_SOUTH_EAST:
+ return org.bukkit.block.BlockFace.NORTH_NORTH_WEST;
+
+ case SOUTH_SOUTH_WEST:
+ return org.bukkit.block.BlockFace.NORTH_NORTH_EAST;
+
+ case WEST_SOUTH_WEST:
+ return org.bukkit.block.BlockFace.EAST_NORTH_EAST;
+
+ case SELF:
+ return org.bukkit.block.BlockFace.SELF;
+ }
+
+ return org.bukkit.block.BlockFace.SELF;
+ }
+}
+
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/MaterialData.java b/src/main/java/com/dfsek/terra/api/generic/world/block/MaterialData.java
new file mode 100644
index 000000000..d632c52d1
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/MaterialData.java
@@ -0,0 +1,10 @@
+package com.dfsek.terra.api.generic.world.block;
+
+import com.dfsek.terra.api.generic.Handle;
+
+public interface MaterialData extends Handle {
+ boolean matches(MaterialData other);
+
+ boolean matches(BlockData other);
+
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/data/Bisected.java b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Bisected.java
new file mode 100644
index 000000000..3c897f048
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Bisected.java
@@ -0,0 +1,20 @@
+package com.dfsek.terra.api.generic.world.block.data;
+
+import com.dfsek.terra.api.generic.world.block.BlockData;
+
+public interface Bisected extends BlockData {
+ Half getHalf();
+
+ void setHalf(Half half);
+
+ enum Half {
+ /**
+ * The top half of the block, normally with the higher y coordinate.
+ */
+ TOP,
+ /**
+ * The bottom half of the block, normally with the lower y coordinate.
+ */
+ BOTTOM
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/data/Directional.java b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Directional.java
new file mode 100644
index 000000000..d7f5979a1
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Directional.java
@@ -0,0 +1,10 @@
+package com.dfsek.terra.api.generic.world.block.data;
+
+import com.dfsek.terra.api.generic.world.block.BlockData;
+import com.dfsek.terra.api.generic.world.block.BlockFace;
+
+public interface Directional extends BlockData {
+ BlockFace getFacing();
+
+ void setFacing(BlockFace facing);
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/data/Slab.java b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Slab.java
new file mode 100644
index 000000000..3587f957f
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Slab.java
@@ -0,0 +1,4 @@
+package com.dfsek.terra.api.generic.world.block.data;
+
+public interface Slab extends Bisected, Waterlogged {
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/data/Stairs.java b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Stairs.java
new file mode 100644
index 000000000..5ac6bfcfd
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Stairs.java
@@ -0,0 +1,30 @@
+package com.dfsek.terra.api.generic.world.block.data;
+
+public interface Stairs extends Waterlogged, Directional, Bisected {
+ Shape getShape();
+
+ void setShape(Shape shape);
+
+ enum Shape {
+ /**
+ * Regular stair block.
+ */
+ STRAIGHT,
+ /**
+ * Inner corner stair block with higher left side.
+ */
+ INNER_LEFT,
+ /**
+ * Inner corner stair block with higher right side.
+ */
+ INNER_RIGHT,
+ /**
+ * Outer corner stair block with higher left side.
+ */
+ OUTER_LEFT,
+ /**
+ * Outer corner stair block with higher right side.
+ */
+ OUTER_RIGHT
+ }
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/block/data/Waterlogged.java b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Waterlogged.java
new file mode 100644
index 000000000..da3caacf7
--- /dev/null
+++ b/src/main/java/com/dfsek/terra/api/generic/world/block/data/Waterlogged.java
@@ -0,0 +1,9 @@
+package com.dfsek.terra.api.generic.world.block.data;
+
+import com.dfsek.terra.api.generic.world.block.BlockData;
+
+public interface Waterlogged extends BlockData {
+ boolean isWaterlogged();
+
+ void setWaterlogged(boolean waterlogged);
+}
diff --git a/src/main/java/com/dfsek/terra/api/generic/world/vector/Vector3.java b/src/main/java/com/dfsek/terra/api/generic/world/vector/Vector3.java
index 48e38ebec..7a156466c 100644
--- a/src/main/java/com/dfsek/terra/api/generic/world/vector/Vector3.java
+++ b/src/main/java/com/dfsek/terra/api/generic/world/vector/Vector3.java
@@ -53,7 +53,7 @@ public class Vector3 implements Cloneable {
return FastMath.floorToInt(z);
}
- public Vector3 multiply(int m) {
+ public Vector3 multiply(double m) {
x *= m;
y *= m;
z *= m;
@@ -101,4 +101,7 @@ public class Vector3 implements Cloneable {
return new Location(world, this.clone());
}
+ public Vector3 normalize() {
+ return this.multiply(1D / this.length());
+ }
}
diff --git a/src/main/java/com/dfsek/terra/command/FixChunkCommand.java b/src/main/java/com/dfsek/terra/command/FixChunkCommand.java
index 77994fdfc..7efd71d29 100644
--- a/src/main/java/com/dfsek/terra/command/FixChunkCommand.java
+++ b/src/main/java/com/dfsek/terra/command/FixChunkCommand.java
@@ -1,7 +1,6 @@
package com.dfsek.terra.command;
import com.dfsek.terra.api.gaea.command.WorldCommand;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import org.bukkit.World;
import org.bukkit.command.Command;
import org.bukkit.command.CommandSender;
diff --git a/src/main/java/com/dfsek/terra/command/SaveDataCommand.java b/src/main/java/com/dfsek/terra/command/SaveDataCommand.java
index 11c302eb9..cbd22670f 100644
--- a/src/main/java/com/dfsek/terra/command/SaveDataCommand.java
+++ b/src/main/java/com/dfsek/terra/command/SaveDataCommand.java
@@ -3,7 +3,6 @@ package com.dfsek.terra.command;
import com.dfsek.terra.api.gaea.command.Command;
import com.dfsek.terra.api.gaea.command.WorldCommand;
import com.dfsek.terra.config.lang.LangUtil;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import org.bukkit.World;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
diff --git a/src/main/java/com/dfsek/terra/command/biome/BiomeInfoCommand.java b/src/main/java/com/dfsek/terra/command/biome/BiomeInfoCommand.java
index 64581efb6..e1b6f0c32 100644
--- a/src/main/java/com/dfsek/terra/command/biome/BiomeInfoCommand.java
+++ b/src/main/java/com/dfsek/terra/command/biome/BiomeInfoCommand.java
@@ -7,7 +7,6 @@ import com.dfsek.terra.carving.UserDefinedCarver;
import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.lang.LangUtil;
import com.dfsek.terra.config.templates.BiomeTemplate;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import com.dfsek.terra.generation.items.TerraStructure;
import org.bukkit.World;
import org.bukkit.command.Command;
diff --git a/src/main/java/com/dfsek/terra/command/biome/BiomeLocateCommand.java b/src/main/java/com/dfsek/terra/command/biome/BiomeLocateCommand.java
index 109eb08b6..c5252d4e5 100644
--- a/src/main/java/com/dfsek/terra/command/biome/BiomeLocateCommand.java
+++ b/src/main/java/com/dfsek/terra/command/biome/BiomeLocateCommand.java
@@ -5,7 +5,6 @@ import com.dfsek.terra.api.gaea.command.WorldCommand;
import com.dfsek.terra.async.AsyncBiomeFinder;
import com.dfsek.terra.biome.UserDefinedBiome;
import com.dfsek.terra.config.lang.LangUtil;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.World;
diff --git a/src/main/java/com/dfsek/terra/command/structure/LocateCommand.java b/src/main/java/com/dfsek/terra/command/structure/LocateCommand.java
index 93f7f0e54..6624ce2e1 100644
--- a/src/main/java/com/dfsek/terra/command/structure/LocateCommand.java
+++ b/src/main/java/com/dfsek/terra/command/structure/LocateCommand.java
@@ -4,7 +4,6 @@ import com.dfsek.terra.Terra;
import com.dfsek.terra.api.gaea.command.WorldCommand;
import com.dfsek.terra.async.AsyncStructureFinder;
import com.dfsek.terra.config.lang.LangUtil;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import com.dfsek.terra.generation.items.TerraStructure;
import org.bukkit.Bukkit;
import org.bukkit.Location;
diff --git a/src/main/java/com/dfsek/terra/debug/gui/DebugFrame.java b/src/main/java/com/dfsek/terra/debug/gui/DebugFrame.java
index 3fd28f5f4..ed9012618 100644
--- a/src/main/java/com/dfsek/terra/debug/gui/DebugFrame.java
+++ b/src/main/java/com/dfsek/terra/debug/gui/DebugFrame.java
@@ -3,7 +3,6 @@ package com.dfsek.terra.debug.gui;
import com.dfsek.terra.Terra;
import com.dfsek.terra.api.gaea.generation.GenerationPhase;
import com.dfsek.terra.biome.UserDefinedBiome;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import com.dfsek.terra.image.ImageLoader;
import net.jafama.FastMath;
import org.bukkit.Bukkit;
diff --git a/src/main/java/com/dfsek/terra/generation/ChunkGeneratorImpl.java b/src/main/java/com/dfsek/terra/generation/ChunkGeneratorImpl.java
index e12f50c5c..e3f23d7b7 100644
--- a/src/main/java/com/dfsek/terra/generation/ChunkGeneratorImpl.java
+++ b/src/main/java/com/dfsek/terra/generation/ChunkGeneratorImpl.java
@@ -1,47 +1,203 @@
package com.dfsek.terra.generation;
+import com.dfsek.terra.Terra;
+import com.dfsek.terra.TerraWorld;
+import com.dfsek.terra.api.gaea.biome.Biome;
+import com.dfsek.terra.api.gaea.generation.GenerationPhase;
+import com.dfsek.terra.api.gaea.generation.GenerationPopulator;
+import com.dfsek.terra.api.gaea.math.ChunkInterpolator3;
+import com.dfsek.terra.api.gaea.population.PopulationManager;
+import com.dfsek.terra.api.gaea.profiler.ProfileFuture;
+import com.dfsek.terra.api.gaea.profiler.WorldProfiler;
+import com.dfsek.terra.api.gaea.world.palette.Palette;
import com.dfsek.terra.api.generic.generator.BlockPopulator;
import com.dfsek.terra.api.generic.generator.ChunkGenerator;
import com.dfsek.terra.api.generic.world.BiomeGrid;
import com.dfsek.terra.api.generic.world.World;
+import com.dfsek.terra.api.generic.world.block.BlockData;
+import com.dfsek.terra.api.generic.world.vector.Vector3;
+import com.dfsek.terra.biome.UserDefinedBiome;
+import com.dfsek.terra.config.base.ConfigPack;
+import com.dfsek.terra.config.lang.LangUtil;
+import com.dfsek.terra.config.templates.BiomeTemplate;
+import com.dfsek.terra.debug.Debug;
+import com.dfsek.terra.population.FloraPopulator;
+import com.dfsek.terra.population.OrePopulator;
+import com.dfsek.terra.population.TreePopulator;
+import com.dfsek.terra.util.PaletteUtil;
+import com.dfsek.terra.util.SlabUtil;
import org.jetbrains.annotations.NotNull;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.util.Collections;
+import java.util.HashMap;
import java.util.List;
+import java.util.Map;
import java.util.Random;
+import java.util.logging.Level;
public class ChunkGeneratorImpl implements ChunkGenerator {
+ private static final Map popMap = new HashMap<>();
+ private final PopulationManager popMan;
+ private final ConfigPack configPack;
+ private final Terra main;
+ private boolean needsLoad = true;
+
+ public ChunkGeneratorImpl(ConfigPack c, Terra main) {
+ popMan = new PopulationManager(main);
+ this.configPack = c;
+ this.main = main;
+ popMan.attach(new OrePopulator(main));
+ popMan.attach(new TreePopulator(main));
+ popMan.attach(new FloraPopulator(main));
+ }
+
+ public static synchronized void saveAll() {
+ for(Map.Entry e : popMap.entrySet()) {
+ try {
+ e.getValue().saveBlocks(e.getKey());
+ Debug.info("Saved data for world " + e.getKey().getName());
+ } catch(IOException ioException) {
+ ioException.printStackTrace();
+ }
+ }
+ }
+
+ public static synchronized void fixChunk(Chunk c) {
+ if(!(c.getWorld().getGenerator() instanceof TerraChunkGenerator)) throw new IllegalArgumentException();
+ popMap.get(c.getWorld()).checkNeighbors(c.getX(), c.getZ(), c.getWorld());
+ }
+
@Override
public boolean isParallelCapable() {
- return false;
+ return true;
}
@Override
public boolean shouldGenerateCaves() {
- return false;
+ return configPack.getTemplate().vanillaCaves();
}
@Override
public boolean shouldGenerateDecorations() {
- return false;
+ return configPack.getTemplate().vanillaDecorations();
}
@Override
public boolean shouldGenerateMobs() {
- return false;
+ return configPack.getTemplate().vanillaMobs();
}
@Override
public boolean shouldGenerateStructures() {
- return false;
+ return configPack.getTemplate().vanillaStructures();
}
@Override
- public void generateChunkData(@NotNull World world, @NotNull Random random, int x, int z, @NotNull BiomeGrid biome, ChunkData data) {
+ public void generateChunkData(@NotNull World world, @NotNull Random random, int x, int z, @NotNull BiomeGrid biome, ChunkData chunk) {
+ TerraWorld tw = main.getWorld(world);
+ try(ProfileFuture ignore = tw.getProfiler().measure("TotalChunkGenTime")) {
+ ChunkInterpolator3 interp;
+ try(ProfileFuture ignored = tw.getProfiler().measure("ChunkBaseGenTime")) {
+ interp = new ChunkInterpolator3(world, x, z, tw.getGrid());
+ if(needsLoad) load(world); // Load population data for world.
+ if(!tw.isSafe()) return;
+ int xOrig = (x << 4);
+ int zOrig = (z << 4);
+ com.dfsek.terra.api.gaea.biome.BiomeGrid grid = tw.getGrid();
+
+ ElevationInterpolator elevationInterpolator;
+ try(ProfileFuture ignored1 = tw.getProfiler().measure("ElevationTime")) {
+ elevationInterpolator = new ElevationInterpolator(x, z, tw.getGrid());
+ }
+
+ Sampler sampler = new Sampler(interp, elevationInterpolator);
+
+ for(byte x = 0; x < 16; x++) {
+ for(byte z = 0; z < 16; z++) {
+ int paletteLevel = 0;
+
+ int cx = xOrig + x;
+ int cz = zOrig + z;
+
+ Biome b = grid.getBiome(xOrig + x, zOrig + z, GenerationPhase.PALETTE_APPLY);
+ BiomeTemplate c = ((UserDefinedBiome) b).getConfig();
+
+ int sea = c.getSeaLevel();
+ Palette seaPalette = c.getOceanPalette();
+
+ boolean justSet = false;
+ BlockData data = null;
+ for(int y = world.getMaxHeight() - 1; y >= 0; y--) {
+ if(sampler.sample(x, y, z) > 0) {
+ justSet = true;
+ data = PaletteUtil.getPalette(x, y, z, c, sampler).get(paletteLevel, cx, cz);
+ chunk.setBlock(x, y, z, data);
+ if(paletteLevel == 0 && c.doSlabs() && y < 255) {
+ SlabUtil.prepareBlockPartFloor(data, chunk.getBlockData(x, y + 1, z), chunk, new Vector3(x, y + 1, z), c.getSlabPalettes(),
+ c.getStairPalettes(), c.getSlabThreshold(), sampler);
+ }
+ paletteLevel++;
+ } else if(y <= sea) {
+ chunk.setBlock(x, y, z, seaPalette.get(sea - y, x + xOrig, z + zOrig));
+ if(justSet && c.doSlabs()) {
+ SlabUtil.prepareBlockPartCeiling(data, chunk.getBlockData(x, y, z), chunk, new Vector3(x, y, z), c.getSlabPalettes(), c.getStairPalettes(), c.getSlabThreshold(), sampler);
+ }
+ justSet = false;
+ paletteLevel = 0;
+ } else {
+ if(justSet && c.doSlabs()) {
+ SlabUtil.prepareBlockPartCeiling(data, chunk.getBlockData(x, y, z), chunk, new Vector3(x, y, z), c.getSlabPalettes(), c.getStairPalettes(), c.getSlabThreshold(), sampler);
+ }
+ justSet = false;
+ paletteLevel = 0;
+ }
+ }
+ }
+ }
+ }
+ try(ProfileFuture ignored = measure("BiomeApplyTime")) {
+ com.dfsek.terra.api.gaea.biome.BiomeGrid grid = getBiomeGrid(world);
+ int xOrig = (chunkX << 4);
+ int zOrig = (chunkZ << 4);
+ for(byte x = 0; x < 4; x++) {
+ for(byte z = 0; z < 4; z++) {
+ int cx = xOrig + (x << 2);
+ int cz = zOrig + (z << 2);
+ Biome b = grid.getBiome(cx, cz, GenerationPhase.PALETTE_APPLY);
+ biome.setBiome(x << 2, z << 2, b.getVanillaBiome());
+ }
+ }
+ }
+ for(GenerationPopulator g : getGenerationPopulators(world)) {
+ g.populate(world, chunk, random, chunkX, chunkZ, interp);
+ }
+ }
+
+
+ return chunk;
}
@Override
public List getDefaultPopulators(World world) {
- return null;
+ return Collections.emptyList();
+ }
+
+ public void attachProfiler(WorldProfiler p) {
+ popMan.attachProfiler(p);
+ }
+
+ private void load(org.bukkit.World w) {
+ try {
+ popMan.loadBlocks(w);
+ } catch(FileNotFoundException e) {
+ LangUtil.log("warning.no-population", Level.WARNING);
+ } catch(IOException | ClassNotFoundException e) {
+ e.printStackTrace();
+ }
+ popMap.put(w, popMan);
+ needsLoad = false;
}
}
diff --git a/src/main/java/com/dfsek/terra/generation/Sampler.java b/src/main/java/com/dfsek/terra/generation/Sampler.java
index 15b0079ad..3189e2272 100644
--- a/src/main/java/com/dfsek/terra/generation/Sampler.java
+++ b/src/main/java/com/dfsek/terra/generation/Sampler.java
@@ -1,13 +1,13 @@
package com.dfsek.terra.generation;
-import com.dfsek.terra.api.gaea.math.ChunkInterpolator;
+import com.dfsek.terra.api.gaea.math.ChunkInterpolator3;
import net.jafama.FastMath;
public class Sampler {
- private final ChunkInterpolator interpolator;
+ private final ChunkInterpolator3 interpolator;
private final ElevationInterpolator elevationInterpolator;
- public Sampler(ChunkInterpolator interpolator, ElevationInterpolator elevationInterpolator) {
+ public Sampler(ChunkInterpolator3 interpolator, ElevationInterpolator elevationInterpolator) {
this.interpolator = interpolator;
this.elevationInterpolator = elevationInterpolator;
}
diff --git a/src/main/java/com/dfsek/terra/generation/TerraChunkGenerator.java b/src/main/java/com/dfsek/terra/generation/TerraChunkGenerator.java
deleted file mode 100644
index 909673760..000000000
--- a/src/main/java/com/dfsek/terra/generation/TerraChunkGenerator.java
+++ /dev/null
@@ -1,212 +0,0 @@
-package com.dfsek.terra.generation;
-
-import com.dfsek.terra.Terra;
-import com.dfsek.terra.TerraWorld;
-import com.dfsek.terra.api.gaea.biome.Biome;
-import com.dfsek.terra.api.gaea.generation.GaeaChunkGenerator;
-import com.dfsek.terra.api.gaea.generation.GenerationPhase;
-import com.dfsek.terra.api.gaea.generation.GenerationPopulator;
-import com.dfsek.terra.api.gaea.math.ChunkInterpolator;
-import com.dfsek.terra.api.gaea.population.PopulationManager;
-import com.dfsek.terra.api.gaea.profiler.ProfileFuture;
-import com.dfsek.terra.api.gaea.profiler.WorldProfiler;
-import com.dfsek.terra.api.gaea.world.palette.Palette;
-import com.dfsek.terra.biome.UserDefinedBiome;
-import com.dfsek.terra.config.base.ConfigPack;
-import com.dfsek.terra.config.lang.LangUtil;
-import com.dfsek.terra.config.templates.BiomeTemplate;
-import com.dfsek.terra.debug.Debug;
-import com.dfsek.terra.population.CavePopulator;
-import com.dfsek.terra.population.FloraPopulator;
-import com.dfsek.terra.population.OrePopulator;
-import com.dfsek.terra.population.StructurePopulator;
-import com.dfsek.terra.population.TreePopulator;
-import com.dfsek.terra.util.PaletteUtil;
-import com.dfsek.terra.util.SlabUtil;
-import org.bukkit.Chunk;
-import org.bukkit.World;
-import org.bukkit.block.data.BlockData;
-import org.bukkit.generator.BlockPopulator;
-import org.bukkit.util.Vector;
-import org.jetbrains.annotations.NotNull;
-
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Random;
-import java.util.logging.Level;
-
-
-public class TerraChunkGenerator extends GaeaChunkGenerator {
- private static final Map popMap = new HashMap<>();
- private final PopulationManager popMan;
- private final ConfigPack configPack;
- private boolean needsLoad = true;
- private final Terra main;
-
- public ConfigPack getConfigPack() {
- return configPack;
- }
-
-
- public TerraChunkGenerator(ConfigPack c, Terra main) {
- super(ChunkInterpolator.InterpolationType.TRILINEAR);
- popMan = new PopulationManager(main);
- this.configPack = c;
- this.main = main;
- popMan.attach(new OrePopulator(main));
- popMan.attach(new TreePopulator(main));
- popMan.attach(new FloraPopulator(main));
- }
-
- public static synchronized void saveAll() {
- for(Map.Entry e : popMap.entrySet()) {
- try {
- e.getValue().saveBlocks(e.getKey());
- Debug.info("Saved data for world " + e.getKey().getName());
- } catch(IOException ioException) {
- ioException.printStackTrace();
- }
- }
- }
-
- public static synchronized void fixChunk(Chunk c) {
- if(!(c.getWorld().getGenerator() instanceof TerraChunkGenerator)) throw new IllegalArgumentException();
- popMap.get(c.getWorld()).checkNeighbors(c.getX(), c.getZ(), c.getWorld());
- }
-
- @Override
- public void attachProfiler(WorldProfiler p) {
- super.attachProfiler(p);
- popMan.attachProfiler(p);
- }
-
- @Override
- @SuppressWarnings("try")
- public ChunkData generateBase(@NotNull World world, @NotNull Random random, int chunkX, int chunkZ, ChunkInterpolator interpolator) {
- if(needsLoad) load(world); // Load population data for world.
- ChunkData chunk = createChunkData(world);
- TerraWorld tw = main.getWorld(world);
- if(!tw.isSafe()) return chunk;
- int xOrig = (chunkX << 4);
- int zOrig = (chunkZ << 4);
- com.dfsek.terra.api.gaea.biome.BiomeGrid grid = getBiomeGrid(world);
-
- ElevationInterpolator elevationInterpolator;
- try(ProfileFuture ignore = tw.getProfiler().measure("ElevationTime")) {
- elevationInterpolator = new ElevationInterpolator(chunkX, chunkZ, tw.getGrid());
- }
-
- Sampler sampler = new Sampler(interpolator, elevationInterpolator);
-
- for(byte x = 0; x < 16; x++) {
- for(byte z = 0; z < 16; z++) {
- int paletteLevel = 0;
-
- int cx = xOrig + x;
- int cz = zOrig + z;
-
- Biome b = grid.getBiome(xOrig + x, zOrig + z, GenerationPhase.PALETTE_APPLY);
- BiomeTemplate c = ((UserDefinedBiome) b).getConfig();
-
- int sea = c.getSeaLevel();
- Palette seaPalette = c.getOceanPalette();
-
- boolean justSet = false;
- BlockData data = null;
- for(int y = world.getMaxHeight() - 1; y >= 0; y--) {
- if(sampler.sample(x, y, z) > 0) {
- justSet = true;
- data = PaletteUtil.getPalette(x, y, z, c, sampler).get(paletteLevel, cx, cz);
- chunk.setBlock(x, y, z, data);
- if(paletteLevel == 0 && c.doSlabs() && y < 255) {
- SlabUtil.prepareBlockPartFloor(data, chunk.getBlockData(x, y + 1, z), chunk, new Vector(x, y + 1, z), c.getSlabPalettes(),
- c.getStairPalettes(), c.getSlabThreshold(), sampler);
- }
- paletteLevel++;
- } else if(y <= sea) {
- chunk.setBlock(x, y, z, seaPalette.get(sea - y, x + xOrig, z + zOrig));
- if(justSet && c.doSlabs()) {
- SlabUtil.prepareBlockPartCeiling(data, chunk.getBlockData(x, y, z), chunk, new Vector(x, y, z), c.getSlabPalettes(), c.getStairPalettes(), c.getSlabThreshold(), sampler);
- }
- justSet = false;
- paletteLevel = 0;
- } else {
- if(justSet && c.doSlabs()) {
- SlabUtil.prepareBlockPartCeiling(data, chunk.getBlockData(x, y, z), chunk, new Vector(x, y, z), c.getSlabPalettes(), c.getStairPalettes(), c.getSlabThreshold(), sampler);
- }
- justSet = false;
- paletteLevel = 0;
- }
- }
- }
- }
- return chunk;
- }
-
- private void load(World w) {
- try {
- popMan.loadBlocks(w);
- } catch(FileNotFoundException e) {
- LangUtil.log("warning.no-population", Level.WARNING);
- } catch(IOException | ClassNotFoundException e) {
- e.printStackTrace();
- }
- popMap.put(w, popMan);
- needsLoad = false;
- }
-
- @Override
- public int getNoiseOctaves(World world) {
- return 1;
- }
-
- @Override
- public double getNoiseFrequency(World world) {
- return 0.02;
- }
-
- @Override
- public List getGenerationPopulators(World world) {
- return Collections.emptyList();
- }
-
- @Override
- public com.dfsek.terra.api.gaea.biome.BiomeGrid getBiomeGrid(World world) {
- return main.getWorld(world).getGrid();
- }
-
- @Override
- public @NotNull List getDefaultPopulators(@NotNull World world) {
- return Arrays.asList(new CavePopulator(main), new StructurePopulator(main), popMan);
- }
-
- @Override
- public boolean isParallelCapable() {
- return true;
- }
-
- @Override
- public boolean shouldGenerateCaves() {
- return configPack.getTemplate().vanillaCaves();
- }
-
- @Override
- public boolean shouldGenerateDecorations() {
- return configPack.getTemplate().vanillaDecorations();
- }
-
- @Override
- public boolean shouldGenerateMobs() {
- return configPack.getTemplate().vanillaMobs();
- }
-
- @Override
- public boolean shouldGenerateStructures() {
- return configPack.getTemplate().vanillaStructures();
- }
-}
diff --git a/src/main/java/com/dfsek/terra/structure/spawn/Requirement.java b/src/main/java/com/dfsek/terra/structure/spawn/Requirement.java
index 55df1f574..dd23438f2 100644
--- a/src/main/java/com/dfsek/terra/structure/spawn/Requirement.java
+++ b/src/main/java/com/dfsek/terra/structure/spawn/Requirement.java
@@ -2,7 +2,6 @@ package com.dfsek.terra.structure.spawn;
import com.dfsek.terra.Terra;
import com.dfsek.terra.api.gaea.math.FastNoiseLite;
-import com.dfsek.terra.generation.TerraChunkGenerator;
import org.bukkit.World;
import java.util.Objects;
diff --git a/src/main/java/com/dfsek/terra/util/SlabUtil.java b/src/main/java/com/dfsek/terra/util/SlabUtil.java
index 74f08eca2..b9ca5f9ef 100644
--- a/src/main/java/com/dfsek/terra/util/SlabUtil.java
+++ b/src/main/java/com/dfsek/terra/util/SlabUtil.java
@@ -1,22 +1,22 @@
package com.dfsek.terra.util;
import com.dfsek.terra.api.gaea.world.palette.Palette;
+import com.dfsek.terra.api.generic.generator.ChunkGenerator;
+import com.dfsek.terra.api.generic.world.block.BlockData;
+import com.dfsek.terra.api.generic.world.block.MaterialData;
+import com.dfsek.terra.api.generic.world.block.data.Bisected;
+import com.dfsek.terra.api.generic.world.block.data.Stairs;
+import com.dfsek.terra.api.generic.world.block.data.Waterlogged;
+import com.dfsek.terra.api.generic.world.vector.Vector3;
import com.dfsek.terra.generation.Sampler;
-import org.bukkit.Material;
import org.bukkit.block.BlockFace;
-import org.bukkit.block.data.Bisected;
-import org.bukkit.block.data.BlockData;
-import org.bukkit.block.data.Waterlogged;
import org.bukkit.block.data.type.Slab;
-import org.bukkit.block.data.type.Stairs;
-import org.bukkit.generator.ChunkGenerator;
-import org.bukkit.util.Vector;
import java.util.Map;
public final class SlabUtil {
- public static void prepareBlockPartFloor(BlockData down, BlockData orig, ChunkGenerator.ChunkData chunk, Vector block, Map> slabs,
- Map> stairs, double thresh, Sampler sampler) {
+ public static void prepareBlockPartFloor(BlockData down, BlockData orig, ChunkGenerator.ChunkData chunk, Vector3 block, Map> slabs,
+ Map> stairs, double thresh, Sampler sampler) {
if(sampler.sample(block.getBlockX(), block.getBlockY() - 0.4, block.getBlockZ()) > thresh) {
if(stairs != null) {
Palette stairPalette = stairs.get(down.getMaterial());
@@ -34,8 +34,8 @@ public final class SlabUtil {
}
}
- public static void prepareBlockPartCeiling(BlockData up, BlockData orig, ChunkGenerator.ChunkData chunk, Vector block, Map> slabs,
- Map> stairs, double thresh, Sampler sampler) {
+ public static void prepareBlockPartCeiling(BlockData up, BlockData orig, ChunkGenerator.ChunkData chunk, Vector3 block, Map> slabs,
+ Map> stairs, double thresh, Sampler sampler) {
if(sampler.sample(block.getBlockX(), block.getBlockY() + 0.4, block.getBlockZ()) > thresh) {
if(stairs != null) {
Palette stairPalette = stairs.get(up.getMaterial());
@@ -56,7 +56,7 @@ public final class SlabUtil {
}
}
- private static boolean placeStair(BlockData orig, ChunkGenerator.ChunkData chunk, Vector block, double thresh, Sampler sampler, Stairs stairNew) {
+ private static boolean placeStair(BlockData orig, ChunkGenerator.ChunkData chunk, Vector3 block, double thresh, Sampler sampler, Stairs stairNew) {
if(sampler.sample(block.getBlockX() - 0.55, block.getBlockY(), block.getBlockZ()) > thresh) {
stairNew.setFacing(BlockFace.WEST);
} else if(sampler.sample(block.getBlockX(), block.getBlockY(), block.getBlockZ() - 0.55) > thresh) {