34

我希望有一个内部(非窗口)对话框来询问成员输入。我希望将对话框集中放置在现有的 JPanel 上。

我查看了分层窗格,这些似乎无法使用,因为所有窗格中只有一个布局管理器(或没有布局管理器)。我想我可以尝试覆盖 JLayeredPane 并提供自定义布局,但这似乎很极端。

玻璃板似乎也不合适。

如何才能做到这一点?Swing 中没有可用的 z-index 概念吗?

编辑

分层窗格不合适的原因是由于每层缺少布局管理器。面板可调整大小,面板 A 应保持在 100% 的区域,面板 B 应保持集中。

4

6 回答 6

38

我认为 LayeredPane 是你最好的选择。您将需要第三个面板来包含 A 和 B。这第三个面板将是 layeredPane,然后面板 A 和 B 仍然可以有一个不错的 LayoutManagers。您所要做的就是使 B 居中于 A 之上,在 Swing 路径中​​有很多关于如何做到这一点的示例。没有 LayoutManager 的定位教程

public class Main {
    private JFrame frame = new JFrame();
    private JLayeredPane lpane = new JLayeredPane();
    private JPanel panelBlue = new JPanel();
    private JPanel panelGreen = new JPanel();
    public Main()
    {
        frame.setPreferredSize(new Dimension(600, 400));
        frame.setLayout(new BorderLayout());
        frame.add(lpane, BorderLayout.CENTER);
        lpane.setBounds(0, 0, 600, 400);
        panelBlue.setBackground(Color.BLUE);
        panelBlue.setBounds(0, 0, 600, 400);
        panelBlue.setOpaque(true);
        panelGreen.setBackground(Color.GREEN);
        panelGreen.setBounds(200, 100, 100, 100);
        panelGreen.setOpaque(true);
        lpane.add(panelBlue, new Integer(0), 0);
        lpane.add(panelGreen, new Integer(1), 0);
        frame.pack();
        frame.setVisible(true);
    }


    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        new Main();
    }

}

您可以使用 setBounds 将面板定位在分层窗格内并设置它们的大小。

编辑以反映对原始帖子的更改 您将需要添加组件侦听器,以检测何时调整父容器的大小,然后动态更改面板 A 和 B 的边界。

于 2009-05-12T13:28:14.197 回答
5

您可以像这样添加未修饰的 JDialog:

import java.awt.event.*;

import javax.swing.*;

public class TestSwing {
  public static void main(String[] args) throws Exception {
    JFrame frame = new JFrame("Parent");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setSize(800, 600);
    frame.setVisible(true);

    final JDialog dialog = new JDialog(frame, "Child", true);    
    dialog.setSize(300, 200);
    dialog.setLocationRelativeTo(frame);
    JButton button = new JButton("Button");
    button.addActionListener(new ActionListener() {
      @Override
      public void actionPerformed(ActionEvent e) {
        dialog.dispose();
      }
    });
    dialog.add(button);
    dialog.setUndecorated(true);
    dialog.setVisible(true);
  }
}
于 2009-05-12T14:11:46.463 回答
5

我只是想补充一点,Swing 中有一个Z 顺序的概念,请参阅 [java.awt.Component#setComponentZOrder][1]

这会影响组件在其父组件数组中的位置,从而确定绘制顺序。

请注意,您应该重写javax.swing.JComponent#isOptimizedDrawingEnabled以在父容器中返回 false 以使重叠的组件正确重绘,否则它们的重绘将相互破坏。(JComponents 假定没有重叠的子级,除非 isOptimizedDrawingEnabled 返回 false)

[1]: http: //java.sun.com/j2se/1.5.0/docs/api/java/awt/Container.html#setComponentZOrder (java.awt.Component , int)

于 2009-05-13T16:15:13.517 回答
1

在现有的 JPanel 上使用 1 x 1 GridLayout,然后将您的面板添加到该 JPanel。1 比 1 的 GridLayout 的唯一问题是您无法在 JPanel 上放置其他项目。在这种情况下,您必须找出合适的布局。您使用的每个面板都可以使用自己的布局,这样就不会有问题。

我是否正确理解了这个问题?

于 2009-05-12T13:04:18.837 回答
1

JOptionPane.showInternalInputDialog 可能做你想要的。如果没有,了解它缺少什么会很​​有帮助。

于 2009-05-12T13:16:31.680 回答
0

这里还有另一个可能感兴趣的布局管理器:Overlay Layout 这是一个简单的教程:OverlayLayout:用于对位于彼此之上的组件进行布局管理。覆盖布局允许您将面板放置在彼此之上,并在每个面板内设置布局。您还可以分别设置每个面板的大小和位置。

(我从几年前开始回答这个问题的原因是因为我偶然发现了同样的问题,而且我很少看到 StackOverflow 上提到 Overlay Layout,虽然它似乎有很好的记录。希望这可以帮助某人其他人一直在寻找它。)

于 2016-07-21T08:40:32.043 回答