Use Same Event For Multiple JLabels - java

I am using NetBeans and am wanting to use one MouseClick event for 3 JLabels. My issue is that in the Designer when I click on Properties - Events, NetBeans wants to add a custom event handler to my code like this
private void jLabel4MouseClicked(java.awt.event.MouseEvent evt) {
// TODO add your handling code here:
}
But all I want is for the Designer to let me use this custom event as my OnClick event for all labels.
public void mousePressed(MouseEvent mEvt) {
JLabel label = (JLabel) mEvt.getSource();
Icon icon = label.getIcon();
//JOptionPane.showMessageDialog(label, icon);
}

Related

How to "close" a JMenu in an Event Handler - Java

I have a simple MouseAdapter that I add to a JMenu. I want the menu to show its contents when moused over, react when clicked on, and hide its contents when the mouse leaves it. Here's where I add the listener:
public final void addGuiReaction(Runnable clickReaction) {
JMenu THIS = this;
this.addMouseListener(new MouseAdapter() {
final Runnable reaction = clickReaction;
final JMenu source = THIS;
#Override
public void mouseClicked(MouseEvent arg0) {reaction.run();}
#Override
public void mouseEntered(MouseEvent arg0) {source.doClick();} // Opens the menu
#Override
public void mouseExited(MouseEvent arg0) {/* Need to "close" the menu */}
});
}
This works just fine for both the reaction and the open when moused over functionality, but I can't figure out how to close it. Tried both setSelected(false) and setPopupMenuVisible(false) but the issue with both is that the menu doesn't open again the next time I mouse over it.
Anyone knows a nice way of closing the menu?
Answering to "How to close the JMenu..."
In place of this:
/* Need to "close" the menu */
You can put this:
source.dispatchEvent(new KeyEvent(source, KeyEvent.KEY_PRESSED, 0, 0, KeyEvent.VK_ESCAPE));
Hence simulate the ESC key press which will trigger the respective Action from the ActionMap of the JMenuBar.
However this will not fully solve your problem as while the keyboard arrow keys will work, you will not be able to use the mouse to select any of the items of the JMenu as trying to enter any of them will trigger the JMenu mouseExited event. You may need to attach a proper mouse event listener to the menu items as well.

MouseMotionListener doesn't respond over JButtons

So I have a JPanel called contentPanel that holds 2 inner containers. The first is a scorePanel that holds a few buttons, a slider and a label. The other is a buttonPanel which is a grid of JButtons.
In my contentPanel class, I have implemented the MouseMotionListener interface and added this listener to buttonPanel called buttons.
The issue I'm having is that the mouseMoved method never gets called and I cannot get mouse coordinates while the mouse is hovering over a button. If instead I add the listener to each button, I get the mouse coordinates, but only as they relate to the origin of the button it's hovering inside of. Additionally if I add the listener to the contentPanel, I get the mouse coordinates starting from the origin of that container, but it does not trigger the event over the buttons.
Can anyone explain how to mitigate this problem and get the mouse coordinates from the origin of the button panel without JButton obstruction?
Tia.
*UPDATE: * I have made one change that has enabled the correct behavior I'm seeking, however only with a caveat. I adjusted the padding space between the buttons in the GridLayout to 15px and now when the mouse enters those in-between regions, the mouseEvent triggers. This will enable the same effect as what I seek.
I located some research about JButton's or other components consuming MouseEvents and not passing the event onto their parents. The solution was recommended by a member of the team at Sun/Oracle, which is to re-dispatch the event to the parent of the JComponent, which would be its container.
This was achieved with the following code:
JComponent subComponent = new JButton("JButton");
MouseAdapter redispatcher = new MouseAdapter()
{
#Override
public void mouseEntered(MouseEvent evt)
{
dispatchMouseEvent(evt);
}
#Override
public void mouseExited(MouseEvent evt)
{
dispatchMouseEvent(evt);
}
#Override
public void mouseMoved(MouseEvent evt)
{
dispatchMouseEvent(evt);
}
#Override
public void mousePressed(MouseEvent evt)
{
dispatchMouseEvent(evt);
}
private void dispatchMouseEvent(MouseEvent evt)
{
Container parent = evt.getComponent().getParent();
parent.dispatchEvent(SwingUtilities.convertMouseEvent(evt.getComponent(), evt, parent));
}
};
subComponent.addMouseListener(redispatcher);
subComponent.addMouseMotionListener(redispatcher);
Which was inevitably a great solution to passing events along. (http://www.jyloo.com/news/?pubId=1315817317000)

JMenu submenu mouse listener didn't listen; action listener did--why?

I just began using JMenu. To ease into it, I decided to use Netbeans form design tool, which has worked great for all components in this app.
Clicking a top-level menu item works great.
For one menu item, I made a submenu with 3 items, each with a mouse click listener.
Here's relevant code for one of the 3 submenus:
private JMenuItem mnuEditDicAddAllScratch;
mnuEditDicAddAllScratch = new JMenuItem();
private void mnuEditDicAddAllScratchMouseClicked(MouseEvent evt) {
new WordsToAdd(); // never happened
}
mnuEditDicAddAllScratch.addMouseListener(new MouseAdapter() {
public void mouseClicked(MouseEvent evt) {
mnuEditDicAddAllScratchMouseClicked(evt);
}
});
mnuEdit.add(mnuEditDicAddAllScratch);
It didn't work. Clicks ignored.
So I tried an Action listener:
private void mnuEditDicAddAllScratchActionPerformed(ActionEvent evt) {
new WordsToAdd(); // WORKED
}
mnuEditDicAddAllScratch.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
mnuEditDicAddAllScratchActionPerformed(evt);
}
});
And it worked.
So a question is, "Why didn't mouse click listener listen?"
Also, "If I should stay away from mouse click events, why or under what circumstances?"
(And, pre-emptive strike: I should stay away from Netbeans form designer.)
You should use the best tool for the job at hand. This means that for JMenuItems and for JButtons, you should use ActionListeners, not MouseListeners (exceptions notwithstanding). For instance if you disable a button, you want the button to not work, right? This works with ActionListeners but not with MouseListeners.
For the best information on this type of stuff, go to the source: Swing Tutorials.
mnuEditDicAddAllScratch.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent actionEvent) {
mnuEditDicAddAllScratchActionPerformed();
}
});

