Java выравнивает 3 панели с помощью группового макета

Я не могу заставить свои 3 панели правильно выровняться. В основном у меня есть 1 большая панель и 2 меньшие (не обязательно одинаковые). Большой находится слева, а 2 меньших справа, один над другим. Размер компонентов должен оставаться динамически изменяемым.

Я хочу это (9 - большой, 1 - один из маленьких, 2 - другой маленький):

999999 111
999999 111
999999 111
999999 222
999999 222

Я получаю следующее:

999999 111
999999 111
999999 111
999999 
999999 
       222
       222

Мой код выглядит следующим образом: graphsimscrollpane большая, а рабочая панель и информационная панель - меньшие:

    private void createLayout(GroupLayout groupLayout) {
    groupLayout.setHorizontalGroup(
            groupLayout.createSequentialGroup()
                .addContainerGap()
                .addComponent(graphSimScrollPane,  0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                .addContainerGap(20, Short.MAX_VALUE)
                .addGroup(groupLayout.createParallelGroup(Alignment.CENTER)
                        .addComponent(workPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                        .addComponent(informationPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
        );
        groupLayout.setVerticalGroup(
            groupLayout.createSequentialGroup()
                .addGroup(groupLayout.createParallelGroup(Alignment.CENTER)
                    .addComponent(graphSimScrollPane,  0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                    .addComponent(workPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
                .addComponent(informationPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
        );
        guiFrame.getContentPane().setLayout(groupLayout);
}

person Sven    schedule 14.02.2013    source источник
comment
Есть ли причина, по которой вы не можете их вложить? В Android, который очень похож на свинг, я бы выполнил это, используя горизонтальную линейную компоновку с видом 9999 слева, а затем вертикальную компоновку справа с видами 111 и 222.   -  person amarunowski    schedule 14.02.2013
comment
Я думаю, что мог бы сделать это, однако я предпочитаю использовать групповой макет из-за возможности изменения размера и потому, что его легко использовать в Windowbuilder, инструменте, который я использую для создания этого графического интерфейса.   -  person Sven    schedule 14.02.2013


Ответы (2)


Базовая структура вашего GroupLayout будет похожа на этот код:

    JPanel pnl = new JPanel();
    GroupLayout l = new GroupLayout(pnl);
    pnl.setLayout(l);

    JButton b1 = new JButton("1");
    JButton b2 = new JButton("2");
    JButton b3 = new JButton("3");

    l.setHorizontalGroup(
            l.createSequentialGroup()
                .addComponent(b1)
                .addGroup(l.createParallelGroup()
                    .addComponent(b2)
                    .addComponent(b3)));

    l.setVerticalGroup(
            l.createParallelGroup()
                .addComponent(b1)
                .addGroup(l.createSequentialGroup()
                    .addComponent(b2)
                    .addComponent(b3)));

    JFrame f = new JFrame("test");
    f.setContentPane(pnl);
    f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    f.setSize(1024, 768);
    f.setVisible(true);

На простом английском языке ограничение на горизонтальной оси читается как «b1, затем b2 и b3 параллельно». Ограничение по вертикальной оси гласит: «b1 параллельно с группой, состоящей из b1, затем b2».

Очевидно, здесь отсутствуют свойства изменения размера. Вам нужно дать более подробную информацию о том, как вы хотите, чтобы компонент вел себя относительно их размера.

Одной из возможностей было бы предоставить двум небольшим компонентам все пространство по вертикали, но предоставить им только предпочитаемое ими пространство по горизонтали. И, конечно же, дайте большому компоненту оставшееся место.

    l.setHorizontalGroup(
            l.createSequentialGroup()
                .addComponent(b1, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                .addGroup(l.createParallelGroup()
                    .addComponent(b2, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
                    .addComponent(b3, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)));

    l.setVerticalGroup(
            l.createParallelGroup()
                .addComponent(b1, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                .addGroup(l.createSequentialGroup()
                    .addComponent(b2, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                    .addComponent(b3, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)));

Обратите внимание, что структура такая же, как и в первом коде, добавлены только параметры размера.

person barjak    schedule 14.02.2013
comment
+! для ввода :-) Хотел бы я понять работу GroupLayout, но много раз это выходит за рамки моей головы. Надеюсь, ваш ответ сработает для ОП :-) - person nIcE cOw; 14.02.2013
comment
@GagandeepBali: см. также контрастирующие примеры здесь и здесь. - person trashgod; 14.02.2013
comment
Спасибо, групповой макет настолько универсален, но часто выходит за рамки моей головы. - person Sven; 15.02.2013

Я действительно не знаю, как использовать GroupLayout, хотя, если вы хотите выполнить задачу, используя GridBagLayout, то этот пример кода может выполнить эту задачу за вас. Пожалуйста, посмотрите:

import javax.swing.*;
import java.awt.*;
import java.util.Random;

/**
 * Created with IntelliJ IDEA.
 * User: Gagandeep Bali
 * Date: 2/14/13
 * Time: 8:18 PM
 * To change this template use File | Settings | File Templates.
 */
public class GridBagExample
{
    private GridBagConstraints gbc;
    private Random random;
    private JPanel largePanel;
    private JPanel smallPanel;
    private JPanel superSmallPanel;

    public GridBagExample()
    {
        gbc = new GridBagConstraints();
        gbc.anchor = GridBagConstraints.FIRST_LINE_START;

        random = new Random();
    }

    private void displayGUI()
    {
        JFrame frame = new JFrame("GridBagLayout Example");
        frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);

        JPanel contentPane = getPanel();
        contentPane.setLayout(new GridBagLayout());

        largePanel = getPanel();
        contentPane.add(largePanel, getConstraints(
                    GridBagConstraints.BOTH, 0, 0, 1, 2, 0.7f, 1.0f));
        smallPanel = getPanel();
        contentPane.add(smallPanel, getConstraints(
                    GridBagConstraints.BOTH, 1, 0, 1, 1, 0.3f, 0.7f));
        superSmallPanel = getPanel();
        contentPane.add(superSmallPanel, getConstraints(
                    GridBagConstraints.BOTH, 1, 1, 1, 1, 0.3f, 0.3f));

        frame.setContentPane(contentPane);
        frame.pack();
        frame.setLocationByPlatform(true);
        frame.setVisible(true);
    }

    private JPanel getPanel()
    {
        JPanel panel = new JPanel();
        panel.setOpaque(true);
        panel.setBackground(getColor());
        panel.setBorder(BorderFactory.createCompoundBorder(
                BorderFactory.createLineBorder(getColor(), 5),
                    BorderFactory.createEmptyBorder(5, 5, 5, 5)));

        return panel;
    }

    private Color getColor()
    {
        return (new Color(
                random.nextFloat(), random.nextFloat()
                , random.nextFloat(), random.nextFloat()));
    }

    private GridBagConstraints getConstraints(
                int filler, int x, int y, int w, int h
                                 , float weightx, float weighty)
    {
        gbc.fill = filler;
        gbc.gridx = x;
        gbc.gridy = y;
        gbc.gridwidth = w;
        gbc.gridheight = h;
        gbc.weightx = weightx;
        gbc.weighty = weighty;

        return gbc;
    }

    public static void main(String... args)
    {
        EventQueue.invokeLater(new Runnable()
        {
            @Override
            public void run()
            {
                new GridBagExample().displayGUI();
            }
        });
    }
}
person nIcE cOw    schedule 14.02.2013