Несколько панелей друг под другом

Возможно ли, чтобы у меня была верхняя панель для входа в систему. Затем средняя и нижняя панель внизу. Я использую gridbaglayout и назначил 2 панели. С одной панелью связаны компоненты для входа в систему, а с другой панелью связаны другие компоненты. Однако, это происходит не по плану. Я пытался сделать это с помощью Box/Borderlayout, но тогда я не смог создать нужный интервал.

Вот эскиз того, что я хочу.

http://s16.postimage.org/dtefn48qd/16_11_2012_11_24_40.png

public class GUI extends JFrame{

    private JPanel myTopPL, myTopPL2;
    private JTextField myUsernameTF;
    private JTextField myPasswordTF;
    private JTextField myMessageTF;
    private JLabel myUsernameLBL;
    private JLabel myPasswordLBL;
    private JLabel myItemsLBL;
    private JTextArea myMainTA;
    private JButton myLoginBN;
    private JButton myConnectBN;
    private JButton mySendBN;
    private JComboBox myItemsCB;

    public GUI () {

        super("GUI ");

        setLayout(new GridBagLayout());
        myTopPL = new JPanel();
        myTopPL2 = new JPanel();
        myTopPL.setLayout(new GridBagLayout());
        myTopPL2.setLayout(new GridBagLayout());
        GridBagConstraints myTopPLGBC = new GridBagConstraints();
        myTopPLGBC.weightx = 1;
        myTopPLGBC.weighty = 1;
        GridBagConstraints myTopPLGBC2 = new GridBagConstraints();
        myTopPLGBC.weightx = 2;
        myTopPLGBC.weighty = 2;

        myUsernameLBL = new JLabel("Username: ");
        myUsernameLBL.setFont(new Font("Arial", Font.BOLD, 13));
        myTopPLGBC.gridx = 1;
        myTopPLGBC.gridy = 1;
        myTopPLGBC.insets = new Insets(5,5,5,5);
        myTopPL.add(myUsernameLBL, myTopPLGBC);

        myUsernameTF = new JTextField(10);
        myTopPLGBC.gridx = 2;
        myTopPLGBC.gridy = 1;
        myTopPLGBC.insets = new Insets(5,5,5,5);
        myTopPL.add(myUsernameTF,myTopPLGBC);

        myPasswordLBL = new JLabel("Password: ");
        myPasswordLBL.setFont(new Font("Arial", Font.BOLD, 13));
        myTopPLGBC.gridx = 3;
        myTopPLGBC.gridy = 1;
        myTopPLGBC.insets = new Insets(5,5,5,5);
        myTopPL.add(myPasswordLBL, myTopPLGBC);

        myPasswordTF = new JTextField(10);
        myTopPLGBC.gridx = 4;
        myTopPLGBC.gridy = 1;
        myTopPLGBC.insets = new Insets(5,5,5,5);
        myTopPL.add(myPasswordTF,myTopPLGBC);

        myLoginBN = new JButton("Login");
        myTopPLGBC.gridx = 5;
        myTopPLGBC.gridy = 1;
        myTopPLGBC.insets = new Insets(5,5,5,5);
        myTopPL.add(myLoginBN,myTopPLGBC);

        myItemsLBL = new JLabel("Items: ");
        myItemsLBL.setFont(new Font("Arial", Font.BOLD, 13));
        myTopPLGBC2.gridx = 1;
        myTopPLGBC2.gridy = 3;
        myTopPLGBC2.insets = new Insets(5,5,5,5);
        myTopPL2.add(myItemsLBL, myTopPLGBC2);

        myItemsCB = new JComboBox();
        myItemsCB.addItem("     Select an Item     ");
        myTopPLGBC2.gridx = 1;
        myTopPLGBC2.gridy = 4;
        myTopPLGBC2.insets = new Insets(5,5,5,5);
        myTopPL2.add(myItemsCB, myTopPLGBC2);

        myConnectBN = new JButton("Connect");
        myTopPLGBC2.gridx = 2;
        myTopPLGBC2.gridy = 4;
        myTopPLGBC2.insets = new Insets (5,5,5,5);
        myTopPL2.add(myConnectBN, myTopPLGBC2);

        GridBagConstraints GBC = new GridBagConstraints();
        GBC.anchor = GridBagConstraints.NORTHWEST;
        GBC.weightx = 1;
        GBC.weighty = 1; 
        this.add(myTopPL,GBC);  

        GridBagConstraints GBC2 = new GridBagConstraints();
        GBC2.anchor = GridBagConstraints.NORTHWEST;
        GBC2.weightx = 2;
        GBC2.weighty = 2; 
        this.add(myTopPL2,GBC2);    

    }

