improve constant baking in SamplerFunction

This commit is contained in:
dfsek
2022-05-14 14:19:49 -07:00
parent cc9c7870ba
commit 2abf809d0f
2 changed files with 87 additions and 26 deletions

View File

@@ -0,0 +1,58 @@
package com.dfsek.terra.addons.terrascript.sampler;
import com.dfsek.terra.addons.terrascript.parser.lang.ImplementationArguments;
import com.dfsek.terra.addons.terrascript.parser.lang.Returnable;
import com.dfsek.terra.addons.terrascript.parser.lang.Scope;
import com.dfsek.terra.addons.terrascript.parser.lang.functions.Function;
import com.dfsek.terra.addons.terrascript.script.TerraImplementationArguments;
import com.dfsek.terra.addons.terrascript.tokenizer.Position;
import com.dfsek.terra.api.noise.NoiseSampler;
public class ConstantSamplerFunction implements Function<Number> {
private final Returnable<Number> x, y, z;
private final NoiseSampler sampler;
private final boolean twoD;
private final Position position;
public ConstantSamplerFunction(NoiseSampler sampler,
Returnable<Number> x,
Returnable<Number> y,
Returnable<Number> z,
boolean twoD,
Position position) {
this.x = x;
this.y = y;
this.z = z;
this.sampler = sampler;
this.twoD = twoD;
this.position = position;
}
@Override
public Number apply(ImplementationArguments implementationArguments, Scope scope) {
TerraImplementationArguments arguments = (TerraImplementationArguments) implementationArguments;
double x = this.x.apply(implementationArguments, scope).doubleValue();
double z = this.z.apply(implementationArguments, scope).doubleValue();
if(twoD) {
return sampler.noise(arguments.getWorld().getSeed(), x, z);
} else {
double y = this.y.apply(implementationArguments, scope).doubleValue();
return sampler.noise(arguments.getWorld().getSeed(), x, y, z);
}
}
@Override
public Position getPosition() {
return position;
}
@Override
public ReturnType returnType() {
return ReturnType.NUMBER;
}
}

View File

@@ -17,7 +17,7 @@ import com.dfsek.terra.addons.terrascript.tokenizer.Position;
import com.dfsek.terra.api.noise.NoiseSampler;
public class SamplerFunctionBuilder implements FunctionBuilder<SamplerFunction> {
public class SamplerFunctionBuilder implements FunctionBuilder<com.dfsek.terra.addons.terrascript.parser.lang.functions.Function<Number>> {
private final Map<String, DimensionApplicableNoiseSampler> samplers2d;
private final Map<String, DimensionApplicableNoiseSampler> samplers3d;
@@ -36,41 +36,44 @@ public class SamplerFunctionBuilder implements FunctionBuilder<SamplerFunction>
@SuppressWarnings("unchecked")
@Override
public SamplerFunction build(List<Returnable<?>> argumentList, Position position) {
Function<Supplier<String>, NoiseSampler> function;
public com.dfsek.terra.addons.terrascript.parser.lang.functions.Function<Number> build(List<Returnable<?>> argumentList, Position position) {
Returnable<String> arg = (Returnable<String>) argumentList.get(0);
if(argumentList.size() == 3) { // 2D
if(arg instanceof StringConstant constant) {
NoiseSampler sampler = Objects.requireNonNull(samplers2d.get(constant.getConstant()),
"No such 2D noise function " + constant.getConstant()).getSampler();
function = s -> sampler;
return new ConstantSamplerFunction(Objects.requireNonNull(samplers2d.get(constant.getConstant()), "No such 2D noise function " + constant.getConstant()).getSampler(),
(Returnable<Number>) argumentList.get(1),
new NumericConstant(0, position),
(Returnable<Number>) argumentList.get(2),
true,
position);
} else {
function = s -> Objects.requireNonNull(samplers2d.get(s.get()), "No such 2D noise function " + s.get()).getSampler();
return new SamplerFunction((Returnable<String>) argumentList.get(0),
(Returnable<Number>) argumentList.get(1),
new NumericConstant(0, position),
(Returnable<Number>) argumentList.get(2),
s -> Objects.requireNonNull(samplers2d.get(s.get()), "No such 2D noise function " + s.get()).getSampler(),
true,
position);
}
return new SamplerFunction((Returnable<String>) argumentList.get(0),
(Returnable<Number>) argumentList.get(1),
new NumericConstant(0, position),
(Returnable<Number>) argumentList.get(2),
function,
true,
position);
} else { // 3D
if(arg instanceof StringConstant constant) {
NoiseSampler sampler = Objects.requireNonNull(samplers3d.get(constant.getConstant()),
"No such 3D noise function " + constant.getConstant()).getSampler();
function = s -> sampler;
return new ConstantSamplerFunction(Objects.requireNonNull(samplers3d.get(constant.getConstant()), "No such 2D noise function " + constant.getConstant()).getSampler(),
(Returnable<Number>) argumentList.get(1),
(Returnable<Number>) argumentList.get(2),
(Returnable<Number>) argumentList.get(3),
true,
position);
} else {
function = s -> Objects.requireNonNull(samplers3d.get(s.get()), "No such 3D noise function " + s.get()).getSampler();
return new SamplerFunction((Returnable<String>) argumentList.get(0),
(Returnable<Number>) argumentList.get(1),
(Returnable<Number>) argumentList.get(2),
(Returnable<Number>) argumentList.get(3),
s -> Objects.requireNonNull(samplers2d.get(s.get()), "No such 2D noise function " + s.get()).getSampler(),
true,
position);
}
return new SamplerFunction((Returnable<String>) argumentList.get(0),
(Returnable<Number>) argumentList.get(1),
(Returnable<Number>) argumentList.get(2),
(Returnable<Number>) argumentList.get(3),
function,
false,
position);
}
}