JDialog: Remove titlebar, keep border

2019-07-22 02:00发布

问题:

Is it possible to remove the title bar from a JDialog, but keeping the border?

The base SSCCE looks like this:

package test;

import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JList;
import javax.swing.SwingUtilities;

public class SSCCE extends JFrame {
    private JDialog dialog;

    public SSCCE() {
        dialog = new JDialog();
        dialog.setSize(100, 100);
        dialog.add(new JList<>(new String[] { "One", "Two", "Three" }));
        dialog.setUndecorated(true);

        setSize(300, 200);
        setLocationRelativeTo(null);
        setDefaultCloseOperation(EXIT_ON_CLOSE);
    }

    public void showDialog() {
        dialog.setLocationRelativeTo(this);
        dialog.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                SSCCE ex = new SSCCE();
                ex.setVisible(true);
                ex.showDialog();
            }
        });
    }
}

Running it I see this:

But I don't want the title bar on the JDialog. The standard answer is to use setUndecorated(true). But then I lose the window borders as well, and I don't want that. Looks like this:

What I want is something like this mockup:

How do I achieve that?

EDIT:

I tried going with one of the LaF borders, but I'm getting some strange results. Just for testing I went with "RootPane.errorDialogBorder" and expected to get a fat red border around my dialog. But instead I got this:

That looks to me like the unfocused version of the "RootPane.frameBorder" border. Why did I get that one instead?

回答1:

It needs to somehow be based on the current LaF border style.

As you already know it is not possible to use the actual dialog/frame border.

Seems like you need a Border to highlight the popup so it stands out from the text field. I think the closest you can come is to use a Border that is defined by the LAF. For example you might be able to use the "TitledBorder.border" property defined in the UIManager it is a simple Border but appears to be slightly different for each LAF.

Take a look at UIManager Default. It displays all the Border for each LAF