    public static void main(String[] args) {

        GUI GUI = new GUI ();
        GUI .setDefaultCloseOperation(RMIAuctionHouse.EXIT_ON_CLOSE);
        GUI .setSize(750,500);
        GUI .setVisible(true);
    }
}

person Community    schedule 16.11.2012    source источник


Ответы (3)


Я бы разбил приложение на отдельные области ответственности и сосредоточился на создании элементов пользовательского интерфейса для его поддержки. Это позволит вам сосредоточиться на потребностях каждого раздела вашего приложения, а также даст вам возможность изменять макет по мере необходимости.

введите здесь описание изображения

public class TestLayout15 {

    public static void main(String[] args) {
        new TestLayout15();
    }

    public TestLayout15() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                }

                JFrame frame = new JFrame("Test");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.setLayout(new BorderLayout());
                frame.add(new MainPane());
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }

        });
    }

    public class MainPane extends JPanel {

        private JTextField messageField;
        private JButton sendButton;

        public MainPane() {
            setBorder(new EmptyBorder(4, 4, 4, 4));
            setLayout(new GridBagLayout());
            GridBagConstraints gbc = new GridBagConstraints();
            gbc.gridx = 0;
            gbc.gridy = 0;
            gbc.weightx = 1;
            gbc.fill = GridBagConstraints.HORIZONTAL;
            gbc.gridwidth = GridBagConstraints.REMAINDER;
            add(new LoginPane(), gbc);
            gbc.gridy++;
            add(new ConnectPane(), gbc);
            gbc.gridy++;
            gbc.weighty = 1;
            gbc.fill = GridBagConstraints.BOTH;
            add(new JScrollPane(new JTextArea(5, 20)), gbc);

            gbc.gridwidth = 1;

            messageField = new JTextField(10);
            sendButton = new JButton("Send");

            gbc.gridy++;
            gbc.weighty = 0;
            gbc.fill = GridBagConstraints.HORIZONTAL;
            add(messageField, gbc);
            gbc.gridx++;
            gbc.weightx = 0;
            add(sendButton, gbc);            
        }

    }

    public class ConnectPane extends JPanel {

        private JComboBox comboBox;
        private JButton connectButton;

        public ConnectPane() {
            comboBox = new JComboBox();
            connectButton = new JButton("Connect");

            setLayout(new GridBagLayout());
            GridBagConstraints gbc = new GridBagConstraints();
            gbc.gridx = 0;
            gbc.gridy = 0;
            gbc.anchor = GridBagConstraints.WEST;
            add(comboBox, gbc);

            gbc.gridx++;
            gbc.weightx = 1;
            add(connectButton, gbc);
        }

    }

    public class LoginPane extends JPanel {

        private JTextField userNameField;
        private JPasswordField passwordField;
        private JButton loginButton;

        public LoginPane() {

            userNameField = new JTextField(10);
            passwordField = new JPasswordField(10);
            loginButton = new JButton("Login");

            setLayout(new GridBagLayout());
            GridBagConstraints gbc = new GridBagConstraints();
            gbc.gridx = 0;
            gbc.gridy = 0;
            gbc.anchor = GridBagConstraints.WEST;
            add(new JLabel("User name:"), gbc);

            gbc.gridx++;
            add(userNameField, gbc);

            gbc.gridx++;
            add(new JLabel("Password:"), gbc);

            gbc.gridx++;
            add(passwordField, gbc);

            gbc.gridx++;
            gbc.weightx = 1;
            add(loginButton, gbc);

        }

    }

}
person MadProgrammer    schedule 16.11.2012

