Chapter 16. Layout Managers

A layout manager arranges the child components of a container, as shown in Figure 16.1. It positions and sets the size of components within the container’s display area according to a particular layout scheme. The layout manager’s job is to fit the components into the available area while maintaining the proper spatial relationships among the components. Swing comes with a few standard layout managers that will collectively handle most situations; you can make your own layout managers if you have special requirements.

A layout manager at work

Figure 16-1. A layout manager at work

Every container has a default layout manager; therefore, when you make a new container, it comes with a LayoutManager object of the appropriate type. You can install a new layout manager at any time with the setLayout( ) method. For example, we can set the layout manager of a container to a BorderLayout:

setLayout (new BorderLayout( ));

Notice that we call the BorderLayout constructor, but we don’t even save a reference to the layout manager. This is typical; once you have installed a layout manager, it does its work behind the scenes, interacting with the container. You rarely call the layout manager’s methods directly, so you don’t usually need a reference (a notable exception is CardLayout). However, you do need to know what the layout manager is going to do with your components as you work with them.

The LayoutManager is consulted whenever a container’s doLayout( ) method is called to reorganize the contents. It does its job by calling the setLocation( ) and setBounds( ) methods of the individual child components to arrange them in the container’s display area. A container is laid out the first time it is displayed, and thereafter whenever the container’s revalidate( ) method is called. Containers that are a subclass of the Window class (Frame, JFrame, and JWindow) are automatically validated whenever they are packed or resized. Calling pack( ) sets the window’s size as small as possible while holding all its components at their preferred sizes.

Every component determines three important pieces of information used by the layout manager in placing and sizing it: a minimum size, a maximum size, and a preferred size. These sizes are reported by the getMinimumSize( ) , getMaximum-Size( ), and getPreferredSize( ) methods of Component, respectively. For example, a plain JButton object can normally be changed to any size. However, the button’s designer can provide a preferred size for a good-looking button. The layout manager might use this size when there are no other constraints, or it might ignore it, depending on its scheme. Now if we give the button a label, the button may need a new minimum size in order to display itself properly. The layout manager might show more respect for the button’s minimum size and guarantee that it has at least that much space. Similarly, a particular component might not be able to display itself properly if it is too large (perhaps it has to scale up an image); it can use getMaximumSize( ) to report the largest size it considers acceptable.

The preferred size of a Container object has the same meaning as for any other type of component. However, since a Container may hold its own components and want to arrange them in its own layout, its preferred size is a function of its layout manager. The layout manager is therefore involved in both sides of the issue. It asks the components in its container for their preferred (or minimum) sizes in order to arrange them. Based on those values, it calculates the preferred size of its own container (which can be communicated to the container’s parent).

When a layout manager is called to arrange its components, it is working within a fixed area. It usually begins by looking at its container’s dimensions, and the preferred or minimum sizes of the child components. It then doles out screen area and sets the sizes of components according to its scheme. You can override the getMinimumSize( ), getMaximumSize( ), and getPreferredSize( ) methods of a component, but you should do this only if you are actually specializing the component, and it has new needs. If you find yourself fighting with a layout manager because it’s changing the size of one of your components, you are probably using the wrong kind of layout manager or not composing your user interface properly. Remember that it’s possible to use a number of JPanel objects in a given display, each one with its own LayoutManager. Try breaking down the problem: place related components in their own JPanel and then arrange the panels in the container. When that becomes too complicated, you can choose to use a constraint-based layout manager like GridBagLayout, which we’ll discuss later in this chapter.

FlowLayout

FlowLayout is a simple layout manager that tries to arrange components with their preferred sizes, from left to right and top to bottom in the container. A FlowLayout can have a specified row justification of LEFT, CENTER, or RIGHT, and a fixed horizontal and vertical padding. By default, a flow layout uses CENTER justification, meaning that all components are centered within the area allotted to them. FlowLayout is the default for JPanels.

The following example adds five buttons to the content pane of a JFrame using the default FlowLayout; the result is shown in Figure 16.2.

//file: Flow.java
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

public class Flow extends JPanel {

  public Flow( ) {
    // FlowLayout is default layout manager for a JPanel
    add(new JButton("One"));
    add(new JButton("Two"));
    add(new JButton("Three"));
    add(new JButton("Four"));
    add(new JButton("Five"));
  }

  public static void main(String[] args) {
    JFrame f = new JFrame("Flow");
    f.addWindowListener(new WindowAdapter( ) {
      public void windowClosing(WindowEvent e) { System.exit(0); }
    });
    f.setSize(400, 75);
    f.setLocation(200, 200);
    Flow flow = new Flow( );
    f.setContentPane(flow);
    f.setVisible(true);
  }
}
A flow layout

Figure 16-2. A flow layout

If the window is narrow enough, some of the buttons will spill over to a second or third row.

Get Learning Java now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.