Finished untested biome generator.
Also: Changed plugin structure to adapt better to server API Refactored by reorganizing packages.
This commit is contained in:
parent
35e52ae61b
commit
533a758799
@ -3,16 +3,16 @@ package ca.recrown.islandsurvivalcraft;
|
||||
import org.bukkit.generator.ChunkGenerator;
|
||||
import org.bukkit.plugin.java.JavaPlugin;
|
||||
|
||||
import ca.recrown.islandsurvivalcraft.worldgeneration.BiomePerIslandGenerator;
|
||||
import ca.recrown.islandsurvivalcraft.worldgeneration.IslandSurvivalCraftWorldGenerator;
|
||||
import ca.recrown.islandsurvivalcraft.world.IslandSurvivalCraftChunkGenerator;
|
||||
import ca.recrown.islandsurvivalcraft.world.IslandWorldGenerator;
|
||||
import ca.recrown.islandsurvivalcraft.world.generation.BiomePerIslandGenerator;
|
||||
|
||||
public class IslandSurvivalCraft extends JavaPlugin {
|
||||
IslandSurvivalCraftWorldGenerator generator;
|
||||
IslandSurvivalCraftChunkGenerator generator;
|
||||
|
||||
@Override
|
||||
public void onEnable() {
|
||||
generator = new IslandSurvivalCraftWorldGenerator(new BiomePerIslandGenerator());
|
||||
generator.initialize();
|
||||
generator = new IslandSurvivalCraftChunkGenerator(new BiomePerIslandGenerator());
|
||||
super.onEnable();
|
||||
}
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
package ca.recrown.islandsurvivalcraft.world;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
@ -11,32 +11,27 @@ import ca.recrown.islandsurvivalcraft.Utilities;
|
||||
|
||||
public class BiomeSelector {
|
||||
private boolean initialized = false;
|
||||
private Random random;
|
||||
private final HashMap<Biome, Float> lands;
|
||||
private HashMap<Float, ArrayList<Biome>> temperaturesForLand;
|
||||
private final HashMap<Float, ArrayList<Biome>> temperaturePartitionedLandBiomes;
|
||||
private final HashMap<Biome, Float> oceans;
|
||||
private HashMap<Float, ArrayList<Biome>> temperaturesForOcean;
|
||||
private final HashMap<Float, ArrayList<Biome>> temperaturePartitionedOceanBiomes;
|
||||
private final Random random;
|
||||
private final HashMap<Biome, Float> lands = new HashMap<>();
|
||||
private HashMap<Float, ArrayList<Biome>> temperaturesForLand = new HashMap<>();
|
||||
private final HashMap<Float, ArrayList<Biome>> temperaturePartitionedLandBiomes = new HashMap<>();
|
||||
private final HashMap<Biome, Float> oceans = new HashMap<>();
|
||||
private HashMap<Float, ArrayList<Biome>> temperaturesForOcean = new HashMap<>();
|
||||
private final HashMap<Float, ArrayList<Biome>> temperaturePartitionedOceanBiomes = new HashMap<>();
|
||||
|
||||
|
||||
public BiomeSelector() {
|
||||
lands = new HashMap<>();
|
||||
oceans = new HashMap<>();
|
||||
temperaturePartitionedLandBiomes = new HashMap<>();
|
||||
public BiomeSelector(Random random) {
|
||||
this.random = random;
|
||||
|
||||
temperaturePartitionedLandBiomes.put(0.05f, new ArrayList<>());
|
||||
temperaturePartitionedLandBiomes.put(0.30f, new ArrayList<>());
|
||||
temperaturePartitionedLandBiomes.put(0.95f, new ArrayList<>());
|
||||
temperaturePartitionedLandBiomes.put(2f, new ArrayList<>());
|
||||
temperaturePartitionedOceanBiomes = new HashMap<>();
|
||||
|
||||
temperaturePartitionedOceanBiomes.put(0.00f, new ArrayList<>());
|
||||
temperaturePartitionedOceanBiomes.put(0.5f, new ArrayList<>());
|
||||
}
|
||||
|
||||
public void setRandom(Random random) {
|
||||
this.random = random;
|
||||
}
|
||||
|
||||
public void initialize() {
|
||||
if (initialized) throw new IllegalStateException("Biome selector is already initialized.");
|
||||
|
@ -1,4 +1,4 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
package ca.recrown.islandsurvivalcraft.world;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
@ -7,8 +7,7 @@ import org.bukkit.util.noise.SimplexOctaveGenerator;
|
||||
import ca.recrown.islandsurvivalcraft.pathfinding.CoordinateValidatable;
|
||||
import ca.recrown.islandsurvivalcraft.pathfinding.DepthFirstSearch;
|
||||
|
||||
public class IslandLocationGenerator implements CoordinateValidatable {
|
||||
private Random random;
|
||||
public class IslandLocationMapper implements CoordinateValidatable {
|
||||
private SimplexOctaveGenerator noiseGenerator;
|
||||
private final int noiseOctaves = 8;
|
||||
private final int islandGenerationPercent = 47;
|
||||
@ -22,17 +21,11 @@ public class IslandLocationGenerator implements CoordinateValidatable {
|
||||
private int shallowDepth;
|
||||
private final DepthFirstSearch dfs;
|
||||
|
||||
public IslandLocationGenerator() {
|
||||
public IslandLocationMapper(Random random, int seaLevel, int shallowDepth) {
|
||||
dfs = new DepthFirstSearch(this);
|
||||
}
|
||||
|
||||
public void updateParameters(Random random, int seaLevel, int shallowDepth) {
|
||||
this.seaLevel = seaLevel;
|
||||
this.shallowDepth = shallowDepth;
|
||||
if (!random.equals(this.random)) {
|
||||
this.random = random;
|
||||
this.noiseGenerator = new SimplexOctaveGenerator(random, noiseOctaves);
|
||||
}
|
||||
this.seaLevel = seaLevel;
|
||||
this.shallowDepth = shallowDepth;
|
||||
}
|
@ -0,0 +1,29 @@
|
||||
package ca.recrown.islandsurvivalcraft.world;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.generator.ChunkGenerator;
|
||||
|
||||
import ca.recrown.islandsurvivalcraft.world.generation.IslandBiomeGenerator;
|
||||
|
||||
public class IslandSurvivalCraftChunkGenerator extends ChunkGenerator {
|
||||
private final IslandWorldGeneratorAlternator alternator;
|
||||
|
||||
public IslandSurvivalCraftChunkGenerator(IslandBiomeGenerator biomeGenerator) {
|
||||
alternator = new IslandWorldGeneratorAlternator(biomeGenerator);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChunkData generateChunkData(World world, Random random, int chunkX, int chunkZ, BiomeGrid biome) {
|
||||
IslandWorldGenerator worldGenerator = alternator.getIslandChunkGeneratorSystemForWorld(world, random);
|
||||
ChunkData chunk = createChunkData(world);
|
||||
|
||||
for (int localX = 0; localX < 16; localX++) {
|
||||
for (int localZ = 0; localZ < 16; localZ++) {
|
||||
worldGenerator.GenerateChunk(chunkX, chunkZ, localX, localZ, chunk, biome);
|
||||
}
|
||||
}
|
||||
return chunk;
|
||||
}
|
||||
}
|
@ -0,0 +1,48 @@
|
||||
package ca.recrown.islandsurvivalcraft.world;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.generator.ChunkGenerator.BiomeGrid;
|
||||
import org.bukkit.generator.ChunkGenerator.ChunkData;
|
||||
|
||||
import ca.recrown.islandsurvivalcraft.world.generation.BedrockGenerator;
|
||||
import ca.recrown.islandsurvivalcraft.world.generation.IslandBiomeGenerator;
|
||||
|
||||
/**
|
||||
* A world generator.
|
||||
*/
|
||||
public class IslandWorldGenerator {
|
||||
private final int maxHeight;
|
||||
private final BedrockGenerator bedrockGenerator;
|
||||
private final BiomeSelector biomeSelector;
|
||||
private final IslandBiomeGenerator biomeGenerator;
|
||||
|
||||
public final World world;
|
||||
public final IslandLocationMapper islandMapGenerator;
|
||||
public final Random random;
|
||||
|
||||
public IslandWorldGenerator(World world, IslandBiomeGenerator generator, Random random) {
|
||||
this.world = world;
|
||||
this.maxHeight = world.getMaxHeight();
|
||||
this.random = random;
|
||||
this.biomeSelector = new BiomeSelector(random);
|
||||
this.bedrockGenerator = new BedrockGenerator(random);
|
||||
this.islandMapGenerator = new IslandLocationMapper(random, world.getSeaLevel(), 4);
|
||||
this.biomeGenerator = generator;
|
||||
biomeSelector.initialize();
|
||||
}
|
||||
|
||||
public void GenerateChunk(int chunkX, int chunkZ, int localX, int localZ, ChunkData chunk, BiomeGrid biomeGrid) {
|
||||
int worldX = 16 * chunkX + localX;
|
||||
int worldZ = 16 * chunkZ + localZ;
|
||||
|
||||
//Sets the biome.
|
||||
biomeGenerator.GenerateBiome(chunkX, chunkZ, localX, localZ, biomeGrid);
|
||||
|
||||
//Sets the bedrock.
|
||||
int bedrockHeight = bedrockGenerator.getBedrockHeight(worldX, worldZ);
|
||||
chunk.setRegion(localX, 0, localZ, localX, bedrockHeight, localZ, Material.BEDROCK);
|
||||
}
|
||||
}
|
@ -0,0 +1,31 @@
|
||||
package ca.recrown.islandsurvivalcraft.world;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Random;
|
||||
import java.util.UUID;
|
||||
|
||||
import org.bukkit.World;
|
||||
|
||||
import ca.recrown.islandsurvivalcraft.world.generation.IslandBiomeGenerator;
|
||||
|
||||
/**
|
||||
* Alternates the data used on a per world basis.
|
||||
* Uses IslandWorldGenerator as the container for each world.
|
||||
*/
|
||||
public class IslandWorldGeneratorAlternator {
|
||||
private HashMap<UUID, IslandWorldGenerator> chunkGenerator;
|
||||
private IslandBiomeGenerator islandBiomeGenerator;
|
||||
|
||||
public IslandWorldGeneratorAlternator(IslandBiomeGenerator biomeGenerator) {
|
||||
chunkGenerator = new HashMap<>();
|
||||
this.islandBiomeGenerator = biomeGenerator;
|
||||
}
|
||||
|
||||
public IslandWorldGenerator getIslandChunkGeneratorSystemForWorld(World world, Random random) {
|
||||
if (!chunkGenerator.containsKey(world.getUID())) {
|
||||
chunkGenerator.put(world.getUID(), new IslandWorldGenerator(world, islandBiomeGenerator.getInstance(), random));
|
||||
}
|
||||
|
||||
return chunkGenerator.get(world.getUID());
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
package ca.recrown.islandsurvivalcraft.world.generation;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
@ -10,8 +10,7 @@ public class BedrockGenerator {
|
||||
private final int maxBedrockHeight = 5;
|
||||
private final int minBedrockHeight = 1;
|
||||
|
||||
public void setRandom(Random random) {
|
||||
if (random.equals(this.random)) return;
|
||||
public BedrockGenerator(Random random) {
|
||||
this.random = random;
|
||||
noiseGenerator = new SimplexOctaveGenerator(random, 8);
|
||||
noiseGenerator.setScale(0.1D);
|
@ -1,4 +1,4 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
package ca.recrown.islandsurvivalcraft.world.generation;
|
||||
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.block.Biome;
|
||||
@ -6,9 +6,12 @@ import org.bukkit.generator.ChunkGenerator.BiomeGrid;
|
||||
|
||||
import ca.recrown.islandsurvivalcraft.pathfinding.CoordinateTargetValidatable;
|
||||
import ca.recrown.islandsurvivalcraft.pathfinding.DepthFirstSearch;
|
||||
import ca.recrown.islandsurvivalcraft.world.BiomeSelector;
|
||||
import ca.recrown.islandsurvivalcraft.world.IslandLocationMapper;
|
||||
|
||||
public class BiomePerIslandGenerator implements IslandBiomeGenerator, CoordinateTargetValidatable {
|
||||
private IslandLocationGenerator islandLocator;
|
||||
private boolean initialized;
|
||||
private IslandLocationMapper islandLocator;
|
||||
private BiomeSelector biomeSelector;
|
||||
private TemperatureMapGenerator temperatureMapGenerator;
|
||||
private int buildHeight;
|
||||
@ -18,20 +21,20 @@ public class BiomePerIslandGenerator implements IslandBiomeGenerator, Coordinate
|
||||
private Biome shoreBiome;
|
||||
private float temperature;
|
||||
|
||||
private BiomeGrid currentBiomeGrid;
|
||||
private int currentChunkX, currentChunkZ;
|
||||
|
||||
public BiomePerIslandGenerator() {
|
||||
this.temperatureMapGenerator = new TemperatureMapGenerator();
|
||||
dfs = new DepthFirstSearch(islandLocator);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void initialize(IslandLocationGenerator mapGenerator, BiomeSelector biomeSelector) {
|
||||
public void initialize(World world, IslandLocationMapper mapGenerator, BiomeSelector biomeSelector) {
|
||||
if (initialized) throw new IllegalStateException("Biome generator already initialized.");
|
||||
initialized = true;
|
||||
this.islandLocator = mapGenerator;
|
||||
this.biomeSelector = biomeSelector;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setWorld(World world) {
|
||||
if (world.equals(this.world)) return;
|
||||
this.world = world;
|
||||
this.temperatureMapGenerator.setSeed(world.getSeed());
|
||||
this.buildHeight = world.getMaxHeight();
|
||||
@ -49,29 +52,44 @@ public class BiomePerIslandGenerator implements IslandBiomeGenerator, Coordinate
|
||||
if (mainBiome != null && shoreBiome != null) {
|
||||
return true;
|
||||
}
|
||||
} else if (x/16 == currentChunkX && y/16 == currentChunkZ) {
|
||||
int localX = x - (currentChunkX * 16);
|
||||
int localZ = y - (currentChunkZ * 16);
|
||||
Biome foundBiome = currentBiomeGrid.getBiome(localX, 0, localZ);
|
||||
if (islandLocator.isShore(x, y)) {
|
||||
shoreBiome = foundBiome;
|
||||
} else {
|
||||
mainBiome = foundBiome;
|
||||
}
|
||||
if (mainBiome != null && shoreBiome != null) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void GenerateBiome(int chunkX, int chunkZ, int localX, int localZ, BiomeGrid biome) {
|
||||
public void GenerateBiome(int chunkX, int chunkZ, int localX, int localZ, BiomeGrid biomeGrid) {
|
||||
int worldX = chunkX * 16 + localX;
|
||||
int worldZ = chunkZ * 16 + localZ;
|
||||
|
||||
if (islandLocator.isIsland(worldX, worldZ)) {
|
||||
if (mainBiome == null && shoreBiome == null) {
|
||||
this.currentBiomeGrid = biomeGrid;
|
||||
this.currentChunkX = chunkX;
|
||||
this.currentChunkZ = chunkZ;
|
||||
if (!dfs.findTarget(this)) {
|
||||
temperature = temperatureMapGenerator.getTemperature(worldX, worldZ);
|
||||
mainBiome = biomeSelector.getLandBiome(temperature);
|
||||
shoreBiome = biomeSelector.getShoreBiome(mainBiome, temperature);
|
||||
}
|
||||
}
|
||||
|
||||
} else {
|
||||
mainBiome = null;
|
||||
shoreBiome = null;
|
||||
}
|
||||
for (int y = 0; y < buildHeight; y++) {
|
||||
|
||||
|
||||
Biome designatedBiome = mainBiome;
|
||||
if (mainBiome == null) {
|
||||
designatedBiome = Biome.OCEAN;
|
||||
@ -79,7 +97,13 @@ public class BiomePerIslandGenerator implements IslandBiomeGenerator, Coordinate
|
||||
designatedBiome = shoreBiome;
|
||||
}
|
||||
|
||||
biome.setBiome(localX, y, localZ, designatedBiome);
|
||||
for (int y = 0; y < buildHeight; y++) {
|
||||
biomeGrid.setBiome(localX, y, localZ, designatedBiome);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public IslandBiomeGenerator getInstance() {
|
||||
return new BiomePerIslandGenerator();
|
||||
}
|
||||
}
|
@ -0,0 +1,14 @@
|
||||
package ca.recrown.islandsurvivalcraft.world.generation;
|
||||
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.block.Biome;
|
||||
import org.bukkit.generator.ChunkGenerator.BiomeGrid;
|
||||
|
||||
import ca.recrown.islandsurvivalcraft.world.BiomeSelector;
|
||||
import ca.recrown.islandsurvivalcraft.world.IslandLocationMapper;
|
||||
|
||||
public interface IslandBiomeGenerator {
|
||||
public void initialize(World world, IslandLocationMapper mapGenerator, BiomeSelector biome);
|
||||
public void GenerateBiome(int chunkX, int chunkZ, int localX, int localZ, BiomeGrid biomeGrid);
|
||||
public IslandBiomeGenerator getInstance();
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
package ca.recrown.islandsurvivalcraft.world.generation;
|
||||
|
||||
import java.util.Random;
|
||||
|
@ -0,0 +1,5 @@
|
||||
package ca.recrown.islandsurvivalcraft.world.shapers;
|
||||
|
||||
public class IslandShaper {
|
||||
|
||||
}
|
@ -1,10 +0,0 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.generator.ChunkGenerator.BiomeGrid;
|
||||
|
||||
public interface IslandBiomeGenerator {
|
||||
public void initialize(IslandLocationGenerator mapGenerator, BiomeSelector biome);
|
||||
public void setWorld(World world);
|
||||
public void GenerateBiome(int chunkX, int chunkZ, int localX, int localZ, BiomeGrid biome);
|
||||
}
|
@ -1,50 +0,0 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.World;
|
||||
import org.bukkit.generator.ChunkGenerator;
|
||||
|
||||
public class IslandSurvivalCraftWorldGenerator extends ChunkGenerator {
|
||||
private final BedrockGenerator bedrockGenerator;
|
||||
private final BiomeSelector biomeSelector;
|
||||
private final IslandBiomeGenerator biomeGenerator;
|
||||
private final IslandLocationGenerator islandMapGenerator;
|
||||
|
||||
public IslandSurvivalCraftWorldGenerator(IslandBiomeGenerator generator) {
|
||||
this.biomeSelector = new BiomeSelector();
|
||||
this.bedrockGenerator = new BedrockGenerator();
|
||||
this.islandMapGenerator = new IslandLocationGenerator();
|
||||
this.biomeGenerator = generator;
|
||||
}
|
||||
|
||||
public void initialize() {
|
||||
biomeSelector.initialize();
|
||||
biomeGenerator.initialize(islandMapGenerator, biomeSelector);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChunkData generateChunkData(World world, Random random, int x, int z, BiomeGrid biome) {
|
||||
bedrockGenerator.setRandom(random);
|
||||
biomeSelector.setRandom(random);
|
||||
biomeGenerator.setWorld(world);
|
||||
islandMapGenerator.updateParameters(random, world.getSeaLevel(), 4);
|
||||
|
||||
ChunkData chunk = createChunkData(world);
|
||||
for (int localX = 0; localX < 16; localX++) {
|
||||
for (int localZ = 0; localZ < 16; localZ++) {
|
||||
int worldX = 16*x + localX;
|
||||
int worldZ = 16*z + localZ;
|
||||
|
||||
//generate bedrock layer
|
||||
int bedrockHeight = bedrockGenerator.getBedrockHeight(worldX, worldZ);
|
||||
chunk.setBlock(localX, bedrockHeight, localZ, Material.BEDROCK);
|
||||
|
||||
//Set biomes
|
||||
biomeGenerator.GenerateBiome(x, z, localX, localZ, biome);
|
||||
}
|
||||
}
|
||||
return chunk;
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package ca.recrown.islandsurvivalcraft.worldgeneration;
|
||||
package ca.recrown.islandsurvivalcraft.world;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
@ -18,8 +18,7 @@ public class BiomeSelectorTest {
|
||||
@BeforeAll
|
||||
public void setUp() {
|
||||
|
||||
biomeSelector = new BiomeSelector();
|
||||
biomeSelector.setRandom(new Random());
|
||||
biomeSelector = new BiomeSelector(new Random());
|
||||
biomeSelector.initialize();
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user