Sunday, September 20, 2015

Dragging objects with a mouse in JavaFX

Dragging objects is pretty straightforward in JavaFX as long as some key concepts are kept straight.  If we go with the strategy of attaching the event handler to the object to be dragged, then the very first time that the onMouseDragged event is invoked, the (x,y) coordinates given by the event parameter will be the location on the object that was clicked.

If we then move the object, on subsequent invocations of the event as a result of moving the mouse, the (x,y) coordinates will be the relative distance between the mouse position at the time of the preceding event and the current mouse position.  This works because the new position of the object is determined by the previous mouse location.

In either case, it works pretty well to use the (x,y) coordinate of the mouse as an offset by which to translate the object.  The code below demonstrates the concept nicely, provided that a suitable GUI has been created using SceneBuilder and a suitable main() has also been created.  The drag() method is set up to work properly with a draggable Node of any subtype.

import javafx.fxml.FXML;
import javafx.scene.Node;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.Pane;
import javafx.scene.shape.Circle;

public class DemoController {
 @FXML
 Pane pane;
 
 @FXML
 Circle ball1, ball2;
 
 @FXML
 void initialize() {
  ball1.setOnMouseDragged(event -> drag(event));
  ball2.setOnMouseDragged(event -> drag(event));
 }
 
 public void drag(MouseEvent event) {
  Node n = (Node)event.getSource();
  n.setTranslateX(n.getTranslateX() + event.getX());
  n.setTranslateY(n.getTranslateY() + event.getY());
 }
}

No comments:

Post a Comment