package com.hypixel.hytale.procedurallib.condition;
import com.hypixel.hytale.procedurallib.property.NoiseProperty;
import java.util.Arrays;
import javax.annotation.Nonnull;
public class NoiseHeightThresholdInterpreter implements IHeightThresholdInterpreter {
protected final NoiseProperty noise;
@Nonnull
protected final float[] keys;
@Nonnull
protected final IHeightThresholdInterpreter[] values;
protected final int length;
protected final int lowestNonOne;
protected final int highestNonZero;
public NoiseHeightThresholdInterpreter(NoiseProperty noise, @Nonnull float[] keys, @Nonnull IHeightThresholdInterpreter[] values) {
if (keys.length != values.length) {
throw new IllegalStateException("Length of keys and values are different!");
} else {
checkInterpreterLength(values);
this.noise = noise;
this.keys = keys;
this.values = values;
this.length = values[0].getLength();
int lowestNonOne = 0;
for(IHeightThresholdInterpreter value : values) {
if (value.getLowestNonOne() < lowestNonOne) {
lowestNonOne = value.getLowestNonOne();
}
}
this.lowestNonOne = lowestNonOne;
int highestNonZero = this.length - 1;
for(IHeightThresholdInterpreter value : values) {
if (value.getHighestNonZero() > highestNonZero) {
highestNonZero = value.getHighestNonZero();
}
}
this.highestNonZero = highestNonZero;
}
}
public int getLowestNonOne() {
return this.lowestNonOne;
}
public int getHighestNonZero() {
return this.highestNonZero;
}
protected double noise(int seed, double x, double y) {
return this.noise.get(seed, x, y);
}
public double getContext(int seed, double x, double y) {
return this.noise(seed, x, y);
}
public int getLength() {
return this.length;
}
public float getThreshold(int seed, double x, double z, int height) {
return this.getThreshold(seed, x, z, height, this.getContext(seed, x, z));
}
public float getThreshold(int seed, double x, double z, int height, double context) {
if (height > this.highestNonZero) {
return 0.0F;
} else {
int length = this.keys.length;
for(int i = 0; i < length; ++i) {
if (context <= (double)this.keys[i]) {
if (i == 0) {
return this.values[0].getThreshold(seed, x, z, height);
}
float distance = ((float)context - this.keys[i - 1]) / (this.keys[i] - this.keys[i - 1]);
return IHeightThresholdInterpreter.lerp(this.values[i - 1].getThreshold(seed, x, z, height), this.values[i].getThreshold(seed, x, z, height), distance);
}
}
return this.values[length - 1].getThreshold(seed, x, z, height);
}
}
static float lerp(float from, float to, float t) {
return from + (to - from) * t;
}
private static void checkInterpreterLength(@Nonnull IHeightThresholdInterpreter[] values) {
int length = values[0].getLength();
for(int i = 1; i < values.length; ++i) {
if (values[i].getLength() != length) {
throw new IllegalStateException("ThresholdKeyInterpreter have different size!");
}
}
}
@Nonnull
public String toString() {
String var10000 = String.valueOf(this.noise);
return "NoiseHeightThresholdInterpreter{noise=" + var10000 + ", keys=" + Arrays.toString(this.keys) + ", values=" + Arrays.toString(this.values) + ", length=" + this.length + ", lowestNonOne=" + this.lowestNonOne + ", highestNonZero=" + this.highestNonZero + "}";
}
}