gpt4 book ai didi

java - JLabel 无法使用鼠标运动监听器正确移动,为什么?

转载 作者:行者123 更新时间:2023-11-30 03:43:07 25 4
gpt4 key购买 nike

每当我拖动鼠标时,我都需要相应地移动 JLabel。
为什么拖动时显示多个 JLabel 而没有在正确的位置显示组件?

public class Mover extends JFrame 
{

private JPanel jPanel;
private JLabel jLabel1;
private JLabel jLabel2;
private int myXX = 0;
private int myYY = 0;

public Mover() {
setSize(500, 500);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

jPanel = new JPanel(null);
jLabel1 = new JLabel("label one");
jLabel2 = new JLabel("label two");

jLabel1.setBounds(100, 100, 100, 100);
jLabel2.setBounds(100, 100, 100, 100);
jLabel1.addMouseMotionListener(new MouseMotionListener() {

@Override
public void mouseMoved(MouseEvent e) {
}

@Override
public void mouseDragged(MouseEvent e) {
System.out.println("Label One");
myXX = e.getX() - (jLabel1.getWidth() / 2);
myYY = e.getY() - (jLabel1.getHeight() / 2);
jLabel1.setLocation(myXX, myYY);
repaint();
}
});
jLabel2.addMouseMotionListener(new MouseMotionListener() {

@Override
public void mouseMoved(MouseEvent e) {
}

@Override
public void mouseDragged(MouseEvent e) {
System.out.println("Label Two");

myXX = e.getX() - (jLabel2.getWidth() / 2);
myYY = e.getY() - (jLabel2.getHeight() / 2);
jLabel2.setLocation(myXX, myYY);
repaint();
}
});
jPanel.add(jLabel1);
jPanel.add(jLabel2);
add(jPanel);
repaint();
revalidate();
setVisible(true);
}

public static void main(String args[]) {
new Mover();
}
}

这个问题有完美的解决办法吗?
显然提前致谢。

最佳答案

MouseEvent 信息与生成事件的组件(在本例中为标签)相关。

这意味着0x0实际上是标签的左上角。您需要将事件的点信息转换为其父上下文,例如...

Point p = e.getPoint();
p = SwingUtilities.convertPoint(e.getComponent(), p, e.getComponent().getParent());

您也不需要创建 myXXmyYY 实例字段,因为它们只真正具有驱动它们的鼠标事件的上下文。

您还应该看看Initial Threads并确保您在事件调度线程的上下文中启动您的程序...

您也不需要为每个组件创建单独的监听器,只需巧妙地使用 MouseEvent 中的可用信息,您就可以为所有组件使用单个监听器并减少代码重复...

import java.awt.Component;
import java.awt.EventQueue;
import java.awt.Point;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class Mover extends JFrame {

private JPanel jPanel;
private JLabel jLabel1;
private JLabel jLabel2;

public Mover() {
setSize(500, 500);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

jPanel = new JPanel(null);
jLabel1 = new JLabel("label one");
jLabel2 = new JLabel("label two");

jLabel1.setBounds(100, 100, 100, 100);
jLabel2.setBounds(100, 100, 100, 100);

MouseMotionListener mover = new MouseMotionListener() {

@Override
public void mouseMoved(MouseEvent e) {
}

@Override
public void mouseDragged(MouseEvent e) {
System.out.println("Label One");

Component child = e.getComponent();
Point p = e.getPoint();
p = SwingUtilities.convertPoint(e.getComponent(), p, e.getComponent().getParent());

int myXX = p.x - (child.getWidth() / 2);
int myYY = p.y - (child.getHeight() / 2);
child.setLocation(myXX, myYY);
repaint();
}
};

jLabel1.addMouseMotionListener(mover);
jLabel2.addMouseMotionListener(mover);

jPanel.add(jLabel1);
jPanel.add(jLabel2);
add(jPanel);
setVisible(true);
}

public static void main(String args[]) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}

new Mover();
}
});
}
}

如果我没有指出直接从像 JFrame 这样的顶级容器扩展是不好的做法,并且会将您锁定在一次性容器中,那么我就会对您造成伤害。如果您愿意的话,将来很难重新使用该容器或将其添加到其他容器...此外,您并没有真正向其添加任何功能...

关于java - JLabel 无法使用鼠标运动监听器正确移动,为什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26375259/

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