Add perlin noise to staircase generation.

This commit is contained in:
2022-10-27 17:26:55 +02:00
parent e7f9022dfb
commit eb5a3e1a76
11 changed files with 205 additions and 161 deletions

View File

@@ -1,16 +1,16 @@
package de.nicolasklier.custom_structures.structures;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.Set;
import org.spongepowered.noise.module.source.Perlin;
import de.nicolasklier.custom_structures.CustomStructures;
import de.nicolasklier.custom_structures.events.PlayerTick;
import de.nicolasklier.custom_structures.utils.PerlinNoise;
import net.minecraft.block.Block;
import net.minecraft.block.BlockState;
import net.minecraft.block.Blocks;
@@ -19,7 +19,6 @@ import net.minecraft.client.MinecraftClient;
import net.minecraft.state.property.Properties;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Direction;
import net.minecraft.util.math.Direction.Axis;
public class Generations {
@@ -38,53 +37,106 @@ public class Generations {
int length = options.height * options.stretch * (options.mirror ? 2 : 1);
Random rng = new Random();
PerlinNoise noise = null;
Perlin noise = null;
int minecartTrackPosition = options.minecartTrack
&& options.width > 2
&& options.weight > 2
? options.width / 2
: 0;
int minecartRedstoneTorchStep = 0;
int y = -(options.weight);
int step = 0;
if (options.noise != null) {
noise = new PerlinNoise(rng, options.noise.roughness, length, length);
noise.initialise();
noise = new Perlin();
noise.setSeed(rng.nextInt());
noise.setOctaveCount(3);
noise.setFrequency(0.3);
noise.setPersistence(0.3);
}
// Final length is height times stretch factor. If mirroring is enabled, then it will be twice as long.
int x = 0;
boolean isMirroring = y > options.height * options.stretch;
boolean reachedTop = false;
// Very dangerous. But since we use noise to control the stretch of the staircase we cannot know how long it will be at the end.
while (true) {
x++;
if (step >= options.stretch) {
step = 0;
// Check if we already reached our final height. If yes, go downwards
if (isMirroring) {
y -= 1;
} else {
y++;
boolean isMirroring = y > options.height && options.mirror || reachedTop;
if (isMirroring) {
reachedTop = true;
}
// Break conditions
if (isMirroring && y <= -options.weight) {
break;
}
if (!options.mirror && y >= options.height) {
break;
}
if (noise != null) {
// In 20% of all cases the y-level shouldn't change.
if (noise.get(x, 0, 0) < options.noise.threshold) {
if (isMirroring) y--;
else y++;
}
System.out.println("Noise: " + noise.get(x, 0, 0) + " | X: " + x + " Y: " + y);
} else {
if (step >= options.stretch) {
step = 0;
// Check if we already reached our final height. If yes, go downwards
if (isMirroring) {
y--;
} else {
y++;
}
}
}
for (int z = 0; z < options.width; z++) {
boolean isNextHeight = true;
boolean isNextHeight = false;
if (options.stretch > 1) {
if (noise != null) {
if (isMirroring) {
isNextHeight = step == 0;
if (noise.get(x, 0, 0) < options.noise.threshold) {
isNextHeight = true;
}
} else {
isNextHeight = step + 1 == options.stretch;
if (noise.get(x + 1, 0, 0) < options.noise.threshold) {
isNextHeight = true;
}
}
} else {
if (options.stretch > 1) {
if (isMirroring) {
isNextHeight = step == 0;
} else {
isNextHeight = step + 1 == options.stretch;
}
}
}
Block block = Blocks.COBBLESTONE;
// Build supporting fence
if (x % options.fenceVerticalDensity == 0 && y > 0) {
/*if (x % options.fenceVerticalDensity == 0 && y > 0) {
// From left to right
for (int z2 = 0; z2 <= options.width; z2 += (options.width - 1) / options.fenceHorizontalDensity) {
// Place fence manually on ground because the loop below offsets by one.
placeQueue.put(at.add(x + 1, 0, z2), getRandomFance(rng));
int y2 = y - options.weight;
int y2 = y + 2;
while (true) {
break;
Material mat = instance.getServer().getOverworld().getBlockState(new BlockPos(x, y2, z2)).getMaterial();
if (mat == Material.AIR || mat == Material.WATER) {
placeQueue.put(at.add(x, y2, z2), getRandomFance(rng));
@@ -93,18 +145,23 @@ public class Generations {
break;
}
System.out.println("Fence stuff " + y2 + "(" + mat.toString() + ")");
if (y2 <= -64)
break;
y2--;
}
}
}
}*/
boolean putStair = false;
// Decide if there should be mossy cobblestone or glass. If yes, then don't put a stair there.
// Decide if there should be mossy cobblestone or cracked stone. If yes, then don't put a stair there.
if (rng.nextFloat() < options.chanceMossyCobblestone / 100f) {
block = Blocks.MOSSY_COBBLESTONE;
} else if (rng.nextFloat() < options.chanceGlass / 100f) {
block = Blocks.GLASS;
} else if (rng.nextFloat() < options.chanceStoneBricks / 100f) {
block = Blocks.STONE_BRICKS;
} else {
putStair = true;
}
@@ -129,8 +186,8 @@ public class Generations {
if (rng.nextFloat() < options.chanceSlap / 100f) {
placeQueue.put(at.add(x, y + options.weight, z), Blocks.SMOOTH_STONE_SLAB.getDefaultState());
} else {
CustomStructures.LOGGER.info("Noise [" + x + ", " + y + "]: " + noise.getValueAt(x, y + options.weight));
if (noise.getValueAt(x, y + options.weight) < options.chanceWoodStair / 100f) {
//CustomStructures.LOGGER.info("Noise [" + x + ", " + y + ", " + z + "]: " + noise.get(x, y + options.weight, z));
if (noise.get(x, y + options.weight, 0) < options.chanceWoodStair / 100f) {
// Override stair as wood stair, copying the facing.
stairState = Blocks.OAK_STAIRS.getDefaultState()
@@ -146,7 +203,7 @@ public class Generations {
if (rng.nextFloat() < 0.04) {
placeQueue.put(at.add(x, y + options.weight - 1, z), Blocks.GLOWSTONE.getDefaultState());
}
}
}
// Build wall
if ((z == 0 || z == options.width - 1) && options.wallHeight > 0) {
@@ -163,6 +220,21 @@ public class Generations {
.with(Properties.HORIZONTAL_FACING, facing));
}
}
// Minecart rails
if (minecartTrackPosition > 0 && z == minecartTrackPosition) {
System.array
if (minecartRedstoneTorchStep >= 4) {
placeQueue.put(at.add(x, y + options.weight - 2, z), Blocks.REDSTONE_TORCH.getDefaultState());
placeQueue.put(at.add(x, y + options.weight, z), Blocks.POWERED_RAIL.getDefaultState());
minecartRedstoneTorchStep = 0;
} else {
placeQueue.put(at.add(x, y + options.weight, z), Blocks.RAIL.getDefaultState());
}
minecartRedstoneTorchStep++;
}
}
step++;

View File

@@ -6,6 +6,11 @@ public class StaircaseNoiseOptions {
public float roughness = 0.1f;
/**
* Noise value that will change the y-level of the staircase.
*/
public float threshold = 0.7f;
public Random rng = new Random();
}

View File

@@ -42,9 +42,9 @@ public class StaircaseOptions {
public boolean mirror = false;
/**
* Value between 0% and 100% being the chance to spawn glass.
* Value between 0% and 100% being the chance to spawn stone bricks.
*/
public short chanceGlass = 10;
public short chanceStoneBricks = 10;
/**
* Value between 0% and 100% being the chance to spawn glowstone.
@@ -71,4 +71,6 @@ public class StaircaseOptions {
* To disable this feature set it to null.
*/
public StaircaseNoiseOptions noise = null;
public boolean minecartTrack = false;
}