如何外部化 MouseListener?
How to externalize a MouseListener?
(注意: 我知道 MouseAdapter
-class 的存在,但由于我稍后可能会覆盖所有方法,所以它的优势消失了?)
我有一个 class MainProgram.java,我在其中添加了几个组件。它们中的大多数都有一个 Listener(ActionListener、MouseListener,...),这在我的主 class 中有点拥挤。
因此我正在尝试 "externalize" 那些听众进入他们自己的 classes。到目前为止,我在我的 main-class 中使用了内部 classes,这使得访问变量、组件……非常简单直接。
但是对于外部侦听器,我不确定实现它们的最佳方式是什么。
例如,当我想知道点击了哪个标签时,我正在获取事件,获取事件源,将其转换为 JLabel
然后获取文本在我比较字符串的标签上!
这有效,但似乎很容易出错(如果我在主 class 中更改 JLabel 文本怎么办?-> 监听器中断)并且非常不干净。
我试图通过 google 和 Whosebug 搜索更好的方法,但只找到了内部 class 方法。
那么有没有更好的方法来访问我的组件/外部化我的听众?
public class MainProgram extends JFrame {
public MainProgram() {
super("Landing Page");
setSize(400, 400);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel westPanel = new JPanel();
JLabel lbl_orderStatus = new JLabel("Order Status");
JLabel lbl_technicalDocu = new JLabel("Technical Documentation");
JLabel lbl_checkReport = new JLabel("Check Report");
MouseListenerBoldFont mouseListenerLabelBoldPlain = new MouseListenerBoldFont();
lbl_orderStatus.addMouseListener(mouseListenerLabelBoldPlain);
lbl_technicalDocu.addMouseListener(mouseListenerLabelBoldPlain);
lbl_checkReport.addMouseListener(mouseListenerLabelBoldPlain);
westPanel.add(lbl_orderStatus);
westPanel.add(lbl_technicalDocu);
westPanel.add(lbl_checkReport);
add(westPanel);
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
MainProgram window = new MainProgram();
window.setVisible(true);
}
catch (Exception e) {
e.printStackTrace();
}
}
});
}
MouseListenerBoldFont.java:
public class MouseListenerBoldFont implements MouseListener{
Object lbl_westPanel;
@Override
public void mouseClicked(MouseEvent e) {
if(((JLabel)e.getSource()).getText().equals("Order Status")){
System.out.println("Order Status clicked");
};
if(((JLabel)e.getSource()).getText().equals("Technical Documentation")){
System.out.println("Technical Documentation clicked");
};
if(((JLabel)e.getSource()).getText().equals("Check Report")){
System.out.println("Check Report clicked");
};
}
@Override
public void mouseEntered(MouseEvent e) {
lbl_westPanel = e.getSource();
((JComponent) lbl_westPanel).setFont(new Font("tahoma", Font.BOLD, 12));
}
@Override
public void mouseExited(MouseEvent e) {
lbl_westPanel = e.getSource();
((JComponent) lbl_westPanel).setFont(new Font("tahoma", Font.PLAIN, 11));
}
@Override
public void mousePressed(MouseEvent e) {
}
@Override
public void mouseReleased(MouseEvent e) {
}
}
您可能仍想使用扩展 MouseAdapter 的 class,因为它可以同时用作 MouseListener、MouseMotionListener 和 MouseWheelListener(您只需添加它作为所有这些成一个组件)。我不确定为什么您需要获取 JLabel 上的文本以检测它是否已被单击。您应该创建一个扩展 MouseAdapter 的 class 并使其专用于 JLabel,然后将其添加到该 JLabel。如果您希望将 JLabel 作为参数,您应该定义一个自定义构造函数,以便它自动知道正在与什么 JLabel 进行交互。然后,您可以添加一个将事件传递给主 class.
的方法
我的建议是编写内联 (anonymous-class) 处理程序,将实际处理转发给另一个 non-anonymous 函数。这会给你类似的东西:
JLabel lblOrderStatus = new JLabel("Order Status");
lblOrderStatus.addMouseListener(new MouseAdapter() {
public void mouseClicked(MouseEvent evt) {
doWhateverClickOnOrderStatusRequires();
}
});
// much later
private void doWhateverClickOnOrderStatusRequires() { ... }
外部not-quite-handler方法的名称(doWhateverClickOnOrderStatusRequires
)应该捕获它试图完成的任务(例如,launchRockets
);使用此模式,您可以从多个处理程序调用相同的 not-quite-handler 方法。由于编译器将检查调用是否有效 compile-time,因此不涉及脆弱的 string-constants。
确定这不是最好的方法,但可能对您的问题有用
public class MyLabel extends JLabel implements MouseListener {
public MyLabel() {
addMouseListener(this);
}
public MyLabel(String txt) {
super(txt);
addMouseListener(this);
}
public void mouseClicked(MouseEvent e) {
System.out.println(getText() + " clicked");
}
public void mouseEntered(MouseEvent e) {
setFont(new Font("tahoma", Font.BOLD, 12));
}
public void mouseExited(MouseEvent e) {
setFont(new Font("tahoma", Font.PLAIN, 11));
}
public void mousePressed(MouseEvent e) { }
public void mouseReleased(MouseEvent e) { }
}
然后
JLabel lbl_orderStatus = new MyLabel("Order Status");
JLabel lbl_technicalDocu = new MyLabel("Technical Documentation");
JLabel lbl_checkReport = new MyLabel("Check Report");
// MouseListenerBoldFont mouseListenerLabelBoldPlain = new MouseListenerBoldFont();
//
// lbl_orderStatus.addMouseListener(mouseListenerLabelBoldPlain);
// lbl_technicalDocu.addMouseListener(mouseListenerLabelBoldPlain);
// lbl_checkReport.addMouseListener(mouseListenerLabelBoldPlain);
(注意: 我知道 MouseAdapter
-class 的存在,但由于我稍后可能会覆盖所有方法,所以它的优势消失了?)
我有一个 class MainProgram.java,我在其中添加了几个组件。它们中的大多数都有一个 Listener(ActionListener、MouseListener,...),这在我的主 class 中有点拥挤。
因此我正在尝试 "externalize" 那些听众进入他们自己的 classes。到目前为止,我在我的 main-class 中使用了内部 classes,这使得访问变量、组件……非常简单直接。
但是对于外部侦听器,我不确定实现它们的最佳方式是什么。
例如,当我想知道点击了哪个标签时,我正在获取事件,获取事件源,将其转换为 JLabel
然后获取文本在我比较字符串的标签上!
这有效,但似乎很容易出错(如果我在主 class 中更改 JLabel 文本怎么办?-> 监听器中断)并且非常不干净。
我试图通过 google 和 Whosebug 搜索更好的方法,但只找到了内部 class 方法。
那么有没有更好的方法来访问我的组件/外部化我的听众?
public class MainProgram extends JFrame {
public MainProgram() {
super("Landing Page");
setSize(400, 400);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel westPanel = new JPanel();
JLabel lbl_orderStatus = new JLabel("Order Status");
JLabel lbl_technicalDocu = new JLabel("Technical Documentation");
JLabel lbl_checkReport = new JLabel("Check Report");
MouseListenerBoldFont mouseListenerLabelBoldPlain = new MouseListenerBoldFont();
lbl_orderStatus.addMouseListener(mouseListenerLabelBoldPlain);
lbl_technicalDocu.addMouseListener(mouseListenerLabelBoldPlain);
lbl_checkReport.addMouseListener(mouseListenerLabelBoldPlain);
westPanel.add(lbl_orderStatus);
westPanel.add(lbl_technicalDocu);
westPanel.add(lbl_checkReport);
add(westPanel);
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
MainProgram window = new MainProgram();
window.setVisible(true);
}
catch (Exception e) {
e.printStackTrace();
}
}
});
}
MouseListenerBoldFont.java:
public class MouseListenerBoldFont implements MouseListener{
Object lbl_westPanel;
@Override
public void mouseClicked(MouseEvent e) {
if(((JLabel)e.getSource()).getText().equals("Order Status")){
System.out.println("Order Status clicked");
};
if(((JLabel)e.getSource()).getText().equals("Technical Documentation")){
System.out.println("Technical Documentation clicked");
};
if(((JLabel)e.getSource()).getText().equals("Check Report")){
System.out.println("Check Report clicked");
};
}
@Override
public void mouseEntered(MouseEvent e) {
lbl_westPanel = e.getSource();
((JComponent) lbl_westPanel).setFont(new Font("tahoma", Font.BOLD, 12));
}
@Override
public void mouseExited(MouseEvent e) {
lbl_westPanel = e.getSource();
((JComponent) lbl_westPanel).setFont(new Font("tahoma", Font.PLAIN, 11));
}
@Override
public void mousePressed(MouseEvent e) {
}
@Override
public void mouseReleased(MouseEvent e) {
}
}
您可能仍想使用扩展 MouseAdapter 的 class,因为它可以同时用作 MouseListener、MouseMotionListener 和 MouseWheelListener(您只需添加它作为所有这些成一个组件)。我不确定为什么您需要获取 JLabel 上的文本以检测它是否已被单击。您应该创建一个扩展 MouseAdapter 的 class 并使其专用于 JLabel,然后将其添加到该 JLabel。如果您希望将 JLabel 作为参数,您应该定义一个自定义构造函数,以便它自动知道正在与什么 JLabel 进行交互。然后,您可以添加一个将事件传递给主 class.
的方法我的建议是编写内联 (anonymous-class) 处理程序,将实际处理转发给另一个 non-anonymous 函数。这会给你类似的东西:
JLabel lblOrderStatus = new JLabel("Order Status");
lblOrderStatus.addMouseListener(new MouseAdapter() {
public void mouseClicked(MouseEvent evt) {
doWhateverClickOnOrderStatusRequires();
}
});
// much later
private void doWhateverClickOnOrderStatusRequires() { ... }
外部not-quite-handler方法的名称(doWhateverClickOnOrderStatusRequires
)应该捕获它试图完成的任务(例如,launchRockets
);使用此模式,您可以从多个处理程序调用相同的 not-quite-handler 方法。由于编译器将检查调用是否有效 compile-time,因此不涉及脆弱的 string-constants。
确定这不是最好的方法,但可能对您的问题有用
public class MyLabel extends JLabel implements MouseListener {
public MyLabel() {
addMouseListener(this);
}
public MyLabel(String txt) {
super(txt);
addMouseListener(this);
}
public void mouseClicked(MouseEvent e) {
System.out.println(getText() + " clicked");
}
public void mouseEntered(MouseEvent e) {
setFont(new Font("tahoma", Font.BOLD, 12));
}
public void mouseExited(MouseEvent e) {
setFont(new Font("tahoma", Font.PLAIN, 11));
}
public void mousePressed(MouseEvent e) { }
public void mouseReleased(MouseEvent e) { }
}
然后
JLabel lbl_orderStatus = new MyLabel("Order Status");
JLabel lbl_technicalDocu = new MyLabel("Technical Documentation");
JLabel lbl_checkReport = new MyLabel("Check Report");
// MouseListenerBoldFont mouseListenerLabelBoldPlain = new MouseListenerBoldFont();
//
// lbl_orderStatus.addMouseListener(mouseListenerLabelBoldPlain);
// lbl_technicalDocu.addMouseListener(mouseListenerLabelBoldPlain);
// lbl_checkReport.addMouseListener(mouseListenerLabelBoldPlain);