【问题标题】:can't set undecorated for JDialog created by JOptionPane.createDialog无法为 JOptionPane.createDialog 创建的 JDialog 设置未装饰
【发布时间】:2026-01-04 16:45:01
【问题描述】:

我从 JOptionPane 创建了 JDiolog

        var pane = new JOptionPane(e.getMessage(),JOptionPane.ERROR_MESSAGE,JOptionPane.DEFAULT_OPTION);
        var dialog = pane.createDialog("Error");
        dialog.setUndecorated(true);
        dialog.setBackground(new Color(0, 0,0,78));
        dialog.setVisible(true);
        return;

但是这段代码抛出异常

Exception in thread "AWT-EventQueue-0" java.awt.IllegalComponentStateException: The dialog is displayable.
  at java.desktop/java.awt.Dialog.setUndecorated(Dialog.java:1265)
  at com.quiz.server.LoginDialog.lambda$new$1(LoginDialog.java:56)
  blalablablabla.....

但我注释掉了这些行

    dialog.setUndecorated(true);
    dialog.setBackground(new Color(0, 0,0,78));

然后就可以了

【问题讨论】:

    标签: java swing joptionpane jdialog awt-eventqueue


    【解决方案1】:

    以下代码 sn-p 将显示没有装饰的 JOptionPane 对话框:

        boolean defaultLFDecorated = JDialog.isDefaultLookAndFeelDecorated();
        try {
            JDialog.setDefaultLookAndFeelDecorated(true);
            JOptionPane pane = new JOptionPane("This is a message", JOptionPane.ERROR_MESSAGE, JOptionPane.DEFAULT_OPTION);
            JDialog dialog = pane.createDialog("Error");
            dialog.getRootPane().setWindowDecorationStyle(JRootPane.NONE);
            pane.setOpaque(false);
            ArrayList<Component> components = new ArrayList<Component>(Arrays.asList(pane.getComponents()));
            while(!components.isEmpty()) {
                Component c = components.remove(0);
                if(c instanceof JComponent) {
                    ((JComponent)c).setOpaque(false);
                }
    
                if(c instanceof Container) {
                    components.addAll(Arrays.asList(((Container)c).getComponents()));
                }
            }
            dialog.setBackground(new Color(0, 0, 0, 78));
            dialog.setVisible(true);
            dialog.dispose();
        }
        finally {
            JDialog.setDefaultLookAndFeelDecorated(defaultLFDecorated);
        }
    

    【讨论】:

    • 我不能用它设置背景颜色,但它可以在没有装饰的情况下工作。非常感谢:)
    • @noone 我已经修改了代码 sn-p 来遍历组件和 setOpaque(false)