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

Add interpolators

This commit is contained in:
Victor 2017-09-08 16:36:51 +03:00
parent 076825a814
commit aec580e60c
8 changed files with 131 additions and 13 deletions

View File

@ -15,7 +15,8 @@ public final class BundleLoader {
return Arrays.asList( return Arrays.asList(
CompositionBundle.class, CompositionBundle.class,
NodesBundle.class, NodesBundle.class,
NodeUtilsBundle.class NodeUtilsBundle.class,
InterpolatorsBundle.class
); );
} }

View File

@ -0,0 +1,31 @@
package com.annimon.hotarufx.bundles;
import com.annimon.hotarufx.lib.Context;
import com.annimon.hotarufx.lib.InterpolatorValue;
import java.util.HashMap;
import java.util.Map;
import javafx.animation.Interpolator;
public class InterpolatorsBundle implements Bundle {
private static final Map<String, FunctionInfo> FUNCTIONS;
static {
FUNCTIONS = new HashMap<>();
}
@Override
public Map<String, FunctionInfo> functionsInfo() {
return FUNCTIONS;
}
@Override
public void load(Context context) {
Bundle.super.load(context);
context.variables().put("linear", new InterpolatorValue(Interpolator.LINEAR));
context.variables().put("discrete", new InterpolatorValue(Interpolator.DISCRETE));
context.variables().put("easeIn", new InterpolatorValue(Interpolator.EASE_IN));
context.variables().put("easeOut", new InterpolatorValue(Interpolator.EASE_OUT));
context.variables().put("ease", new InterpolatorValue(Interpolator.EASE_BOTH));
context.variables().put("easeBoth", new InterpolatorValue(Interpolator.EASE_BOTH));
}
}

View File

@ -0,0 +1,45 @@
package com.annimon.hotarufx.lib;
import com.annimon.hotarufx.exceptions.TypeException;
import javafx.animation.Interpolator;
import lombok.Getter;
public class InterpolatorValue implements Value {
@Getter
private final Interpolator interpolator;
public InterpolatorValue(Interpolator interpolator) {
this.interpolator = interpolator;
}
@Override
public int type() {
return Types.INTERPOLATOR;
}
@Override
public Object raw() {
return interpolator;
}
@Override
public int asInt() {
throw new TypeException("Cannot cast interpolator to integer");
}
@Override
public double asNumber() {
throw new TypeException("Cannot cast interpolator to number");
}
@Override
public String asString() {
throw new TypeException("Cannot cast interpolator to string");
}
@Override
public int compareTo(Value o) {
return 0;
}
}

View File

