Different island terrain (WIP)

This commit is contained in:
paulevsGitch 2021-03-28 20:04:52 +03:00
parent 83f4f923b1
commit 21358808e4
3 changed files with 90 additions and 4 deletions

View file

@ -0,0 +1,59 @@
package ru.betterend.util.sdf.operator;
import net.minecraft.client.texture.NativeImage;
import net.minecraft.util.math.MathHelper;
public class SDFHeightmap extends SDFDisplacement {
private float intensity = 1F;
private NativeImage map;
private float offsetX;
private float offsetZ;
private float angle;
private float scale;
public SDFHeightmap() {
setFunction((pos) -> {
if (map == null) {
return 0F;
}
float dx = MathHelper.clamp(pos.getX() * scale + offsetX, 0, map.getWidth() - 2);
float dz = MathHelper.clamp(pos.getZ() * scale + offsetZ, 0, map.getHeight() - 2);
int x1 = MathHelper.floor(dx);
int z1 = MathHelper.floor(dz);
int x2 = x1 + 1;
int z2 = z1 + 1;
dx = dx - x1;
dz = dz - z1;
float a = (map.getPixelColor(x1, z1) & 255) / 255F;
float b = (map.getPixelColor(x2, z1) & 255) / 255F;
float c = (map.getPixelColor(x1, z2) & 255) / 255F;
float d = (map.getPixelColor(x2, z2) & 255) / 255F;
a = MathHelper.lerp(dx, a, b);
b = MathHelper.lerp(dx, c, d);
return -MathHelper.lerp(dz, a, b) * intensity;
});
}
public SDFHeightmap setMap(NativeImage map) {
this.map = map;
offsetX = map.getWidth() * 0.5F;
offsetZ = map.getHeight() * 0.5F;
scale = map.getWidth();
return this;
}
public SDFHeightmap setAngle(float angle) {
this.angle = angle;
return this;
}
public SDFHeightmap setScale(float scale) {
this.scale = map.getWidth() * scale;
return this;
}
public SDFHeightmap setIntensity(float intensity) {
this.intensity = intensity;
return this;
}
}

View file

@ -1,5 +1,7 @@
package ru.betterend.world.generator; package ru.betterend.world.generator;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
@ -8,10 +10,13 @@ import java.util.Random;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import com.google.common.collect.Maps; import com.google.common.collect.Maps;
import net.minecraft.client.texture.NativeImage;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import ru.betterend.BetterEnd;
import ru.betterend.noise.OpenSimplexNoise; import ru.betterend.noise.OpenSimplexNoise;
import ru.betterend.util.MHelper; import ru.betterend.util.MHelper;
import ru.betterend.util.sdf.SDF; import ru.betterend.util.sdf.SDF;
import ru.betterend.util.sdf.operator.SDFHeightmap;
import ru.betterend.util.sdf.operator.SDFScale; import ru.betterend.util.sdf.operator.SDFScale;
import ru.betterend.util.sdf.operator.SDFSmoothUnion; import ru.betterend.util.sdf.operator.SDFSmoothUnion;
import ru.betterend.util.sdf.operator.SDFTranslate; import ru.betterend.util.sdf.operator.SDFTranslate;
@ -19,7 +24,7 @@ import ru.betterend.util.sdf.primitive.SDFCappedCone;
public class IslandLayer { public class IslandLayer {
private static final Random RANDOM = new Random(); private static final Random RANDOM = new Random();
private static final SDF ISLAND; private static final SDF[] ISLAND;
private final List<BlockPos> positions = new ArrayList<BlockPos>(9); private final List<BlockPos> positions = new ArrayList<BlockPos>(9);
private final Map<BlockPos, SDF> islands = Maps.newHashMap(); private final Map<BlockPos, SDF> islands = Maps.newHashMap();
@ -86,11 +91,11 @@ public class IslandLayer {
SDF island = islands.get(pos); SDF island = islands.get(pos);
if (island == null) { if (island == null) {
if (pos.getX() == 0 && pos.getZ() == 0) { if (pos.getX() == 0 && pos.getZ() == 0) {
island = new SDFScale().setScale(1.3F).setSource(ISLAND); island = new SDFScale().setScale(1.3F).setSource(ISLAND[0]);
} }
else { else {
RANDOM.setSeed(getSeed(pos.getX(), pos.getZ())); RANDOM.setSeed(getSeed(pos.getX(), pos.getZ()));
island = new SDFScale().setScale(RANDOM.nextFloat() + 0.5F).setSource(ISLAND); island = new SDFScale().setScale(RANDOM.nextFloat() + 0.5F).setSource(ISLAND[0]);
} }
islands.put(pos, island); islands.put(pos, island);
} }
@ -130,7 +135,24 @@ public class IslandLayer {
return new SDFTranslate().setTranslate(0, minY + hh, 0).setSource(sdf); return new SDFTranslate().setTranslate(0, minY + hh, 0).setSource(sdf);
} }
private static NativeImage loadMap(String path) {
InputStream stream = IslandLayer.class.getResourceAsStream(path);
if (stream != null) {
try {
NativeImage map = NativeImage.read(stream);
stream.close();
return map;
}
catch (IOException e) {
BetterEnd.LOGGER.warning(e.getMessage());
}
}
return null;
}
static { static {
NativeImage map = loadMap("/assets/" + BetterEnd.MOD_ID + "/textures/heightmaps/mountain_1.png");
SDF cone1 = makeCone(0, 0.4F, 0.2F, -0.3F); SDF cone1 = makeCone(0, 0.4F, 0.2F, -0.3F);
SDF cone2 = makeCone(0.4F, 0.5F, 0.1F, -0.1F); SDF cone2 = makeCone(0.4F, 0.5F, 0.1F, -0.1F);
SDF cone3 = makeCone(0.5F, 0.45F, 0.03F, 0.0F); SDF cone3 = makeCone(0.5F, 0.45F, 0.03F, 0.0F);
@ -139,6 +161,11 @@ public class IslandLayer {
SDF coneBottom = new SDFSmoothUnion().setRadius(0.02F).setSourceA(cone1).setSourceB(cone2); SDF coneBottom = new SDFSmoothUnion().setRadius(0.02F).setSourceA(cone1).setSourceB(cone2);
SDF coneTop = new SDFSmoothUnion().setRadius(0.02F).setSourceA(cone3).setSourceB(cone4); SDF coneTop = new SDFSmoothUnion().setRadius(0.02F).setSourceA(cone3).setSourceB(cone4);
ISLAND = new SDFSmoothUnion().setRadius(0.01F).setSourceA(coneTop).setSourceB(coneBottom); SDF map1 = new SDFHeightmap().setMap(map).setIntensity(0.3F).setSource(coneTop);
ISLAND = new SDF[] {
new SDFSmoothUnion().setRadius(0.01F).setSourceA(coneTop).setSourceB(coneBottom),
new SDFSmoothUnion().setRadius(0.01F).setSourceA(map1).setSourceB(coneBottom)
};
} }
} }

Binary file not shown.

After

Width:  |  Height:  |  Size: 19 KiB