10

I want to use JCheckBoxMenuItems in a JPopupMenu. It works, but the problem is that the popup menu disappears when a checkbox item has been checked or unchecked. So if one wants to check/uncheck several items, the popup needs to be launched repeatedly, which is irritating.

Curiously, if I use just plain JCheckBox items in the menu (instead of JCheckBoxMenuItems), the behavior is just as it should be: the popup stays there and the checkboxes can be checked/unchecked. Once done, the popup can be closed just by clicking outside it.

How do I make the popup to behave like that when the items there are JCheckBoxMenuItems? I would prefer using JCheckBoxMenuItems because of their looks.

Joonas Pulakka
  • 34,943
  • 25
  • 103
  • 165
  • I think this is a bug and should be fixed by the Swing library authors, rather than avoided using workarounds. The only problem is, that Java developpers rather find excuses than fix their bugs. – Tomáš Zato - Reinstate Monica Mar 15 '15 at 21:57

2 Answers2

12

Well, found working answer from http://forums.sun.com/thread.jspa?threadID=5432911. Basically, create a custom UI:

public class StayOpenCheckBoxMenuItemUI extends BasicCheckBoxMenuItemUI {

   @Override
   protected void doClick(MenuSelectionManager msm) {
      menuItem.doClick(0);
   }

   public static ComponentUI createUI(JComponent c) {
      return new StayOpenCheckBoxMenuItemUI();
   }
}

And set it in the JCheckBoxMenuItem:

myJCheckBoxMenuItem.setUI(new StayOpenCheckBoxMenuItemUI());

Don't know if this is the most elegant possible solution, but works perfectly.

Joonas Pulakka
  • 34,943
  • 25
  • 103
  • 165
  • "working answer" refers to link to forums sun com which is broken – gnat Oct 13 '11 at 11:02
  • 1
    Additional information on this solution can be found here: http://www.coderanch.com/t/497325/GUI/java/keep-popup-while-clicking-JCheckBoxMenuItem – Steven Oct 21 '11 at 21:28
3

I ran into an issue with the nice Joonas Pulakka's answer because the "UIManager lookandFeel" was ignored.

I found the nice trick below on http://tips4java.wordpress.com/2010/09/12/keeping-menus-open/

The point is to reopen immediatly the menu after it has been closed, it's invisible and keep the application look and feel and behavior.

public class StayOpenCBItem extends JCheckBoxMenuItem {

    private static MenuElement[] path;

    {
        getModel().addChangeListener(new ChangeListener() {
            @Override
            public void stateChanged(ChangeEvent e) {
                if (getModel().isArmed() && isShowing()) {
                    path = MenuSelectionManager.defaultManager().getSelectedPath();
                }
            }
        });
    }

    public StayOpenCBItem(String text) {
        super(text);
    }

    @Override
    public void doClick(int pressTime) {
        super.doClick(pressTime);
        MenuSelectionManager.defaultManager().setSelectedPath(path);
    }
}
FabiF
  • 2,726
  • 2
  • 15
  • 26
  • For me, this does not work when used in a `JPopupMenu`. Quoting author from the article’s comments “The enhancements provided here were not intended to work with any kind of popup menu.” – qqilihq Dec 19 '19 at 08:24