0

How I can create a JPanel with a lot of buttons aligned float left and with vertical scrollbars only?

The buttons should be sorted like below.

1  2  3  4
5  6  7  8
9 10 11 12
Andrew Thompson
  • 168,117
  • 40
  • 217
  • 433
  • You can use [GridLayout](https://docs.oracle.com/javase/tutorial/uiswing/layout/grid.html) to create a panel with the buttons you want. – Sazzadur Rahaman Jul 19 '18 at 00:44
  • There are many question and answers about [calculators](https://stackoverflow.com/questions/49762451/using-jpanel-to-make-a-calculator-how-to-use-layout/49790765#49790765) which can help you – c0der Jul 19 '18 at 04:01

2 Answers2

1

If you use GridLayout, then you will not be able to add a scrollpane since it will resize automatically to fit all the components inside of it. An easier approach is to use a FlowLayout and setPreferredSize(...) to set the size of your panel. Though it is not advised to set the size of panels, you still need to have the scrollbar put into use somehow. Here is a MCVE:

enter image description here

import java.awt.Dimension;
import java.awt.FlowLayout;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;

public class Example extends JFrame {

    private final int BUTTON_WIDTH = 100;
    private final int BUTTON_HEIGHT = 50;
    private final int BUTTON_ROWS = 3;
    private final int BUTTON_COLUMNS = 4;
    private final int OFFSET = 20;// the width of the actual scroll bar in pixels (approximately).
    private final int PANEL_WIDTH = BUTTON_WIDTH * BUTTON_COLUMNS + OFFSET;
    private final int PANEL_HEIGHT = BUTTON_HEIGHT * BUTTON_ROWS + OFFSET;
    private final int SCROLL_HEIGHT = 100;//or whatever you would like...
    private final JButton[] buttons = new JButton[BUTTON_ROWS * BUTTON_COLUMNS];

    public Example() {
        JPanel panel = new JPanel(new FlowLayout());
        JScrollPane scroll = new JScrollPane(panel, JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,
            JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);
        panel.setPreferredSize(new Dimension(PANEL_WIDTH, PANEL_HEIGHT));
        scroll.setPreferredSize(new Dimension(PANEL_WIDTH + OFFSET, SCROLL_HEIGHT));
        for (int i = 0; i < buttons.length; i++) {
            JButton button = new JButton((i + 1) + "");
            buttons[i] = button;
            button.setPreferredSize(new Dimension(BUTTON_WIDTH, BUTTON_HEIGHT));
            panel.add(button);
        }

        //if you want the panel to resize when window is stretched.
        //setLayout(new FlowLayout(FlowLayout.CENTER));
        add(scroll);
        setLocationRelativeTo(null);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        pack();
        setVisible(true);
    }

    public static void main(String[] args) {
        new Example();
    }
}
M. Al Jumaily
  • 731
  • 1
  • 6
  • 21
1

Add the buttons to a (panel with a) grid layout to arrange them in rows and columns. Add that panel to a scroll pane, then add the scroll pane to the line start constraint of a border layout, and they will appear on the left.

enter image description here

import java.awt.*;
import javax.swing.*;
import javax.swing.border.EmptyBorder;

public class LeftAlignedButtonGrid {

    private JComponent ui = null;

    LeftAlignedButtonGrid() {
        initUI();
    }

    public void initUI() {
        if (ui!=null) return;

        /* BorderLayout offers a LINE_START constraint that will put a 
        single child component on the left hand side of the GUI (in any
        locale that uses left-to-right text orientation) */
        ui = new JPanel(new BorderLayout(4,4));

        JPanel buttonPanel = new JPanel(new GridLayout(0,4,2,2));
        for (int ii=1; ii<13; ii++) {
            buttonPanel.add(new JButton("" + ii));
        }
        ui.add(new JScrollPane(buttonPanel, 
                JScrollPane.VERTICAL_SCROLLBAR_ALWAYS, 
                JScrollPane.HORIZONTAL_SCROLLBAR_NEVER),
                BorderLayout.LINE_START);
        ui.setBorder(new EmptyBorder(4,4,4,4));
    }

    public JComponent getUI() {
        return ui;
    }

    public static void main(String[] args) {
        Runnable r = new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (Exception useDefault) {
                }
                LeftAlignedButtonGrid o = new LeftAlignedButtonGrid();

                JFrame f = new JFrame(o.getClass().getSimpleName());
                f.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
                f.setLocationByPlatform(true);

                f.setContentPane(o.getUI());
                f.pack();
                // comment this out to allow the height of the GUI to be reduced, 
                // thus making the vertical scroll bar to have a purpose!
                //f.setMinimumSize(f.getSize());

                f.setVisible(true);
            }
        };
        SwingUtilities.invokeLater(r);
    }
}
Andrew Thompson
  • 168,117
  • 40
  • 217
  • 433