Why ChangeListener of JTabbedPane loads with starting of main JFrame?

Following is snap of my ChangeListner method, when i run my project, before i actually reach to tabbedPan the
JOptionDialog pops out(actually along with jframe loads)! My actual purpose is i want to listen the changing of tabs so that i can load some contents on that tab from database! help me
jTabbedPane1.addChangeListener(new ChangeListener() {
public void stateChanged(ChangeEvent evt) {
jtabpanChangeListner(evt);
}
});
private void jtabpanChangeListner(ChangeEvent evt) {
// TODO add your handling code here:
int index = jTabbedPane1.getSelectedIndex();
String msg = jTabbedPane1.getTitleAt(index);
System.out.println("Tab changed to: " +msg);
JOptionPane.showMessageDialog(jTabbedPane1,"hello change me do you?+");}
JTabbedPane sends ChangeEvent's when a selected tab changes. In particular, when the JTabbedPane is empty and you add a first tab the JTabbedPane will send the ChangeEvent meaning that selected tab changed from null to something.
You need to either take into account that first change event, or to add the ChangeListener after you added the first tab into the JTabbedPane.

stackoverflow error when I add a glasspane to my frame

I am trying to add a universal right click to textfields in my application. I came across a solution where I could add a glass pane on top my frame, make it invisible and register that as a universal mouse listener. If the component is a text field I show the pop up menu, otherwise I redispatch the event. I have pasted the code below...
This example works fine. But when I use this with my application though, I get a stackoverflow error at
Exception in thread "AWT-EventQueue-0" java.lang.StackOverflowError
at apple.awt.CWindow._getLocationOnScreen(Native Method)
at apple.awt.CWindow.getLocationOnScreen(CWindow.java:878)
at java.awt.Component.getLocationOnScreen_NoTreeLock(Component.java:1960)
at java.awt.Component.getLocationOnScreen(Component.java:1938)
at javax.swing.SwingUtilities.convertPointToScreen(SwingUtilities.java:364)
at javax.swing.SwingUtilities.convertPoint(SwingUtilities.java:165)
at com.aesthete.csmart.ui.common.components.RightClickGlassPane.redispatchMouseEvent(RightClickGlassPane.java:79)
at com.aesthete.csmart.ui.common.components.RightClickGlassPane.mouseEntered(RightClickGlassPane.java:61)
I understand that every time the mouse is entered on a component the glass pane receives the event and then redispatches. But why is it getting converted into a recursive call?
EDIT:
Just wanted to show everyone how I solved it with Camickr suggestion:
SwingUtilities.invokeLater(new Runnable() {
public void run() {
final JPopupMenu popup = new JPopupMenu();
JMenuItem mnItemCopy = new JMenuItem("Copy", CommonUI.getScaledImage(13, 13, "/images/copy.png"));
JMenuItem mnItemCut = new JMenuItem("Cut", CommonUI.getScaledImage(13, 13, "/images/cut.png"));
JMenuItem mnItemPaste = new JMenuItem("Paste", CommonUI.getScaledImage(13, 13, "/images/paste.png"));
popup.add(mnItemCopy);
popup.add(mnItemCut);
popup.add(mnItemPaste);
Toolkit.getDefaultToolkit().addAWTEventListener(new AWTEventListener() {
#Override
public void eventDispatched(AWTEvent event) {
if(event instanceof MouseEvent) {
MouseEvent mouseevent=(MouseEvent)event;
if(mouseevent.isPopupTrigger()) {
if (mouseevent.getComponent() instanceof JTextField) {
popup.show(mouseevent.getComponent(), mouseevent.getX(), mouseevent.getY());
}
}
}
}
}, AWTEvent.MOUSE_EVENT_MASK);
}
});
I am trying to add a universal right click to textfields in my application.
Check out Global Event LIsteners. Just check the source of the event and do processing as required. No need to redispatch events.
Note, you should NOT assume a right click is the LAF way to display a popup. Read the section from the Swing tutorial on Bringing Up a Popup Menu for a better solution.

Categories

Resources