diff --git a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/LayeredChunkGeneratorAddon.java b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/LayeredChunkGeneratorAddon.java index aa502eb58..956d85784 100644 --- a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/LayeredChunkGeneratorAddon.java +++ b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/LayeredChunkGeneratorAddon.java @@ -19,11 +19,14 @@ import com.dfsek.terra.addons.chunkgenerator.config.palette.SimpleLayerPaletteTe import com.dfsek.terra.addons.chunkgenerator.config.predicate.BelowLayerPredicateTemplate; import com.dfsek.terra.addons.chunkgenerator.config.predicate.RangeLayerPredicateTemplate; import com.dfsek.terra.addons.chunkgenerator.config.predicate.SamplerLayerPredicateTemplate; +import com.dfsek.terra.addons.chunkgenerator.config.predicate.SamplerListLayerPredicateTemplate; import com.dfsek.terra.addons.chunkgenerator.config.resolve.PaletteLayerResolverTemplate; import com.dfsek.terra.addons.chunkgenerator.config.resolve.PredicateLayerResolverTemplate; import com.dfsek.terra.addons.chunkgenerator.config.sampler.SimpleLayerSamplerTemplate; import com.dfsek.terra.addons.chunkgenerator.generation.LayeredChunkGenerator; import com.dfsek.terra.addons.chunkgenerator.layer.palette.BiomeDefinedLayerPalette; +import com.dfsek.terra.addons.chunkgenerator.layer.predicate.SamplerLayerPredicate; +import com.dfsek.terra.addons.chunkgenerator.layer.predicate.SamplerListLayerPredicate.CoordinateTest; import com.dfsek.terra.addons.chunkgenerator.util.InstanceWrapper; import com.dfsek.terra.addons.manifest.api.AddonInitializer; import com.dfsek.terra.api.Platform; @@ -98,6 +101,12 @@ public class LayeredChunkGeneratorAddon implements AddonInitializer { predicateTypeRegistry.register(addon.key("BELOW"), BelowLayerPredicateTemplate::new); predicateTypeRegistry.register(addon.key("RANGE"), RangeLayerPredicateTemplate::new); predicateTypeRegistry.register(addon.key("SAMPLER"), SamplerLayerPredicateTemplate::new); + predicateTypeRegistry.register(addon.key("SAMPLER_LIST"), SamplerListLayerPredicateTemplate::new); + + event.getPack().applyLoader(CoordinateTest.class, CoordinateTest.Template::new) + .applyLoader(SamplerLayerPredicate.Operator.class, + (type, o, loader, depthTracker) -> SamplerLayerPredicate.Operator.valueOf((String) o)); + CheckedRegistry> predicateRegistry = event.getPack().getOrCreateRegistry(LAYER_PREDICATE_TOKEN); event.loadTemplate(new LayerPredicatePackConfigTemplate()).getPredicates().forEach((key, predicate) -> { predicateRegistry.register(addon.key(key), new InstanceWrapper<>(predicate)); diff --git a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/config/predicate/SamplerLayerPredicateTemplate.java b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/config/predicate/SamplerLayerPredicateTemplate.java index 93265156d..63a6fe4da 100644 --- a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/config/predicate/SamplerLayerPredicateTemplate.java +++ b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/config/predicate/SamplerLayerPredicateTemplate.java @@ -7,6 +7,7 @@ import com.dfsek.tectonic.api.config.template.object.ObjectTemplate; import com.dfsek.terra.addons.chunkgenerator.api.LayerPredicate; import com.dfsek.terra.addons.chunkgenerator.api.LayerSampler; import com.dfsek.terra.addons.chunkgenerator.layer.predicate.SamplerLayerPredicate; +import com.dfsek.terra.addons.chunkgenerator.layer.predicate.SamplerLayerPredicate.Operator; import com.dfsek.terra.addons.chunkgenerator.util.InstanceWrapper; import com.dfsek.terra.api.config.meta.Meta; @@ -20,8 +21,12 @@ public class SamplerLayerPredicateTemplate implements ObjectTemplate { + + @Value("sampler") + private @Meta InstanceWrapper sampler; + + @Value("tests") + private List tests; + + @Value("default-threshold") + @Default + private double defaultThreshold = 0; + + @Value("default-operator") + @Default + private Operator defaultOperator = Operator.GreaterThan; + + @Override + public LayerPredicate get() { + return new SamplerListLayerPredicate(sampler.get(), defaultOperator, tests); + } +} diff --git a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerLayerPredicate.java b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerLayerPredicate.java index 632205420..27fd6d886 100644 --- a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerLayerPredicate.java +++ b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerLayerPredicate.java @@ -11,13 +11,57 @@ public class SamplerLayerPredicate implements LayerPredicate { private final double threshold; - public SamplerLayerPredicate(LayerSampler sampler, double threshold) { + private final Operator operator; + + public SamplerLayerPredicate(LayerSampler sampler, Operator operator, double threshold) { this.sampler = sampler; + this.operator = operator; this.threshold = threshold; } @Override public boolean test(long seed, Biome biome, int x, int y, int z) { - return sampler.sample(seed, biome, x, y, z) > threshold; + return operator.evaluate(sampler.sample(seed, biome, x, y, z), threshold); + } + + public enum Operator { + GreaterThan { + @Override + public boolean evaluate(double a, double b) { + return a > b; + } + }, + GreaterThanOrEqual { + @Override + public boolean evaluate(double a, double b) { + return a >= b; + } + }, + LessThan { + @Override + public boolean evaluate(double a, double b) { + return a < b; + } + }, + LessThanOrEqual { + @Override + public boolean evaluate(double a, double b) { + return a <= b; + } + }, + Equals { + @Override + public boolean evaluate(double a, double b) { + return a == b; + } + }, + NotEquals { + @Override + public boolean evaluate(double a, double b) { + return a != b; + } + }; + + public abstract boolean evaluate(double a, double b); } } diff --git a/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerListLayerPredicate.java b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerListLayerPredicate.java new file mode 100644 index 000000000..6735c3310 --- /dev/null +++ b/common/addons/chunk-generator-layered/src/main/java/com/dfsek/terra/addons/chunkgenerator/layer/predicate/SamplerListLayerPredicate.java @@ -0,0 +1,58 @@ +package com.dfsek.terra.addons.chunkgenerator.layer.predicate; + +import com.dfsek.tectonic.api.config.template.annotations.Default; +import com.dfsek.tectonic.api.config.template.annotations.Value; +import com.dfsek.tectonic.api.config.template.object.ObjectTemplate; + +import java.util.List; + +import com.dfsek.terra.addons.chunkgenerator.api.LayerPredicate; +import com.dfsek.terra.addons.chunkgenerator.api.LayerSampler; +import com.dfsek.terra.addons.chunkgenerator.layer.predicate.SamplerLayerPredicate.Operator; +import com.dfsek.terra.api.world.biome.Biome; + + +public class SamplerListLayerPredicate implements LayerPredicate { + + private final List tests; + private final Operator operator; + private final LayerSampler sampler; + + public SamplerListLayerPredicate(LayerSampler sampler, Operator operator, List tests) { + this.sampler = sampler; + this.operator = operator; + this.tests = tests; + } + + @Override + public boolean test(long seed, Biome biome, int x, int y, int z) { + for (CoordinateTest test : tests) { + if (operator.evaluate(sampler.sample(seed, biome, x + test.x, y + test.y, z + test.z), test.threshold)) return true; + } + return false; + } + + public record CoordinateTest(int x, int y, int z, double threshold) { + + public static class Template implements ObjectTemplate { + + @Value("x") + private int x; + + @Value("y") + private int y; + + @Value("z") + private int z; + + @Value("threshold") + @Default + private double threshold = 0; + + @Override + public CoordinateTest get() { + return new CoordinateTest(x, y, z, threshold); + } + } + } +}