Iris is 50%-200% faster & now has timings

This commit is contained in:
Daniel Mills
2020-01-21 07:45:20 -05:00
parent 31c2ea888b
commit f6780fcb76
14 changed files with 467 additions and 54 deletions

View File

@@ -6,10 +6,13 @@ import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Biome;
import org.bukkit.generator.ChunkGenerator.BiomeGrid;
import org.bukkit.generator.ChunkGenerator.ChunkData;
import org.bukkit.util.NumberConversions;
import mortar.util.text.C;
import ninja.bytecode.iris.Iris;
import ninja.bytecode.iris.IrisMetrics;
import ninja.bytecode.iris.controller.PackController;
import ninja.bytecode.iris.generator.atomics.AtomicChunkData;
import ninja.bytecode.iris.generator.genobject.GenObjectDecorator;
@@ -25,11 +28,14 @@ import ninja.bytecode.iris.generator.parallax.ParallaxWorldGenerator;
import ninja.bytecode.iris.pack.BiomeType;
import ninja.bytecode.iris.pack.CompiledDimension;
import ninja.bytecode.iris.pack.IrisBiome;
import ninja.bytecode.iris.pack.IrisDimension;
import ninja.bytecode.iris.pack.IrisRegion;
import ninja.bytecode.iris.util.ChunkPlan;
import ninja.bytecode.iris.util.InterpolationMode;
import ninja.bytecode.iris.util.IrisInterpolation;
import ninja.bytecode.iris.util.MB;
import ninja.bytecode.iris.util.SChunkVector;
import ninja.bytecode.shuriken.bench.PrecisionStopwatch;
import ninja.bytecode.shuriken.collections.GList;
import ninja.bytecode.shuriken.logging.L;
import ninja.bytecode.shuriken.math.CNG;
@@ -74,14 +80,24 @@ public class IrisGenerator extends ParallaxWorldGenerator
private GenLayerCliffs glCliffs;
private RNG rTerrain;
private CompiledDimension dim;
private IrisMetrics metrics = new IrisMetrics(0, 512);
private int objectHits;
public IrisGenerator()
{
this(Iris.getController(PackController.class).getDimension("overworld"));
}
public void hitObject()
{
objectHits++;
}
public IrisGenerator(CompiledDimension dim)
{
objectHits = 0;
CNG.hits = 0;
CNG.creates = 0;
this.dim = dim;
disposed = false;
L.i("Preparing Dimension: " + dim.getName() + " With " + dim.getBiomes().size() + " Biomes...");
@@ -147,6 +163,7 @@ public class IrisGenerator extends ParallaxWorldGenerator
public IrisBiome getBiome(int wxx, int wzx)
{
PrecisionStopwatch c = getMetrics().start();
IrisBiome biome = glBiome.getBiome(wxx, wzx);
IrisBiome real = glBiome.getBiome(wxx, wzx, true);
boolean frozen = getRegion(biome) != null ? getRegion(biome).isFrozen() : false;
@@ -157,10 +174,22 @@ public class IrisGenerator extends ParallaxWorldGenerator
biome = height > 61 && height < 65 ? frozen ? biome : getBeach(real) : biome;
biome = height > 63 && biome.getType().equals(BiomeType.FLUID) ? getBeach(real) : biome;
biome = height >= beach && !biome.getType().equals(BiomeType.LAND) ? real : biome;
getMetrics().stop("biome:ms:x256:/terrain:..", c);
return biome;
}
public ChunkData generateChunkData(World world, Random random, int x, int z, BiomeGrid biome)
{
PrecisionStopwatch s = getMetrics().start();
ChunkData d = super.generateChunkData(world, random, x, z, biome);
getMetrics().stop("chunk:ms", s);
getMetrics().put("noise-hits", CNG.hits);
metrics.setGenerators((int) CNG.creates);
CNG.hits = 0;
return d;
}
public IrisBiome biome(String name)
{
return getDimension().getBiomeByName(name);
@@ -176,6 +205,11 @@ public class IrisGenerator extends ParallaxWorldGenerator
return Math.round((double) z * (Iris.settings.gen.horizontalZoom / 1.90476190476));
}
public IrisMetrics getMetrics()
{
return metrics;
}
public IrisBiome getOcean(IrisBiome biome, int height)
{
IrisRegion region = glBiome.getRegion(biome.getRegion());
@@ -221,9 +255,39 @@ public class IrisGenerator extends ParallaxWorldGenerator
return (int) Math.round(M.clip(getANoise((int) x, (int) z, plan, biome), 0D, 1D) * 253);
}
public double getInterpolation(int x, int z, ChunkPlan plan)
{
PrecisionStopwatch s = getMetrics().start();
double d = 0;
InterpolationMode m = Iris.settings.gen.interpolationMode;
if(m.equals(InterpolationMode.BILINEAR))
{
d = IrisInterpolation.getBilinearNoise(x, z, Iris.settings.gen.interpolationRadius, (xf, zf) -> getBiomedHeight((int) Math.round(xf), (int) Math.round(zf), plan));
}
else if(m.equals(InterpolationMode.BICUBIC))
{
d = IrisInterpolation.getBicubicNoise(x, z, Iris.settings.gen.interpolationRadius, (xf, zf) -> getBiomedHeight((int) Math.round(xf), (int) Math.round(zf), plan));
}
else if(m.equals(InterpolationMode.HERMITE_BICUBIC))
{
d = IrisInterpolation.getHermiteNoise(x, z, Iris.settings.gen.interpolationRadius, (xf, zf) -> getBiomedHeight((int) Math.round(xf), (int) Math.round(zf), plan));
}
else
{
d = getBiomedHeight((int) Math.round(x), (int) Math.round(z), plan);
}
getMetrics().stop("interpolation:ms:x256:/biome:.", s);
return d;
}
public double getANoise(int x, int z, ChunkPlan plan, IrisBiome biome)
{
double hv = !Iris.settings.performance.fastMode ? IrisInterpolation.getNoise(x, z, Iris.settings.gen.hermiteSampleRadius, (xf, zf) -> getBiomedHeight((int) Math.round(xf), (int) Math.round(zf), plan)) : getBiomedHeight((int) Math.round(x), (int) Math.round(z), plan);
double hv = !Iris.settings.performance.fastMode ? getInterpolation(x, z, plan) : getBiomedHeight((int) Math.round(x), (int) Math.round(z), plan);
hv += glLNoise.generateLayer(hv * Iris.settings.gen.roughness * 215, (double) x * Iris.settings.gen.roughness * 0.82, (double) z * Iris.settings.gen.roughness * 0.82) * (1.6918 * (hv * 2.35));
if(biome.hasCliffs())
@@ -244,7 +308,10 @@ public class IrisGenerator extends ParallaxWorldGenerator
{
try
{
PrecisionStopwatch s = getMetrics().start();
god.decorateParallax(x, z, random);
String xx = "x" + getParallaxSize().getX() * getParallaxSize().getZ();
getMetrics().stop("object:" + xx + ":.:ms:/parallax", s);
}
catch(Throwable e)
@@ -253,9 +320,17 @@ public class IrisGenerator extends ParallaxWorldGenerator
}
}
@Override
public Biome onGenColumn(int wxxf, int wzxf, int x, int z, ChunkPlan plan, AtomicChunkData data)
private double getObjectHits()
{
int hits = objectHits;
objectHits = 0;
return hits;
}
@Override
public Biome onGenColumn(int wxxf, int wzxf, int x, int z, ChunkPlan plan, AtomicChunkData data, boolean surfaceOnly)
{
PrecisionStopwatch s = getMetrics().start();
if(disposed)
{
data.setBlock(x, 0, z, Material.MAGENTA_GLAZED_TERRACOTTA);
@@ -274,7 +349,7 @@ public class IrisGenerator extends ParallaxWorldGenerator
int height = computeHeight(wxx, wzx, plan, biome);
int max = Math.max(height, seaLevel);
for(int i = 0; i < max; i++)
for(int i = surfaceOnly ? max > seaLevel ? max - 2 : height - 2 : 0; i < max; i++)
{
MB mb = ROCK.get(scatterInt(wzx, i, wxx, ROCK.size()));
boolean underwater = i >= height && i < seaLevel;
@@ -328,9 +403,22 @@ public class IrisGenerator extends ParallaxWorldGenerator
data.setBlock(x, i, z, mb.material, mb.data);
}
glCaves.genCaves(wxx, wzx, x, z, height, this, data);
getMetrics().stop("terrain:ms:x256:/chunk:..", s);
if(!surfaceOnly)
{
PrecisionStopwatch c = getMetrics().start();
glCaves.genCaves(wxx, wzx, x, z, height, this, data);
getMetrics().stop("caves:ms:x256:/terrain:..", c);
PrecisionStopwatch v = getMetrics().start();
glCaverns.genCaverns(wxx, wzx, x, z, height, this, biome, data);
getMetrics().stop("caverns:ms:x256:/terrain:..", v);
}
PrecisionStopwatch c = getMetrics().start();
glCarving.genCarves(wxx, wzx, x, z, height, this, biome, data);
glCaverns.genCaverns(wxx, wzx, x, z, height, this, biome, data);
getMetrics().stop("carving:ms:x256:/terrain:..", c);
int hw = 0;
int hl = 0;
@@ -344,6 +432,10 @@ public class IrisGenerator extends ParallaxWorldGenerator
plan.setRealHeight(x, z, hl);
plan.setRealWaterHeight(x, z, hw == 0 ? seaLevel : hw);
plan.setBiome(x, z, biome);
double time = s.getMilliseconds() * 256D;
double atime = getMetrics().get("chunk:ms").getAverage();
getMetrics().setParScale(time / atime);
getMetrics().put("objects:,:/parallax", getObjectHits());
return biome.getRealBiome();
}

View File

@@ -123,7 +123,7 @@ public class WorldReactor
{
for(int j = 0; j < 16; j++)
{
gen.onGenColumn((x << 4) + i, (z << 4) + j, i, j, typlan, tydata);
gen.onGenColumn((x << 4) + i, (z << 4) + j, i, j, typlan, tydata, true);
}
}

View File

@@ -281,22 +281,25 @@ public class GenObject
if(!Iris.settings.performance.noObjectFail)
{
Material m = placer.get(f.clone().subtract(0, 1, 0)).material;
if(i.getY() == mountHeight && (m.equals(Material.WATER) || m.equals(Material.STATIONARY_WATER) || m.equals(Material.LAVA) || m.equals(Material.STATIONARY_LAVA)))
if(f.getBlockY() == 63 && i.getY() == mountHeight)
{
for(Location j : undo.k())
{
placer.set(j, undo.get(j));
}
Material m = placer.get(f.clone().subtract(0, 1, 0)).material;
if(Iris.settings.performance.verbose)
if(m.equals(Material.WATER) || m.equals(Material.STATIONARY_WATER) || m.equals(Material.LAVA) || m.equals(Material.STATIONARY_LAVA))
{
L.w(C.WHITE + "Object " + C.YELLOW + getName() + C.WHITE + " failed to place in " + C.YELLOW + m.toString().toLowerCase() + C.WHITE + " at " + C.YELLOW + F.f(f.getBlockX()) + " " + F.f(f.getBlockY()) + " " + F.f(f.getBlockZ()));
}
for(Location j : undo.k())
{
placer.set(j, undo.get(j));
}
failures++;
return null;
if(Iris.settings.performance.verbose)
{
L.w(C.WHITE + "Object " + C.YELLOW + getName() + C.WHITE + " failed to place in " + C.YELLOW + m.toString().toLowerCase() + C.WHITE + " at " + C.YELLOW + F.f(f.getBlockX()) + " " + F.f(f.getBlockY()) + " " + F.f(f.getBlockZ()));
}
failures++;
return null;
}
}
}

View File

@@ -189,6 +189,7 @@ public class GenObjectDecorator
if(start != null)
{
g.hitObject();
if(Iris.settings.performance.verbose)
{
L.v(C.GRAY + "Placed " + C.DARK_GREEN + i.getName() + C.WHITE + "/" + C.DARK_GREEN + go.getName() + C.GRAY + " at " + C.DARK_GREEN + F.f(start.getBlockX()) + " " + F.f(start.getBlockY()) + " " + F.f(start.getBlockZ()));

View File

@@ -16,6 +16,7 @@ import org.bukkit.event.world.WorldUnloadEvent;
import mortar.api.nms.NMP;
import ninja.bytecode.iris.Iris;
import ninja.bytecode.iris.controller.TimingsController;
import ninja.bytecode.iris.generator.IrisGenerator;
import ninja.bytecode.iris.generator.atomics.AtomicChunkData;
import ninja.bytecode.iris.util.ChunkPlan;
import ninja.bytecode.iris.util.IrisWorldData;
@@ -117,7 +118,7 @@ public abstract class ParallaxWorldGenerator extends ParallelChunkGenerator impl
public ParallaxAnchor computeAnchor(int wx, int wz, ChunkPlan heightBuffer, AtomicChunkData data)
{
onGenColumn(wx, wz, wx & 15, wz & 15, heightBuffer, data);
onGenColumn(wx, wz, wx & 15, wz & 15, heightBuffer, data, false);
return new ParallaxAnchor(heightBuffer.getRealHeight(wx & 15, wz & 15), heightBuffer.getRealWaterHeight(wx & 15, wz & 15), heightBuffer.getBiome(wx & 15, wz & 15), data);
}
@@ -125,7 +126,7 @@ public abstract class ParallaxWorldGenerator extends ParallelChunkGenerator impl
public ParallaxAnchor computeAnchor(int wx, int wz)
{
ChunkPlan heightBuffer = new ChunkPlan();
onGenColumn(wx, wz, wx & 15, wz & 15, heightBuffer, buffer);
onGenColumn(wx, wz, wx & 15, wz & 15, heightBuffer, buffer, false);
return new ParallaxAnchor(heightBuffer.getRealHeight(wx & 15, wz & 15), heightBuffer.getRealWaterHeight(wx & 15, wz & 15), heightBuffer.getBiome(wx & 15, wz & 15), buffer);
}
@@ -140,35 +141,40 @@ public abstract class ParallaxWorldGenerator extends ParallelChunkGenerator impl
public final ChunkPlan initChunk(World world, int x, int z, Random random)
{
PrecisionStopwatch ps = PrecisionStopwatch.start();
TaskGroup g = startWork();
int gg = 0;
int gx = 0;
for(int ii = Iris.settings.performance.fastMode ? -1 : -(getParallaxSize().getX() / 2) - 1; ii < (Iris.settings.performance.fastMode ? 1 : ((getParallaxSize().getX() / 2) + 1)); ii++)
TaskGroup g = startWork();
if(Iris.settings.gen.genObjects)
{
int i = ii;
for(int jj = Iris.settings.performance.fastMode ? -1 : -(getParallaxSize().getZ() / 2) - 1; jj < (Iris.settings.performance.fastMode ? 1 : ((getParallaxSize().getZ() / 2) + 1)); jj++)
for(int ii = Iris.settings.performance.fastMode ? -1 : -(getParallaxSize().getX() / 2) - 1; ii < (Iris.settings.performance.fastMode ? 1 : ((getParallaxSize().getX() / 2) + 1)); ii++)
{
gx++;
int j = jj;
int cx = x + i;
int cz = z + j;
int i = ii;
if(!getWorldData().exists(cx, cz))
for(int jj = Iris.settings.performance.fastMode ? -1 : -(getParallaxSize().getZ() / 2) - 1; jj < (Iris.settings.performance.fastMode ? 1 : ((getParallaxSize().getZ() / 2) + 1)); jj++)
{
g.queue(() ->
{
onGenParallax(cx, cz, getRMaster(cx, cz, -59328));
getWorldData().getChunk(cx, cz);
});
gx++;
int j = jj;
int cx = x + i;
int cz = z + j;
gg++;
if(!getWorldData().exists(cx, cz))
{
g.queue(() ->
{
onGenParallax(cx, cz, getRMaster(cx, cz, -59328));
getWorldData().getChunk(cx, cz);
});
gg++;
}
}
}
}
double a = ps.getMilliseconds();
double b = g.execute().timeElapsed;
((IrisGenerator) this).getMetrics().put("parallax:ms:/chunk", ps.getMillis());
if(Iris.settings.performance.verbose)
{
@@ -186,9 +192,9 @@ public abstract class ParallaxWorldGenerator extends ParallelChunkGenerator impl
}
@Override
public final Biome genColumn(int wx, int wz, int x, int z, ChunkPlan plan, AtomicChunkData data)
public final Biome genColumn(int wx, int wz, int x, int z, ChunkPlan plan, AtomicChunkData data, boolean surface)
{
return onGenColumn(wx, wz, x, z, plan, data);
return onGenColumn(wx, wz, x, z, plan, data, surface);
}
public World getWorld()
@@ -221,7 +227,7 @@ public abstract class ParallaxWorldGenerator extends ParallelChunkGenerator impl
public abstract ChunkPlan onInitChunk(World world, int x, int z, Random random);
public abstract Biome onGenColumn(int wx, int wz, int x, int z, ChunkPlan plan, AtomicChunkData data2);
public abstract Biome onGenColumn(int wx, int wz, int x, int z, ChunkPlan plan, AtomicChunkData data, boolean surfaceOnly);
public abstract void onPostChunk(World world, int x, int z, Random random, AtomicChunkData data, ChunkPlan plan);
}

View File

@@ -48,7 +48,7 @@ public abstract class ParallelChunkGenerator extends ChunkGenerator
public Biome generateFullColumn(int a, int b, int c, int d, ChunkPlan p, AtomicChunkData data)
{
return genColumn(a, b, c, d, p, data);
return genColumn(a, b, c, d, p, data, false);
}
public TaskGroup startParallaxWork()
@@ -158,5 +158,5 @@ public abstract class ParallelChunkGenerator extends ChunkGenerator
public abstract void postChunk(World world, int x, int z, Random random, AtomicChunkData data, ChunkPlan plan);
public abstract Biome genColumn(int wx, int wz, int x, int z, ChunkPlan plan, AtomicChunkData data);
public abstract Biome genColumn(int wx, int wz, int x, int z, ChunkPlan plan, AtomicChunkData data, boolean surfaceOnly);
}