Look ma, no Bukkit API in the core package

This commit is contained in:
dfsek
2020-12-11 17:30:17 -07:00
parent 7ee1d2c391
commit 5bf699cba9
345 changed files with 1352 additions and 2642 deletions
@@ -0,0 +1,79 @@
package com.dfsek.terra.biome;
import com.dfsek.terra.api.gaea.biome.BiomeGrid;
import com.dfsek.terra.api.gaea.biome.NormalizationUtil;
import com.dfsek.terra.api.gaea.math.FastNoiseLite;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.base.ConfigPackTemplate;
import com.dfsek.terra.image.ImageLoader;
import org.jetbrains.annotations.Nullable;
import java.util.Objects;
/**
* Holds 1D array of BiomeGrids.
*/
public class BiomeZone {
private final BiomeGrid[] grids;
private final FastNoiseLite noise;
@Nullable
private final ImageLoader imageLoader;
private final boolean useImage;
private final ImageLoader.Channel channel;
public BiomeZone(World w, ConfigPack wc, BiomeGrid[] grids) {
this.noise = new FastNoiseLite((int) w.getSeed() + 2);
this.noise.setNoiseType(FastNoiseLite.NoiseType.OpenSimplex2);
this.noise.setFractalType(FastNoiseLite.FractalType.FBm);
this.noise.setFractalOctaves(4);
ConfigPackTemplate t = wc.getTemplate();
this.noise.setFrequency(1D / t.getZoneFreq());
this.grids = grids;
imageLoader = t.getImageLoader();
useImage = t.isFromImage();
channel = t.getZoneChannel();
}
/**
* Get BiomeGrid at location
*
* @param x X coordinate
* @param z Z coordinate
* @return BiomeGrid at coordinates.
*/
public BiomeGrid getGrid(int x, int z) {
return grids[NormalizationUtil.normalize(useImage ? Objects.requireNonNull(imageLoader).getNoiseVal(x, z, channel) : noise.getNoise(x, z), grids.length, 4)];
}
/**
* Get the number of BiomeGrids this BiomeZone holds.
*
* @return Number of grids
*/
public int getSize() {
return grids.length;
}
/**
* Get the normalized grid noise at location
*
* @param x X coordinate
* @param z Z coordinate
* @return Normalized noise at coordinates
*/
public int getNoise(int x, int z) {
return NormalizationUtil.normalize(useImage ? Objects.requireNonNull(imageLoader).getNoiseVal(x, z, channel) : noise.getNoise(x, z), grids.length, 4);
}
/**
* Get raw grid noise at location
*
* @param x X coordinate
* @param z Z coordinate
* @return Raw noise at coordinates
*/
public double getRawNoise(int x, int z) {
return useImage ? Objects.requireNonNull(imageLoader).getNoiseVal(x, z, channel) : noise.getNoise(x, z);
}
}
@@ -0,0 +1,85 @@
package com.dfsek.terra.biome;
import com.dfsek.terra.api.gaea.biome.Biome;
import com.dfsek.terra.api.gaea.biome.Decorator;
import com.dfsek.terra.api.gaea.biome.Generator;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.builder.GeneratorBuilder;
import com.dfsek.terra.config.templates.BiomeTemplate;
import com.dfsek.terra.generation.UserDefinedDecorator;
/**
* Class representing a config-defined biome
*/
public class UserDefinedBiome implements Biome {
private final GeneratorBuilder gen;
private final UserDefinedDecorator decorator;
private final com.dfsek.terra.api.generic.world.Biome vanilla;
private final String id;
private final BiomeTemplate config;
private final ConfigPack pack;
private UserDefinedBiome erode;
public UserDefinedBiome(com.dfsek.terra.api.generic.world.Biome vanilla, UserDefinedDecorator dec, GeneratorBuilder gen, BiomeTemplate config, ConfigPack pack) {
this.vanilla = vanilla;
this.decorator = dec;
this.gen = gen;
this.id = config.getID();
this.config = config;
this.pack = pack;
}
/**
* Gets the Vanilla biome to represent the custom biome.
*
* @return Biome - The Vanilla biome.
*/
@Override
public com.dfsek.terra.api.generic.world.Biome getVanillaBiome() {
return vanilla;
}
/**
* Gets the Generator instance used to generate the biome.
*
* @return Generator - The terrain generation instance.
*/
@Override
public Generator getGenerator() {
return gen.build(0);
}
/**
* Returns the Decorator instance containing information about the population in the biome.
*
* @return Decorator - the Decorator instance.
*/
@Override
public Decorator getDecorator() {
return decorator;
}
public String getID() {
return id;
}
public UserDefinedBiome getErode() {
if(erode == null) {
erode = (config.getErode() == null) ? this : pack.getBiome(config.getErode());
}
return erode;
}
public BiomeTemplate getConfig() {
return config;
}
@Override
public Generator getGenerator(World w) {
return gen.build(w.getSeed());
}
}
@@ -0,0 +1,29 @@
package com.dfsek.terra.biome.grid;
import com.dfsek.terra.api.gaea.biome.Biome;
import com.dfsek.terra.api.gaea.biome.BiomeGrid;
import com.dfsek.terra.api.gaea.generation.GenerationPhase;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.api.generic.world.vector.Location;
/**
* BiomeGrid implementation that holds a single biome.
*/
public class SingleBiomeGrid extends BiomeGrid {
private final Biome biome;
public SingleBiomeGrid(World w, Biome biome) {
super(w, 0, 0, 1, 1);
this.biome = biome;
}
@Override
public Biome getBiome(int x, int z, GenerationPhase phase) {
return biome;
}
@Override
public Biome getBiome(Location l) {
return biome;
}
}
@@ -0,0 +1,43 @@
package com.dfsek.terra.biome.grid;
import com.dfsek.terra.api.gaea.biome.Biome;
import com.dfsek.terra.api.gaea.biome.BiomeGrid;
import com.dfsek.terra.api.gaea.biome.NormalizationUtil;
import com.dfsek.terra.api.gaea.generation.GenerationPhase;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.api.generic.world.vector.Location;
import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.base.ConfigPackTemplate;
import com.dfsek.terra.image.ImageLoader;
public class UserDefinedGrid extends BiomeGrid {
private final ImageLoader imageLoader;
private final boolean fromImage;
private final ImageLoader.Channel channelX;
private final ImageLoader.Channel channelZ;
public UserDefinedGrid(World w, double freq1, double freq2, Biome[][] b, ConfigPack c) {
super(w, freq1, freq2, b.length, b[0].length);
super.setGrid(b);
ConfigPackTemplate t = c.getTemplate();
imageLoader = t.getImageLoader();
fromImage = t.isFromImage();
channelX = t.getBiomeXChannel();
channelZ = t.getBiomeZChannel();
}
@Override
public Biome getBiome(int x, int z, GenerationPhase phase) {
if(fromImage) {
double xi = imageLoader.getNoiseVal(x, z, channelX);
double zi = imageLoader.getNoiseVal(x, z, channelZ);
return super.getGrid()[NormalizationUtil.normalize(xi, getSizeX(), 4)][NormalizationUtil.normalize(zi, getSizeZ(), 4)];
}
return super.getBiome(x, z, phase);
}
@Override
public Biome getBiome(Location l, GenerationPhase phase) {
return this.getBiome(l.getBlockX(), l.getBlockZ(), phase);
}
}
@@ -0,0 +1,17 @@
package com.dfsek.terra.biome.grid.master;
import com.dfsek.terra.api.gaea.biome.BiomeGrid;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.biome.grid.UserDefinedGrid;
public abstract class TerraBiomeGrid extends BiomeGrid {
public TerraBiomeGrid(World w, double freq1, double freq2, int sizeX, int sizeZ) {
super(w, freq1, freq2, sizeX, sizeZ);
}
public abstract UserDefinedGrid getGrid(int x, int z);
public enum Type {
RADIAL, STANDARD
}
}
@@ -0,0 +1,68 @@
package com.dfsek.terra.biome.grid.master;
import com.dfsek.terra.api.gaea.biome.Biome;
import com.dfsek.terra.api.gaea.biome.BiomeGrid;
import com.dfsek.terra.api.gaea.generation.GenerationPhase;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.api.generic.world.vector.Location;
import com.dfsek.terra.api.generic.world.vector.Vector2;
import com.dfsek.terra.biome.BiomeZone;
import com.dfsek.terra.biome.UserDefinedBiome;
import com.dfsek.terra.biome.grid.UserDefinedGrid;
import com.dfsek.terra.biome.postprocessing.CoordinatePerturb;
import com.dfsek.terra.biome.postprocessing.ErosionNoise;
import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.base.ConfigPackTemplate;
import net.jafama.FastMath;
public class TerraRadialBiomeGrid extends TerraBiomeGrid {
private static final int failNum = 0;
private final BiomeZone zone;
private final double radiusSq;
private final BiomeGrid internal;
private CoordinatePerturb perturb;
private ErosionNoise erode;
public TerraRadialBiomeGrid(World w, double freq1, double freq2, BiomeZone zone, ConfigPack c, double radius, BiomeGrid internal) {
super(w, freq1, freq2, 0, 0);
ConfigPackTemplate t = c.getTemplate();
if(c.getTemplate().isBlend()) {
perturb = new CoordinatePerturb(t.getBlendFreq(), t.getBlendAmp(), w.getSeed());
}
this.zone = zone;
if(c.getTemplate().isErode()) {
erode = new ErosionNoise(t.getErodeFreq(), t.getErodeThresh(), t.getErodeOctaves(), w.getSeed());
}
this.radiusSq = FastMath.pow2(radius);
this.internal = internal;
}
@Override
public UserDefinedGrid getGrid(int x, int z) {
return (UserDefinedGrid) zone.getGrid(x, z);
}
@Override
public Biome getBiome(int x, int z, GenerationPhase phase) {
int xp = x, zp = z;
if(perturb != null && (phase.equals(GenerationPhase.PALETTE_APPLY) || phase.equals(GenerationPhase.POPULATE))) {
Vector2 perturbCoords = perturb.getShiftedCoords(x, z);
xp = (int) perturbCoords.getX();
zp = (int) perturbCoords.getZ();
}
UserDefinedBiome b;
if(x * x + z * z > radiusSq) {
b = (UserDefinedBiome) zone.getGrid(xp, zp).getBiome(xp, zp, phase);
} else {
b = (UserDefinedBiome) internal.getBiome(xp, zp, phase);
}
if(erode != null && erode.isEroded(xp, zp)) return b.getErode();
return b;
}
@Override
public Biome getBiome(Location l, GenerationPhase phase) {
return getBiome(l.getBlockX(), l.getBlockZ(), phase);
}
}
@@ -0,0 +1,57 @@
package com.dfsek.terra.biome.grid.master;
import com.dfsek.terra.api.gaea.biome.Biome;
import com.dfsek.terra.api.gaea.generation.GenerationPhase;
import com.dfsek.terra.api.generic.world.World;
import com.dfsek.terra.api.generic.world.vector.Location;
import com.dfsek.terra.api.generic.world.vector.Vector2;
import com.dfsek.terra.biome.BiomeZone;
import com.dfsek.terra.biome.UserDefinedBiome;
import com.dfsek.terra.biome.grid.UserDefinedGrid;
import com.dfsek.terra.biome.postprocessing.CoordinatePerturb;
import com.dfsek.terra.biome.postprocessing.ErosionNoise;
import com.dfsek.terra.config.base.ConfigPack;
import com.dfsek.terra.config.base.ConfigPackTemplate;
public class TerraStandardBiomeGrid extends TerraBiomeGrid {
private static final int failNum = 0;
private final BiomeZone zone;
private CoordinatePerturb perturb;
private ErosionNoise erode;
public TerraStandardBiomeGrid(World w, double freq1, double freq2, BiomeZone zone, ConfigPack c) {
super(w, freq1, freq2, 0, 0);
ConfigPackTemplate t = c.getTemplate();
if(c.getTemplate().isBlend()) {
perturb = new CoordinatePerturb(t.getBlendFreq(), t.getBlendAmp(), w.getSeed());
}
this.zone = zone;
if(c.getTemplate().isErode()) {
erode = new ErosionNoise(t.getErodeFreq(), t.getErodeThresh(), t.getErodeOctaves(), w.getSeed());
}
}
@Override
public UserDefinedGrid getGrid(int x, int z) {
return (UserDefinedGrid) zone.getGrid(x, z);
}
@Override
public Biome getBiome(int x, int z, GenerationPhase phase) {
int xp = x, zp = z;
if(perturb != null && (phase.equals(GenerationPhase.PALETTE_APPLY) || phase.equals(GenerationPhase.POPULATE))) {
Vector2 perturbCoords = perturb.getShiftedCoords(x, z);
xp = (int) perturbCoords.getX();
zp = (int) perturbCoords.getZ();
}
UserDefinedBiome b = (UserDefinedBiome) zone.getGrid(xp, zp).getBiome(xp, zp, phase);
if(erode != null && erode.isEroded(xp, zp)) return b.getErode();
return b;
}
@Override
public Biome getBiome(Location l, GenerationPhase phase) {
return getBiome(l.getBlockX(), l.getBlockZ(), phase);
}
}
@@ -0,0 +1,16 @@
package com.dfsek.terra.biome.palette;
import com.dfsek.terra.api.gaea.world.palette.Palette;
import com.dfsek.terra.api.generic.world.block.BlockData;
public class PaletteHolder {
private final Palette<BlockData>[] palettes;
protected PaletteHolder(Palette<BlockData>[] palettes) {
this.palettes = palettes;
}
public Palette<BlockData> getPalette(int y) {
return palettes[y];
}
}
@@ -0,0 +1,34 @@
package com.dfsek.terra.biome.palette;
import com.dfsek.terra.api.gaea.world.palette.Palette;
import com.dfsek.terra.api.generic.world.block.BlockData;
import net.jafama.FastMath;
import java.util.Map;
import java.util.TreeMap;
public class PaletteHolderBuilder {
private final TreeMap<Integer, Palette<BlockData>> paletteMap = new TreeMap<>();
public PaletteHolderBuilder add(int y, Palette<BlockData> palette) {
paletteMap.put(y, palette);
return this;
}
@SuppressWarnings({"unchecked", "rawtypes", "RedundantSuppression"})
public PaletteHolder build() {
Palette<BlockData>[] palettes = new Palette[paletteMap.lastKey() + 1];
for(int y = 0; y <= FastMath.max(paletteMap.lastKey(), 255); y++) {
Palette<BlockData> d = null;
for(Map.Entry<Integer, Palette<BlockData>> e : paletteMap.entrySet()) {
if(e.getKey() >= y) {
d = e.getValue();
break;
}
}
if(d == null) throw new IllegalArgumentException("No palette for Y=" + y);
palettes[y] = d;
}
return new PaletteHolder(palettes);
}
}
@@ -0,0 +1,24 @@
package com.dfsek.terra.biome.palette;
import com.dfsek.terra.api.gaea.math.ProbabilityCollection;
import com.dfsek.terra.api.generic.world.block.BlockData;
import org.jetbrains.annotations.NotNull;
public class PaletteLayer {
private final ProbabilityCollection<BlockData> layer;
private final int size;
public PaletteLayer(@NotNull ProbabilityCollection<BlockData> layer, int size) {
this.layer = layer;
this.size = size;
}
@NotNull
public ProbabilityCollection<BlockData> getLayer() {
return layer;
}
public int getSize() {
return size;
}
}
@@ -0,0 +1,16 @@
package com.dfsek.terra.biome.palette;
import com.dfsek.terra.api.gaea.world.palette.Palette;
public class SinglePalette<E> extends Palette<E> {
private final E item;
public SinglePalette(E item) {
this.item = item;
}
@Override
public E get(int i, int i1, int i2) {
return item;
}
}
@@ -0,0 +1,41 @@
package com.dfsek.terra.biome.postprocessing;
import com.dfsek.terra.api.gaea.math.FastNoiseLite;
import com.dfsek.terra.api.generic.world.vector.Vector2;
/**
* Offset a coordinate pair by an amount.
*/
public class CoordinatePerturb {
private final FastNoiseLite perturbX;
private final FastNoiseLite perturbZ;
private final double amplitude;
/**
* Create a CoordinatePerturb object with a given frequency, amplitude, and seed.
*
* @param frequency Noise frequency
* @param amplitude Offset amplitude
* @param seed Noise seed
*/
public CoordinatePerturb(double frequency, double amplitude, long seed) {
perturbX = new FastNoiseLite((int) seed);
perturbX.setNoiseType(FastNoiseLite.NoiseType.OpenSimplex2);
perturbX.setFrequency(frequency);
perturbZ = new FastNoiseLite((int) seed + 1);
perturbZ.setNoiseType(FastNoiseLite.NoiseType.OpenSimplex2);
perturbZ.setFrequency(frequency);
this.amplitude = amplitude;
}
/**
* Offset a coordinate pair
*
* @param x X coordinate
* @param z Z coordinate
* @return Vector2 containing offset coordinates
*/
public Vector2 getShiftedCoords(int x, int z) {
return new Vector2(perturbX.getNoise(x, z) * amplitude + x, perturbZ.getNoise(x, z) * amplitude + z);
}
}
@@ -0,0 +1,34 @@
package com.dfsek.terra.biome.postprocessing;
import com.dfsek.terra.api.gaea.math.FastNoiseLite;
import net.jafama.FastMath;
/**
* Class to hold noise function to determine erosion.
*/
public class ErosionNoise {
private final double thresh;
private final FastNoiseLite noise;
public ErosionNoise(double freq1, double thresh, int octaves, long seed) {
FastNoiseLite main = new FastNoiseLite((int) (seed + 1));
main.setNoiseType(FastNoiseLite.NoiseType.OpenSimplex2);
main.setFractalType(FastNoiseLite.FractalType.FBm);
main.setFractalOctaves(octaves);
main.setFrequency(freq1);
this.thresh = thresh;
this.noise = main;
}
/**
* Get whether a location is eroded
*
* @param x X coordinate
* @param z Z coordinate
* @return Whether location is eroded
*/
public boolean isEroded(int x, int z) {
double abs = FastMath.pow(noise.getNoise(x, z), 2);
return abs < thresh;
}
}