1
0
mirror of https://github.com/aNNiMON/HotaruFX.git synced 2024-09-19 14:14:21 +03:00

Ability to get and set node properties

This commit is contained in:
Victor 2017-08-30 17:54:19 +03:00
parent 0d2b24f850
commit 40100d8aaa
3 changed files with 61 additions and 23 deletions

View File

@ -1,5 +1,6 @@
package com.annimon.hotarufx.lib; package com.annimon.hotarufx.lib;
import com.annimon.hotarufx.exceptions.HotaruRuntimeException;
import com.annimon.hotarufx.exceptions.TypeException; import com.annimon.hotarufx.exceptions.TypeException;
import com.annimon.hotarufx.visual.Property; import com.annimon.hotarufx.visual.Property;
import com.annimon.hotarufx.visual.PropertyBindings; import com.annimon.hotarufx.visual.PropertyBindings;
@ -32,9 +33,32 @@ public class NodeValue implements Value {
return node; return node;
} }
@SuppressWarnings("unchecked")
public void fill(MapValue map) { public void fill(MapValue map) {
map.getMap().forEach((key, value) -> { map.getMap().forEach(this::set);
}
@SuppressWarnings("unchecked")
public Value get(String key) {
if (!bindings.containsKey(key)) {
throw new HotaruRuntimeException("Unable to get property " + key + " from node value");
}
final Property property = bindings.get(key);
val timeline = property.getProperty().get();
val type = property.getType();
switch (type) {
case NUMBER:
return type.<Number>getToHFX().apply(
((PropertyTimeline<Number>) timeline).getProperty().getValue());
case PAINT:
return type.<Paint>getToHFX().apply(
((PropertyTimeline<Paint>) timeline).getProperty().getValue());
default:
throw new TypeException("Unknown type of node property");
}
}
@SuppressWarnings("unchecked")
public void set(String key, Value value) {
if (!bindings.containsKey(key)) return; if (!bindings.containsKey(key)) return;
final Property property = bindings.get(key); final Property property = bindings.get(key);
val timeline = property.getProperty().get(); val timeline = property.getProperty().get();
@ -49,7 +73,6 @@ public class NodeValue implements Value {
type.<Paint>getFromHFX().apply(value)); type.<Paint>getFromHFX().apply(value));
break; break;
} }
});
} }
@Override @Override

View File

@ -5,6 +5,7 @@ import com.annimon.hotarufx.exceptions.TypeException;
import com.annimon.hotarufx.exceptions.VariableNotFoundException; import com.annimon.hotarufx.exceptions.VariableNotFoundException;
import com.annimon.hotarufx.lib.Context; import com.annimon.hotarufx.lib.Context;
import com.annimon.hotarufx.lib.MapValue; import com.annimon.hotarufx.lib.MapValue;
import com.annimon.hotarufx.lib.NodeValue;
import com.annimon.hotarufx.lib.NumberValue; import com.annimon.hotarufx.lib.NumberValue;
import com.annimon.hotarufx.lib.StringValue; import com.annimon.hotarufx.lib.StringValue;
import com.annimon.hotarufx.lib.Types; import com.annimon.hotarufx.lib.Types;
@ -102,7 +103,7 @@ public class InterpreterVisitor implements ResultVisitor<Value, Context> {
public Value get(AccessNode node, Context context) { public Value get(AccessNode node, Context context) {
Value container = node.root.accept(this, context); Value container = node.root.accept(this, context);
return getContainer(node.indices, context, container) return getContainer(node.indices, context, container)
.orElseThrow(() -> new TypeException("Map expected", node.start(), node.end())); .orElseThrow(() -> new TypeException("Unable to get property from non-accessible type", node.start(), node.end()));
} }
@Override @Override
@ -110,14 +111,20 @@ public class InterpreterVisitor implements ResultVisitor<Value, Context> {
Value container = node.root.accept(this, context); Value container = node.root.accept(this, context);
int lastIndex = node.indices.size() - 1; int lastIndex = node.indices.size() - 1;
Supplier<TypeException> exceptionSupplier = () -> Supplier<TypeException> exceptionSupplier = () ->
new TypeException("Map expected", node.start(), node.end()); new TypeException("Unable to set property to non-accessible type", node.start(), node.end());
container = getContainer(node.indices.subList(0, lastIndex), context, container) container = getContainer(node.indices.subList(0, lastIndex), context, container)
.orElseThrow(exceptionSupplier); .orElseThrow(exceptionSupplier);
switch (container.type()) { switch (container.type()) {
case Types.MAP: case Types.MAP: {
val key = node.indices.get(lastIndex).accept(this, context).asString(); val key = node.indices.get(lastIndex).accept(this, context).asString();
((MapValue) container).getMap().put(key, value); ((MapValue) container).getMap().put(key, value);
break; } break;
case Types.NODE: {
val key = node.indices.get(lastIndex).accept(this, context).asString();
((NodeValue) container).set(key, value);
} break;
default: default:
throw exceptionSupplier.get(); throw exceptionSupplier.get();
} }
@ -127,10 +134,16 @@ public class InterpreterVisitor implements ResultVisitor<Value, Context> {
private Optional<Value> getContainer(List<Node> nodes, Context context, Value container) { private Optional<Value> getContainer(List<Node> nodes, Context context, Value container) {
for (Node index : nodes) { for (Node index : nodes) {
switch (container.type()) { switch (container.type()) {
case Types.MAP: case Types.MAP: {
val key = index.accept(this, context).asString(); val key = index.accept(this, context).asString();
container = ((MapValue) container).getMap().get(key); container = ((MapValue) container).getMap().get(key);
break; } break;
case Types.NODE: {
val key = index.accept(this, context).asString();
container = ((NodeValue) container).get(key);
} break;
default: default:
return Optional.empty(); return Optional.empty();
} }

View File

@ -7,4 +7,6 @@ A = circle({
fill: "red" fill: "red"
}) })
A.radius = 10
render(A) render(A)