Layouts - Part 2 - Border Layout

To look at the BorderLayout we shall use the example from the JTextField tutorial, so if you've not had a look at it, it may be a good idea to do this now.

In this example, we have converted the JTextField example from Absolute Positioning to a BorderLayout. The BorderLayout uses a system whereby you can position things on the four sides of a square, then things in the middle. It's easier when you see it explained like this...

Picture of BorderLayout

That is a perfect layout for our Login page. We keep the widgets on the three panels, then place the panels on the various positions. The title goes on PAGE_START, the Login button stretches out across PAGE_END, and the three panels containing the sets of widgets are places on LINE_START, CENTER and LINE_END.

Let's see how it is implemented, and then talk through the code.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
import javax.swing.*;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.Color;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;

public class BorderLayoutExample implements  ActionListener{

    JPanel textPanel, panelForTextFields, completionPanel;
    JLabel titleLabel, usernameLabel, passwordLabel, userLabel, passLabel;
    JTextField usernameField, loginField;
    JButton loginButton;

    public JPanel createContentPane (){

        // We create a bottom JPanel to place everything on.
        //This sets the Border Layout to have a horizontal gap of 10
        //and a vertical gap of 10 between each widget.
        
        JPanel totalGUI = new JPanel();
        totalGUI.setLayout(new BorderLayout(10, 10));

        // Setting the preferredSize is basically making sure the widget
        // is not re-sized to be smaller or bigger than this unless it needs to be.
        // Also, when adding, we have the area of the JPanel as a second argument.

        titleLabel = new JLabel("Login Screen");
        titleLabel.setPreferredSize(new Dimension(290, 30));
        titleLabel.setHorizontalAlignment(0);
        totalGUI.add(titleLabel, BorderLayout.PAGE_START);

        // Creation of a Panel to contain the JLabels
        textPanel = new JPanel();
        textPanel.setPreferredSize(new Dimension(70, 80));
        totalGUI.add(textPanel, BorderLayout.LINE_START);

        // Username Label
        usernameLabel = new JLabel("Username");
        usernameLabel.setPreferredSize(new Dimension(70, 30));
        usernameLabel.setHorizontalAlignment(4);
        textPanel.add(usernameLabel);

        // Login Label
        passwordLabel = new JLabel("Password");
        passwordLabel.setPreferredSize(new Dimension(70, 30));
        passwordLabel.setHorizontalAlignment(4);
        textPanel.add(passwordLabel);

        // TextFields Panel Container
        panelForTextFields = new JPanel();
        panelForTextFields.setPreferredSize(new Dimension(100, 70));
        totalGUI.add(panelForTextFields, BorderLayout.CENTER);

        // Username Textfield
        usernameField = new JTextField(8);
        usernameField.setPreferredSize(new Dimension(100, 30));
        panelForTextFields.add(usernameField);

        // Login Textfield
        loginField = new JTextField(8);
        loginField.setPreferredSize(new Dimension(100, 30));
        panelForTextFields.add(loginField);

        // Creation of a Panel to contain the completion JLabels
        completionPanel = new JPanel();
        completionPanel.setPreferredSize(new Dimension(70, 80));
        totalGUI.add(completionPanel, BorderLayout.LINE_END);

        // Username Label
        userLabel = new JLabel("Wrong");
        userLabel.setForeground(Color.red);
        userLabel.setPreferredSize(new Dimension(70, 30));
        completionPanel.add(userLabel);

        // Login Label
        passLabel = new JLabel("Wrong");
        passLabel.setForeground(Color.red);
        passLabel.setPreferredSize(new Dimension(70, 30));
        completionPanel.add(passLabel);

        // Button for Logging in
        loginButton = new JButton("Login");
        loginButton.addActionListener(this);
        totalGUI.add(loginButton, BorderLayout.PAGE_END);

        totalGUI.setOpaque(true);
        return totalGUI;
    }

    // With this action performed, we simply check to see if the username and
    // password match "Bob" as the username and "Robert" as the password.
    // If they do, we set the labels ajacent to them to "Correct!" and color
    // them green.
    // At the end, we check if both labels are green. If they are, we set the
    // screen to be 'Logging In'.

