由于人们在理解和使用 GridBagLayout 的时候遇到了很多问题,所以 Swing 还提供了
BoxLayout,它具有 GridBagLayout 的许多好处,却不像 GridBagLayout 那么复杂。
所以当你需要手工编写布局代码的时候,可以考虑使用它(再次提醒,如果你的设计过于
复杂,那么就应该使用 GUI 构造工具来生成布局代码)。BoxLayout 使你可以在水平方
向或者垂直方向控制组件的位置,并且通过被称为“支架和胶水”(struts and glue)的
机制来控制组件的间隔。首先,我们使用与演示其它布局管理器相同的方式,看一看如何
直接使用 BoxLayout:
//: c14:BoxLayout1.java
// Vertical and horizontal BoxLayouts.
// <applet code=BoxLayout1 width=450 height=200></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class BoxLayout1 extends JApplet {
public void init() {
JPanel jpv = new JPanel();
jpv.setLayout(new BoxLayout(jpv, BoxLayout.Y_AXIS));
for(int i = 0; i < 5; i++)
jpv.add(new JButton("jpv " + i));
JPanel jph = new JPanel();
jph.setLayout(new BoxLayout(jph, BoxLayout.X_AXIS));
for(int i = 0; i < 5; i++)
jph.add(new JButton("jph " + i));
Container cp = getContentPane();
cp.add(BorderLayout.EAST, jpv);
cp.add(BorderLayout.SOUTH, jph);
}
public static void main(String[] args) {
Console.run(new BoxLayout1(), 450, 200);
}
}
BoxLayout的构造器与其它布局管理器有所不同,你要把“将由BoxLayout控制的容器”
作为第一个参数,布局的方向作为第二个参数提供给构造器。
为了简化使用方式,有一个被称为 Box 的特殊容器,它缺省地使用 BoxLayout 作为布局
管理器。Box 具有两个静态方法来创建水平或者垂直对齐的箱子,下面的例子就使用了 Box
来水平和垂直放置组件。
//: c14:Box1.java
// Vertical and horizontal BoxLayouts.
// <applet code=Box1 width=450 height=200></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box1 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
for(int i = 0; i < 5; i++)
bv.add(new JButton("bv " + i));
Box bh = Box.createHorizontalBox();
for(int i = 0; i < 5; i++)
bh.add(new JButton("bh " + i));
Container cp = getContentPane();
cp.add(BorderLayout.EAST, bv);
cp.add(BorderLayout.SOUTH, bh);
}
public static void main(String[] args) {
Console.run(new Box1(), 450, 200);
}
} ///:~
一旦创建了Box对象,你就可以在把组件添加到内容面板上的时候,把它作为第二个参数去
传递了。
支架(strut)可以以象素为单位来增加组件之间的空隙。如果要使用支架,你只需在添加
组件的时候,把它加入到要格开的组件之间即可:
//: c14:Box2.java
// Adding struts.
// <applet code=Box2 width=450 height=300></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box2 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
for(int i = 0; i < 5; i++) {
bv.add(new JButton("bv " + i));
bv.add(Box.createVerticalStrut(i * 10));
}
Box bh = Box.createHorizontalBox();
for(int i = 0; i < 5; i++) {
bh.add(new JButton("bh " + i));
bh.add(Box.createHorizontalStrut(i * 10));
}
Container cp = getContentPane();
cp.add(BorderLayout.EAST, bv);
cp.add(BorderLayout.SOUTH, bh);
}
public static void main(String[] args) {
Console.run(new Box2(), 450, 300);
}
} ///:~
支架能够把组件格开固定的距离,胶水(glue)正好相反;它尽可能地将组件分离开。所
以与其说它是“胶水”,不如说它是“弹簧”(它们的设计基于所谓的“弹簧和支架”算
法,所以选用的术语有点神秘)。
//: c14:Box3.java
// Using Glue.
// <applet code=Box3 width=450 height=300></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box3 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
bv.add(new JLabel("Hello"));
bv.add(Box.createVerticalGlue());
bv.add(new JLabel("Applet"));
bv.add(Box.createVerticalGlue());
bv.add(new JLabel("World"));
Box bh = Box.createHorizontalBox();
bh.add(new JLabel("Hello"));
bh.add(Box.createHorizontalGlue());
bh.add(new JLabel("Applet"));
bh.add(Box.createHorizontalGlue());
bh.add(new JLabel("World"));
bv.add(Box.createVerticalGlue());
bv.add(bh);
bv.add(Box.createVerticalGlue());
getContentPane().add(bv);
}
public static void main(String[] args) {
Console.run(new Box3(), 450, 300);
}
} ///:~
支架只在一个方向上起效果,但“刚性区域”(rigid area)可以在两个方向上固定组件之
间的空隙:
//: c14:Box4.java
// Rigid areas are like pairs of struts.
// <applet code=Box4 width=450 height=300></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box4 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
bv.add(new JButton("Top"));
bv.add(Box.createRigidArea(new Dimension(120, 90)));
bv.add(new JButton("Bottom"));
Box bh = Box.createHorizontalBox();
bh.add(new JButton("Left"));
bh.add(Box.createRigidArea(new Dimension(160, 80)));
bh.add(new JButton("Right"));
bv.add(bh);
getContentPane().add(bv);
}
public static void main(String[] args) {
Console.run(new Box4(), 450, 300);
}
} ///:~
你要注意:“刚性区域”是有些争议的。因为它使用了绝对值,所以有人认为这么做带来
BoxLayout,它具有 GridBagLayout 的许多好处,却不像 GridBagLayout 那么复杂。
所以当你需要手工编写布局代码的时候,可以考虑使用它(再次提醒,如果你的设计过于
复杂,那么就应该使用 GUI 构造工具来生成布局代码)。BoxLayout 使你可以在水平方
向或者垂直方向控制组件的位置,并且通过被称为“支架和胶水”(struts and glue)的
机制来控制组件的间隔。首先,我们使用与演示其它布局管理器相同的方式,看一看如何
直接使用 BoxLayout:
//: c14:BoxLayout1.java
// Vertical and horizontal BoxLayouts.
// <applet code=BoxLayout1 width=450 height=200></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class BoxLayout1 extends JApplet {
public void init() {
JPanel jpv = new JPanel();
jpv.setLayout(new BoxLayout(jpv, BoxLayout.Y_AXIS));
for(int i = 0; i < 5; i++)
jpv.add(new JButton("jpv " + i));
JPanel jph = new JPanel();
jph.setLayout(new BoxLayout(jph, BoxLayout.X_AXIS));
for(int i = 0; i < 5; i++)
jph.add(new JButton("jph " + i));
Container cp = getContentPane();
cp.add(BorderLayout.EAST, jpv);
cp.add(BorderLayout.SOUTH, jph);
}
public static void main(String[] args) {
Console.run(new BoxLayout1(), 450, 200);
}
}
BoxLayout的构造器与其它布局管理器有所不同,你要把“将由BoxLayout控制的容器”
作为第一个参数,布局的方向作为第二个参数提供给构造器。
为了简化使用方式,有一个被称为 Box 的特殊容器,它缺省地使用 BoxLayout 作为布局
管理器。Box 具有两个静态方法来创建水平或者垂直对齐的箱子,下面的例子就使用了 Box
来水平和垂直放置组件。
//: c14:Box1.java
// Vertical and horizontal BoxLayouts.
// <applet code=Box1 width=450 height=200></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box1 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
for(int i = 0; i < 5; i++)
bv.add(new JButton("bv " + i));
Box bh = Box.createHorizontalBox();
for(int i = 0; i < 5; i++)
bh.add(new JButton("bh " + i));
Container cp = getContentPane();
cp.add(BorderLayout.EAST, bv);
cp.add(BorderLayout.SOUTH, bh);
}
public static void main(String[] args) {
Console.run(new Box1(), 450, 200);
}
} ///:~
一旦创建了Box对象,你就可以在把组件添加到内容面板上的时候,把它作为第二个参数去
传递了。
支架(strut)可以以象素为单位来增加组件之间的空隙。如果要使用支架,你只需在添加
组件的时候,把它加入到要格开的组件之间即可:
//: c14:Box2.java
// Adding struts.
// <applet code=Box2 width=450 height=300></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box2 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
for(int i = 0; i < 5; i++) {
bv.add(new JButton("bv " + i));
bv.add(Box.createVerticalStrut(i * 10));
}
Box bh = Box.createHorizontalBox();
for(int i = 0; i < 5; i++) {
bh.add(new JButton("bh " + i));
bh.add(Box.createHorizontalStrut(i * 10));
}
Container cp = getContentPane();
cp.add(BorderLayout.EAST, bv);
cp.add(BorderLayout.SOUTH, bh);
}
public static void main(String[] args) {
Console.run(new Box2(), 450, 300);
}
} ///:~
支架能够把组件格开固定的距离,胶水(glue)正好相反;它尽可能地将组件分离开。所
以与其说它是“胶水”,不如说它是“弹簧”(它们的设计基于所谓的“弹簧和支架”算
法,所以选用的术语有点神秘)。
//: c14:Box3.java
// Using Glue.
// <applet code=Box3 width=450 height=300></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box3 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
bv.add(new JLabel("Hello"));
bv.add(Box.createVerticalGlue());
bv.add(new JLabel("Applet"));
bv.add(Box.createVerticalGlue());
bv.add(new JLabel("World"));
Box bh = Box.createHorizontalBox();
bh.add(new JLabel("Hello"));
bh.add(Box.createHorizontalGlue());
bh.add(new JLabel("Applet"));
bh.add(Box.createHorizontalGlue());
bh.add(new JLabel("World"));
bv.add(Box.createVerticalGlue());
bv.add(bh);
bv.add(Box.createVerticalGlue());
getContentPane().add(bv);
}
public static void main(String[] args) {
Console.run(new Box3(), 450, 300);
}
} ///:~
支架只在一个方向上起效果,但“刚性区域”(rigid area)可以在两个方向上固定组件之
间的空隙:
//: c14:Box4.java
// Rigid areas are like pairs of struts.
// <applet code=Box4 width=450 height=300></applet>
import javax.swing.*;
import java.awt.*;
import com.bruceeckel.swing.*;
public class Box4 extends JApplet {
public void init() {
Box bv = Box.createVerticalBox();
bv.add(new JButton("Top"));
bv.add(Box.createRigidArea(new Dimension(120, 90)));
bv.add(new JButton("Bottom"));
Box bh = Box.createHorizontalBox();
bh.add(new JButton("Left"));
bh.add(Box.createRigidArea(new Dimension(160, 80)));
bh.add(new JButton("Right"));
bv.add(bh);
getContentPane().add(bv);
}
public static void main(String[] args) {
Console.run(new Box4(), 450, 300);
}
} ///:~
你要注意:“刚性区域”是有些争议的。因为它使用了绝对值,所以有人认为这么做带来
的问题比带来的好处要更多。