一个JFrame和两个JPanel

时间:2012-02-22 11:45:11

标签: java swing

我是Java的新手,我对面板有疑问。我的程序中有一个JFrame和两个JPanels

  • 当我点击button1时,panel1将显示在框架中。
  • 当我点击button2时,panel2将显示在框架中,panel1将消失/隐藏。

问题是panel1无法仅显示panel2。如何以这种方式显示两个面板?

这是我的代码:

public class test{

public static void main(String args[]){

     JButton b1 = new JButton("show p1");
     JButton b2 = new JButton("show p2");
     JLabel l1 = new JLabel("This is p1");
     JLabel l2 = new JLabel("This is p2");

     final JPanel p1 = new JPanel(new FlowLayout());
     p1.add(l1);
     final JPanel p2 = new JPanel(new FlowLayout());
     p2.add(l2);
     JPanel buttonPNL = new JPanel(new FlowLayout());
     buttonPNL.add(b1);
     buttonPNL.add(b2);

     b1.addActionListener(new ActionListener(){
        public void actionPerformed(ActionEvent e){
                p1.setVisible(true);
                p2.setVisible(false);   
        }
     });

     b2.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                    p1.setVisible(false);
                    p2.setVisible(true);   
            }
      });

     JFrame frm = new JFrame();
     frm.setLayout(new BorderLayout());
     frm.add(p1,BorderLayout.CENTER);
     frm.add(p2,BorderLayout.CENTER);
     frm.add(buttonPNL,BorderLayout.SOUTH);
     frm.setVisible(true);
     frm.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
     frm.setSize(300,300);
 }
}

5 个答案:

答案 0 :(得分:6)

BorderLayout只能处理每个约束的一个组件,即在CENTER中添加p2的那一刻,p1被遗忘。因此,要么删除/添加actionListeners,要么使用另一个LayoutManager,如f.i. CardLayout

答案 1 :(得分:3)

要实现此类目标,您需要使用CardLayout

此外,从JFrame中删除旧的JPanel以添加新的JPanel后,请始终在JFrame上执行revalidate()和repaint()以实现更改。请记住,在任何给定位置的任何给定时间只能添加一个组件。请尝试修改此代码:

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class PanelTest
{
    public PanelTest()
    {
        JButton b1 = new JButton("show p1");
        JButton b2 = new JButton("show p2");
        JLabel l1 = new JLabel("This is p1");
        JLabel l2 = new JLabel("This is p2");

        final JPanel p1 = new JPanel(new FlowLayout());
        p1.add(l1);
        final JPanel p2 = new JPanel(new FlowLayout());
        p2.add(l2);
        JPanel buttonPNL = new JPanel(new FlowLayout());
        buttonPNL.add(b1);
        buttonPNL.add(b2);

        final JFrame frm = new JFrame(); // shifted this line here.

        b1.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                    // Added by me , these three lines
                    if (p2.isShowing())
                    {
                        frm.remove(p2);
                        frm.add(p1, BorderLayout.CENTER);                   
                        frm.revalidate(); // for JDK 1.7+
                        //frm.getRootPane().revalidate(); // for JDK 1.6 or lower
                        frm.repaint();
                    }
            }
        });

        b2.addActionListener(new ActionListener(){
                public void actionPerformed(ActionEvent e){
                        if (p1.isShowing())
                        {
                            frm.remove(p1);
                            frm.add(p2, BorderLayout.CENTER);                   
                            // Added by me , these three lines
                            frm.revalidate(); // for JDK 1.7+
                            //frm.getRootPane().revalidate(); // for JDK 1.6 or lower
                            frm.repaint();
                        }
                }
        });


        frm.setLayout(new BorderLayout());
        frm.add(p1,BorderLayout.CENTER);
        frm.add(buttonPNL,BorderLayout.SOUTH);
        frm.setVisible(true);
        frm.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frm.setSize(300,300);
    }

    public static void main(String... args)
    {
        SwingUtilities.invokeLater(new Runnable()
        {
            public void run()
            {
                new PanelTest();
            }
        });
    }
}

答案 2 :(得分:2)

我认为问题是你在CENTER中只能有一个JComponent。因此,将两个面板包裹在一个面板中,只在CENTER中包含它:

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

public class JFrameProblem {

    public static void main(String[] args){

        JButton b1 = new JButton("show p1"); JButton b2 = new JButton("show p2");

        JLabel l1 = new JLabel("This is p1");
        JLabel l2 = new JLabel("This is p2");

        final JPanel p1 = new JPanel(new FlowLayout());
        p1.add(l1);
        final JPanel p2 = new JPanel(new FlowLayout());
        p2.add(l2);
        p2.setVisible(false);

        JPanel panelPNL = new JPanel(new FlowLayout());
        panelPNL.add(p1);
        panelPNL.add(p2);

        JPanel buttonPNL = new JPanel(new FlowLayout());
        buttonPNL.add(b1);
        buttonPNL.add(b2);

        b1.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                p1.setVisible(true);
                p2.setVisible(false);
            }
        });

        b2.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e){
                p1.setVisible(false);
                p2.setVisible(true);
            }
        });

        JFrame frm = new JFrame();
        frm.setLayout(new BorderLayout());
        frm.add(panelPNL,BorderLayout.CENTER);
        frm.add(buttonPNL, BorderLayout.SOUTH);
        frm.setVisible(true);
        frm.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frm.setSize(300,300);
        frm.pack();
        frm.setVisible(true);
    }

}

答案 3 :(得分:2)

我将使用选项卡式窗格来实现此功能。有关详细信息,请参阅How to Use Tabbed Panes

TabbedPaneDemo

答案 4 :(得分:1)

您可以使用BorderLayout执行此操作,您只需记住重新添加要显示的面板。实际上你已经解决了重估问题,因为你正在使用setVisible()。

这基本上就是kleopatra所说的 - 这是代码:

JButton b1 = new JButton("show p1");
JButton b2 = new JButton("show p2");
JLabel l1 = new JLabel("This is p1");
JLabel l2 = new JLabel("This is p2");

final JPanel p1 = new JPanel(new FlowLayout());
p1.add(l1);
final JPanel p2 = new JPanel(new FlowLayout());
p2.add(l2);
JPanel buttonPNL = new JPanel(new FlowLayout());
buttonPNL.add(b1);
buttonPNL.add(b2);

final JFrame frm = new JFrame();
b1.addActionListener(new ActionListener() {
    public void actionPerformed(ActionEvent e) {
        p1.setVisible(true);
        p2.setVisible(false);
        frm.add(p1, BorderLayout.CENTER);
    }
});

b2.addActionListener(new ActionListener() {
    public void actionPerformed(ActionEvent e) {
        p1.setVisible(false);
        p2.setVisible(true);
        frm.add(p2, BorderLayout.CENTER);
    }
});

frm.setLayout(new BorderLayout());
frm.add(p1, BorderLayout.CENTER);
p2.setVisible(false); // initial state
frm.add(buttonPNL, BorderLayout.SOUTH);
frm.setVisible(true);
frm.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frm.setSize(300, 300);