Для начала замените вызов GUI.setSize(750,500) на GUI.pack(). Это изменит размер окна в соответствии с вашим содержимым. После этого вы увидите, что вторая панель появляется справа от первой. Это связано с тем, что вы не установили gridx/gridy для GBC2, поэтому по умолчанию myTopPL2 помещается справа от myTopPL1, а не под ним.

Я редко явно устанавливаю gridx/gridy при использовании GridBagLayout. Для вашей первой строки дисплея я бы использовал значения по умолчанию для всех, кроме myLoginBN, где я бы установил gridwidth на GridBagConstraints.REMAINDER. Это говорит GridBagLayout, что в этой строке больше ничего нет. Следующий элемент, добавленный с gbc по умолчанию, будет помещен в начало второй строки.

Мелкие гниды:

  • Use standard Java capitalization:
    • Class name are camelcase with a leading uppercase character. So, "Gui", not "GUI".
    • Имена экземпляров имеют верблюжий регистр с начальным строчным символом. Итак, "gbc1", а не "GBC1"
  • Используйте SwingUtilities.InvokeLater, чтобы запустить графический интерфейс в EDT.

    SwingUtilities.invokeLater(new Runnable() {
        public void run() {
            GUI GUI = new GUI ();
            GUI .setDefaultCloseOperation(RMIAuctionHouse.EXIT_ON_CLOSE);
            GUI .setSize(750,500);
            GUI .setVisible(true);
        }});
    
person Devon_C_Miller    schedule 16.11.2012

Кажется, вы не знакомы с макетами Java, поэтому я рекомендую вам попробовать нулевой (абсолютный) макет:

setLayout(null);
...
component.setBounds( x, y, width, heigh );
add(component);

Вот пример

package gui;

import java.awt.Font;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;


public class GUI extends JFrame{

    private JTextField myUsernameTF;
    private JLabel myUsernameLBL;

    public GUI() {

        super("GUI ");
        setLayout(null);     

        myUsernameLBL = new JLabel("Username: ");
        myUsernameLBL.setFont(new Font("Arial", Font.BOLD, 13));
        myUsernameLBL.setBounds(50,30,80,20);
        add(myUsernameLBL);

        myUsernameTF = new JTextField(10);
        myUsernameTF.setBounds(190,30,80,20);
        add(myUsernameTF);

        // and so on ...



    }

    public static void main(String[] args) {
        GUI frame = new GUI();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setSize(750,500);
        frame.setVisible(true);
    }
}

Удачи на тернистом пути в освоении Java-свинга =)

person gmatagmis    schedule 16.11.2012
comment
-1 Пожалуйста, пересмотрите эти тревожные вопросы: null макет, сбивающее с толку имя contentPane, необоснованные двойные скобки и замена панели содержимого, когда ваш первый маркер говорит нельзя этого делать. См. также этот ответ. - person trashgod; 16.11.2012
comment
Как вы можете сказать Кажется, вы не знакомы с макетами Java и я рекомендую вам попробовать нулевой (абсолютный) макет в одном и том же предложении? Тот факт, что они кажутся незнакомыми с макетами, — это лучшая возможность для обучения, которую я только мог рассмотреть. Нулевые макеты хороши только для таких вещей, как анимация, а не для дизайна форм - ИМХО. - person MadProgrammer; 16.11.2012
comment
@MadProgrammer: Верно, несмотря на ошибочную орфографическую коррекцию определенно. :-) - person trashgod; 17.11.2012
comment
Если у вас две учетные записи, вы можете запросить объединение. - person trashgod; 17.11.2012
comment
@trashgod iPad + плачущий, извивающийся 6-месячной давности плохо печатает :( (к тому же я был возмущен рекомендацией нулевой раскладки) - person MadProgrammer; 17.11.2012