MouseMotionListener 似乎闹鬼
Posted
技术标签:
【中文标题】MouseMotionListener 似乎闹鬼【英文标题】:MouseMotionListener appears to be Haunted 【发布时间】:2021-02-25 04:31:17 【问题描述】:我刚刚学习 java,我有一个项目,我希望能够用鼠标在窗口周围移动 JLabel。
我建立了一个名为BasicWindow1的类,实现了一个MouseMotionListener,实例化了一个JFrame容器,在JFrame中添加了一个JLabel,设置了一个mouseDragged方法,将JLabel的setBounds方法与MouseEvent信息挂钩,编译它跑了……
但是……
当我拖动 JLabel 时,第二个 GHOST 标签出现在其上方,并与它的虚拟兄弟一起愉快地移动。
我已经包含了下面的代码,我希望有人会感兴趣并理顺我。我猜这可能是一个简单的初学者错误,但它让我发疯了。
在调试级别,我在 mouseDragged 方法中插入了一个带有 MouseEvent 的 println(e),它显示 MOUSE_DRAGGED x,y 元素在 2 个不同的 x,y 路径之间振荡,一个用于 GHOST,一个用于它的虚拟兄弟。
感谢收看, 迈克
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
public class BasicWindow1 implements MouseMotionListener
JFrame jf = new JFrame();
JLabel label2 = new JLabel("label2");
public BasicWindow1(String string)
//JFrame
jf.setTitle(string);
jf.setSize(400,400);
jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
jf.setLayout(null);
jf.setVisible(true);
label2.setOpaque(true);
label2.setBackground(Color.cyan);
label2.setBounds(0,150,75,25);
label2.addMouseMotionListener(this);
jf.add(label2);
//end constructor
public void mouseDragged(MouseEvent e)
label2.setBounds(e.getX(),e.getY(),75,25);
System.out.println("e = " + e);
public void mouseMoved(MouseEvent e)
public static void main(String[] args)
BasicWindow1 mybw = new BasicWindow1("Basic Window for Stack Overflow");
【问题讨论】:
一定是因为getY()和getYOnScreen()的区别。后者没有振荡(尽管偏移量有点偏)。它背后可能有一个与“事件相对于源组件的位置”有关的逻辑,但我刚刚醒来。以下是创建draggable component 的方法。 【参考方案1】:您的问题是您将MouseMotionListener
添加到了错误的组件中。您需要将其添加到label2
的父级,即jf
的内容窗格。
试试下面的代码。
import java.awt.Color;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
import javax.swing.JFrame;
import javax.swing.JLabel;
public class BasicWindow1 implements MouseMotionListener
JFrame jf = new JFrame();
JLabel label2 = new JLabel("label2");
public BasicWindow1(String string)
// JFrame
jf.setTitle(string);
jf.setSize(400, 400);
jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
jf.setLayout(null);
jf.setVisible(true);
label2.setOpaque(true);
label2.setBackground(Color.cyan);
label2.setBounds(0, 150, 75, 25);
jf.getContentPane().addMouseMotionListener(this); // CHANGE HERE
jf.add(label2);
// end constructor
public void mouseDragged(MouseEvent e)
label2.setLocation(e.getX(), e.getY()); // CHANGE HERE
public void mouseMoved(MouseEvent e)
public static void main(String[] args)
BasicWindow1 mybw = new BasicWindow1("Basic Window for Stack Overflow");
方法getX()
和getY()
,在类MouseEvent
中,返回鼠标指针在您添加MOuseMotionListener
的组件的坐标空间中的位置。在您的情况下,这是鼠标指针在 JLabel
内的位置,但这不是您想要的。您希望鼠标指针的位置在要拖动JLabel
的组件的坐标空间中,其中JFrame
或更准确地说是JFrame
的内容窗格。
有关替代解决方案,请参阅dragging a jlabel around the screen
【讨论】:
以上是关于MouseMotionListener 似乎闹鬼的主要内容,如果未能解决你的问题,请参考以下文章
为啥 DragHandler exportAs Drag 禁用了我的 MouseMotionListener?
如何将自定义的 MouseMotionListener 添加到 JPanel?
MouseMotionListener 不会将坐标传输到 Canvas