2015-07-31 2 views
1

Просто попав в JavaFX, мне очень понравилось, но я не совсем уверен, как оживить свойство AnchorPane.leftAnchor.Анимация статического свойства?

В настоящее время я использую временную шкалу для анимации Node.translateXProperty(), и это дает мне приятную плавную анимацию. Однако, хотя мой узел, похоже, перемещается, кажется, что с точки зрения получения щелчков мыши он не перемещается. Так что, действительно, то, что я хотел бы сделать, это анимировать статическое свойство AnchorPane.leftAnchor узла, возможно ли это?

В идеале, я хотел бы сохранить свою временную шкалу, как это делают другие вещи тоже, так что ..

1) Можно анимировать статическое свойство таким же образом, я могу оживить обычное свойство, как это:

new KeyFrame(Duration.ZERO, new KeyValue(node.translateXProperty(), from, Interpolator.EASE_BOTH)) 

2) Если это невозможно, я могу перевести щелчки мыши, чтобы совпасть с преобразованной позиции?

Приветствие

Garry

ответ

3

Если вы анимировать translateX и translateY свойства, то координаты мыши на узле, который анимационный, извлекаемые MouseEvent.getX() и MouseEvent.getY(), будет локальным по отношению к системе координат этого узла: т.е. они не будут затронуты изменением местоположения самого узла. То же самое верно, если вы анимируете объекты layoutX и layoutY (что вы бы сделали, если вы анимировали AnchorPane.leftAnchor «свойство»).

Вы можете преобразовать точку в локальной системе координат узла в свою систему координат родителя, вызвав Node.localToParent(...).

Примечание Есть и другие подобные методы на Node, такие как localToScene и localToScreen, а также некоторые методы удобства на MouseEvent: getSceneX(), getScreenX(), а так же для y.

Чтобы ответить на ваш реальный вопрос (хотя я подозреваю, что это избыточно, возможно ...), вы можете создать новое свойство и «оживить» это свойство. Затем добавьте к нему слушателя и обновите leftAnchor, когда он изменится. Этот SSCCE демонстрирует эту технику (хотя вы можете использовать TranslateTransition вместо этого и получить координаты мыши точно так же).

import javafx.animation.KeyFrame; 
import javafx.animation.KeyValue; 
import javafx.animation.Timeline; 
import javafx.application.Application; 
import javafx.beans.property.DoubleProperty; 
import javafx.beans.property.SimpleDoubleProperty; 
import javafx.geometry.Point2D; 
import javafx.scene.Scene; 
import javafx.scene.layout.AnchorPane; 
import javafx.scene.layout.Region; 
import javafx.stage.Stage; 
import javafx.util.Duration; 

public class AnimateXAnchor extends Application { 

    @Override 
    public void start(Stage primaryStage) { 
     Region rect = new Region(); 
     rect.setPrefSize(100, 100); 
     rect.setStyle("-fx-background-color: cornflowerblue;"); 

     rect.setOnMousePressed(e -> { 
      double x = e.getX(); 
      double y = e.getY(); 
      System.out.printf("Mouse click in local coordinates: [%.1f, %.1f]%n", x, y); 

      Point2D clickInParent = rect.localToParent(x, y); 
      System.out.printf("Mouse click in parent coordinates: [%.1f, %.1f]%n%n", clickInParent.getX(), clickInParent.getY()); 

     }); 

     AnchorPane root = new AnchorPane(); 
     root.getChildren().add(rect); 
     AnchorPane.setTopAnchor(rect, 10.0); 

     DoubleProperty x = new SimpleDoubleProperty(); 
     x.addListener((obs, oldX, newX) -> AnchorPane.setLeftAnchor(rect, newX.doubleValue())); 

     Timeline animation = new Timeline(
      new KeyFrame(Duration.ZERO, new KeyValue(x, 0)), 
      new KeyFrame(Duration.seconds(5), new KeyValue(x, 400)) 
     ); 

     Scene scene = new Scene(root, 600, 600); 
     primaryStage.setScene(scene); 
     primaryStage.show(); 
     animation.play(); 
    } 

    public static void main(String[] args) { 
     launch(args); 
    } 
} 
+0

Спасибо, Джеймс, вторая часть вашего ответа, с созданием нового имущества была точным решением, которое мне было необходимо, оно отлично работает. Благодаря! – Garry