@ -7,6 +7,7 @@ import com.annimon.hotarufx.visual.Property;
import com.annimon.hotarufx.visual.PropertyTimeline; import com.annimon.hotarufx.visual.PropertyTimeline;
import java.util.HashMap; import java.util.HashMap;
import java.util.Map; import java.util.Map;
import javafx.animation.Interpolator;
import javafx.scene.Node; import javafx.scene.Node;
import javafx.scene.paint.Paint; import javafx.scene.paint.Paint;
import javafx.scene.text.Font; import javafx.scene.text.Font;
@ -41,44 +42,59 @@ public class PropertyValue implements Value {
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
private Function add() { private Function add() {
return args -> { return args -> {
Validator.with(args).checkAtLeast(2); Validator.with(args).checkOrOr(2, 3);
final Interpolator interpolator;
if (args.length == 2) {
interpolator = Interpolator.LINEAR;
} else {
if (args[2].type() != Types.INTERPOLATOR) {
throw new TypeException("Interpolator required at third argument");
}
interpolator = ((InterpolatorValue) args[2]).getInterpolator();
}
val type = property.getType(); val type = property.getType();
switch (type) { switch (type) {
case BOOLEAN: case BOOLEAN:
((PropertyTimeline<Boolean>)property.getProperty().get()).add( ((PropertyTimeline<Boolean>)property.getProperty().get()).add(
KeyFrame.of(args[0].asInt()), KeyFrame.of(args[0].asInt()),
type.<Boolean>getFromHFX().apply(args[1]) type.<Boolean>getFromHFX().apply(args[1]),
interpolator
); );
break; break;
case NUMBER: case NUMBER:
((PropertyTimeline<Number>)property.getProperty().get()).add( ((PropertyTimeline<Number>)property.getProperty().get()).add(
KeyFrame.of(args[0].asInt()), KeyFrame.of(args[0].asInt()),
type.<Number>getFromHFX().apply(args[1]) type.<Number>getFromHFX().apply(args[1]),
interpolator
); );
break; break;
case STRING: case STRING:
((PropertyTimeline<String>)property.getProperty().get()).add( ((PropertyTimeline<String>)property.getProperty().get()).add(
KeyFrame.of(args[0].asInt()), KeyFrame.of(args[0].asInt()),
type.<String>getFromHFX().apply(args[1]) type.<String>getFromHFX().apply(args[1]),
interpolator
); );
break; break;
case NODE: case NODE:
case CLIP_NODE: case CLIP_NODE:
((PropertyTimeline<Node>)property.getProperty().get()).add( ((PropertyTimeline<Node>)property.getProperty().get()).add(
KeyFrame.of(args[0].asInt()), KeyFrame.of(args[0].asInt()),
type.<Node>getFromHFX().apply(args[1]) type.<Node>getFromHFX().apply(args[1]),
interpolator
); );
break; break;
case PAINT: case PAINT:
((PropertyTimeline<Paint>)property.getProperty().get()).add( ((PropertyTimeline<Paint>)property.getProperty().get()).add(
KeyFrame.of(args[0].asInt()), KeyFrame.of(args[0].asInt()),
type.<Paint>getFromHFX().apply(args[1]) type.<Paint>getFromHFX().apply(args[1]),
interpolator
); );
break; break;
case FONT: case FONT:
((PropertyTimeline<Font>)property.getProperty().get()).add( ((PropertyTimeline<Font>)property.getProperty().get()).add(
KeyFrame.of(args[0].asInt()), KeyFrame.of(args[0].asInt()),
type.<Font>getFromHFX().apply(args[1]) type.<Font>getFromHFX().apply(args[1]),
interpolator
); );
break; break;
} }

View File

@ -10,5 +10,6 @@ public class Types {
MAP = 4, MAP = 4,
NODE = 5, NODE = 5,
PROPERTY = 6, PROPERTY = 6,
FUNCTION = 7; INTERPOLATOR = 7,
FUNCTION = 8;
} }

View File

@ -0,0 +1,17 @@
package com.annimon.hotarufx.visual;
import javafx.animation.Interpolator;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
@Getter
@RequiredArgsConstructor
public class KeyFrameValue<T> {
private final T value;
private final Interpolator interpolator;
public KeyFrameValue(T value) {
this(value, Interpolator.LINEAR);
}
}

View File

@ -2,6 +2,7 @@ package com.annimon.hotarufx.visual;
import java.util.Map; import java.util.Map;
import java.util.TreeMap; import java.util.TreeMap;
import javafx.animation.Interpolator;
import javafx.beans.value.WritableValue; import javafx.beans.value.WritableValue;
import lombok.Getter; import lombok.Getter;
@ -9,7 +10,7 @@ import lombok.Getter;
public class PropertyTimeline<T> { public class PropertyTimeline<T> {
private final WritableValue<T> property; private final WritableValue<T> property;
private final Map<KeyFrame, T> keyFrames; private final Map<KeyFrame, KeyFrameValue<T>> keyFrames;
public PropertyTimeline(WritableValue<T> property) { public PropertyTimeline(WritableValue<T> property) {
this.property = property; this.property = property;
@ -17,7 +18,12 @@ public class PropertyTimeline<T> {
} }
public PropertyTimeline<T> add(KeyFrame keyFrame, T value) { public PropertyTimeline<T> add(KeyFrame keyFrame, T value) {
keyFrames.put(keyFrame, value); keyFrames.put(keyFrame, new KeyFrameValue<>(value));
return this;
}
public PropertyTimeline<T> add(KeyFrame keyFrame, T value, Interpolator interpolator) {
keyFrames.put(keyFrame, new KeyFrameValue<>(value, interpolator));
return this; return this;
} }
} }

View File

@ -33,8 +33,9 @@ public final class PropertyTimelineHolder<T> {
public void applyIfPresent(TimeLine timeline) { public void applyIfPresent(TimeLine timeline) {
if (isEmpty()) return; if (isEmpty()) return;
propertyTimeline.getKeyFrames().forEach((keyFrame, value) -> { propertyTimeline.getKeyFrames().forEach((keyFrame, p) -> {
timeline.addKeyFrame(keyFrame, new KeyValue(propertyTimeline.getProperty(), value)); timeline.addKeyFrame(keyFrame, new KeyValue(
propertyTimeline.getProperty(), p.getValue(), p.getInterpolator()));
}); });
} }