JScrollPanes inside GridBagLayout gets randomly resized
Here's the rude guys :)
Basically I have a GridBagLayout with two columns: a list enclosed by a scrollpane in each one. The scroll bars are stretched in the BOTH direction .
If I gradually decrease the height of this panel (by dragging the edge of the window), I see a "random" resizing on the scrolls:
-
the second width decreases when the first Hscroll panel appears
-
then the second width shrinks again for no reason ...
If I am not porting my components, don't get this behavior.
And if you replace the right-hand list with a tree , it behaves differently: by decreasing the window height 380-ich px, the tree changes ...
If I don't migrate my components, the tree will still be resized if you resize the window!
Do you guys know what's going on?
PS: The actual layout I'm trying to build is more complex than this example. At the same time, I use SpringLayout to do what I want, but it takes a lot (not so pretty) things to set up
protected static ListModel newListModel(int n) {
DefaultListModel lm = new DefaultListModel();
for (int i = 0; i < n; ++i)
lm.addElement("AAA");
return lm;
}
protected static JComponent createContentPane() {
JPanel pane = new JPanel(new GridBagLayout());
GridBagConstraints gbc = new GridBagConstraints();
gbc.anchor = GridBagConstraints.CENTER;
gbc.fill = GridBagConstraints.BOTH;
gbc.weightx = 1;
gbc.weighty = 1;
gbc.gridy = 0;
gbc.gridx = 0;
pane.add(new JScrollPane(new JList(newListModel(12))), gbc);
++gbc.gridx;
pane.add(new JScrollPane(new JList(newListModel(4))), gbc);
return pane;
}
public static void main(String[] args) {
JFrame f = new JFrame();
f.getContentPane().add(createContentPane());
f.setSize(800, 400);
f.setLocationRelativeTo(null);
f.setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE);
f.setVisible(true);
}
source to share
I have an application with multiple ScrollPanes in a GridBagLayout and they also exhibit abrupt resizing when the window is resized. The jump appears to occur when the ScrollPane's actual size goes over its "preferred size". I found a workaround: set your preferred size to 1x1 pixel. If a component has a positive weight and is stretched BOTH, it will still fill the entire cell, but it will not jump. If you need multiple cells to resize in different proportions, you can set the preferred size to another, for example 2x1 pixels.
source to share
- This is the basic principles of GridBagLayout , you forgot to define
anchor
, then you can fix the placedJComponent
in the rellativePoin
t and I think thatGridBagLayout
complicated your GUI, this LayoutManager is better to use to place a lot ofJComponents
for one container (no usenested layout
)
eg
import java.awt.*;
import javax.swing.*;
import javax.swing.border.*;
public class BorderPanels extends JFrame {
private static final long serialVersionUID = 1L;
public BorderPanels() {
setLayout(new GridBagLayout());// set LayoutManager
GridBagConstraints gbc = new GridBagConstraints();
JPanel panel1 = new JPanel();
Border eBorder = BorderFactory.createEtchedBorder();
panel1.setBorder(BorderFactory.createTitledBorder(eBorder, "20pct"));
gbc.gridx = gbc.gridy = 0;
gbc.gridwidth = gbc.gridheight = 1;
gbc.fill = GridBagConstraints.BOTH;
gbc.anchor = GridBagConstraints.NORTHWEST;
gbc.weightx = gbc.weighty = 20;
add(panel1, gbc); // add compoenet to the COntentPane
JPanel panel2 = new JPanel();
panel2.setBorder(BorderFactory.createTitledBorder(eBorder, "60pct"));
gbc.gridy = 1;
gbc.weightx = gbc.weighty = 60;
//gbc.insets = new Insets(2, 2, 2, 2);
add(panel2, gbc); // add component to the COntentPane
JPanel panel3 = new JPanel();
panel3.setBorder(BorderFactory.createTitledBorder(eBorder, "20pct"));
gbc.gridy = 2;
gbc.weightx = gbc.weighty = 20;
gbc.insets = new Insets(2, 2, 2, 2);
add(panel3, gbc);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // important
pack();
setVisible(true); // important
}
public static void main(String[] args) {
javax.swing.SwingUtilities.invokeLater(new Runnable() { // important
public void run() {
BorderPanels borderPanels = new BorderPanels();
}
});
}
}
to avoid the complications of simple things
-
use a GridLayout (all
JComponents
have the sameDimmension
on screen) -
use BoxLayout or BorderLayout
source to share