1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88
| package collisions;
import javafx.animation.AnimationTimer;
import javafx.animation.Interpolator;
import javafx.animation.TranslateTransition;
import javafx.application.Application;
import javafx.beans.binding.Bindings;
import javafx.css.PseudoClass;
import javafx.geometry.Point2D;
import javafx.scene.Scene;
import javafx.scene.layout.Pane;
import javafx.scene.shape.Circle;
import javafx.scene.shape.Rectangle;
import javafx.stage.Stage;
import javafx.util.Duration;
import java.net.URL;
import java.util.Optional;
public final class Main extends Application {
private static final PseudoClass COLLISION_PSEUDO_CLASS = PseudoClass.getPseudoClass("collision");
@Override
public void start(final Stage stage) throws Exception {
// Les cercles.
final var c1 = new Circle(20, 20, 15);
c1.getStyleClass().add("c1");
final var c2 = new Circle(250, 250, 50);
c2.getStyleClass().add("c2");
// Les boites englobantes des cercles.
final var bounds1 = new Rectangle();
bounds1.getStyleClass().add("bounds1");
bounds1.xProperty().bind(Bindings.selectDouble(c1.boundsInParentProperty(), "minX"));
bounds1.yProperty().bind(Bindings.selectDouble(c1.boundsInParentProperty(), "minY"));
bounds1.widthProperty().bind(Bindings.selectDouble(c1.boundsInParentProperty(), "width"));
bounds1.heightProperty().bind(Bindings.selectDouble(c1.boundsInParentProperty(), "height"));
final var bounds2 = new Rectangle();
bounds2.getStyleClass().add("bounds2");
bounds2.xProperty().bind(Bindings.selectDouble(c2.boundsInParentProperty(), "minX"));
bounds2.yProperty().bind(Bindings.selectDouble(c2.boundsInParentProperty(), "minY"));
bounds2.widthProperty().bind(Bindings.selectDouble(c2.boundsInParentProperty(), "width"));
bounds2.heightProperty().bind(Bindings.selectDouble(c2.boundsInParentProperty(), "height"));
// Montage de l'UI.
final var root = new Pane();
root.getChildren().addAll(bounds1, bounds2);
root.getChildren().addAll(c1, c2);
final var scene = new Scene(root, 500, 500);
Optional.ofNullable(Main.class.getResource("styles.css"))
.stream()
.map(URL::toExternalForm)
.forEach(scene.getStylesheets()::add);
stage.setScene(scene);
stage.setResizable(false);
stage.show();
// Collision.
final var worldClock = new AnimationTimer() {
@Override
public void handle(long l) {
final var b1 = c1.getBoundsInParent();
final var b2 = c2.getBoundsInParent();
boolean colorBound = false;
boolean colorShape = false;
if (b1.intersects(b2)) {
colorBound = true;
final var center1 = new Point2D(b1.getCenterX(), b1.getCenterY());
final double distance = center1.distance(b2.getCenterX(), b2.getCenterY());
if (distance < c1.getRadius() + c2.getRadius()) {
colorBound = false;
colorShape = true;
}
}
bounds1.pseudoClassStateChanged(COLLISION_PSEUDO_CLASS, colorBound);
c1.pseudoClassStateChanged(COLLISION_PSEUDO_CLASS, colorShape);
}
};
worldClock.start();
// Animation.
final var animation = new TranslateTransition(Duration.seconds(10), c1);
animation.setInterpolator(Interpolator.LINEAR);
animation.setCycleCount(TranslateTransition.INDEFINITE);
animation.setAutoReverse(true);
animation.setToX(500 - 2 * 15 - 20);
animation.setToY(500 - 2 * 15 - 20);
animation.play();
}
} |
Partager