Implement simplex mask (fixes #437)

This commit is contained in:
Hannes Greule 2020-07-04 17:31:59 +02:00
parent 704e76eb6d
commit ed6f3e7b4a
4 changed files with 77 additions and 29 deletions

View File

@ -69,7 +69,7 @@ public final class MaskFactory extends AbstractFactory<Mask> {
register(new XAxisMaskParser(worldEdit));
register(new YAxisMaskParser(worldEdit));
register(new ZAxisMaskParser(worldEdit));
register(new SimplexMaskParser(worldEdit));
}

View File

@ -1,6 +1,5 @@
package com.sk89q.worldedit.extension.factory.parser;
import com.sk89q.util.StringUtil;
import com.sk89q.worldedit.WorldEdit;
import com.sk89q.worldedit.extension.input.InputParseException;
import com.sk89q.worldedit.extension.input.ParserContext;
@ -115,4 +114,40 @@ public abstract class RichParser<E> extends InputParser<E> {
}
return arguments.toArray(new String[0]);
}
/**
* Returns a stream of suggestions for positive doubles.
*
* @param argumentInput the given input to filter with.
* @return a stream of suggestions.
*/
protected Stream<String> suggestPositiveDoubles(String argumentInput) {
if (argumentInput.isEmpty()) {
return Stream.of("1", "2", "3", "4", "5", "6", "7", "8", "9");
}
// if already a valid number, suggest more digits
if (isDouble(argumentInput)) {
Stream<String> numbers = Stream.of("", "0", "1", "2", "3", "4", "5", "6", "7", "8", "9");
if (argumentInput.indexOf('.') == -1) {
numbers = Stream.concat(numbers, Stream.of("."));
}
return numbers.map(s -> argumentInput + s);
}
// no valid input anymore
return Stream.empty();
}
private static boolean isDouble(String input) {
boolean point = false;
for (char c : input.toCharArray()) {
if (!Character.isDigit(c)) {
if (c == '.' && !point) {
point = true;
} else {
return false;
}
}
}
return true;
}
}

View File

@ -0,0 +1,39 @@
package com.sk89q.worldedit.extension.factory.parser.mask;
import com.boydti.fawe.object.mask.SimplexMask;
import com.sk89q.worldedit.WorldEdit;
import com.sk89q.worldedit.extension.factory.parser.RichParser;
import com.sk89q.worldedit.extension.input.InputParseException;
import com.sk89q.worldedit.extension.input.ParserContext;
import com.sk89q.worldedit.function.mask.Mask;
import org.jetbrains.annotations.NotNull;
import java.util.stream.Stream;
public class SimplexMaskParser extends RichParser<Mask> {
private static final String SIMPLEX_PREFIX = "#simplex";
public SimplexMaskParser(WorldEdit worldEdit) {
super(worldEdit, SIMPLEX_PREFIX);
}
@Override
protected Stream<String> getSuggestions(String argumentInput, int index) {
if (index < 3) {
suggestPositiveDoubles(argumentInput);
}
return Stream.empty();
}
@Override
protected Mask parseFromInput(@NotNull String[] arguments, ParserContext context) throws InputParseException {
if (arguments.length != 3) return null;
double scale = Double.parseDouble(arguments[0]);
double min = Double.parseDouble(arguments[1]);
double max = Double.parseDouble(arguments[2]);
scale = 1d / Math.max(1d, scale);
min = (min - 50d) / 50d;
max = (max - 50d) / 50d;
return new SimplexMask(scale, min, max);
}
}

View File

@ -22,19 +22,7 @@ public class SimplexPatternParser extends RichParser<Pattern> {
@Override
protected Stream<String> getSuggestions(String argumentInput, int index) {
if (index == 0) {
if (argumentInput.isEmpty()) {
return Stream.of("1", "2", "3", "4", "5", "6", "7", "8", "9");
}
// if already a valid number, suggest more digits
if (isDouble(argumentInput)) {
Stream<String> numbers = Stream.of("", "0", "1", "2", "3", "4", "5", "6", "7", "8", "9");
if (argumentInput.indexOf('.') == -1) {
numbers = Stream.concat(numbers, Stream.of("."));
}
return numbers.map(s -> argumentInput + s);
}
// no valid input anymore
return Stream.empty();
return suggestPositiveDoubles(argumentInput);
}
if (index == 1) {
return worldEdit.getPatternFactory().getSuggestions(argumentInput).stream();
@ -58,18 +46,4 @@ public class SimplexPatternParser extends RichParser<Pattern> {
throw new InputParseException("Pattern " + inner.getClass().getSimpleName() + " cannot be used with #simplex");
}
}
private static boolean isDouble(String input) {
boolean point = false;
for (char c : input.toCharArray()) {
if (!Character.isDigit(c)) {
if (c == '.' && !point) {
point = true;
} else {
return false;
}
}
}
return true;
}
}