mirror of
https://github.com/PolyhedralDev/Terra.git
synced 2025-07-02 07:55:28 +00:00
continue work on janky pregenerator
This commit is contained in:
parent
ee093397d3
commit
75fbda5a9f
@ -160,4 +160,9 @@ public class Location implements Cloneable {
|
||||
public Vector3 toVector() {
|
||||
return vector.clone();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "(" + getX() + ", " + getY() + ", " + getZ() + ")";
|
||||
}
|
||||
}
|
||||
|
@ -152,8 +152,10 @@ public class MasterChunkGenerator implements TerraChunkGenerator {
|
||||
Palette<BlockData> stairPalette = stairs.get(down.getMaterial());
|
||||
if(stairPalette != null) {
|
||||
BlockData stair = stairPalette.get(0, block.getBlockX(), block.getBlockZ()).clone();
|
||||
Stairs stairNew = (Stairs) stair;
|
||||
if(placeStair(orig, chunk, block, thresh, sampler, stairNew)) return; // Successfully placed part.
|
||||
if(stair instanceof Stairs) {
|
||||
Stairs stairNew = (Stairs) stair;
|
||||
if(placeStair(orig, chunk, block, thresh, sampler, stairNew)) return; // Successfully placed part.
|
||||
}
|
||||
}
|
||||
}
|
||||
BlockData slab = slabs.getOrDefault(down.getMaterial(), blank).get(0, block.getBlockX(), block.getBlockZ());
|
||||
@ -171,9 +173,11 @@ public class MasterChunkGenerator implements TerraChunkGenerator {
|
||||
Palette<BlockData> stairPalette = stairs.get(up.getMaterial());
|
||||
if(stairPalette != null) {
|
||||
BlockData stair = stairPalette.get(0, block.getBlockX(), block.getBlockZ()).clone();
|
||||
Stairs stairNew = (Stairs) stair.clone();
|
||||
stairNew.setHalf(Bisected.Half.TOP);
|
||||
if(placeStair(orig, chunk, block, thresh, sampler, stairNew)) return; // Successfully placed part.
|
||||
if(stair instanceof Stairs) {
|
||||
Stairs stairNew = (Stairs) stair.clone();
|
||||
stairNew.setHalf(Bisected.Half.TOP);
|
||||
if(placeStair(orig, chunk, block, thresh, sampler, stairNew)) return; // Successfully placed part.
|
||||
}
|
||||
}
|
||||
}
|
||||
BlockData slab = slabs.getOrDefault(up.getMaterial(), blank).get(0, block.getBlockX(), block.getBlockZ()).clone();
|
||||
|
@ -0,0 +1,17 @@
|
||||
package com.dfsek.terra;
|
||||
|
||||
import net.querz.mca.MCAUtil;
|
||||
|
||||
public final class DirectUtils {
|
||||
|
||||
/**
|
||||
* Compute long region ID from chunk coords
|
||||
*
|
||||
* @param x X
|
||||
* @param z Z
|
||||
* @return Region IS
|
||||
*/
|
||||
public static long regionID(int x, int z) {
|
||||
return (((long) MCAUtil.chunkToRegion(x)) << 32) | (MCAUtil.chunkToRegion(z) & 0xffffffffL);
|
||||
}
|
||||
}
|
@ -15,6 +15,18 @@ public class Data implements BlockData, MaterialData {
|
||||
this.data.putString("Name", noProp);
|
||||
}
|
||||
|
||||
public Data(CompoundTag tag) {
|
||||
if(tag == null) {
|
||||
this.data = new CompoundTag();
|
||||
data.putString("Name", "minecraft:air");
|
||||
} else {
|
||||
this.data = tag;
|
||||
}
|
||||
String id = data.getString("Name");
|
||||
if(id.contains("[")) noProp = id.substring(0, id.indexOf('[')); // Strip properties for now TODO: actually do properties lol
|
||||
else noProp = id;
|
||||
}
|
||||
|
||||
@Override
|
||||
public MaterialData getMaterial() {
|
||||
return this;
|
||||
@ -68,4 +80,15 @@ public class Data implements BlockData, MaterialData {
|
||||
public CompoundTag getHandle() {
|
||||
return data;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return noProp.hashCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object obj) {
|
||||
if(!(obj instanceof Data)) return false;
|
||||
return ((Data) obj).noProp.equals(noProp);
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,85 @@
|
||||
package com.dfsek.terra.platform;
|
||||
|
||||
import com.dfsek.terra.api.math.vector.Location;
|
||||
import com.dfsek.terra.api.math.vector.Vector3;
|
||||
import com.dfsek.terra.api.platform.block.Block;
|
||||
import com.dfsek.terra.api.platform.block.BlockData;
|
||||
import com.dfsek.terra.api.platform.block.BlockFace;
|
||||
import com.dfsek.terra.api.platform.block.MaterialData;
|
||||
import com.dfsek.terra.api.platform.block.state.BlockState;
|
||||
import net.jafama.FastMath;
|
||||
|
||||
public class DirectBlock implements Block {
|
||||
private final DirectWorld world;
|
||||
private final Vector3 pos;
|
||||
|
||||
public DirectBlock(DirectWorld world, Vector3 pos) {
|
||||
this.world = world;
|
||||
this.pos = pos;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setBlockData(BlockData data, boolean physics) {
|
||||
world.compute(FastMath.floorDiv(pos.getBlockX(), 16), FastMath.floorDiv(pos.getBlockZ(), 16)).setBlockStateAt(pos.getBlockX(), pos.getBlockY(), pos.getBlockZ(), ((Data) data).getHandle(), false);
|
||||
}
|
||||
|
||||
@Override
|
||||
public BlockData getBlockData() {
|
||||
return new Data(world.getData(pos.getBlockX(), pos.getBlockY(), pos.getBlockZ()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public BlockState getState() {
|
||||
return new DirectBlockState();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Block getRelative(BlockFace face) {
|
||||
return world.getBlockAt(pos.getBlockX() + face.getModX(), pos.getBlockY() + face.getModY(), pos.getBlockZ() + face.getModZ());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Block getRelative(BlockFace face, int len) {
|
||||
return world.getBlockAt(pos.getBlockX() + face.getModX() * len, pos.getBlockY() + face.getModY() * len, pos.getBlockZ() + face.getModZ() * len);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() {
|
||||
return getBlockData().getAsString().equals("minecraft:air");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Location getLocation() {
|
||||
return pos.toLocation(world);
|
||||
}
|
||||
|
||||
@Override
|
||||
public MaterialData getType() {
|
||||
return new Data(world.getData(pos.getBlockX(), pos.getBlockY(), pos.getBlockZ()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getX() {
|
||||
return pos.getBlockX();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getZ() {
|
||||
return pos.getBlockY();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getY() {
|
||||
return pos.getBlockY();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isPassable() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object getHandle() {
|
||||
return world;
|
||||
}
|
||||
}
|
@ -0,0 +1,42 @@
|
||||
package com.dfsek.terra.platform;
|
||||
|
||||
import com.dfsek.terra.api.platform.block.Block;
|
||||
import com.dfsek.terra.api.platform.block.BlockData;
|
||||
import com.dfsek.terra.api.platform.block.state.BlockState;
|
||||
|
||||
public class DirectBlockState implements BlockState {
|
||||
@Override
|
||||
public Block getBlock() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getX() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getY() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getZ() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public BlockData getBlockData() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean update(boolean applyPhysics) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object getHandle() {
|
||||
return null;
|
||||
}
|
||||
}
|
@ -1,20 +1,25 @@
|
||||
package com.dfsek.terra.platform;
|
||||
|
||||
import com.dfsek.terra.api.math.vector.Vector3;
|
||||
import com.dfsek.terra.api.platform.block.Block;
|
||||
import com.dfsek.terra.api.platform.block.BlockData;
|
||||
import com.dfsek.terra.api.platform.generator.ChunkGenerator;
|
||||
import com.dfsek.terra.api.platform.world.World;
|
||||
import net.querz.mca.Chunk;
|
||||
import net.querz.nbt.tag.CompoundTag;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class DirectChunkData implements ChunkGenerator.ChunkData {
|
||||
public class DirectChunkData implements ChunkGenerator.ChunkData, com.dfsek.terra.api.platform.world.Chunk {
|
||||
private final Chunk delegate;
|
||||
private final int offX;
|
||||
private final int offZ;
|
||||
private final DirectWorld world;
|
||||
private final int x;
|
||||
private final int z;
|
||||
|
||||
public DirectChunkData(Chunk delegate, int offX, int offZ) {
|
||||
public DirectChunkData(Chunk delegate, DirectWorld world, int x, int z) {
|
||||
this.delegate = delegate;
|
||||
this.offX = offX;
|
||||
this.offZ = offZ;
|
||||
this.world = world;
|
||||
this.x = x;
|
||||
this.z = z;
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -38,4 +43,24 @@ public class DirectChunkData implements ChunkGenerator.ChunkData {
|
||||
if(tag == null) return new Data("minecraft:air");
|
||||
return new Data(tag.getString("Name"));
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getX() {
|
||||
return x;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getZ() {
|
||||
return z;
|
||||
}
|
||||
|
||||
@Override
|
||||
public World getWorld() {
|
||||
return world;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Block getBlock(int x, int y, int z) {
|
||||
return new DirectBlock(world, new Vector3(x + (this.x << 4), y, z + (this.z << 4)));
|
||||
}
|
||||
}
|
||||
|
@ -1,6 +1,8 @@
|
||||
package com.dfsek.terra.platform;
|
||||
|
||||
import com.dfsek.terra.DirectUtils;
|
||||
import com.dfsek.terra.api.math.vector.Location;
|
||||
import com.dfsek.terra.api.math.vector.Vector3;
|
||||
import com.dfsek.terra.api.platform.block.Block;
|
||||
import com.dfsek.terra.api.platform.generator.ChunkGenerator;
|
||||
import com.dfsek.terra.api.platform.world.Chunk;
|
||||
@ -8,13 +10,20 @@ import com.dfsek.terra.api.platform.world.Tree;
|
||||
import com.dfsek.terra.api.platform.world.World;
|
||||
import com.dfsek.terra.api.platform.world.entity.Entity;
|
||||
import com.dfsek.terra.api.platform.world.entity.EntityType;
|
||||
import net.jafama.FastMath;
|
||||
import net.querz.mca.MCAFile;
|
||||
import net.querz.mca.MCAUtil;
|
||||
import net.querz.nbt.tag.CompoundTag;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
|
||||
public class DirectWorld implements World {
|
||||
private final long seed;
|
||||
private final GenWrapper generator;
|
||||
private final Map<Long, MCAFile> files = new HashMap<>();
|
||||
|
||||
public DirectWorld(long seed, GenWrapper generator) {
|
||||
this.seed = seed;
|
||||
@ -53,7 +62,10 @@ public class DirectWorld implements World {
|
||||
|
||||
@Override
|
||||
public Chunk getChunkAt(int x, int z) {
|
||||
return null;
|
||||
MCAFile file = compute(x, z);
|
||||
net.querz.mca.Chunk chunk = file.getChunk(x, z);
|
||||
if(chunk == null) chunk = net.querz.mca.Chunk.newChunk();
|
||||
return new DirectChunkData(chunk, this, x, z);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -63,12 +75,12 @@ public class DirectWorld implements World {
|
||||
|
||||
@Override
|
||||
public Block getBlockAt(int x, int y, int z) {
|
||||
return null;
|
||||
return new DirectBlock(this, new Vector3(x, y, z));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Block getBlockAt(Location l) {
|
||||
return null;
|
||||
return getBlockAt(l.getBlockX(), l.getBlockY(), l.getBlockZ());
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -85,4 +97,16 @@ public class DirectWorld implements World {
|
||||
public Object getHandle() {
|
||||
return generator;
|
||||
}
|
||||
|
||||
public MCAFile compute(int x, int z) {
|
||||
return files.computeIfAbsent(DirectUtils.regionID(x, z), k -> new MCAFile(MCAUtil.chunkToRegion(x), MCAUtil.chunkToRegion(z)));
|
||||
}
|
||||
|
||||
public CompoundTag getData(int x, int y, int z) {
|
||||
return compute(FastMath.floorDiv(x, 16), FastMath.floorDiv(z, 16)).getBlockStateAt(x, y, z);
|
||||
}
|
||||
|
||||
public Map<Long, MCAFile> getFiles() {
|
||||
return files;
|
||||
}
|
||||
}
|
||||
|
@ -4,6 +4,7 @@ import com.dfsek.terra.api.math.vector.Location;
|
||||
import com.dfsek.terra.api.platform.block.MaterialData;
|
||||
import com.dfsek.terra.api.platform.world.Tree;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Random;
|
||||
import java.util.Set;
|
||||
|
||||
@ -20,6 +21,6 @@ public class RawTree implements Tree { // TODO: implement
|
||||
|
||||
@Override
|
||||
public Set<MaterialData> getSpawnable() {
|
||||
return null;
|
||||
return Collections.emptySet();
|
||||
}
|
||||
}
|
||||
|
@ -1,26 +1,28 @@
|
||||
package com.dfsek.terra.region;
|
||||
|
||||
import com.dfsek.terra.StandalonePlugin;
|
||||
import com.dfsek.terra.api.platform.generator.ChunkGenerator;
|
||||
import com.dfsek.terra.api.math.MathUtil;
|
||||
import com.dfsek.terra.api.util.FastRandom;
|
||||
import com.dfsek.terra.api.util.GlueList;
|
||||
import com.dfsek.terra.generation.MasterChunkGenerator;
|
||||
import com.dfsek.terra.generation.math.SamplerCache;
|
||||
import com.dfsek.terra.platform.DirectChunkData;
|
||||
import com.dfsek.terra.platform.DirectWorld;
|
||||
import com.dfsek.terra.platform.GenWrapper;
|
||||
import net.querz.mca.Chunk;
|
||||
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 net.querz.mca.MCAFile;
|
||||
import net.querz.mca.MCAUtil;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
public class Generator {
|
||||
private final Map<Long, MCAFile> files = new HashMap<>();
|
||||
|
||||
private final long seed;
|
||||
|
||||
public Generator(long seed) {
|
||||
@ -29,7 +31,7 @@ public class Generator {
|
||||
|
||||
public void generate() throws IOException {
|
||||
|
||||
int rad = 50;
|
||||
int rad = 25;
|
||||
|
||||
StandalonePlugin plugin = new StandalonePlugin();
|
||||
plugin.load();
|
||||
@ -38,26 +40,31 @@ public class Generator {
|
||||
MasterChunkGenerator generator = new MasterChunkGenerator(plugin.getRegistry().get("DEFAULT"), plugin, new SamplerCache(plugin));
|
||||
GenWrapper wrapper = new GenWrapper(generator);
|
||||
|
||||
FloraPopulator floraPopulator = new FloraPopulator(plugin);
|
||||
StructurePopulator structurePopulator = new StructurePopulator(plugin);
|
||||
TreePopulator treePopulator = new TreePopulator(plugin);
|
||||
OrePopulator orePopulator = new OrePopulator(plugin);
|
||||
CavePopulator cavePopulator = new CavePopulator(plugin);
|
||||
|
||||
int count = 0;
|
||||
|
||||
List<Double> times = new GlueList<>();
|
||||
|
||||
DirectWorld world = new DirectWorld(seed, wrapper);
|
||||
|
||||
for(int cx = -rad; cx <= rad; cx++) {
|
||||
for(int cz = -rad; cz <= rad; cz++) {
|
||||
long start = System.nanoTime();
|
||||
|
||||
long key = (((long) MCAUtil.chunkToRegion(cx)) << 32) | (MCAUtil.chunkToRegion(cz) & 0xffffffffL);
|
||||
DirectChunkData chunkData = (DirectChunkData) world.getChunkAt(cx, cz);
|
||||
generator.generateChunkData(world, null, cx, cz, chunkData);
|
||||
|
||||
int finalCx = cx;
|
||||
int finalCz = cz;
|
||||
MCAFile file = files.computeIfAbsent(key, k -> new MCAFile(MCAUtil.chunkToRegion(finalCx), MCAUtil.chunkToRegion(finalCz)));
|
||||
cavePopulator.populate(world, new FastRandom(MathUtil.getCarverChunkSeed(cx, cz, seed)), chunkData);
|
||||
structurePopulator.populate(world, new FastRandom(MathUtil.getCarverChunkSeed(cx, cz, seed)), chunkData);
|
||||
orePopulator.populate(world, new FastRandom(MathUtil.getCarverChunkSeed(cx, cz, seed)), chunkData);
|
||||
floraPopulator.populate(world, new FastRandom(MathUtil.getCarverChunkSeed(cx, cz, seed)), chunkData);
|
||||
treePopulator.populate(world, new FastRandom(MathUtil.getCarverChunkSeed(cx, cz, seed)), chunkData);
|
||||
|
||||
Chunk chunk = Chunk.newChunk();
|
||||
|
||||
ChunkGenerator.ChunkData chunkData = new DirectChunkData(chunk, cx, cz);
|
||||
generator.generateChunkData(new DirectWorld(seed, wrapper), null, cx, cz, chunkData);
|
||||
|
||||
file.setChunk(cx, cz, chunk);
|
||||
|
||||
long end = System.nanoTime() - start;
|
||||
count++;
|
||||
@ -75,7 +82,7 @@ public class Generator {
|
||||
}
|
||||
}
|
||||
|
||||
for(Map.Entry<Long, MCAFile> entry : files.entrySet()) {
|
||||
for(Map.Entry<Long, MCAFile> entry : world.getFiles().entrySet()) {
|
||||
entry.getValue().cleanupPalettesAndBlockStates();
|
||||
int x = (int) (entry.getKey() >> 32);
|
||||
int z = (int) (long) entry.getKey();
|
||||
|
Loading…
x
Reference in New Issue
Block a user