Search code examples
javaswingjoptionpaneuimanager

UIManager in Java Swing not working consistently? / JOptionPane Message Background


I'm trying to set the background color in my custom JOptionPane and no matter what, I cannot get the message part of the option pane to change color.

Attempt #1 was to set the pane background and opaque.

Attempt #2 was to also loop through the pane's components, and set the opaque and/or background attributes if they were JPanel or JLabel.

This did not work for the message part. From what I can see, the JPanel does not even exist as one of the components.

Attempt #3 was to use UIManager, however this is not working consistently.

What I mean is, if you were to run the program 5 times, sometimes no background colors are changed, sometimes they all are changed, and sometimes some of them are changed.

I am running inside an invokeLater thread.

UIManager.put("OptionPane.background",Color.white);
UIManager.put("JOptionPane.background",Color.white);
UIManager.put("Panel.background",Color.white);
UIManager.put("JPanel.background",Color.white);

Any ideas?


Solution

  • You can use following workaround:

        JLabel messageLabel = new JLabel("Background is cyan!") {
            /**
             * {@inheritDoc}
             */
            @Override
            public void addNotify() {
                super.addNotify();
                if (getRootPane() != null) {
                    List<Component> children = findAllChildren(getRootPane());
                    for (Component comp : children) {
                        if (!(comp instanceof JButton)) {
                            comp.setBackground(Color.CYAN);
                        }
                    }
                }
            }
    
            private List<Component> findAllChildren(Component aComp) {
                List<Component> result = new ArrayList<Component>();
                result.add(aComp);
                if (aComp instanceof Container) {
                    Component[] children = ((Container) aComp).getComponents();
                    for (Component c : children) {
                        result.addAll(findAllChildren(c));
                    }
                }
                return result;
            }
        };
        JOptionPane.showConfirmDialog(null, messageLabel, "Test title", JOptionPane.YES_NO_CANCEL_OPTION);