gpt4 book ai didi

java - 使用 mouseDragged 时,如何让图像移动而不首先跳转到鼠标光标的位置?

转载 作者:行者123 更新时间:2023-12-02 03:44:22 25 4
gpt4 key购买 nike

我有一个程序,可以通过单击和拖动在屏幕上移动图像。唯一的问题是,当我单击图像并开始在面板上拖动它时,图像首先跳转到鼠标光标的位置。如何防止这种情况发生,以便无论我单击图像的何处,图像都会简单地移动?我只能让鼠标光标在开始拖动时跳到鼠标箭头下方,或者在开始拖动时跳到鼠标箭头上方,或者设置到要拖动的图像的中间。

我正在使用以下函数将 Image 类的 Image 对象移动到另一个类中:

moveImage(selected,x,y);

其中 x 和 y 是 mouseDragged 方法中的坐标。这是我的图像类:

import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

class Image {

private int x;
private int y;
private BufferedImage image;
private StringBuffer filepath;
private boolean isTurned;

public Image(int x, int y, String filepath) throws IOException {
this.filepath = new StringBuffer(filepath);
this.x = x;
this.y = y;
this.image = ImageIO.read(new File(String.valueOf(filepath)));
}

public void draw(Graphics g){

g.drawImage(image, x, y, null);

}

public void undraw (Graphics g, Color c ){
g.setColor(c);
g.fillRect(x,y, image.getWidth(), image.getHeight());

}

public boolean containsXY (int x, int y){

if ( (this.x <= x ) && (x <= (this.x+this.image.getWidth())) && (this.y <= y ) && (y <= (this.y+this.image.getHeight())) ){

return true;
}

return false;
}

public void move (Graphics g, int x, int y) {
System.out.println("int x = " + x + " int y = " + y);
System.out.println("this x = " + this.x + " this y = " + this.y);
System.out.println("width: " + this.image.getWidth() + " height: " + this.image.getHeight());

undraw(g, Color.WHITE);

/* this.x = x - ((x+image.getWidth())-x);
this.y = y -((y+image.getHeight())-y);

this.x = x - (x-this.x);
this.y = y - (y-this.y);

this.x = x - (this.x+image.getWidth()-x);
this.y = y - (this.y+image.getHeight()-y);



this.x = this.x + (x-image.getWidth());
this.y = this.y + (y-image.getHeight());

this.x = x - (image.getWidth());
this.y = y - (image.getHeight());*/

this.x = x - (image.getWidth()/2);
this.y = y - (image.getHeight()/2);


draw(g);
}

public void turn(Graphics g) throws IOException {

if (isTurned) {
filepath.replace(filepath.length()-9, filepath.length(), ".gif" );
undraw(g, Color.WHITE);
image = ImageIO.read(new File(String.valueOf(filepath)));
draw(g);
isTurned = false;
}

else {
filepath.replace(filepath.length()-4, filepath.length(), " back.gif" );
undraw(g, Color.WHITE);
image = ImageIO.read(new File(String.valueOf(filepath)));
draw(g);
isTurned = true;
}
}

}

正如您所看到的,在 move 方法中,我尝试了很多不同的方法来操作传入的鼠标事件拖动的坐标。现在在我正在使用的代码中

this.x = x - (image.getWidth()/2);
this.y = y - (image.getHeight()/2);

当我拖动鼠标光标时,它会使鼠标光标锁定在图像的中间,这是我目前能做的最好的事情。因此,当我想要移动图像并单击图像的一角时,它会“弹出”到图像的中间并锁定在那里,同时拖动图像。但我不想要这个。我希望鼠标光标停留在我开始拖动时单击的图像位置上,而不是在其他地方重新绘制图像,然后开始拖动。

这是我调用 Image 对象的类,我在这个类中调用它:s 方法 moveImage:

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;

class PaintSurface extends JLabel implements MouseListener, MouseMotionListener {

private int x, y;
private JButton browse;
private Collection<Image> images = new ArrayList<Image>();
private final JFileChooser fc = new JFileChooser();
private Image selected;

public PaintSurface(JButton b){
browse = b;
addMouseListener(this);
addMouseMotionListener(this);
browse.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {

int x = fc.showOpenDialog(browse);

if (x == JFileChooser.APPROVE_OPTION){
try {
buttonPressed(fc);

} catch (IOException e1) {
e1.printStackTrace();
}
}

else if (x ==JFileChooser.CANCEL_OPTION){
System.out.println("No file selected.");
}
}
});
}

public void paintComponent (Graphics g){
super.paintComponent(g);



for (Image i: images){
i.draw(g);

}


}



public void addImage(Image i){

images.add(i);
Graphics g = getGraphics();
i.draw(g);

}

public void buttonPressed(JFileChooser fc) throws IOException {

File selectedFile = fc.getSelectedFile();
String filepath = String.valueOf(selectedFile.getAbsolutePath());
Image i = new Image(x, y, filepath );
selected = i;
addImage(i);
repaint();

}

public Image findImage(int x, int y){

Image[] imageArray = images.toArray(new Image[images.size()]);

for (int i = imageArray.length - 1; i >= 0; i--){
if (imageArray[i].containsXY(x, y)){
return imageArray[i];
}
}
return null;
}


public void moveImage (Image i, int x, int y) { //

i.move(getGraphics(), x, y);
}

public boolean removeImage(Image i){

Graphics g = getGraphics();
i.undraw(g, Color.WHITE);
return images.remove(i);

}

@Override
public void mouseClicked(MouseEvent e) {
x = e.getX();
y = e.getY();
System.out.println("mouseclick");

selected = findImage(x,y);

if (selected != null) {

Graphics g = getGraphics();

try {
selected.turn(g);
repaint();
} catch (IOException e1) {
e1.printStackTrace();
}
selected = null;
}

}

@Override
public void mousePressed(MouseEvent e) {
Image i = findImage(e.getX(), e.getY());

if (i == null) {

System.out.println("null mousepress");
return;

}

else {
System.out.println("not null mousepress");
if (i == selected){
return;
}
else {
removeImage(i);
addImage(i);
selected = i;

}


}






}

@Override
public void mouseDragged(MouseEvent e) {
int x = e.getX();
int y = e.getY();

if (selected != null) {
moveImage(selected,x,y);
repaint();
}
}

@Override
public void mouseReleased(MouseEvent e) {
selected = null;
}

@Override
public void mouseEntered(MouseEvent e) {

}

@Override
public void mouseExited(MouseEvent e) {

}

@Override
public void mouseMoved(MouseEvent e) {

}
}

有这方面经验的人可以帮忙吗?大约一周以来我一直用这个拉扯我的头发......

最佳答案

您需要跟踪单击位置的变化,而不是移动到新的光标位置。在mousePressed中,存储原始按下位置:

// lastX, lastY are object variables
lastX = e.getX();
lastY = e.getY();

mouseDragged中,计算增量

public void mouseDragged(MouseEvent e) {
int x = i.getX() + e.getX() - lastX;
int y = i.getY() + e.getY() - lastY;

if (selected != null) {
moveImage(selected,x,y);
repaint();
}
lastX = e.getX();
lastY = e.getY();
}

关于java - 使用 mouseDragged 时,如何让图像移动而不首先跳转到鼠标光标的位置?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36450770/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com