JComboBox/JMenu problem
My app lists files in a directory and then adds these files into a combo box model. The combo box itself is placed inside a JMenu.
There are also two other items in the menu, 1) To add a file, 2) To remove a file. Both of these uses JFileChooser抯 and both update the combo box, via the model.
The app seems to work fine. No exception is thrown running under 1.6, but under 1.4, the following is displayed:
java.lang.NullPointerException
at javax.swing.plaf.basic.BasicPopupMenuUI$MouseGrabber.grabContainer(BasicPopupMenuUI.java:383)
at javax.swing.plaf.basic.BasicPopupMenuUI$MouseGrabber.requestAddGrab(BasicPopupMenuUI.java:267)
at javax.swing.plaf.basic.BasicPopupMenuUI$MouseGrabber.stateChanged(BasicPopupMenuUI.java:323)
at javax.swing.MenuSelectionManager.fireStateChanged(MenuSelectionManager.java:161)
at javax.swing.MenuSelectionManager.setSelectedPath(MenuSelectionManager.java:87)
at javax.swing.JPopupMenu.setVisible(JPopupMenu.java:751)
at javax.swing.JPopupMenu.show(JPopupMenu.java:927)
at javax.swing.plaf.basic.BasicComboPopup.show(BasicComboPopup.java:177)
at javax.swing.plaf.basic.BasicComboPopup.togglePopup(BasicComboPopup.java:982)
at javax.swing.plaf.basic.BasicComboPopup$InvocationMouseHandler.mousePressed(BasicComboPopup.java:632)
at java.awt.Component.processMouseEvent(Component.java:5097)
at java.awt.Component.processEvent(Component.java:4897)
at java.awt.Container.processEvent(Container.java:1569)
at java.awt.Component.dispatchEventImpl(Component.java:3615)
at java.awt.Container.dispatchEventImpl(Container.java:1627)
at java.awt.Component.dispatchEvent(Component.java:3477)
at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:3483)
at java.awt.LightweightDispatcher.processMouseEvent(Container.java:3195)
at java.awt.LightweightDispatcher.dispatchEvent(Container.java:3128)
at java.awt.Container.dispatchEventImpl(Container.java:1613)
at java.awt.Window.dispatchEventImpl(Window.java:1606)
at java.awt.Component.dispatchEvent(Component.java:3477)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:456)
at java.awt.EventDispatchThread.pumpOneEventForHierarchy(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:151)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:145)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:137)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:100)
I don抰 know if this will help, 1.4 is not used anymore, still the problem remains.
When the combo box is clicked, it should write to the console:
fav.addActionListener(new AbstractAction(){
public void actionPerformed(ActionEvent e)
{
System.out.println("Combo action");
/*// Copy to pl
((TrackList)favMod.getSelectedItem()).copyTo(plTrList);
// Make the pl outer
player.setOuterList(plTrList);
// Player from outer
player.setFromPlayer(false);
// Play
player.play();*/
}
});
Were 慺av?is the JComboBox.
But the action isn抰 called. Nor does the drop down list appear when the little arrow clicked. I have tried this app on 2 computers, and they both have the same problem.
Any help will be grand.
Luke
[3457 byte] By [
dfgstga] at [2007-11-26 14:28:33]

