JavaFX ImageView 旋转更改拖放



所以我有一个ImageView,可以使用鼠标拖放,并通过单击按钮旋转90度。这两件事在独立完成时都可以工作(因此 ImageView 可以旋转或移动,而不是两者兼而有之)。当我旋转 ImageView 并尝试移动它时,它似乎是随机移动的。

我使用以下方法旋转图像视图:

imageView.setRotate(90);

这导致了我所说的看似随机的运动。

我还尝试使用以下方法旋转图像视图:

imageView.getTransforms().add(new Rotate(rotation, position + (width / 2), position + (height / 2));

位置是屏幕上的图像位置。宽度和高度是图像视图的宽度和高度。

这在大多数情况下都有效(ImageView 不再以意外的方式移动),但是现在它可以移动并放置在窗格 (javafx.scene.layout.Pane) 的边界之外,这是它的父级。

ImageView 保持在边界内的方式是:

imageView.setOnMouseDragged(new EventHandler<MouseEvent>(){
public void handle(MouseEvent e) {
if(!e.isPrimaryButtonDown()) return;
ImageView iv = (ImageView) e.getSource();
if(e.getX() > iv.getParent().getTranslateX()) iv.setX(e.getX());
if(e.getY() > iv.getParent().getTranslateY()) iv.setY(e.getY());
}
});

此窗格的父项是前面所述的窗格。这在旋转图像视图之前工作正常。

我不确定从这里开始,所以我感谢任何帮助。谢谢。


编辑原始问题:

使用第二种旋转方法:

imageView.getTransforms().add(new Rotate(rotation, position + (width / 2), position + (height / 2));

除了 x 和 y 的平移更改我旋转 ImageView 之外,此方法还有效。例如,如果我将鼠标向右移动到旋转 90 度的图像上,那么 e.getX() 在我的 MouseDraggedEvent 中的位置不会改变,但 e.getY() 会减少。这表明 e.getX() 和 e.getY() 的方式取决于 ImageView 的旋转。

有没有办法在不影响 ImageView 的 x 和 y 坐标的情况下旋转?

e.getX()e.getY()位于影像视图的坐标系中;旋转后,该坐标系仍然是影像视图的局部坐标系。因此,您将图像视图的 x 坐标设置为旋转后实际上与 y 坐标有更多关系的内容(以某种非平凡的方式)。

您应该通过计算鼠标相对于固定内容(例如场景)移动的量来计算拖动量。

这是一个有效的 SSCCE(双击旋转):

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.scene.layout.Pane;
import javafx.scene.paint.Color;
import javafx.stage.Stage;
public class ImageTransformTest extends Application {
@Override
public void start(Stage primaryStage) {
ImageView arrow = new ImageView(createImage());
Pane pane = new Pane(arrow);
pane.setMinSize(600,  600);
new Dragger(arrow) ;
arrow.setOnMouseClicked(e -> {
if (e.getClickCount() == 2) {
arrow.setRotate(arrow.getRotate() + 90);
}
});
Scene scene = new Scene(pane) ;
primaryStage.setScene(scene);
primaryStage.show();
}
private static class Dragger {
private double x ;
private double y ;
Dragger(ImageView imageView) {
imageView.setOnMousePressed(e -> {
x = e.getSceneX();
y = e.getSceneY();
});
imageView.setOnMouseDragged(e -> {
double deltaX = e.getSceneX() - x ;
double deltaY = e.getSceneY() - y ;
imageView.setX(imageView.getX() + deltaX);
imageView.setY(imageView.getY() + deltaY);
x = e.getSceneX() ;
y = e.getSceneY() ;
});
}
}
private Image createImage() {
WritableImage image = new WritableImage(100, 100);
for (int y = 0 ; y < 40 ; y++) {
for (int x = 0 ; x < 50 - 50 * y / 40 ; x++) {
image.getPixelWriter().setColor(x, y, Color.TRANSPARENT);
}
for (int x = 50 - 50 * y / 40 ; x < 50 + 50 * y / 40 ; x ++) {
image.getPixelWriter().setColor(x, y, Color.BLUE);
}
for (int x = 50 + 50 * y ; x < 100 ; x++) {
image.getPixelWriter().setColor(x, y, Color.TRANSPARENT);
}
}
for (int y = 40 ; y < 100 ; y++) {
for (int x = 0 ; x < 100 ; x++) {
image.getPixelWriter().setColor(x, y, x < 30 || x > 70 ? Color.TRANSPARENT : Color.BLUE);
}
}
return image ;
}
public static void main(String[] args) {
launch(args);
}
}

最新更新