Swing GroupLayout: Resizing and limiting component sizes
In this example, GroupLayout
can simply rely on the preferred size of the label, without having to resort to any setXXXSize()
method. In this approach,
- The space for the labels always accommodates the largest label.
- The text fields are resizable in a useful way.
- The result is correct across platforms and fonts.
- "You do not need to specify anything for most of the components…because the components themselves have the desired resizing behavior as default."—How to Use GroupLayout: Component Size and Resizability
The use of GroupLayout.Alignment.TRAILING
to right justify the labels is a personal preference, and I've added a second panel to show how it works nested in another layout.
import java.awt.EventQueue;
import javax.swing.BorderFactory;
import javax.swing.Box;
import javax.swing.BoxLayout;
import javax.swing.GroupLayout;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
/** @see http://stackoverflow.com/questions/8492065 */
public class GroupPanel extends JPanel {
private JLabel label1 = new JLabel("Primary:");
private JTextField field1 = new JTextField(16);
private JLabel label2 = new JLabel("Secondary:");
private JTextField field2 = new JTextField(16);
private JLabel label3 = new JLabel("Tertiary:");
private JTextField field3 = new JTextField(16);
public GroupPanel(int n) {
this.setBorder(BorderFactory.createTitledBorder("Panel " + n));
GroupLayout layout = new GroupLayout(this);
this.setLayout(layout);
layout.setAutoCreateGaps(true);
layout.setAutoCreateContainerGaps(true);
layout.setHorizontalGroup(layout.createSequentialGroup()
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.TRAILING)
.addComponent(label1)
.addComponent(label2)
.addComponent(label3))
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
.addComponent(field1)
.addComponent(field2)
.addComponent(field3))
);
layout.setVerticalGroup(layout.createSequentialGroup()
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.BASELINE)
.addComponent(label1)
.addComponent(field1))
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.BASELINE)
.addComponent(label2)
.addComponent(field2))
.addGroup(layout.createParallelGroup(GroupLayout.Alignment.BASELINE)
.addComponent(label3)
.addComponent(field3))
);
}
private static void display() {
JFrame f = new JFrame("GroupPanel");
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setLayout(new BoxLayout(f.getContentPane(), BoxLayout.Y_AXIS));
f.add(new GroupPanel(1));
f.add(new GroupPanel(2));
f.add(Box.createVerticalGlue());
f.pack();
f.setLocationRelativeTo(null);
f.setVisible(true);
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
display();
}
});
}
}
How to align things in GroupLayout?
To answer my own question adding a preferredGap()
does the trick.
The final code is
layout.setHorizontalGroup(layout
.createSequentialGroup()
.addComponent(label, labelWidth, labelWidth, labelWidth)
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED,
GroupLayout.PREFERRED_SIZE, Short.MAX_VALUE)
.addGroup(layout
.createParallelGroup(GroupLayout.Alignment.CENTER)
.addComponent(installButton, BUTTON_WIDTH, BUTTON_WIDTH,
BUTTON_WIDTH).addComponent(installProgressBar)
.addComponent(updateLabel).addComponent(updateButton)
.addComponent(removeButton)));
layout.setVerticalGroup(layout
.createParallelGroup()
.addComponent(label)
.addGroup(layout
.createSequentialGroup()
.addComponent(installButton)
.addGroup(layout.createParallelGroup()
.addComponent(installProgressBar)
.addComponent(updateLabel))
.addComponent(updateButton).addComponent(removeButton)));
layout
.linkSize(SwingConstants.HORIZONTAL, installButton, installProgressBar,
updateLabel, updateButton, removeButton);
Related Topics
How to Implement Constants in Java
Difference Between File.Separator and Slash in Paths
Java "Void" and "Non Void" Constructor
What Is the Easiest/Best/Most Correct Way to Iterate Through the Characters of a String in Java
Why Is There No Multiple Inheritance in Java, But Implementing Multiple Interfaces Is Allowed
Java: Multiple Class Declarations in One File
Jquery, Spring MVC @Requestbody and JSON - Making It Work Together
How to Fix Org.Hibernate.Lazyinitializationexception - Could Not Initialize Proxy - No Session
Java System Properties and Environment Variables
Difference Between @Mock and @Injectmocks
How to Map a Composite Key with JPA and Hibernate
How to Find Files That Match a Wildcard String in Java
Should I Initialize Variable Within Constructor or Outside Constructor
What Is the "Execute Around" Idiom
Why Can't Strings Be Mutable in Java and .Net
How to Specify Jackson to Only Use Fields - Preferably Globally