# 1
If you need further help then you need to create a [url http://homepage1.nifty.com/algafield/sscce.html]Short, Self Contained, Compilable and Executable, Example Program[/url] (SSCCE) that demonstrates the incorrect behaviour, because I can't guess exactly what you are doing based on the information provided.
And don't forget to use the [url http://forum.java.sun.com/help.jspa?sec=formatting]Code Formatting Tags[/url] so the code retains its original formatting.
# 2
package hmc.it.model.table.filter.view;
import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JPopupMenu;
/**
* This example demonstrates a NullPointer exception that occurs
* when a JComboBox is added as a Component to a JPopupMenu and
* then the combo box gets expanded to select another item.
*
* To see it in action, just compile and run this class. It is self-
* contained.
*
* Once it is started, click on the button to bring up the popup,
* then try to open the combo box. You'll get the following stack
* trace:
*
* java.lang.NullPointerException
* at javax.swing.plaf.basic.BasicPopupMenuUI$MouseGrabber.grabContainer(BasicPopupMenuUI.java:383)
* ....
*
* @author Vadim Yarovoy (vyarovoy@veripath.us)
* @date Jan, 10, 2007
*/
public class JComboBoxInJPopupMenuNullPointerExample {
/**
* @param args
*/
public static void main( String[] args ) {
//create frame
JFrame f = new JFrame();
f.setSize( 100, 100 );
f.setLocation( 500, 300 );
f.setTitle( "NullPointer example" );
//create button
JButton b = new JButton( "Click me" );
b.addActionListener( new ActionListener() {
public void actionPerformed( ActionEvent ev ) {
//create popup
JPopupMenu pm = new JPopupMenu();
//create the combo
JComboBox cb = new JComboBox(
new Object[] { "Open me", "Item 1", "Item 2", "Item 3" } );
//add cb to pm
pm.add( cb );
pm.show( (JButton)ev.getSource(), 10, 10 );
}
});
//add button to the frame
f.getContentPane().add( b, BorderLayout.CENTER );
f.show();
}
}
# 3
Well, I'm guessing its because when you click on the combo box another popup menu appears and the original popup is closed which is causing the problem. I don't know the solution.
However, I would suggest that instead of adding a combo box to the popup you could just add a menu item and multiple sub menu items. The code is already in place to support this type of multiple popup.
Other than that you will need to build your own popup, as follows:
JComboBox cb = new JComboBox(new Object[] { "Open me", "Item 1", "Item 2", "Item 3" } );
PopupFactory factory = PopupFactory.getSharedInstance();
Popup popup = factory.getPopup(this, cb, getLocation().x, getLocation().y);
popup.show();
Window window = SwingUtilities.windowForComponent(cb);
if (window != null)
{
window.setFocusableWindowState(true);
}
KeyboardFocusManager.getCurrentKeyboardFocusManager().focusNextComponent(cb);
But now you are resonsible for closing the popup when it loses focus or an item has been selected.
# 4
Thanks for that, to tell you the truth I didn抰 really have any idea what the problem was. But now I see how two popup menus on top of each other could be a problem.
The reason I thought about using combo boxes was that I wanted he menu items to change dynamically.
I have found a way to use menu items and a HashMap to perform the same sort of behaviour.
Thanks again, and please feel free to play about with my little tester app.
import java.util.*;
import java.awt.event.*;
import javax.swing.*;
public class MenuBarTester extends JFrame
{
// The model to link the buttons on the favourites with there data object
private HashMap favMod = new HashMap();
// All the data objects to add at the start
private String[] data = new String[]{
"The","Cat","Sat","On","The","Mat"
};
// The menus
private JMenu menFav = new JMenu("Favourites");
private JMenuBar menuBar = new JMenuBar();
// Main
public static void main(String[] args)
{ new MenuBarTester(); }
public MenuBarTester()
{
// Set all the favourites in the fav menu
setFavs(data);
// Add
menuBar.add(menFav);
// Show frame
try
{
// Set look and feel to systems, might as well
UIManager.setLookAndFeel(
UIManager.getSystemLookAndFeelClassName());
} catch (Exception ex) {}
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setSize(100,100);
this.setJMenuBar(menuBar);
this.setVisible(true);
}
public void setFavs(Object[] inFavs)
{
// Remove all
favMod.clear();
for (int i=0;i<inFavs.length;i++)
{
System.out.println(i+" is "+inFavs[i]);
// Make a new button
JMenuItem favItem = new JMenuItem(inFavs[i].toString());
// This button now links to the TrackList in pos i
favMod.put(favItem,inFavs[i]);
// Add the action adapter
favItem.addActionListener(new FavItemActionAdapter());
// Add it to the menu
menFav.add(favItem);
}
}
private class FavItemActionAdapter implements ActionListener
{
public void actionPerformed(ActionEvent e)
{
// Get the source
Object bottom=e.getSource();
System.out.println("This button is linked to "+
favMod.get(bottom));
}
}
}
>
