Animation 设置动画时,节点仅沿一个方向移动,而不是来回移动

Animation 设置动画时,节点仅沿一个方向移动,而不是来回移动,animation,javafx,Animation,Javafx,在学习如何使用javafx时,我的节点或“目标”从一个边缘反弹到另一个边缘时遇到了问题。第一次穿过窗格后,它们停了下来。到目前为止我拥有的这段代码 public class game extends Application implements EventHandler<ActionEvent>{ target1 target1 = new target1(); target2 target2 = new target2(); shooter shooter = new shoot

在学习如何使用javafx时,我的节点或“目标”从一个边缘反弹到另一个边缘时遇到了问题。第一次穿过窗格后,它们停了下来。到目前为止我拥有的这段代码

public class game extends Application implements EventHandler<ActionEvent>{

target1 target1 = new target1();
target2 target2 = new target2();
shooter shooter = new shooter();
Button fireButton = new Button("Fire!");
Pane pane = new Pane();

/**
 * 
 * @param primaryStage 
 */
@Override
public void start(Stage primaryStage) {

    Scene scene = new Scene(pane, 800, 600);
    primaryStage.setTitle("GAME");
    primaryStage.setScene(scene);

    pane.getChildren().add(fireButton);
    fireButton.setLayoutX(700);
    fireButton.setLayoutY(500);
    pane.getChildren().add(shooter);
    shooter.setX(380);
    shooter.setY(540);
    shooter.setWidth(40);
    shooter.setHeight(20);
    shooter.setArcWidth(20);
    shooter.setArcHeight(20);


    pane.getChildren().add(target1);
    target1.setX(0);
    target1.setY(250);
    target1.setWidth(30);
    target1.setHeight(20);
    target1.setArcWidth(20);
    target1.setArcHeight(20);

    pane.getChildren().add(target2);
    target2.setX(0);
    target2.setY(150);
    target2.setWidth(15);
    target2.setHeight(10);
    target2.setArcWidth(20);
    target2.setArcHeight(20);

    primaryStage.show();
    ShooterButtonPressHandler shooterButton = new ShooterButtonPressHandler();
    fireButton.setOnAction(shooterButton);

    KeyFrame keyFrame = new KeyFrame(Duration.millis(1), this);
    Timeline animation = new Timeline(keyFrame);
    animation.setCycleCount(Timeline.INDEFINITE);
    animation.play();


}

/**
 * @param args the command line arguments
 */
public static void main(String[] args) {
    launch(args);
}

@Override
public void handle(ActionEvent event) {
    if (target1.isColliding(pane) ) {
        target1.processCollision();
    }
    target1.animate(pane);
    if (target2.isColliding(pane) ) {
        target2.processCollision();
    }
    target2.animate(pane);

}
/**
 * 
 */
public class ShooterButtonPressHandler implements EventHandler<ActionEvent>{

    @Override
    public void handle(ActionEvent event) {
        if (target1.getX() >= 370 && target1.getX()<= 400){
            System.out.println("hit");
        }
        if (target2.getX() >= 370 && target2.getX()<= 400){
            System.out.println("hit");
        }
        else {
            System.out.println("miss");
        }        
    }                
}
问题

你所面临的问题是因为这个声明

this.setX(side);

让我们考虑一个场景,你的目标到达边界。在本阶段,对于target1:

X = 790
width = 30
side = 800

X + width = 790 + 30 = 820, which is greater than 800
所以

现在我们有

X = 800
width = 30
side = 800

X + width = 800 + 30 = 830, which is greater than 800
同样,我们有
collision=true
,这将永远持续下去

解决方案

您可以将X设置为小于
side+width
的值。实现这一目标有多种方法,其中之一就是

this.setX(this.getX()-this.getWidth())

但是,这将破坏两个目标之间的同步,因为它们的宽度不相等。寻找更好的解决方案留给读者

还有一个问题,我想指出,碰撞涉及的是右端的碰撞,而不是左端的碰撞。为了兼顾这两个方面,您可以按如下方式编辑代码:

public Boolean isColliding(Pane pane) {
    Double side = pane.getWidth();
    Boolean collision = false;
    if(this.getX() + this.getWidth() >= side) {
        this.setX(this.getX() - this.getWidth());
        collision = true;
    } else if (this.getX() - this.getWidth() <= 0) {
        this.setX(this.getX() + this.getWidth());
        collision = true;
    }
    return collision;
}
public Boolean isColliding(窗格){
双面=pane.getWidth();
布尔冲突=假;
if(this.getX()+this.getWidth()>=side){
this.setX(this.getX()-this.getWidth());
碰撞=真;

}否则如果(this.getX()-this.getWidth())非常感谢!我在编码时总是忽略这样的细节。这个习惯很难改掉,但一定要改掉,因为我编码的越多,我就越喜欢lol。
X = 800
width = 30
side = 800

X + width = 800 + 30 = 830, which is greater than 800
public Boolean isColliding(Pane pane) {
    Double side = pane.getWidth();
    Boolean collision = false;
    if(this.getX() + this.getWidth() >= side) {
        this.setX(this.getX() - this.getWidth());
        collision = true;
    } else if (this.getX() - this.getWidth() <= 0) {
        this.setX(this.getX() + this.getWidth());
        collision = true;
    }
    return collision;
}