添加两个 JPanel 时出现问题

Issue when adding two JPanels

我正在尝试将两个 JPanel 添加到 JFrame,一个具有简单的背景,另一个具有按钮等。要么我只得到按钮,要么只得到背景。我在任何地方都找不到解决我的问题的方法,因此我们将不胜感激。我还是新手Java,所以请不要讨厌

GUIMainMenu:

public class GuiMainMenu extends JFrame implements ActionListener, KeyListener {
    private static final long serialVersionUID = -7936366600070922227L;

    Color blue = new Color(114, 137, 218);
    Color gray = new Color(44, 47, 51);
    Color white = new Color(255, 255, 255);

    ImagePanel panel = new ImagePanel(new ImageIcon("image.png").getImage());

    public static int width;
    public static int height;

    JPanel p = new JPanel();
    JPanel p1 = new JPanel();
    JLabel l = new JLabel();
    JLabel l1 = new JLabel();
    JLabel l2 = new JLabel();
    JButton b = new JButton();
    JButton b1 = new JButton();
    JButton b2 = new JButton();
    String title = "-";

    
    public GuiMainMenu() {
        setSize(m.X, m.Y);
        setTitle(title);
        setResizable(true);
        setLocationRelativeTo(null);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        addKeyListener(this);

        p.setLayout(null);

        width = getWidth();
        height = getHeight();

        getRootPane().addComponentListener(new ComponentAdapter() {
            public void componentResized(ComponentEvent e) {
                width = getWidth();
                height = getHeight();

                addButtons();
                addLabels();
            }
        });

        addLabels();
        addButtons();
        
        add(p);
        add(panel);
        setVisible(true);
    }

    public void addLabels() {
        l.setSize(width, height);
        l.setLocation(5, -40);
        l.setText("x");
        l.setHorizontalAlignment(SwingConstants.LEFT);
        l.setVerticalAlignment(SwingConstants.BOTTOM);
        l.setForeground(blue);
        l.setFont(new Font("Trebuchet MS", Font.PLAIN, 15));

        l1.setSize(width, height);
        l1.setLocation(-22, -40);
        l1.setText("y");
        l1.setHorizontalAlignment(SwingConstants.RIGHT);
        l1.setVerticalAlignment(SwingConstants.BOTTOM);
        l1.setForeground(blue);
        l1.setFont(new Font("Trebuchet MS", Font.PLAIN, 15));

        l2.setText("test label");
        l2.setSize(width, height);
        l2.setLocation(0, -75);
        l2.setVerticalAlignment(SwingConstants.CENTER);
        l2.setHorizontalAlignment(SwingConstants.CENTER);
        l2.setForeground(blue);
        l2.setFont(new Font("Trebuchet MS", Font.BOLD, 26));

        p.add(l);
        p.add(l1);
        p.add(l2);
        validate();
    }

    public void addButtons() {
        b.setText("button0");
        b.setFocusable(false);
        b.setBorder(null);
        b.setLocation(width / 2 - 200, height / 2 - 35);
        b.setSize(400, 35);
        b.setForeground(white);
        b.setBackground(blue);
        b.addActionListener(this);

        b1.setText("button1");
        b1.setFocusable(false);
        b1.setBorder(null);
        b1.setLocation(width / 2 - 200, height / 2 + 10);
        b1.setSize(400, 35);
        b1.setForeground(white);
        b1.setBackground(blue);
        b1.addActionListener(this);

        p.add(b);
        p.add(b1);
        validate();
    }

    @Override
    public void actionPerformed(ActionEvent arg0) {
    }

    @Override
    public void keyPressed(KeyEvent arg0) {
    }

    @Override
    public void keyReleased(KeyEvent arg0) {
    }

    @Override
    public void keyTyped(KeyEvent arg0) {
    }
}

图片面板Class:

class ImagePanel extends JPanel {
    private static final long serialVersionUID = -7270956677693528549L;
    private Image img;

    public ImagePanel(String img) {
        this(new ImageIcon(img).getImage());
    }

    public ImagePanel(Image img) {
        this.img = img;
    }

    public void paintComponent(Graphics g) {
        g.drawImage(img, 0, 0, GuiMainMenu.width, GuiMainMenu.height, null);
    }
}

我想您想显示一个带有背景图像和各种组件的 JFrame。我认为在查看您的代码后,您的一些误解导致了问题。

我创建了一小段代码来完成基础工作,也许可以帮助您解决问题。 (未经测试!)

@SuppressWarnings("serial")
public class GuiMainMenu extends JFrame{

    private BufferedImage imageBackground;  // TODO: load your background image

    public GuiMainMenu(){
        setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        setPreferredSize(new Dimension(1024, 768));
        setMinimumSize(new Dimension(800, 600));
        // TODO: setLayout if needed
        JPanel panel = (JPanel)add(new JPanel(){
            @Override
            public void paintComponent(Graphics g){
                super.paintComponent(g);
                g.drawImage(imageBackground, 0, 0, this);
            }
        });
        addOtherComponents(panel);
        pack();
        setLocationRelativeTo(null);
        setTitle("Your Title her");
        setVisible(true);
    }

    private void addOtherComponents(JPanel panel){
        //TODO: add the needed Stuff
        //panel.add ...
    }
}
p.setLayout(null); 

不要使用空布局。 Swing 旨在与布局管理器一起使用。

阅读有关 Layout Managers 的 Swing 教程部分,了解更多信息和工作示例。

Either I get only buttons or only the background

add(p);
add(panel);

JFrame 的默认布局管理器是 BorderLayout。如果您不指定约束,则两个组件都会添加到 CENTER。但是只会显示最后添加的一个。

尝试以下操作以查看差异:

add(p, BorderLayout.PAGE_STRT);
add(panel, BorderLayout.CENTER);

one with a simple backround and another one with buttons etc.

然而以上并不是你想要的。 Swing 组件具有 parent/child 关系。所以你真正需要的是:

backgroundPanel.add(buttonPanel);
add(backgroundPanel, BorderLayout.CENTER);

注意我使用了更有意义的名称,因为“p”和“panel”并没有描述性。为变量使用描述性名称,以便人们可以理解它们的意思。