AWT03-LayoutManager佈局管理器
1.LayoutManager佈局管理器
在之前的學習中,我們使用setBounds()方法設定容器的位置大小,但我們不得不明白一件事--如果我們手動為容器設定位置大小的話,就會造成程式通用性的下降。
1 import java.awt.*; 2 3 public class LabelDemo { 4 public static void main(String[] args) { 5 Label label = new Label("Hello world"); 6 } 7 }
在該程式碼中,我們定義了一個Label。在很多情況下,我們需要讓label的寬高和"Hello world"這個字串自身的寬高一樣,這個寬高被稱為“最佳大小”。
在Windows上,我們需要將寬高設定為100px,20px。但在Linux上,為了達到相同的效果,我們需要將寬高設定為120px,24px。
一個擁有上千個元件的大型程式中,為了達到各平臺相同的視覺效果,其手動調整工作無疑是一場災難。為了解決這一個問題,LayoutManager誕生了。
2.體系
(介面)LayoutManager
-GridLayout(網格佈局)
-FlowLayout(流式佈局)
-(介面)LayoutManager2
-CardLayout(卡片佈局)
-GridBagLayout(網格包佈局)
-BorderLayout(邊框佈局)
3.五種佈局管理器
3.1 FlowLayout 流式佈局
3.1.1 簡介
FlowLayout佈局管理器中,元件像是流水一般向某方向流動(排列),遇到障礙(邊界)就折回,另起一行重新開始。一般情況下,FlowLayout的排列方向是從左向右。
方法名 | 說明 |
FlowLayout() | 使用預設的對齊方式、預設的垂直間距和預設的水平間距建立LayoutManager佈局管理器。 |
FlowLayout(int align) | 使用指定的對齊方式、預設的垂直間距和預設的水平間距建立LayoutManager佈局管理器。 |
FlowLayout(int align,int hgap,int vgap) | 使用指定的對齊方式、指定的垂直間距和指定的水平間距建立LayoutManager佈局管理器。 |
FlowLayout佈局管理器的排列方向,從左向右、從右向左、從中間向兩邊,該引數使用FlowLayout類的靜態常量:FlowLayout.LEFT、FlowLayout.RIGHT、FlowLayout.CENTER。
水平和垂直間距的單位是px,預設是5px。
3.1.2 程式碼演示
1.新增一個視窗
2.設定佈局管理器
3.新增元件
4.設定大小、pack方法
1 import java.awt.*; 2 3 public class setFlowLayoutDemo { 4 public static void main(String[] args) { 5 Frame f = new Frame("FlowLayoutDemo"); 6 f.setLayout(new FlowLayout(FlowLayout.CENTER,20,20)); 7 8 for (int i = 0;i<10;i++){ 9 f.add(new Button("按鈕"+i)); 10 } 11 f.pack(); 12 f.setVisible(true); 13 } 14 }
3.2 BorderLayout 邊框佈局
3.2.1 簡介
BorderLayout邊框佈局將容器分為North、South、West、East、Center五個區域,普通的元件可以放在這五個區域中任意一個。
當改變BorderLayout的大小時,North、South、Center水平調整,而West、East、Center垂直調整(豎著的橫著調,橫著的豎著調,中間的全部調)。
注意:
1.當向使用BorderLayout佈局的容器中新增元件時,需要指定元件的區域,如果沒有指定預設新增到Center。
2.當向一個區域新增多個元件時,後放入的元件會覆蓋先放入的元件。
方法名 | 說明 |
Borderlayout() | 使用預設的垂直與水平間距建立BorderLayout佈局 |
BorderLayout(int hgap,int vgap) | 使用指定的垂直與水平間距建立BorderLayout佈局 |
3.2.2 程式碼演示
1 import java.awt.*; 2 3 public class setBorderLayoutDemo { 4 public static void main(String[] args) { 5 Frame f = new Frame("BorderLayoutDemo"); 6 7 f.setLayout(new BorderLayout(30,5)); 8 9 f.add(new Button("北按鈕"),BorderLayout.NORTH); 10 f.add(new Button("南按鈕"),BorderLayout.SOUTH); 11 f.add(new Button("東按鈕"),BorderLayout.EAST); 12 f.add(new Button("西按鈕"),BorderLayout.WEST); 13 f.add(new Button("中按鈕"),BorderLayout.CENTER); 14 15 f.pack(); 16 17 f.setVisible(true); 18 19 } 20 }
1 import java.awt.*; 2 3 public class setBorderLayoutDemo { 4 public static void main(String[] args) { 5 Frame f = new Frame("BorderLayoutDemo"); 6 7 f.setLayout(new BorderLayout(30, 5)); 8 9 f.add(new Button("北按鈕"), BorderLayout.NORTH); 10 f.add(new Button("南按鈕"), BorderLayout.SOUTH); 11 // f.add(new Button("東按鈕"),BorderLayout.EAST); 12 // f.add(new Button("西按鈕"),BorderLayout.WEST); 13 // f.add(new Button("中按鈕"),BorderLayout.CENTER); 14 Panel p = new Panel(); 15 p.add(new TextField(20)); 16 p.add(new Button("中間按鈕")); 17 18 f.add(p); 19 20 f.pack(); 21 22 f.setVisible(true); 23 24 } 25 }
3.3 GridLayout 網格佈局
3.3.1 簡介
GridLayout佈局管理器將容器分割成縱橫線分割的網格,每個網格所佔的區域大小相同。當向使用GridLayout佈局的容器中新增元件時,預設從左向右、從上向下,依次新增到每個網格中。與FlowLayout不同的是,放置在GridLayout佈局管理器中的元件大小由元件所處的區域決定(每個元件將佔滿整個區域)。
方法名 | 說明 |
GridLayout(int rows,int cols) | 使用指定的行數、列數以及預設的垂直間距和預設的水平間距建立GridLayout佈局管理器。 |
GridLayout(int rows,int cols,int hgap,int vgap) | 使用指定的行數、列數以及指定的垂直間距和指定的水平間距建立GridLayout佈局管理器。 |
3.3.2 程式碼演示
1 import java.awt.*; 2 3 public class setGridLayout { 4 public static void main(String[] args) { 5 Frame f = new Frame("計算器"); 6 Panel pp = new Panel(); 7 pp.add(new TextField(30)); 8 9 f.add(pp,BorderLayout.NORTH); 10 11 Panel p = new Panel(); 12 p.setLayout(new GridLayout(3,5,4,4)); 13 p.add(new Button("1")); 14 p.add(new Button("2")); 15 p.add(new Button("3")); 16 p.add(new Button("4")); 17 p.add(new Button("5")); 18 p.add(new Button("6")); 19 p.add(new Button("7")); 20 p.add(new Button("8")); 21 p.add(new Button("9")); 22 p.add(new Button("0")); 23 p.add(new Button("+")); 24 p.add(new Button("-")); 25 p.add(new Button("*")); 26 p.add(new Button("/")); 27 p.add(new Button("%")); 28 29 f.add(p); 30 31 f.pack(); 32 33 f.setVisible(true); 34 } 35 }
3.4 GridBagLayout 網格包佈局
GridBagLayout佈局是功能最強大也最複雜,與GridLayout不同,在GridBagLayout中元件可以跨過一個或多個網格且可以設定各個網格大小不同,從而增加了網格佈局的靈活性。當視窗的大小發生變化時,GridBagLayout也可以準確的控制視窗各部分的拉伸。
由於在GridBagLayout中元件可以跨越網格,所以在往容器內新增元件時,需要具體的控制每個元件佔用多少個網格,Java提供GridBagConstraints,與特定的元件繫結,可以完成具體大小和跨越性的設定。
3.5 CardLayout 卡片佈局
CardLayout佈局管理器以時間而非空間來管理其中的元件,它將加入容器中的元件看成一疊卡片(每一張卡片其實就是一個元件),每次只有最上面的Component可見。
方法名 | 說明 |
CardLayout() | 建立預設的CardLayout佈局 |
CardLayout(int hgap,int vgap) | 使用指定的水平間距、垂直間距建立CardLayout |
first(Container target) | 顯示target容器中的第一張卡片 |
last(Container target) | 顯示target容器中的最後一張卡片 |
previous(Container target) | 顯示target容器中的前一張卡片 |
next(Container target) | 顯示target容器中的後一張卡片 |
show(Container target,String name) | 顯示target容器中指定名字的那一張卡片 |
1 import java.awt.*; 2 import java.awt.event.ActionEvent; 3 import java.awt.event.ActionListener; 4 5 public class setCardLayout { 6 public static void main(String[] args) { 7 Frame f = new Frame("CardLayout"); 8 9 Panel p1 = new Panel(); 10 CardLayout cl = new CardLayout(); 11 p1.setLayout(cl); 12 13 String[] names = {"第一張","第二張","第三張","第四張","第五張"}; 14 for (int i = 0;i< names.length;i++){ 15 p1.add(names[i],new Button(names[i])); 16 } 17 18 f.add(p1); 19 20 Panel p2 = new Panel(); 21 22 Button b1 = new Button("第一張"); 23 Button b2 = new Button("上一張"); 24 Button b3 = new Button("第三張"); 25 Button b4 = new Button("下一張"); 26 Button b5 = new Button("最後一張"); 27 28 ActionListener al = new ActionListener() { 29 @Override 30 public void actionPerformed(ActionEvent e) { 31 String command = e.getActionCommand(); 32 switch (command){ 33 case "第一張": 34 cl.first(p1); 35 break; 36 case "上一張": 37 cl.previous(p1); 38 break; 39 case "第三張": 40 cl.show(p1,"第三張"); 41 break; 42 case "下一張": 43 cl.next(p1); 44 break; 45 case "最後一張": 46 cl.last(p1); 47 break; 48 } 49 } 50 }; 51 52 b1.addActionListener(al); 53 b2.addActionListener(al); 54 b3.addActionListener(al); 55 b4.addActionListener(al); 56 b5.addActionListener(al); 57 58 p2.add(b1); 59 p2.add(b2); 60 p2.add(b3); 61 p2.add(b4); 62 p2.add(b5); 63 64 f.add(p2,BorderLayout.SOUTH); 65 66 f.pack(); 67 68 f.setVisible(true); 69 } 70 }
3.6 BoxLayout 盒佈局
BoxLayout是為了簡化開發由Swing引入的,可以在垂直和水平兩個方向上擺放元件。
方法名 | 說明 |
BoxLayout(Container target,int axis) | 指定建立基於target容器的BoxLayout佈局管理器,該佈局管理器裡的元件會按照axis方向排列。其中axis有BoxLayout.X_AXIS(橫向)和BoxLayout.Y_AXIS(縱向)。 |
1 import javax.swing.*; 2 import java.awt.*; 3 4 public class setBoxLayout { 5 public static void main(String[] args) { 6 Frame frame = new Frame("BoxLayout"); 7 8 BoxLayout box = new BoxLayout(frame, BoxLayout.X_AXIS); 9 10 frame.setLayout(box); 11 12 frame.add(new Button("按鈕1")); 13 frame.add(new Button("按鈕2")); 14 15 frame.pack(); 16 frame.setVisible(true); 17 } 18 }
在Swing中,提供了一個新的容器Box,該容器的預設佈局管理器就是BoxLayout。大多數情況下,使用Box容器去容納多個元件,然後再把Box容器最為一個元件新增到其他容器中形成完整的窗口布局。
方法名 | 說明 |
static Box createHorizontalBox() | 建立一個水平排列元件的容器 |
static Box createVerticalBox() | 建立一個垂直排列元件的容器 |
1 import javax.swing.*; 2 import java.awt.*; 3 4 public class BoxLayout { 5 public static void main(String[] args) { 6 Frame frame = new Frame("BoxLayOut"); 7 8 Box hbox = Box.createHorizontalBox(); 9 Box vbox = Box.createVerticalBox(); 10 11 hbox.add(new Button("1")); 12 hbox.add(new Button("2")); 13 14 vbox.add(new Button("3")); 15 vbox.add(new Button("4")); 16 17 frame.add(hbox,BorderLayout.NORTH); 18 frame.add(vbox,BorderLayout.SOUTH); 19 20 frame.pack(); 21 22 frame.setVisible(true); 23 } 24 }
我們發現,在這時生成的介面沒有任何間隔,不是特別美觀,因此可以在需要間隔的地方新增間隔元件。
方法名 | 說明 |
static Component createHorizontalGlue() | 建立一條水平Glue(可在兩個方向上同時拉伸的間距) |
static Component createVerticalGlue() | 建立一條垂直Glue(可在兩個方向上同時拉伸的間距) |
static Component createHorizontalStrut(int width) | 建立一條指定寬度的水平Strut(可以在垂直方向上拉伸的間距) |
static Component createVerticalStrut(int height) | 建立一條指定高度的水平Strut(可以在水平方向上拉伸的間距) |
1 import javax.swing.*; 2 import java.awt.*; 3 4 public class BoxLayout { 5 public static void main(String[] args) { 6 Frame frame = new Frame("BoxLayOut"); 7 8 Box hbox = Box.createHorizontalBox(); 9 Box vbox = Box.createVerticalBox(); 10 11 hbox.add(new Button("水平1")); 12 hbox.add(Box.createHorizontalGlue()); 13 hbox.add(new Button("水平2")); 14 15 vbox.add(new Button("垂直1")); 16 vbox.add(Box.createVerticalGlue()); 17 vbox.add(new Button("垂直2")); 18 19 frame.add(hbox,BorderLayout.NORTH); 20 frame.add(vbox,BorderLayout.SOUTH); 21 22 frame.pack(); 23 24 frame.setVisible(true); 25 } 26 }