mirror of
https://github.com/PolyhedralDev/Terra.git
synced 2025-07-03 16:35:50 +00:00
implementation compilation
This commit is contained in:
parent
18d071128d
commit
03ecf6197a
@ -98,4 +98,6 @@ public interface Vector2 extends Cloneable {
|
||||
int getBlockX();
|
||||
|
||||
int getBlockZ();
|
||||
|
||||
Vector3 extrude(double y);
|
||||
}
|
||||
|
@ -2,6 +2,7 @@ package com.dfsek.terra.api.world;
|
||||
|
||||
import com.dfsek.terra.api.Handle;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.state.BlockState;
|
||||
import com.dfsek.terra.api.entity.Entity;
|
||||
import com.dfsek.terra.api.entity.EntityType;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
@ -36,9 +37,27 @@ public interface World extends Handle {
|
||||
}
|
||||
|
||||
default void setBlockData(Vector3 position, BlockData data) {
|
||||
setBlockData(position.getBlockX(), position.getBlockY(), position.getBlockZ(), data);
|
||||
setBlockData(position, data, false);
|
||||
}
|
||||
|
||||
default void setBlockData(Vector3 position, BlockData data, boolean physics) {
|
||||
setBlockData(position.getBlockX(), position.getBlockY(), position.getBlockZ(), data, physics);
|
||||
}
|
||||
|
||||
BlockState getBlockState(int x, int y, int z);
|
||||
|
||||
default BlockState getBlockState(Vector3 position) {
|
||||
return getBlockState(position.getBlockX(), position.getBlockY(), position.getBlockZ());
|
||||
}
|
||||
|
||||
void setBlockState(int x, int y, int z, BlockState state);
|
||||
|
||||
default void setBlockState(Vector3 position, BlockState state) {
|
||||
setBlockState(position.getBlockX(), position.getBlockY(), position.getBlockZ(), state);
|
||||
}
|
||||
|
||||
|
||||
|
||||
Entity spawnEntity(Location location, EntityType entityType);
|
||||
|
||||
int getMinHeight();
|
||||
|
@ -34,7 +34,7 @@ public class CheckBlockFunction implements Function<String> {
|
||||
|
||||
RotationUtil.rotateVector(xz, arguments.getRotation());
|
||||
|
||||
String data = arguments.getBuffer().getOrigin().clone().add(new Vector3Impl(FastMath.roundToInt(xz.getX()), y.apply(implementationArguments, variableMap).doubleValue(), FastMath.roundToInt(xz.getZ()))).getBlock().getBlockData().getAsString();
|
||||
String data = arguments.getBuffer().getOrigin().getWorld().getBlockData(arguments.getBuffer().getOrigin().clone().add(new Vector3Impl(FastMath.roundToInt(xz.getX()), y.apply(implementationArguments, variableMap).doubleValue(), FastMath.roundToInt(xz.getZ()))).getVector()).getAsString();
|
||||
if(data.contains("[")) return data.substring(0, data.indexOf('[')); // Strip properties
|
||||
else return data;
|
||||
}
|
||||
|
@ -1,7 +1,6 @@
|
||||
package com.dfsek.terra.api.structures.structure.buffer.items;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.data.Waterlogged;
|
||||
import com.dfsek.terra.api.structure.buffer.BufferedItem;
|
||||
@ -22,12 +21,12 @@ public class BufferedBlock implements BufferedItem {
|
||||
|
||||
@Override
|
||||
public void paste(Location origin) {
|
||||
Block block = origin.getBlock();
|
||||
try {
|
||||
if(overwrite || block.isEmpty()) {
|
||||
if(waterlog && data instanceof Waterlogged && block.getBlockData().getBlockType().isWater())
|
||||
BlockData data = origin.getWorld().getBlockData(origin.toVector());
|
||||
if(overwrite || data.isAir()) {
|
||||
if(waterlog && data instanceof Waterlogged && data.getBlockType().isWater())
|
||||
((Waterlogged) data).setWaterlogged(true);
|
||||
block.setBlockData(data, false);
|
||||
origin.getWorld().setBlockData(origin.getVector(), data);
|
||||
}
|
||||
} catch(RuntimeException e) {
|
||||
main.logger().severe("Failed to place block at location " + origin + ": " + e.getMessage());
|
||||
|
@ -1,7 +1,6 @@
|
||||
package com.dfsek.terra.api.structures.structure.buffer.items;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.state.BlockState;
|
||||
import com.dfsek.terra.api.block.state.Container;
|
||||
import com.dfsek.terra.api.event.events.world.generation.LootPopulateEvent;
|
||||
@ -25,15 +24,14 @@ public class BufferedLootApplication implements BufferedItem {
|
||||
@Override
|
||||
public void paste(Location origin) {
|
||||
try {
|
||||
Block block = origin.getBlock();
|
||||
BlockState data = block.getState();
|
||||
BlockState data = origin.getWorld().getBlockState(origin.getVector());
|
||||
if(!(data instanceof Container)) {
|
||||
main.logger().severe("Failed to place loot at " + origin + "; block " + data + " is not container.");
|
||||
return;
|
||||
}
|
||||
Container container = (Container) data;
|
||||
|
||||
LootPopulateEvent event = new LootPopulateEvent(block, container, table, block.getLocation().getWorld().getTerraGenerator().getConfigPack(), structure);
|
||||
LootPopulateEvent event = new LootPopulateEvent(container, table, origin.getWorld().getTerraGenerator().getConfigPack(), structure);
|
||||
main.getEventManager().callEvent(event);
|
||||
if(event.isCancelled()) return;
|
||||
|
||||
|
@ -1,10 +1,9 @@
|
||||
package com.dfsek.terra.api.structures.structure.buffer.items;
|
||||
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockFace;
|
||||
import com.dfsek.terra.api.structure.buffer.BufferedItem;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
|
||||
public class BufferedPulledBlock implements BufferedItem {
|
||||
private final BlockData data;
|
||||
@ -15,13 +14,13 @@ public class BufferedPulledBlock implements BufferedItem {
|
||||
|
||||
@Override
|
||||
public void paste(Location origin) {
|
||||
Block pos = origin.getBlock();
|
||||
while(pos.getY() > origin.getWorld().getMinHeight()) {
|
||||
if(!pos.isEmpty()) {
|
||||
pos.setBlockData(data, false);
|
||||
Vector3 mutable = origin.toVector();
|
||||
while(mutable.getY() > origin.getWorld().getMinHeight()) {
|
||||
if(!origin.getWorld().getBlockData(mutable).isAir()) {
|
||||
origin.getWorld().setBlockData(mutable, data);
|
||||
break;
|
||||
}
|
||||
pos = pos.getRelative(BlockFace.DOWN);
|
||||
mutable.subtract(0, 1, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -17,9 +17,11 @@ public class BufferedStateManipulator implements BufferedItem {
|
||||
@Override
|
||||
public void paste(Location origin) {
|
||||
try {
|
||||
BlockState state = origin.getBlock().getState();
|
||||
BlockState state = origin.getWorld().getBlockState(origin.getVector());
|
||||
state.applyState(data);
|
||||
state.update(false);
|
||||
|
||||
origin.getWorld().setBlockState(origin.getVector(), state);
|
||||
} catch(Exception e) {
|
||||
main.logger().warning("Could not apply BlockState at " + origin + ": " + e.getMessage());
|
||||
e.printStackTrace();
|
||||
|
@ -1,7 +1,6 @@
|
||||
package com.dfsek.terra.commands.structure;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.state.BlockState;
|
||||
import com.dfsek.terra.api.block.state.Sign;
|
||||
@ -60,8 +59,7 @@ public class StructureExportCommand implements CommandTemplate {
|
||||
for(int x = l1.getBlockX(); x <= l2.getBlockX(); x++) {
|
||||
for(int y = l1.getBlockY(); y <= l2.getBlockY(); y++) {
|
||||
for(int z = l1.getBlockZ(); z <= l2.getBlockZ(); z++) {
|
||||
Block block = new LocationImpl(l1.getWorld(), x, y, z).getBlock();
|
||||
BlockState state = block.getState();
|
||||
BlockState state = l1.getWorld().getBlockState(x, y, z);
|
||||
if(state instanceof Sign) {
|
||||
Sign sign = (Sign) state;
|
||||
if(sign.getLine(0).equals("[TERRA]") && sign.getLine(1).equals("[CENTER]")) {
|
||||
@ -78,10 +76,9 @@ public class StructureExportCommand implements CommandTemplate {
|
||||
for(int y = l1.getBlockY(); y <= l2.getBlockY(); y++) {
|
||||
for(int z = l1.getBlockZ(); z <= l2.getBlockZ(); z++) {
|
||||
|
||||
Block block = new LocationImpl(l1.getWorld(), x, y, z).getBlock();
|
||||
BlockData data = block.getBlockData();
|
||||
if(block.getBlockData().isStructureVoid()) continue;
|
||||
BlockState state = block.getState();
|
||||
BlockData data = l1.getWorld().getBlockData(x, y, z);
|
||||
if(data.isStructureVoid()) continue;
|
||||
BlockState state = l1.getWorld().getBlockState(x, y, z);
|
||||
if(state instanceof Sign) {
|
||||
Sign sign = (Sign) state;
|
||||
if(sign.getLine(0).equals("[TERRA]")) {
|
||||
|
@ -76,7 +76,6 @@ public class GenericLoaders implements LoaderRegistrar {
|
||||
.registerLoader(PaletteLayerHolder.class, new PaletteLayerLoader())
|
||||
.registerLoader(SlantHolder.class, new SlantHolderLoader())
|
||||
.registerLoader(FloraLayer.class, new FloraLayerLoader())
|
||||
.registerLoader(Ore.Type.class, (t, o, l) -> Ore.Type.valueOf(o.toString()))
|
||||
.registerLoader(OreConfig.class, new OreConfigLoader())
|
||||
.registerLoader(TreeLayer.class, new TreeLayerLoader())
|
||||
.registerLoader(MaterialSet.class, new MaterialSetLoader())
|
||||
|
@ -1,6 +1,7 @@
|
||||
package com.dfsek.terra.config.dummy;
|
||||
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.state.BlockState;
|
||||
import com.dfsek.terra.api.entity.Entity;
|
||||
import com.dfsek.terra.api.entity.EntityType;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
@ -36,10 +37,25 @@ public class DummyWorld implements World {
|
||||
}
|
||||
|
||||
@Override
|
||||
public Block getBlockAt(int x, int y, int z) {
|
||||
public BlockData getBlockData(int x, int y, int z) {
|
||||
throw new UnsupportedOperationException("Cannot get block in DummyWorld");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setBlockData(int x, int y, int z, BlockData data, boolean physics) {
|
||||
throw new UnsupportedOperationException("Cannot set block in DummyWorld");
|
||||
}
|
||||
|
||||
@Override
|
||||
public BlockState getBlockState(int x, int y, int z) {
|
||||
throw new UnsupportedOperationException("Cannot get block in DummyWorld");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setBlockState(int x, int y, int z, BlockState state) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public Entity spawnEntity(Location location, EntityType entityType) {
|
||||
throw new UnsupportedOperationException("Cannot spawn entity in DummyWorld");
|
||||
|
@ -3,7 +3,6 @@ package com.dfsek.terra.config.factories;
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.config.templates.OreTemplate;
|
||||
import com.dfsek.terra.world.population.items.ores.DeformedSphereOre;
|
||||
import com.dfsek.terra.world.population.items.ores.Ore;
|
||||
import com.dfsek.terra.world.population.items.ores.VanillaOre;
|
||||
|
||||
@ -11,12 +10,6 @@ public class OreFactory implements ConfigFactory<OreTemplate, Ore> {
|
||||
@Override
|
||||
public Ore build(OreTemplate config, TerraPlugin main) {
|
||||
BlockData m = config.getMaterial();
|
||||
switch(config.getType()) {
|
||||
case SPHERE:
|
||||
return new DeformedSphereOre(m, config.getReplaceable(), config.doPhysics(), config.getDeform(), config.getDeformFrequency(), config.getSize(), main, config.getMaterialOverrides());
|
||||
case VANILLA:
|
||||
return new VanillaOre(m, config.getReplaceable(), config.doPhysics(), config.getSize(), main, config.getMaterialOverrides());
|
||||
}
|
||||
return null;
|
||||
return new VanillaOre(m, config.getReplaceable(), config.doPhysics(), config.getSize(), main, config.getMaterialOverrides());
|
||||
}
|
||||
}
|
||||
|
@ -26,11 +26,6 @@ public class OreTemplate extends AbstractableTemplate {
|
||||
@Abstractable
|
||||
private Map<BlockType, BlockData> materials = new HashMap<>();
|
||||
|
||||
@Value("algorithm")
|
||||
@Abstractable
|
||||
@Default
|
||||
private Ore.Type oreType = Ore.Type.VANILLA;
|
||||
|
||||
@Value("replace")
|
||||
@Abstractable
|
||||
private MaterialSet replaceable;
|
||||
@ -82,10 +77,6 @@ public class OreTemplate extends AbstractableTemplate {
|
||||
return id;
|
||||
}
|
||||
|
||||
public Ore.Type getType() {
|
||||
return oreType;
|
||||
}
|
||||
|
||||
public Map<BlockType, BlockData> getMaterialOverrides() {
|
||||
return materials;
|
||||
}
|
||||
|
@ -1,6 +1,5 @@
|
||||
package com.dfsek.terra.vector;
|
||||
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
import com.dfsek.terra.api.world.World;
|
||||
@ -108,11 +107,6 @@ public class LocationImpl implements Location {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Block getBlock() {
|
||||
return world.getBlockAt(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Location subtract(int x, int y, int z) {
|
||||
vector.subtract(x, y, z);
|
||||
|
@ -2,6 +2,7 @@ package com.dfsek.terra.vector;
|
||||
|
||||
import com.dfsek.terra.api.util.MathUtil;
|
||||
import com.dfsek.terra.api.vector.Vector2;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
import net.jafama.FastMath;
|
||||
|
||||
/**
|
||||
@ -141,6 +142,11 @@ public class Vector2Impl implements Vector2 {
|
||||
return FastMath.floorToInt(z);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Vector3 extrude(double y) {
|
||||
return new Vector3Impl(this.x, y, this.z);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "(" + x + ", " + z + ")";
|
||||
|
@ -1,7 +1,6 @@
|
||||
package com.dfsek.terra.world.population;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockType;
|
||||
import com.dfsek.terra.api.config.WorldConfig;
|
||||
@ -9,6 +8,7 @@ import com.dfsek.terra.api.handle.WorldHandle;
|
||||
import com.dfsek.terra.api.profiler.ProfileFrame;
|
||||
import com.dfsek.terra.api.util.PopulationUtil;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
import com.dfsek.terra.api.world.Chunk;
|
||||
import com.dfsek.terra.api.world.TerraWorld;
|
||||
import com.dfsek.terra.api.world.World;
|
||||
@ -46,63 +46,52 @@ public class CavePopulator implements TerraBlockPopulator, Chunkified {
|
||||
|
||||
for(UserDefinedCarver c : config.getRegistry(UserDefinedCarver.class).entries()) {
|
||||
CarverTemplate template = c.getConfig();
|
||||
Map<Location, BlockData> shiftCandidate = new HashMap<>();
|
||||
Set<Block> updateNeeded = new HashSet<>();
|
||||
Map<Vector3, BlockData> shiftCandidate = new HashMap<>();
|
||||
c.carve(chunk.getX(), chunk.getZ(), world, (v, type) -> {
|
||||
try(ProfileFrame ignored = main.getProfiler().profile("carving:" + c.getConfig().getID())) {
|
||||
Block b = chunk.getBlock(v.getBlockX(), v.getBlockY(), v.getBlockZ());
|
||||
BlockData m = b.getBlockData();
|
||||
BlockData m = chunk.getBlockData(v.getBlockX(), v.getBlockY(), v.getBlockZ());
|
||||
BlockType re = m.getBlockType();
|
||||
switch(type) {
|
||||
case CENTER:
|
||||
if(template.getInner().canReplace(re)) {
|
||||
b.setBlockData(template.getInner().get(v.getBlockY()).get(random), false);
|
||||
if(template.getUpdate().contains(re)) updateNeeded.add(b);
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(b.getLocation(), m);
|
||||
chunk.setBlockData(v.getBlockX(), v.getBlockY(), v.getBlockZ(), template.getInner().get(v.getBlockY()).get(random), template.getUpdate().contains(re));
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(v, m);
|
||||
}
|
||||
break;
|
||||
case WALL:
|
||||
if(template.getOuter().canReplace(re)) {
|
||||
b.setBlockData(template.getOuter().get(v.getBlockY()).get(random), false);
|
||||
if(template.getUpdate().contains(re)) updateNeeded.add(b);
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(b.getLocation(), m);
|
||||
chunk.setBlockData(v.getBlockX(), v.getBlockY(), v.getBlockZ(), template.getOuter().get(v.getBlockY()).get(random), template.getUpdate().contains(re));
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(v, m);
|
||||
}
|
||||
break;
|
||||
case TOP:
|
||||
if(template.getTop().canReplace(re)) {
|
||||
b.setBlockData(template.getTop().get(v.getBlockY()).get(random), false);
|
||||
if(template.getUpdate().contains(re)) updateNeeded.add(b);
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(b.getLocation(), m);
|
||||
chunk.setBlockData(v.getBlockX(), v.getBlockY(), v.getBlockZ(), template.getTop().get(v.getBlockY()).get(random), template.getUpdate().contains(re));
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(v, m);
|
||||
}
|
||||
break;
|
||||
case BOTTOM:
|
||||
if(template.getBottom().canReplace(re)) {
|
||||
b.setBlockData(template.getBottom().get(v.getBlockY()).get(random), false);
|
||||
if(template.getUpdate().contains(re)) updateNeeded.add(b);
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(b.getLocation(), m);
|
||||
chunk.setBlockData(v.getBlockX(), v.getBlockY(), v.getBlockZ(), template.getBottom().get(v.getBlockY()).get(random), template.getUpdate().contains(re));
|
||||
if(template.getShift().containsKey(re)) shiftCandidate.put(v, m);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
||||
for(Map.Entry<Location, BlockData> entry : shiftCandidate.entrySet()) {
|
||||
Location l = entry.getKey();
|
||||
Location mut = l.clone();
|
||||
BlockData orig = l.getBlock().getBlockData();
|
||||
for(Map.Entry<Vector3, BlockData> entry : shiftCandidate.entrySet()) {
|
||||
Vector3 l = entry.getKey();
|
||||
Vector3 mut = l.clone();
|
||||
BlockData orig = chunk.getBlockData(l.getBlockX(), l.getBlockY(), l.getBlockZ());
|
||||
do mut.subtract(0, 1, 0);
|
||||
while(mut.getY() > world.getMinHeight() && mut.getBlock().getBlockData().matches(orig));
|
||||
while(mut.getY() > world.getMinHeight() && chunk.getBlockData(mut.getBlockX(), mut.getBlockY(), mut.getBlockZ()).matches(orig));
|
||||
try {
|
||||
if(template.getShift().get(entry.getValue().getBlockType()).contains(mut.getBlock().getBlockData().getBlockType())) {
|
||||
mut.getBlock().setBlockData(shiftStorage.computeIfAbsent(entry.getValue().getBlockType(), BlockType::getDefaultData), false);
|
||||
if(template.getShift().get(entry.getValue().getBlockType()).contains(chunk.getBlockData(mut.getBlockX(), mut.getBlockY(), mut.getBlockZ()).getBlockType())) {
|
||||
chunk.setBlockData(mut.getBlockX(), mut.getBlockY(), mut.getBlockZ(), shiftStorage.computeIfAbsent(entry.getValue().getBlockType(), BlockType::getDefaultData), false);
|
||||
}
|
||||
} catch(NullPointerException ignored) {
|
||||
}
|
||||
}
|
||||
for(Block b : updateNeeded) {
|
||||
BlockData orig = b.getBlockData();
|
||||
b.setBlockData(AIR, false);
|
||||
b.setBlockData(orig, true);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,44 +0,0 @@
|
||||
package com.dfsek.terra.world.population.items.flora;
|
||||
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockFace;
|
||||
import com.dfsek.terra.api.util.GlueList;
|
||||
import com.dfsek.terra.api.util.Range;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
import com.dfsek.terra.api.world.Chunk;
|
||||
import com.dfsek.terra.api.world.Flora;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Flora that is just 1 layer of a single block.
|
||||
*/
|
||||
public class BlockFlora implements Flora {
|
||||
|
||||
private final BlockData data;
|
||||
|
||||
public BlockFlora(BlockData data) {
|
||||
this.data = data;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Block> getValidSpawnsAt(Chunk chunk, int x, int z, Range range) {
|
||||
Block current = chunk.getBlock(x, range.getMin(), z);
|
||||
List<Block> blocks = new GlueList<>();
|
||||
for(int y : range) {
|
||||
if(y > 255 || y < 0) continue;
|
||||
current = current.getRelative(BlockFace.UP);
|
||||
if(current.getType().isSolid() && current.getRelative(BlockFace.UP).isEmpty()) {
|
||||
blocks.add(current); // Add all blocks that are solid with air directly above.
|
||||
}
|
||||
}
|
||||
return blocks;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean plant(Location location) {
|
||||
location.add(0, 1, 0).getBlock().setBlockData(data, true);
|
||||
return true;
|
||||
}
|
||||
}
|
@ -1,52 +0,0 @@
|
||||
package com.dfsek.terra.world.population.items.flora;
|
||||
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockFace;
|
||||
import com.dfsek.terra.api.util.GlueList;
|
||||
import com.dfsek.terra.api.util.Range;
|
||||
import com.dfsek.terra.api.util.collections.MaterialSet;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
import com.dfsek.terra.api.world.Chunk;
|
||||
import com.dfsek.terra.api.world.Flora;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class ConstantFlora implements Flora {
|
||||
private final List<BlockData> data;
|
||||
|
||||
private final MaterialSet spawns;
|
||||
|
||||
public ConstantFlora(MaterialSet spawns, List<BlockData> data) {
|
||||
this.data = data;
|
||||
this.spawns = spawns;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Block> getValidSpawnsAt(Chunk chunk, int x, int z, Range check) {
|
||||
List<Block> blocks = new GlueList<>();
|
||||
for(int y : check) {
|
||||
Block block = chunk.getBlock(x, y, z);
|
||||
if(spawns.contains(block.getType()) && valid(block)) {
|
||||
blocks.add(chunk.getBlock(x, y, z));
|
||||
}
|
||||
}
|
||||
return blocks;
|
||||
}
|
||||
|
||||
private boolean valid(Block block) {
|
||||
for(int i = 1; i < data.size() + 1; i++) {
|
||||
block = block.getRelative(BlockFace.UP);
|
||||
if(!block.isEmpty()) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean plant(Location l) {
|
||||
for(int i = 1; i < data.size() + 1; i++) {
|
||||
l.clone().add(0, i, 0).getBlock().setBlockData(data.get(i - 1), false);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
@ -21,6 +21,6 @@ public class FloraLayer extends PlaceableLayer<Flora> {
|
||||
@Override
|
||||
public void place(Chunk chunk, Vector2 coords) {
|
||||
Flora item = layer.get(noise, (chunk.getX() << 4) + coords.getX(), (chunk.getZ() << 4) + coords.getZ());
|
||||
item.getValidSpawnsAt(chunk, (int) coords.getX(), (int) coords.getZ(), level).forEach(block -> item.plant(block.getLocation()));
|
||||
item.getValidSpawnsAt(chunk, (int) coords.getX(), (int) coords.getZ(), level).forEach(block -> item.plant(block.toLocation(chunk.getWorld())));
|
||||
}
|
||||
}
|
||||
|
@ -1,7 +1,6 @@
|
||||
package com.dfsek.terra.world.population.items.flora;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockFace;
|
||||
import com.dfsek.terra.api.block.data.Directional;
|
||||
@ -12,9 +11,12 @@ import com.dfsek.terra.api.util.GlueList;
|
||||
import com.dfsek.terra.api.util.Range;
|
||||
import com.dfsek.terra.api.util.collections.MaterialSet;
|
||||
import com.dfsek.terra.api.vector.Location;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
import com.dfsek.terra.api.world.Chunk;
|
||||
import com.dfsek.terra.api.world.Flora;
|
||||
import com.dfsek.terra.api.world.World;
|
||||
import com.dfsek.terra.api.world.generator.Palette;
|
||||
import com.dfsek.terra.vector.Vector3Impl;
|
||||
import net.jafama.FastMath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
@ -58,14 +60,14 @@ public class TerraFlora implements Flora {
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Block> getValidSpawnsAt(Chunk chunk, int x, int z, Range range) {
|
||||
public List<Vector3> getValidSpawnsAt(Chunk chunk, int x, int z, Range range) {
|
||||
int size = floraPalette.getSize();
|
||||
Block current = chunk.getBlock(x, search.equals(Search.UP) ? range.getMin() : range.getMax(), z);
|
||||
List<Block> blocks = new ArrayList<>();
|
||||
Vector3 current = new Vector3Impl(x, search.equals(Search.UP) ? range.getMin() : range.getMax(), z);
|
||||
List<Vector3> blocks = new ArrayList<>();
|
||||
for(int y : range) {
|
||||
if(y > 255 || y < 0) continue;
|
||||
current = current.getRelative(search.equals(Search.UP) ? BlockFace.UP : BlockFace.DOWN);
|
||||
if((spawnBlacklist != spawnable.contains(current.getType())) && isIrrigated(current.getRelative(BlockFace.UP, irrigableOffset)) && valid(size, current)) {
|
||||
current = current.add(0, search.equals(Search.UP) ? 1 : -1, 0);
|
||||
if((spawnBlacklist != spawnable.contains(chunk.getBlockData(current.getBlockX(), current.getBlockY(), current.getBlockZ()).getBlockType())) && isIrrigated(current.add(0, irrigableOffset, 0), chunk) && valid(size, current.clone(), chunk)) {
|
||||
blocks.add(current);
|
||||
if(maxPlacements > 0 && blocks.size() >= maxPlacements) break;
|
||||
}
|
||||
@ -73,21 +75,21 @@ public class TerraFlora implements Flora {
|
||||
return blocks;
|
||||
}
|
||||
|
||||
private boolean valid(int size, Block block) {
|
||||
private boolean valid(int size, Vector3 block, Chunk chunk) {
|
||||
for(int i = 0; i < size; i++) { // Down if ceiling, up if floor
|
||||
if(block.getY() + 1 > 255 || block.getY() < 0) return false;
|
||||
block = block.getRelative(ceiling ? BlockFace.DOWN : BlockFace.UP);
|
||||
if(!replaceable.contains(block.getType())) return false;
|
||||
block.add(0, ceiling ? -1 : 1, 0);
|
||||
if(!replaceable.contains(chunk.getBlockData(block.getBlockX(), block.getBlockY(), block.getBlockZ()).getBlockType())) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private boolean isIrrigated(Block b) {
|
||||
private boolean isIrrigated(Vector3 b, Chunk chunk) {
|
||||
if(irrigable == null) return true;
|
||||
return irrigable.contains(b.getRelative(BlockFace.NORTH).getType())
|
||||
|| irrigable.contains(b.getRelative(BlockFace.SOUTH).getType())
|
||||
|| irrigable.contains(b.getRelative(BlockFace.EAST).getType())
|
||||
|| irrigable.contains(b.getRelative(BlockFace.WEST).getType());
|
||||
return irrigable.contains(chunk.getBlockData(b.getBlockX()+1, b.getBlockY(), b.getBlockZ()).getBlockType())
|
||||
|| irrigable.contains(chunk.getBlockData(b.getBlockX()-1, b.getBlockY(), b.getBlockZ()).getBlockType())
|
||||
|| irrigable.contains(chunk.getBlockData(b.getBlockX(), b.getBlockY(), b.getBlockZ()+1).getBlockType())
|
||||
|| irrigable.contains(chunk.getBlockData(b.getBlockX(), b.getBlockY(), b.getBlockZ()-1).getBlockType());
|
||||
}
|
||||
|
||||
|
||||
@ -97,7 +99,7 @@ public class TerraFlora implements Flora {
|
||||
int size = floraPalette.getSize();
|
||||
int c = ceiling ? -1 : 1;
|
||||
|
||||
List<BlockFace> faces = doRotation ? getFaces(location.clone().add(0, c, 0).getBlock()) : new GlueList<>();
|
||||
List<BlockFace> faces = doRotation ? getFaces(location.clone().add(0, c, 0).toVector(), location.getWorld()) : new GlueList<>();
|
||||
if(doRotation && faces.size() == 0) return false; // Don't plant if no faces are valid.
|
||||
|
||||
for(int i = 0; FastMath.abs(i) < size; i += c) { // Down if ceiling, up if floor
|
||||
@ -115,22 +117,22 @@ public class TerraFlora implements Flora {
|
||||
((Rotatable) data).setRotation(oneFace);
|
||||
}
|
||||
}
|
||||
location.clone().add(0, i + c, 0).getBlock().setBlockData(data, physics);
|
||||
location.getWorld().setBlockData(location.toVector().add(0, i + c, 0), data, physics);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private List<BlockFace> getFaces(Block b) {
|
||||
private List<BlockFace> getFaces(Vector3 b, World world) {
|
||||
List<BlockFace> faces = new GlueList<>();
|
||||
test(faces, BlockFace.NORTH, b);
|
||||
test(faces, BlockFace.SOUTH, b);
|
||||
test(faces, BlockFace.EAST, b);
|
||||
test(faces, BlockFace.WEST, b);
|
||||
test(faces, BlockFace.NORTH, b, world);
|
||||
test(faces, BlockFace.SOUTH, b, world);
|
||||
test(faces, BlockFace.EAST, b, world);
|
||||
test(faces, BlockFace.WEST, b, world);
|
||||
return faces;
|
||||
}
|
||||
|
||||
private void test(List<BlockFace> faces, BlockFace f, Block b) {
|
||||
if(testRotation.contains(b.getRelative(f).getType())) faces.add(f);
|
||||
private void test(List<BlockFace> faces, BlockFace f, Vector3 b, World world) {
|
||||
if(testRotation.contains(world.getBlockData(b.getBlockX()+f.getModX(), b.getBlockY()+f.getModY(), b.getBlockZ()+f.getModZ()).getBlockType())) faces.add(f);
|
||||
}
|
||||
|
||||
public enum Search {
|
||||
|
@ -1,51 +0,0 @@
|
||||
package com.dfsek.terra.world.population.items.ores;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockType;
|
||||
import com.dfsek.terra.api.util.Range;
|
||||
import com.dfsek.terra.api.util.collections.MaterialSet;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
import com.dfsek.terra.api.world.Chunk;
|
||||
import com.dfsek.terra.noise.samplers.noise.simplex.OpenSimplex2Sampler;
|
||||
import com.dfsek.terra.vector.Vector3Impl;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.Random;
|
||||
|
||||
public class DeformedSphereOre extends Ore {
|
||||
private final double deform;
|
||||
private final double deformFrequency;
|
||||
private final Range size;
|
||||
|
||||
public DeformedSphereOre(BlockData material, MaterialSet replaceable, boolean applyGravity, double deform, double deformFrequency, Range size, TerraPlugin main, Map<BlockType, BlockData> materials) {
|
||||
super(material, replaceable, applyGravity, main, materials);
|
||||
this.deform = deform;
|
||||
this.deformFrequency = deformFrequency;
|
||||
this.size = size;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void generate(Vector3Impl origin, Chunk c, Random r) {
|
||||
OpenSimplex2Sampler ore = new OpenSimplex2Sampler(r.nextInt());
|
||||
ore.setFrequency(deformFrequency);
|
||||
int rad = size.get(r);
|
||||
for(int x = -rad; x <= rad; x++) {
|
||||
for(int y = -rad; y <= rad; y++) {
|
||||
for(int z = -rad; z <= rad; z++) {
|
||||
Vector3 oreLoc = origin.clone().add(new Vector3Impl(x, y, z));
|
||||
if(oreLoc.getBlockX() > 15 || oreLoc.getBlockZ() > 15 || oreLoc.getBlockY() > c.getWorld().getMaxHeight() || oreLoc.getBlockX() < 0 || oreLoc.getBlockZ() < 0 || oreLoc.getBlockY() < c.getWorld().getMinHeight())
|
||||
continue;
|
||||
if(oreLoc.distance(origin) < (rad + 0.5) * ((ore.getNoise(x, y, z) + 1) * deform)) {
|
||||
Block b = c.getBlock(oreLoc.getBlockX(), oreLoc.getBlockY(), oreLoc.getBlockZ());
|
||||
BlockType type = b.getType();
|
||||
if(getReplaceable().contains(type) && b.getLocation().getY() >= c.getWorld().getMinHeight())
|
||||
b.setBlockData(getMaterial(type), isApplyGravity());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -39,8 +39,4 @@ public abstract class Ore {
|
||||
public boolean isApplyGravity() {
|
||||
return applyGravity;
|
||||
}
|
||||
|
||||
public enum Type {
|
||||
VANILLA, SPHERE
|
||||
}
|
||||
}
|
||||
|
@ -1,7 +1,6 @@
|
||||
package com.dfsek.terra.world.population.items.ores;
|
||||
|
||||
import com.dfsek.terra.api.TerraPlugin;
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockData;
|
||||
import com.dfsek.terra.api.block.BlockType;
|
||||
import com.dfsek.terra.api.util.Range;
|
||||
@ -68,10 +67,10 @@ public class VanillaOre extends Ore {
|
||||
for(int z = zStart; z <= zEnd; z++) {
|
||||
double d15 = (z + 0.5D - (d3 + (d4 - d3) * iFactor)) / (d11 / 2.0D);
|
||||
if(x > 15 || z > 15 || y > 255 || x < 0 || z < 0 || y < 0) continue;
|
||||
Block block = chunk.getBlock(x, y, z);
|
||||
BlockType type = block.getType();
|
||||
|
||||
BlockType type = chunk.getBlockData(x, y, z).getBlockType();
|
||||
if((d13 * d13 + d14 * d14 + d15 * d15 < 1.0D) && getReplaceable().contains(type)) {
|
||||
block.setBlockData(getMaterial(type), isApplyGravity());
|
||||
chunk.setBlockData(x, y, z, getMaterial(type), isApplyGravity());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,12 +1,12 @@
|
||||
package com.dfsek.terra.world.population.items.tree;
|
||||
|
||||
import com.dfsek.terra.api.block.Block;
|
||||
import com.dfsek.terra.api.block.BlockFace;
|
||||
import com.dfsek.terra.api.noise.NoiseSampler;
|
||||
import com.dfsek.terra.api.util.PopulationUtil;
|
||||
import com.dfsek.terra.api.util.ProbabilityCollection;
|
||||
import com.dfsek.terra.api.util.Range;
|
||||
import com.dfsek.terra.api.vector.Vector2;
|
||||
import com.dfsek.terra.api.vector.Vector3;
|
||||
import com.dfsek.terra.api.world.Chunk;
|
||||
import com.dfsek.terra.api.world.Tree;
|
||||
import com.dfsek.terra.world.population.items.PlaceableLayer;
|
||||
@ -20,11 +20,11 @@ public class TreeLayer extends PlaceableLayer<Tree> {
|
||||
@Override
|
||||
public void place(Chunk chunk, Vector2 coords) {
|
||||
Tree item = layer.get(noise, coords.getX(), coords.getZ());
|
||||
Block current = chunk.getBlock((int) coords.getX(), level.getMax(), (int) coords.getZ());
|
||||
Vector3 running = coords.extrude(level.getMax());
|
||||
for(int ignored : level) {
|
||||
current = current.getRelative(BlockFace.DOWN);
|
||||
if(item.getSpawnable().contains(current.getType())) {
|
||||
item.plant(current.getLocation().add(0, 1, 0), PopulationUtil.getRandom(chunk, coords.hashCode()));
|
||||
running.subtract(0,1,0);
|
||||
if(item.getSpawnable().contains(chunk.getBlockData(running.getBlockX(), running.getBlockY(), running.getBlockZ()).getBlockType())) {
|
||||
item.plant(running.toLocation(chunk.getWorld()).add(0, 1, 0), PopulationUtil.getRandom(chunk, coords.hashCode()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user