1 网格组布局
import java.awt.EventQueue;
import javax.swing.JFrame;
/**
* @version 1.35 2015-06-12
* @author Cay Horstmann
*/
public class GridBagLayoutTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
JFrame frame = new FontFrame();
frame.setTitle("GridBagLayoutTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
import java.awt.Font;
import java.awt.GridBagLayout;
import java.awt.event.ActionListener;
import javax.swing.BorderFactory;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JTextArea;
/**
* A frame that uses a grid bag layout to arrange font selection components.
*/
public class FontFrame extends JFrame
{
public static final int TEXT_ROWS = 10;
public static final int TEXT_COLUMNS = 20;
private JComboBox face;
private JComboBox size;
private JCheckBox bold;
private JCheckBox italic;
private JTextArea sample;
public FontFrame()
{
GridBagLayout layout = new GridBagLayout();
setLayout(layout);
ActionListener listener = event -> updateSample();
JLabel faceLabel = new JLabel("Face: ");
face = new JComboBox<>(new String[] { "Serif", "SansSerif", "Monospaced",
"Dialog", "DialogInput" });
face.addActionListener(listener);
JLabel sizeLabel = new JLabel("Size: ");
size = new JComboBox<>(new Integer[] { 8, 10, 12, 15, 18, 24, 36, 48 });
size.addActionListener(listener);
bold = new JCheckBox("Bold");
bold.addActionListener(listener);
italic = new JCheckBox("Italic");
italic.addActionListener(listener);
sample = new JTextArea(TEXT_ROWS, TEXT_COLUMNS);
sample.setText("The quick brown fox jumps over the lazy dog");
sample.setEditable(false);
sample.setLineWrap(true);
sample.setBorder(BorderFactory.createEtchedBorder());
add(faceLabel, new GBC(0, 0).setAnchor(GBC.EAST));
add(face, new GBC(1, 0).setFill(GBC.HORIZONTAL).setWeight(100, 0)
.setInsets(1));
add(sizeLabel, new GBC(0, 1).setAnchor(GBC.EAST));
add(size, new GBC(1, 1).setFill(GBC.HORIZONTAL).setWeight(100, 0)
.setInsets(1));
add(bold, new GBC(0, 2, 2, 1).setAnchor(GBC.CENTER).setWeight(100, 100));
add(italic, new GBC(0, 3, 2, 1).setAnchor(GBC.CENTER).setWeight(100, 100));
add(sample, new GBC(2, 0, 1, 4).setFill(GBC.BOTH).setWeight(100, 100));
pack();
updateSample();
}
public void updateSample()
{
String fontFace = (String) face.getSelectedItem();
int fontStyle = (bold.isSelected() ? Font.BOLD : 0)
+ (italic.isSelected() ? Font.ITALIC : 0);
int fontSize = size.getItemAt(size.getSelectedIndex());
Font font = new Font(fontFace, fontStyle, fontSize);
sample.setFont(font);
sample.repaint();
}
}
import java.awt.*;
/**
* This class simplifies the use of the GridBagConstraints class.
* @version 1.01 2004-05-06
* @author Cay Horstmann
*/
public class GBC extends GridBagConstraints
{
/**
* Constructs a GBC with a given gridx and gridy position and all other grid
* bag constraint values set to the default.
* @param gridx the gridx position
* @param gridy the gridy position
*/
public GBC(int gridx, int gridy)
{
this.gridx = gridx;
this.gridy = gridy;
}
/**
* Constructs a GBC with given gridx, gridy, gridwidth, gridheight and all
* other grid bag constraint values set to the default.
* @param gridx the gridx position
* @param gridy the gridy position
* @param gridwidth the cell span in x-direction
* @param gridheight the cell span in y-direction
*/
public GBC(int gridx, int gridy, int gridwidth, int gridheight)
{
this.gridx = gridx;
this.gridy = gridy;
this.gridwidth = gridwidth;
this.gridheight = gridheight;
}
/**
* Sets the anchor.
* @param anchor the anchor value
* @return this object for further modification
*/
public GBC setAnchor(int anchor)
{
this.anchor = anchor;
return this;
}
/**
* Sets the fill direction.
* @param fill the fill direction
* @return this object for further modification
*/
public GBC setFill(int fill)
{
this.fill = fill;
return this;
}
/**
* Sets the cell weights.
* @param weightx the cell weight in x-direction
* @param weighty the cell weight in y-direction
* @return this object for further modification
*/
public GBC setWeight(double weightx, double weighty)
{
this.weightx = weightx;
this.weighty = weighty;
return this;
}
/**
* Sets the insets of this cell.
* @param distance the spacing to use in all directions
* @return this object for further modification
*/
public GBC setInsets(int distance)
{
this.insets = new Insets(distance, distance, distance, distance);
return this;
}
/**
* Sets the insets of this cell.
* @param top the spacing to use on top
* @param left the spacing to use to the left
* @param bottom the spacing to use on the bottom
* @param right the spacing to use to the right
* @return this object for further modification
*/
public GBC setInsets(int top, int left, int bottom, int right)
{
this.insets = new Insets(top, left, bottom, right);
return this;
}
/**
* Sets the internal padding
* @param ipadx the internal padding in x-direction
* @param ipady the internal padding in y-direction
* @return this object for further modification
*/
public GBC setIpad(int ipadx, int ipady)
{
this.ipadx = ipadx;
this.ipady = ipady;
return this;
}
}
2 组布局
import java.awt.EventQueue
import javax.swing.JFrame
public class GroupLayoutTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
JFrame frame = new FontFrame()
frame.setTitle("GroupLayoutTest")
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE)
frame.setVisible(true)
})
}
}
import java.awt.Font
import java.awt.event.ActionListener
import javax.swing.BorderFactory
import javax.swing.GroupLayout
import javax.swing.JCheckBox
import javax.swing.JComboBox
import javax.swing.JFrame
import javax.swing.JLabel
import javax.swing.JScrollPane
import javax.swing.JTextArea
import javax.swing.LayoutStyle
import javax.swing.SwingConstants
public class FontFrame extends JFrame
{
public static final int TEXT_ROWS = 10
public static final int TEXT_COLUMNS = 20
private JComboBox face
private JComboBox size
private JCheckBox bold
private JCheckBox italic
private JScrollPane pane
private JTextArea sample
public FontFrame()
{
ActionListener listener = event -> updateSample()
// construct components
JLabel faceLabel = new JLabel("Face: ")
face = new JComboBox<>(new String[] { "Serif", "SansSerif", "Monospaced", "Dialog",
"DialogInput" })
face.addActionListener(listener)
JLabel sizeLabel = new JLabel("Size: ")
size = new JComboBox<>(new Integer[] { 8, 10, 12, 15, 18, 24, 36, 48 })
size.addActionListener(listener)
bold = new JCheckBox("Bold")
bold.addActionListener(listener)
italic = new JCheckBox("Italic")
italic.addActionListener(listener)
sample = new JTextArea(TEXT_ROWS, TEXT_COLUMNS)
sample.setText("The quick brown fox jumps over the lazy dog")
sample.setEditable(false)
sample.setLineWrap(true)
sample.setBorder(BorderFactory.createEtchedBorder())
pane = new JScrollPane(sample)
GroupLayout layout = new GroupLayout(getContentPane())
setLayout(layout)
layout.setHorizontalGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
.addGroup(
layout.createSequentialGroup().addContainerGap().addGroup(
layout.createParallelGroup(GroupLayout.Alignment.LEADING).addGroup(
GroupLayout.Alignment.TRAILING,
layout.createSequentialGroup().addGroup(
layout.createParallelGroup(GroupLayout.Alignment.TRAILING)
.addComponent(faceLabel).addComponent(sizeLabel))
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
.addGroup(
layout.createParallelGroup(
GroupLayout.Alignment.LEADING, false)
.addComponent(size).addComponent(face)))
.addComponent(italic).addComponent(bold)).addPreferredGap(
LayoutStyle.ComponentPlacement.RELATED).addComponent(pane)
.addContainerGap()))
layout.linkSize(SwingConstants.HORIZONTAL, new java.awt.Component[] { face, size })
layout.setVerticalGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
.addGroup(
layout.createSequentialGroup().addContainerGap().addGroup(
layout.createParallelGroup(GroupLayout.Alignment.LEADING).addComponent(
pane, GroupLayout.Alignment.TRAILING).addGroup(
layout.createSequentialGroup().addGroup(
layout.createParallelGroup(GroupLayout.Alignment.BASELINE)
.addComponent(face).addComponent(faceLabel))
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
.addGroup(
layout.createParallelGroup(
GroupLayout.Alignment.BASELINE).addComponent(size)
.addComponent(sizeLabel)).addPreferredGap(
LayoutStyle.ComponentPlacement.RELATED).addComponent(
italic, GroupLayout.DEFAULT_SIZE,
GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
.addComponent(bold, GroupLayout.DEFAULT_SIZE,
GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)))
.addContainerGap()))
pack()
}
public void updateSample()
{
String fontFace = (String) face.getSelectedItem()
int fontStyle = (bold.isSelected() ? Font.BOLD : 0)
+ (italic.isSelected() ? Font.ITALIC : 0)
int fontSize = size.getItemAt(size.getSelectedIndex())
Font font = new Font(fontFace, fontStyle, fontSize)
sample.setFont(font)
sample.repaint()
}
}
3 不使用布局
4 自定义布局管理
import java.awt.*;
import javax.swing.*;
/**
* @version 1.33 2015-06-12
* @author Cay Horstmann
*/
public class CircleLayoutTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
JFrame frame = new CircleLayoutFrame();
frame.setTitle("CircleLayoutTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
import javax.swing.*;
/**
* A frame that shows buttons arranged along a circle.
*/
public class CircleLayoutFrame extends JFrame
{
public CircleLayoutFrame()
{
setLayout(new CircleLayout());
add(new JButton("Yellow"));
add(new JButton("Blue"));
add(new JButton("Red"));
add(new JButton("Green"));
add(new JButton("Orange"));
add(new JButton("Fuchsia"));
add(new JButton("Indigo"));
pack();
}
}
import java.awt.*;
/**
* A layout manager that lays out components along a circle.
*/
public class CircleLayout implements LayoutManager
{
private int minWidth = 0;
private int minHeight = 0;
private int preferredWidth = 0;
private int preferredHeight = 0;
private boolean sizesSet = false;
private int maxComponentWidth = 0;
private int maxComponentHeight = 0;
public void addLayoutComponent(String name, Component comp)
{
}
public void removeLayoutComponent(Component comp)
{
}
public void setSizes(Container parent)
{
if (sizesSet) return;
int n = parent.getComponentCount();
preferredWidth = 0;
preferredHeight = 0;
minWidth = 0;
minHeight = 0;
maxComponentWidth = 0;
maxComponentHeight = 0;
for (int i = 0; i < n; i++)
{
Component c = parent.getComponent(i);
if (c.isVisible())
{
Dimension d = c.getPreferredSize();
maxComponentWidth = Math.max(maxComponentWidth, d.width);
maxComponentHeight = Math.max(maxComponentHeight, d.height);
preferredWidth += d.width;
preferredHeight += d.height;
}
}
minWidth = preferredWidth / 2;
minHeight = preferredHeight / 2;
sizesSet = true;
}
public Dimension preferredLayoutSize(Container parent)
{
setSizes(parent);
Insets insets = parent.getInsets();
int width = preferredWidth + insets.left + insets.right;
int height = preferredHeight + insets.top + insets.bottom;
return new Dimension(width, height);
}
public Dimension minimumLayoutSize(Container parent)
{
setSizes(parent);
Insets insets = parent.getInsets();
int width = minWidth + insets.left + insets.right;
int height = minHeight + insets.top + insets.bottom;
return new Dimension(width, height);
}
public void layoutContainer(Container parent)
{
setSizes(parent);
Insets insets = parent.getInsets();
int containerWidth = parent.getSize().width - insets.left - insets.right;
int containerHeight = parent.getSize().height - insets.top - insets.bottom;
int xcenter = insets.left + containerWidth / 2;
int ycenter = insets.top + containerHeight / 2;
int xradius = (containerWidth - maxComponentWidth) / 2;
int yradius = (containerHeight - maxComponentHeight) / 2;
int radius = Math.min(xradius, yradius);
int n = parent.getComponentCount();
for (int i = 0; i < n; i++)
{
Component c = parent.getComponent(i);
if (c.isVisible())
{
double angle = 2 * Math.PI * i / n;
int x = xcenter + (int) (Math.cos(angle) * radius);
int y = ycenter + (int) (Math.sin(angle) * radius);
Dimension d = c.getPreferredSize();
c.setBounds(x - d.width / 2, y - d.height / 2, d.width, d.height);
}
}
}
}
5 遍历顺序