    public void actionPerformed(ActionEvent e) {

        if(e.getSource() == loginButton)
        {
            if(usernameField.getText().trim().compareTo("Bob") == 0)
            {
                userLabel.setForeground(Color.green);
                userLabel.setText("Correct!");
            }
            else
            {
                userLabel.setForeground(Color.red);
                userLabel.setText("Wrong!");
            }

            if(loginField.getText().trim().compareTo("Robert") == 0)
            {
                passLabel.setForeground(Color.green);
                passLabel.setText("Correct!");
            }
            else
            {
                passLabel.setForeground(Color.red);
                passLabel.setText("Wrong!");
            }

            if((userLabel.getForeground() == Color.green) 
            && (passLabel.getForeground() == Color.green))
            {
                titleLabel.setText("Logging in....");
                loginButton.setEnabled(false);
            }
        }
    }


    private static void createAndShowGUI() {

        JFrame.setDefaultLookAndFeelDecorated(true);
        JFrame frame = new JFrame("[=] JTextField of Dreams [=]");

        BorderLayoutExample demo = new BorderLayoutExample();
        frame.setContentPane(demo.createContentPane());
        
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        // We no longer manually re-size, we use pack to automatically size the frame.
        frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        //Schedule a job for the event-dispatching thread:
        //creating and showing this application's GUI.
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                createAndShowGUI();
            }
        });
    }
}
Login Screen showing TextFields

The layout is set on line 22 with two integer arguments. This sets the horizontal and vertical gap respectively (in pixels). The default is 0 pixels gap, which is good or bad depending on what you want your program to look like. Here we set the gap between each at 10 pixels.
22
        totalGUI.setLayout(new BorderLayout(10, 10));
With the LayoutManager, we no longer need to deal with manual location. This means we do not need the setLocation() command, this is only used for absolute positioning.
setSize() is different too, we now set the preferred size. This means the size can be changed if the Frame is re-sized, but if possible the size will be the preferred size.
setPreferredSize uses a Dimension instead of two Integer arguments, so we create a Dimension. The two arguments for the Dimension are int width, int height (just as before). Remember to import the java.awt.Dimension library!

Absolute Positioning     Border Layout
26
27
28
29
30
        textPanel = new JPanel();
        textPanel.setLayout(null);
        textPanel.setLocation(10, 35);
        textPanel.setSize(70, 80);
        totalGUI.add(textPanel);
   
34
35
36
        textPanel = new JPanel();
        textPanel.setPreferredSize(new Dimension(70, 80));
        totalGUI.add(textPanel, BorderLayout.LINE_START);
Notice also that when you add the widget to a Panel containing a BorderLayout, you have to define where you want the Panel to be placed. In this case we want the Button to be placed at the bottom of the screen, at PAGE_END.
83
84
85
        loginButton = new JButton("Login");
        loginButton.addActionListener(this);
        totalGUI.add(loginButton, BorderLayout.PAGE_END);
This layout is particularly good for the overall positioning of panels in a screen. If you place JPanels that contain widgets at the positions around the border, there is a good change your GUI will look really good.

Questions

Let's see what you know about BorderLayout

Question 1. What is different about adding widgets to JPanels in a BorderLayout?

  • a) JPanels need to be added to the widget.
  • b) You use .addToBorderLayout();
  • c) You have to pass the area you want the widget in as a second argument.

Question 2. Which of these statements is NOT true?

  • a) Using a Layout uses less time.
  • b) Using a Layout uses less ozone.
  • c) Using a Layout uses less lines of code.

Question 3. What does setPreferredSize() do?

  • a) Sets the size of the widget, then makes sure the size is never changed.
  • b) Sets the size of the widget, but changes it if the JPanel size is changed.
  • c) Sets the size of the widget, but colours it purple.




Back Top Next
Email Me
Code Style


Required Lessons

External Links

Created and Edited by Stuart Davidson
All Rights Reserved ©

Valid XHTML 1.0 Strict