I was reading about lambdas and out of curiosity, I wanted to know why it is not allowed to use when the class / interface has more than one method, which forces us to do things like below:
component.addMouseListener(new MouseListener() {
@Override
public void mouseReleased(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mousePressed(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseExited(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseEntered(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void mouseClicked(MouseEvent e) {
// TODO Auto-generated method stub
}
});
Searching, I found this question on SOEn about the doubt, but I ended up coming across a solution that circumvents this restriction , as can be seen in this answer :
// note the absence of mouseClicked… interface ClickedListener extends MouseListener { @Override public default void mouseEntered(MouseEvent e) {} @Override public default void mouseExited(MouseEvent e) {} @Override public default void mousePressed(MouseEvent e) {} @Override public default void mouseReleased(MouseEvent e) {} }
You need to define such a helper interface only once.
Now you can add a listener for click-events on a Component c like this:
c.addMouseListener((ClickedListener)(e)->System.out.println("Clicked!"));
I ran a test and I actually saw it work:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
public class MouseListenerLambdaTest {
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
new MouseListenerLambdaTest();
});
}
public MouseListenerLambdaTest() {
initComponents();
}
private void initComponents() {
JFrame f = new JFrame();
f.setResizable(false);
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setPreferredSize(new Dimension(200, 120));
JPanel contentPane = new JPanel();
contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
f.setContentPane(contentPane);
contentPane.setLayout(new FlowLayout(FlowLayout.CENTER, 5, 5));
JLabel label = new JLabel();
contentPane.add(label);
contentPane.addMouseListener((MouseListenerHelper) (e) -> label.setText("Clicked"));
f.pack();
f.setLocationRelativeTo(null);
f.setVisible(true);
}
interface MouseListenerHelper extends MouseListener {
@Override
public default void mouseEntered(MouseEvent e) {
}
@Override
public default void mouseExited(MouseEvent e) {
}
@Override
public default void mousePressed(MouseEvent e) {
}
@Override
public default void mouseReleased(MouseEvent e) {
}
}
}
Running:
Howwasitpossibletocircumventthe MouseListener
/ a> enforces this code? How does this function know that it is the MouseClicked
method if it is not implemented?
Note: I am aware of the existence of adapters, and in this case I could simply use the
MouseAdapter
class, but the use of MouseListener was only illustrative, as not all java listeners have an equivalent adapter. p>