From 076825a8144e9868332d20fbc8bb66b04f739add Mon Sep 17 00:00:00 2001 From: Victor Date: Fri, 8 Sep 2017 14:45:43 +0300 Subject: [PATCH] Add strokeDashArray function --- .../hotarufx/bundles/BundleLoader.java | 7 +-- .../hotarufx/bundles/NodeUtilsBundle.java | 53 +++++++++++++++++++ .../com/annimon/hotarufx/lib/ArrayValue.java | 10 +++- .../ui/controller/EditorController.java | 9 +--- app/src/main/resources/fxml/Editor.fxml | 13 +++-- 5 files changed, 75 insertions(+), 17 deletions(-) create mode 100644 app/src/main/java/com/annimon/hotarufx/bundles/NodeUtilsBundle.java diff --git a/app/src/main/java/com/annimon/hotarufx/bundles/BundleLoader.java b/app/src/main/java/com/annimon/hotarufx/bundles/BundleLoader.java index 9bac0b6..7508ec5 100644 --- a/app/src/main/java/com/annimon/hotarufx/bundles/BundleLoader.java +++ b/app/src/main/java/com/annimon/hotarufx/bundles/BundleLoader.java @@ -11,10 +11,11 @@ import lombok.val; public final class BundleLoader { - public static List> allBundles() { + public static List> runtimeBundles() { return Arrays.asList( CompositionBundle.class, - NodesBundle.class + NodesBundle.class, + NodeUtilsBundle.class ); } @@ -24,7 +25,7 @@ public final class BundleLoader { public static Map functions() { val functions = new HashMap(); - apply(allBundles(), functions, ((bundle, map) -> map.putAll(bundle.functions()))); + apply(runtimeBundles(), functions, ((bundle, map) -> map.putAll(bundle.functions()))); return functions; } diff --git a/app/src/main/java/com/annimon/hotarufx/bundles/NodeUtilsBundle.java b/app/src/main/java/com/annimon/hotarufx/bundles/NodeUtilsBundle.java new file mode 100644 index 0000000..a8f67e7 --- /dev/null +++ b/app/src/main/java/com/annimon/hotarufx/bundles/NodeUtilsBundle.java @@ -0,0 +1,53 @@ +package com.annimon.hotarufx.bundles; + +import com.annimon.hotarufx.exceptions.TypeException; +import com.annimon.hotarufx.lib.ArrayValue; +import com.annimon.hotarufx.lib.Context; +import com.annimon.hotarufx.lib.Function; +import com.annimon.hotarufx.lib.NumberValue; +import com.annimon.hotarufx.lib.Types; +import com.annimon.hotarufx.lib.Validator; +import com.annimon.hotarufx.lib.Value; +import com.annimon.hotarufx.visual.objects.ShapeNode; +import java.util.HashMap; +import java.util.Map; +import java.util.stream.Collectors; +import javafx.scene.shape.Shape; +import lombok.val; +import static com.annimon.hotarufx.bundles.FunctionInfo.of; +import static com.annimon.hotarufx.bundles.FunctionType.COMMON; + +public class NodeUtilsBundle implements Bundle { + + private static final Map FUNCTIONS; + static { + FUNCTIONS = new HashMap<>(); + FUNCTIONS.put("strokeDashArray", of(COMMON, NodeUtilsBundle::strokePattern)); + } + + @Override + public Map functionsInfo() { + return FUNCTIONS; + } + + private static Function strokePattern(Context context) { + return args -> { + val validator = Validator.with(args); + validator.checkOrOr(1, 2); + if (args[0].type() != Types.NODE || !(args[0].raw() instanceof ShapeNode)) { + throw new TypeException("Shape required at first argument"); + } + val shape = (Shape) ((ShapeNode) args[0].raw()).getFxNode(); + if (args.length == 2) { + val array = validator.requireArrayAt(1); + val dashList = array.stream() + .map(Value::asNumber) + .collect(Collectors.toList()); + shape.getStrokeDashArray().setAll(dashList); + return NumberValue.ZERO; + } else { + return ArrayValue.from(shape.getStrokeDashArray(), NumberValue::of); + } + }; + } +} diff --git a/app/src/main/java/com/annimon/hotarufx/lib/ArrayValue.java b/app/src/main/java/com/annimon/hotarufx/lib/ArrayValue.java index a5130e3..33dddb9 100644 --- a/app/src/main/java/com/annimon/hotarufx/lib/ArrayValue.java +++ b/app/src/main/java/com/annimon/hotarufx/lib/ArrayValue.java @@ -2,13 +2,21 @@ package com.annimon.hotarufx.lib; import com.annimon.hotarufx.exceptions.TypeException; import java.util.Arrays; +import java.util.Collection; import java.util.Iterator; +import java.util.function.Function; import java.util.stream.Stream; -import java.util.stream.StreamSupport; import lombok.Getter; public class ArrayValue implements Value, Iterable { + public static ArrayValue from(Collection collection, + Function converter) { + return new ArrayValue(collection.stream() + .map(converter) + .toArray(Value[]::new)); + } + @Getter private final Value[] elements; diff --git a/app/src/main/java/com/annimon/hotarufx/ui/controller/EditorController.java b/app/src/main/java/com/annimon/hotarufx/ui/controller/EditorController.java index efc65e2..a89446b 100644 --- a/app/src/main/java/com/annimon/hotarufx/ui/controller/EditorController.java +++ b/app/src/main/java/com/annimon/hotarufx/ui/controller/EditorController.java @@ -2,10 +2,7 @@ package com.annimon.hotarufx.ui.controller; import com.annimon.hotarufx.Main; import com.annimon.hotarufx.bundles.BundleLoader; -import com.annimon.hotarufx.bundles.CompositionBundle; -import com.annimon.hotarufx.bundles.NodesBundle; import com.annimon.hotarufx.exceptions.Exceptions; -import com.annimon.hotarufx.exceptions.HotaruRuntimeException; import com.annimon.hotarufx.io.DocumentListener; import com.annimon.hotarufx.io.DocumentManager; import com.annimon.hotarufx.io.FileManager; @@ -19,7 +16,6 @@ import com.annimon.hotarufx.ui.control.LibraryItem; import java.io.IOException; import java.io.InputStream; import java.net.URL; -import java.util.Arrays; import java.util.ResourceBundle; import java.util.concurrent.Executors; import javafx.application.Platform; @@ -134,10 +130,7 @@ public class EditorController implements Initializable, DocumentListener { } val context = new Context(); - BundleLoader.load(context, Arrays.asList( - CompositionBundle.class, - NodesBundle.class - )); + BundleLoader.load(context, BundleLoader.runtimeBundles()); val parser = new HotaruParser(HotaruLexer.tokenize(input)); val program = parser.parse(); diff --git a/app/src/main/resources/fxml/Editor.fxml b/app/src/main/resources/fxml/Editor.fxml index 4d58db9..a4d325e 100644 --- a/app/src/main/resources/fxml/Editor.fxml +++ b/app/src/main/resources/fxml/Editor.fxml @@ -270,17 +270,20 @@ + strokeWidth="3" stroke="#aaa" + strokeDashArray="6, 8, 2, 8" /> - line({\n - __startX: -600\n - __startY: -300\n + LINE = line({\n + __startX: -600,\n + __startY: -300,\n __endX: 600\n __endY: 300,\n __stroke: "#AAA",\n __strokeWidth: 5\n - }) + })\n + strokeDashArray(LINE, [25, 20, 5, 20])\n + LINE@strokeDashOffset.add(2 sec, -200)\n