JavaFX setOnMousePressed() - verhält sich wie setOnMouseClicked()?

Bobo2040

Mitglied
Hallo, ich habe ein kleines Problem.
Ich habe einen Spieler,der in der Mitte des Bildschirms zentriert ist, das Spielfeld bewegt sich unter dem Spieler hinweg. Die Steuerung soll über die Maus erfolgen, also wenn die Maus gedrückt wird, soll der Spieler sich zur Maus hinbewegen und solange in Bewegung bleiben, wie die Maus gedrückt wird.
Leider funktioniert das nicht so ganz, der Spieler ruckt kurz in die Richtung, jedoch muss ich dann erneut die Maus Klicken um ihn zu bewegen.
Hier der Code Ausschnitt:
Java:
@Override
                public void handle(long arg0) {
                    scene.setOnMousePressed((MouseEvent event) -> {
                        //System.out.println("Maus geklickt");
                        double mouseX = event.getSceneX();
                        double mouseY = event.getSceneY();
                      
                        double vX = mouseX - WIDTH/2;
                        double vY = mouseY - HEIGHT/2;
                        System.out.println((vX%xSpeed) + " - " + (vY%xSpeed));
                        ballX = ballX + vX % xSpeed;
                        ballY = ballY + vY % xSpeed;
                    });
Das ganze läuft in JavaFX ab, ich habe in der Dokumentation gelesen, das es eine Konstante MOUSE_PRESSED gibt, jedoch weiß ich nicht wie ich das jetzt anwenden soll, da es dazu auch keine Beispiele gibt.
https://docs.oracle.com/javafx/2/api/javafx/scene/input/MouseEvent.html

Danke!🙂
 
Also, du erwartest, dass der Callback, den du per setOnMousePressed(callback) setzt, kontinuierlich mit jedem JavaFX Pulse 60 Mal pro Sekunde ausgeführt wird, solange die Maus gedrückt bleibt. Das ist nicht das, was die Methode tut.
Der Callback von setOnMousePressed wird jedesmal einmal ausgeführt, wenn du eine Maustaste herunterdrückst. Der Callback von setOnMouseClicked wird jedesmal einmal ausgeführt, wenn eine Maustaste losgelassen wird nachdem sie gedrückt wurde.
 
Na du merkst dir in einer Variablen, wenn die Maustaste heruntergedrückt wird und wenn sie wieder losgelassen wird und benutzt z.B. einen JavaFX AnimationTimer für deine Game Loop, in der du den Zustand der Variablen abfragst.
 
Ich habe das jetzt Probiert, es funktioniert so halbwegs, aber nicht wie gewünscht. Ich möchte die Richtungen wechseln können solange wie die Maus gedrückt gehalten wird. Also mouseX und mouseY sollen ständig aktualisiert werden, wenn diese gedrückt wird. Das tut es aber nicht, ich habe mir gedacht, mit der Methode setOnMouseMoved() Maus X/Y zu aktualisieren. Wenn jedoch setOnMousePressed "aktiv" ist wird diese Methode nicht ausgeführt. Wenn ich das ganze mit setOnMouseClicked() versuche, dann bewegt sich der Spieler durchgehend, aber so wie ich das will(->zur Maus). Ich denke bei setOnMouseClicked gibt es kein Released.
Die Frage ist jetzt wie kann ich die MouseX/Y Koordinaten abfragen, während eine andere Methode auf die MouseEvents zugreift?
Hier die Animator Methode:
Java:
AnimationTimer animator = new AnimationTimer(){

                @Override
                public void handle(long arg0) {
                    scene.setOnMousePressed((MouseEvent event) -> {
                        mouseIsPressed = true;
                    });
                  
                    scene.setOnMouseReleased((MouseEvent event) -> {
                        mouseIsPressed = false;
                    });
                  
                    scene.setOnMouseMoved((MouseEvent event) -> {
                        mouseX = event.getSceneX();
                        mouseY = event.getSceneY();
                    });
              
                    viewX = (int) (ballX - WIDTH/2);
                    viewY = (int) (ballY - HEIGHT/2);
                    // RENDER
                    for(int i = 0; i<particles.size(); i++) {
                        Circle tempCircle = particles.get(i).getCircle();
                        int tempX = particles.get(i).getX();
                        int tempY = particles.get(i).getY();
                        tempCircle.setCenterX(tempX - viewX);
                        tempCircle.setCenterY(tempY - viewY);
                    }
                    if(mouseIsPressed) {
                      
                        double rX = mouseX - WIDTH/2;
                        double rY = mouseY - HEIGHT/2;

                        System.out.println(rX + " - " + rY);
                      
                        double vector = Math.sqrt(rX*rX + rY*rY);
                        rX /= vector / xSpeed;
                        rY /= vector / xSpeed;

                        ballX += rX;
                        ballY += rY;
                    }
                    circle.setCenterX(ballX - viewX);
                    circle.setCenterY(ballY - viewY);
                }
            };
            animator.start();
 
setOnMouseDragged() ist das, was du brauchst. Und außerdem setzt du jetzt 60 Mal pro Sekunde die Mouse Callbacks, da du das Setzen der Callbacks in den AnimationTimer.handle() gezogen hast. Warum?

Hier ist ein funktionierendes Beispiel:
Java:
import javafx.animation.*;
import javafx.application.*;
import javafx.scene.*;
import javafx.stage.*;
public class MouseExample extends Application {
  private boolean down;
  private double x, y;
  public void start(Stage stage) {
    Group root = new Group();
    Scene scene = new Scene(root, 300, 250);
    scene.setOnMousePressed((event) -> {
      down = true;
    });
    scene.setOnMouseReleased((event) -> {
      down = false;
    });
    scene.setOnMouseDragged((event) -> {
      x = event.getX();
      y = event.getY();
    });
    new AnimationTimer() {
      public void handle(long now) {
        if (down) {
          System.out.println(x + ", " + y);
        }
      }
    }.start();
    stage.setScene(scene);
    stage.show();
  }
  public static void main(String[] args) {
    Application.launch(args);
  }
}
 
Super danke, jetzt funktioniert es.
Ich dachte das müsse jedesmal in der Animator Schleife aufgerufen werden, ich habe das jetzt ausgelagert und es funktioniert auch so. Danke! 🙂
 

Zurück
Oben