Как заставить мой JScrollBar работать или динамически изменять размер JPanel, чтобы он соответствовал компонентам?

Я тщательно искал ответ на свой вопрос и пробовал несколько вещей, но ни одна из этих вещей не сработала для меня.

У меня есть кнопка, которая открывает JDialog, позволяя пользователю атрибутировать и изменять цвета для трех типов объектов/ограничений.

JDialog состоит из 2 JPanels, первый из которых содержит еще 3 JPanels для всех трех типов объектов, а второй — для кнопок OK/Отмена.

Моя проблема заключается в третьем типе объектов, так называемых «Ограничениях метки».

Этот третий тип объектов может иметь подобъекты, которые динамически добавляются в JPanel по мере их создания пользователем и состоят из имени и кнопки для изменения цвета объекта.

Это метод, который создает JPanel, содержащий текст и кнопку для выбора цвета объекта, и добавляет его к labelColorConstraintPanel, являющемуся полем класса. Этот метод вызывается в другом методе, отвечающем за создание объектов.

 /**
 * Add the last created label constraint class name(number) and its color
 * button to the panel labelColorConstraintPanel. The button allows user to
 * choose the label constraint class color.
 **/
protected void createLabelColorConstraintsPanel() {

    // labelColorConstraintPanel
    JPanel classNameButtonPanel = new JPanel(new GridLayout(0, 2));
// classNameButtonPanel.setPreferredSize(new Dimension(15, 20));
    classNameButtonPanel.setBorder(BorderFactory.createEmptyBorder(3, 3, 3, 3));

    classNameButtonPanel.add(new JLabel("Class " + labelClassesCount + ":"));
    jb_labelConstraintClassChooseColor.get(labelClassesCount - 1).addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent event) {

            JButton lblClassColorButtonClicked = (JButton) event.getSource();
            int buttonIndex = (int) lblClassColorButtonClicked.getClientProperty("index");
            chooseLabelClassColor(buttonIndex);
        }
    });
    classNameButtonPanel.add(jb_labelConstraintClassChooseColor.get(labelClassesCount - 1));

    labelColorConstraintPanel.add(classNameButtonPanel);
}

labelColorConstraintPanel присоединен к JScrollPane, который присоединен к другому JPanel для этого третьего типа объектов - ограничения метки.

Моя проблема в том, что JScrollBar на JScrollPane не появляется. Однако я читал, что установка preferredSize из JPanel внутри JScrollPane на размер больше, чем эта секунда, приведет к появлению вертикальной полосы (см. строки кода с комментариями в методе chooseConstraintsColors).

Таким образом мне удалось сделать бар-шоу, но у меня есть две другие проблемы. Первый: первые кнопки добавили растяжку к общему количеству JPanel, создав огромные кнопки.

Второй: чем больше кнопок я добавляю, тем они изменяются в размерах и в какой-то момент ряды становятся «переполненными».

Наконец, я полагаю, что эти две проблемы представляют собой одну и ту же проблему, но, похоже, я не могу найти решение.

Либо есть другой способ показать JScrollBar без установки preferredSize(), либо есть способ динамически увеличивать размер JPanel по мере добавления к нему новых объектов с фиксированным размером.

Вот основной метод, создающий окно JDialog:

/** Opens a JDialog for choosing the Constraints Colors **/
protected void chooseConstraintColors() {

    jd_colorsChooser = new JDialog((Frame) this.getTopLevelAncestor(), "Choose Constraints Colors", true);
    jd_colorsChooser.getRootPane().setBorder(BorderFactory.createEmptyBorder(3, 3, 3, 3));
    jd_colorsChooser.setLayout(new BorderLayout());

    JPanel constraintsPanel = new JPanel(new BorderLayout());
    JPanel mlConstraintsPanel = new JPanel();
    JPanel clConstraintsPanel = new JPanel();
    JPanel lblConstraintsPanel=new JPanel(new GridLayout(0,1));

    JScrollPane lblConstraintsPane = new JScrollPane(labelColorConstraintPanel,
            ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);
    lblConstraintsPane.setPreferredSize(new Dimension(130,130));
    TitledBorder lblcBorder = BorderFactory.createTitledBorder(
            BorderFactory.createEtchedBorder(EtchedBorder.LOWERED), "Label Constraints Color", TitledBorder.LEFT,
            TitledBorder.TOP);
    lblConstraintsPane.setBorder(lblcBorder);

    // must-link constraints panel
    mlConstraintsPanel.setLayout(new BorderLayout());
    TitledBorder mlcBorder = BorderFactory.createTitledBorder(
            BorderFactory.createEtchedBorder(EtchedBorder.LOWERED), "Must-Link Constraints Color",
            TitledBorder.LEFT, TitledBorder.TOP);
    mlConstraintsPanel.setBorder(mlcBorder);
    jb_mustLinkChooseColor.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent e) {
            chooseMustLinkColor();
        }

    });
    mlConstraintsPanel.add(jb_mustLinkChooseColor, BorderLayout.CENTER);

    // cannot-link constraints panel
    clConstraintsPanel.setLayout(new BorderLayout());
    TitledBorder clcBorder = BorderFactory.createTitledBorder(
            BorderFactory.createEtchedBorder(EtchedBorder.LOWERED), "Cannot-Link Constraints Color",
            TitledBorder.LEFT, TitledBorder.TOP);
    clConstraintsPanel.setBorder(clcBorder);
    jb_cannotLinkChooseColor.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent e) {
            chooseCannotLinkColor();
        }
    });
    clConstraintsPanel.add(jb_cannotLinkChooseColor, BorderLayout.CENTER);

    // label constraints panel
     labelColorConstraintPanel.setPreferredSize(new Dimension(131,131));
     lblConstraintsPanel.add(lblConstraintsPane);

    constraintsPanel.add(mlConstraintsPanel, BorderLayout.NORTH);
    constraintsPanel.add(clConstraintsPanel, BorderLayout.CENTER);
    constraintsPanel.add(lblConstraintsPanel, BorderLayout.SOUTH);

    // button panel
    JPanel buttonPanel = new JPanel();
    JButton ok = new JButton("OK");// update color changes on ok, update
                                    // only fields that have changed
    ok.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent event) {

            if (mustLinkColorTemp != null && mustLinkColorTemp != mustLinkColor) {
                mustLinkColor = mustLinkColorTemp;
                jb_mustLinkChooseColor.setBackground(mustLinkColor);
            }

            if (cannotLinkColorTemp != null && cannotLinkColorTemp != cannotLinkColor) {
                cannotLinkColor = cannotLinkColorTemp;
                jb_cannotLinkChooseColor.setBackground(cannotLinkColor);

            }

            for (int i = 0; i < labelClassesCount; i++) {
                if (labelConstraintColorTemp.get(i) != null
                        && labelConstraintColorTemp.get(i) != labelConstraintColor.get(i)) {

                    labelConstraintColor.set(i, labelConstraintColorTemp.get(i));
                    jb_labelConstraintClassChooseColor.get(i).setBackground(labelConstraintColor.get(i));
                }

            }

            jd_colorsChooser.dispose();
        }
    });

    // exit dialog on cancel
    JButton cancel = new JButton("Cancel");
    cancel.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent event) {

            jb_mustLinkChooseColor.setBackground(mustLinkColor);
            jb_cannotLinkChooseColor.setBackground(cannotLinkColor);
            for (int i = 0; i < labelClassesCount; i++) {

                jb_labelConstraintClassChooseColor.get(i).setBackground(labelConstraintColor.get(i));
            }
            jd_colorsChooser.dispose();
        }
    });

    buttonPanel.add(ok);
    buttonPanel.add(cancel);

    jd_colorsChooser.add(constraintsPanel, BorderLayout.NORTH);
    jd_colorsChooser.add(buttonPanel, BorderLayout.SOUTH);

    jd_colorsChooser.setPreferredSize(new Dimension(270, 270));
    jd_colorsChooser.pack();
    jd_colorsChooser.setLocationRelativeTo(null);
    jd_colorsChooser.setVisible(true);
}

P.S: Поскольку я новичок в StackOverflow, я не могу загружать изображения, но вот описание изображений:

Случай 1: JDialog с 3 панелями и кнопками OK и Cancel.

Если setPreferredSize не используется, кнопки добавляются в третий JPanel один за другим без появления полосы прокрутки.

Случай 2: используется setPrefferedSize(), появляется полоса прокрутки с первой кнопкой, растянутой на размер JPanel, поскольку мы добавляем больше кнопок, ряды с кнопками JPanel становятся переполненными.


person Maria    schedule 12.06.2017    source источник
comment
1) P.S. Поскольку я новичок в stackoverflow, я не могу загружать изображения, но вот описание изображений: Вы можете публиковать ссылки на свои изображения, и мы можем их редактировать. 2) Ваш вопрос слишком велик, без изображений того, что вы пытаетесь сделать, и это сбивает с толку, я вижу, что вы не прошли tour, поэтому просмотрите его, затем прочитайте Как спросить и после этого опубликуйте действительный минимальный воспроизводимый пример, который представляет собой не весь ваш код или фрагменты кода, а простой пример кода, который при запуске покажет ваша проблема. Его не следует размещать на внешних сайтах, а следует размещать в виде текста в формате кода (как вы уже сделали здесь)   -  person Frakcool    schedule 12.06.2017


Ответы (1)


Таким образом мне удалось сделать бар-шоу, но у меня есть две другие проблемы. Первый: первые кнопки добавили растяжение по всей панели JPanel, создав огромные кнопки. Второй: чем больше кнопок я добавляю, тем они изменяются в размерах и в какой-то момент ряды становятся «переполненными».

  1. Не используйте setPreferredSize(). Задача менеджера по компоновке — рассчитать предпочтительный размер.

  2. Вы используете неправильный менеджер компоновки. Вам никогда не придется использовать один менеджер компоновки, в который вы можете вложить менеджер компоновки. Например, вы можете создать JPanel с BorderLayout и добавить эту панель в scrollPane. Затем вы создаете вторую панель с помощью GridLayout, а затем с помощью BorderLayout.PAGE_START панели, используя BorderLayout. Теперь панель будет учитывать размер добавленных к ней компонентов и увеличиваться по мере необходимости.

person camickr    schedule 12.06.2017