360 likes | 453 Views
第 1 讲 界面布局管理. 本节主要内容 :. 回顾几种布局管理器 String 与 StringBuffer 类的使用 事件处理 界面程序设计的应用实例 ( 字符串的查找与替换 ). 1. 布局管理器. 常用的布局管理器有: BorderLayout 类 FlowLayout 类 GridLayout 类 此外,我们将介绍一个很灵活的布局管理器 GridBagLayout 类,可随意设置组件的大小及其放置的位置。. 1.1 BorderLayout( 边界布局管理器 ).
E N D
本节主要内容: • 回顾几种布局管理器 • String与StringBuffer类的使用 • 事件处理 • 界面程序设计的应用实例(字符串的查找与替换)
1.布局管理器 • 常用的布局管理器有: BorderLayout类 FlowLayout类 GridLayout类 此外,我们将介绍一个很灵活的布局管理器 GridBagLayout类,可随意设置组件的大小及其放置的位置。
1.1 BorderLayout(边界布局管理器) 功能:将容器分成东、西、南、北、中五个区域,每个区域最多只能包含一个组件,并通过相应的常量进行标识:NORTH、SOUTH、EAST、WEST 和 CENTER。 构造函数: • BorderLayout() • //构造一个组件之间没有间距的新边界布局。 • BorderLayout(int hgap, int vgap) • //用指定的组件之间的水平和垂直间距构造一个边界布局。
BorderLayout类 (布局图) 水平间距为5 垂直间距为10
2. FlowLayout (流式布局管理器) 功能:它可自动依窗口的大小,将组件由左而右的次序来排 列,一行放不下自动换行的一种布局方式。 构造方法: FlowLayout() • 构造一个新的 FlowLayout,默认的情况下,居中对齐,水平和垂直间隙是 5 个单位。 FlowLayout(int align)构造一个新的 FlowLayout,对齐方式是指定的,默认的水平和垂直间隙是 5 个单位。 FlowLayout(int align, int hgap, int vgap) 创建一个新的流布局管理器,具有指定的对齐方式以及指定的水平和垂直间隙。
FlowLayout类 (布局图) 默认下,组件居中对齐,水平和垂直间距为5 组件向右对齐,水平和垂直间距都为10
3. GridLayout(网格布局管理器) • 功能: • 容器被分成大小相等的矩形网格,单元格的大小由最大的构件所决定,用add()方法将组件一行一行地从左到右放置到布局的每个单元格中。 • 构造方法: • GridLayout() • 创建具有默认值的网格布局,即每个组件占据一行一列。 • GridLayout(int rows,int cols) 创建具有指定行数和列数的网格布局。GridLayout(int rows,int cols,int hgap, int vgap) 创建具有指定行数和列数以及指定的水平和垂直间距的网格布局。
GridLayout类(布局图) 无设置水平和垂直间距 设置水平和垂直间距都为10
button1 button2 button3 button4 button5 button6 button7 button8 button9 1.4 GridBagLayout类与GridBagConstraints类 功能:借助于GridBagConstraints类,实现更灵活的外观管理,提供具有不同大小的行和列来放置组件,每个单元可有不同的大小。
具体的使用方式如下: GridBagLayout gbl=new GridBagLayout(); //只有一种无参构造方法 panel.setLayout(gbl); GridBagConstraints q=new GridBagConstraints(); //配置约束对象 q.***=***; … gbl.setConstraints(component, q); //将组件component按照约束q设置 panel.add(component); 对于约束,下面举出了最常用的几种: fill 当组件的显示区域大于组件大小时的显示方式.默认值为NONE,表示组件大小不变 ;HORIZONTAL表示将组件拉宽到与单元格宽度相同; • VERTICAL表示将组件的高度提升到与单元格高度一致;BOTH表示将组件的高度和宽度都拉伸到与单元格一致.
gridwidth,gridheight • 指定组件所占的单元格的数量,默认值皆为1. gridwidth表示横向单元格数量;gridheight表示纵向单元格数量. gridx,gridy 指定组件所在单元格的位置. gridx表示列数; gridy表示行数. weightx,weighty 指定当图形窗口扩大时,各单元格如何分配被扩大的空间.weightx表示横向扩大权重,weighty表示纵向扩大权重. ipadx,ipady 指定组件内部的填充宽度和高度. insets 指定组件和单元格之间的空隙. anchor 指定当组件小于单元格时的放置方式.
例1.4.1 应用 GridBagLayout类布局 • public void init() • { GridBagLayout layout=new GridBagLayout(); • setLayout(layout); • GridBagConstraints GBC = new • GridBagConstraints(); • Button button1=new Button(“But1"); • Button button2=new Button("But2"); • Button button3=new Button("But3"); • Button button4=new Button("But4"); • Button button5=new Button("But5"); • Button button6=new Button("But6"); • Button button7=new Button("But7"); • Button button8=new Button("But8"); • Button button9=new Button("But9");
But1 But2 But3 • GBC.fill=GridBagConstraints.BOTH; • (按钮可以在水平和垂直两个方向扩展) • layout.setConstraints(button1,GBC); • add(button1); • GBC.gridwidth=GridBagConstraints.RELATIVE; • (该按钮紧挨着前一个按钮) • layout.setConstraints(button2,GBC); • add(button2); • GBC.gridwidth=GridBagConstraints.REMAINDER; • (该按钮为该行的最后一个组件,会占据的剩余的空间) • layout.setConstraints(button3,GBC); • add(button3);
But1 But2 But3 But4 • GBC.gridwidth= • GridBagConstraints.REMAINDER; • (表示该按钮独占一行) • layout.setConstraints(button4,GBC); • add(button4);
But1 But2 But3 But4 But5 But6 • GBC.gridwidth=2; • (表示该按钮占两个单元) • layout.setConstraints(button5,GBC); • add(button5); • GBC.gridwidth= • GridBagConstraints.REMAINDER; • layout.setConstraints(button6,GBC); • add(button6);
But1 But2 But3 But4 But5 But6 But7 • GBC.gridwidth=1; • GBC.gridheight=2;(高度为两个单元) • layout.setConstraints(button7,GBC); • add(button7);
But1 But2 But3 But4 But5 But6 But7 But8 But9 • GBC.gridwidth= GridBagConstraints.REMAINDER; • GBC.gridheight=1; • layout.setConstraints(button8,GBC); • add(button8); • layout.setConstraints • (button9,GBC); • add(button9);
2. String类和StringBuffer类的区别 在Java.lang包中提供了两种类型的字符串 类:String类和StringBuffer类 一类是创建之后不会再做修改和变动的字符串常量String类; 另一类是创建之后允许再做更改和变化的字符串变量StringBuffer类。
2.1 String类的创建 String s = “hello”; JVM先根据内容“hello”查找对象,如果没有找到,则在heap上创建新对象,并将其赋予s1,否则使用已经存在的对象. Java会自动为字符串常量生成一个String类的对象,用双引号括起一串自负即可直接初始化一个String对象. String s = new String(“hello”); JVM直接在heap上创建新的对象,所以在heap中会出现内容相同,地址不同的String对象
2.1.1 String的比较 “==” 比较地址 "equals" 比较内容 • 举例: String s1 = "hello"; String s2 = "hello"; String s3 = new String("hello"); • s1 == s2; // true 地址相同s1 == s3; // false 地址不同s1.equals(s2); // true 内容相同s1.equals(s3); // true 内容相同
2.1.2 String类常用的方法: • public int length( ) • public char charAt(int index) • public String substring(int beginIndex,int endIndex) • public int compareTo(String anotherString) • public boolean equals(Object anObject) • public String replace(char oldChar,char newChar) • String trim() • public String concat(String str)
2.2 StringBuffer类的创建 StringBuffer() 创建一个空的StringBuffer对象 StringBuffer(int len) 设置初始容量 StringBuffer(String str) 用已有字符串String对象来初始化StringBuffer对象
注意: • StringBuffer类的第二种构造方法的效率好于第一种 ,因为StringBuffer内部实现是char数组,默认初始化长度为16,每当字符串长度大于char数组长度的时候,JVM会构造更大的新数组,并将原先的数组内容复制到新数组,而第二种避免了复制数组所需的开销
2.2.1 StringBuffer类常用的方法: StringBuffer append(StringBuffer sb)//字符串连接 StringBufferreplace(int start,int end,String str) 用字符串str替换从start位置到end位置之间的子串 void setCharAt(int index,char c) 将index处的字符换成字符c String toString() 将字符串变量StringBuffer转化为字符串常量String insert(int index, substring) 在index的位置插入substring子串 delete(int start ,int end) 删除start到end之间的字符子串
2.3 举个String与StringBuffer应用例子: • public class Untitled1 { public Untitled1() { } public static void main(String[] args) { Untitled1 untitled11 = new Untitled1(); String s1=“STRING类的值是不是会变的->”; String s2=s1; System.out.println(s2); s1+=“加个试试”; • //String 赋值实际上这个是NEW了一个新的对象了,S1变了 • System.out.println(s2); • //S2没有变,这是因为S2指向的地址 还是 最早的s1所在的地址
StringBuffer b1=new StringBuffer("StringBuffer类的值是会变的->"); • StringBuffer b2=b1; • b2.append("加个试试"); • //StringBuffer赋值,操作b2还是那个对象,System.out.println(b1.toString()); • /*所以加一个字符进去b1指向的对象的值也已经变了, • System.out.println()方法是不能接受可变串的,因此在打印 • StringBuffer前要使用toString()方法将其转化为String. */ • }} • 运行结果:STRING类的值是不是会变的->STRING类的值是不是会变的->StringBuffer类的值是会变的->加个试试
2.4 StringBuffer类的优点: • String 是一种非常常用的数据类型,但由于 String 是不可变对象,在进行 String 的相关操作的时候会产生许多临时的 String 对象,耗费了很多不必要的系统资源. • 而 StringBuffer 在操作上是在一个缓冲中进行的,性能当然优越得多。 不过,一般做为简单的字符串传递和其它操作,只不要改变字符串内容的操作,用 String 效率会高一些。
3. 事件处理机制 举单击按钮事件为例: 事件源(按钮btn) 注册:btn.addActionListener(监听对象) 触发事件 ActionEvent事件 注册 调用并传递参数 监听器对象 实现接口:public void actionPerformed(ActionEvent e)
程序设计时, 对于任何事件处理 • 所需的步骤有:(这里举按钮为例) 引用事件包import java.awt.event.*; addActionListener(this); //注册按钮事件的监听器 类声明时实现按钮处理事件的接口ActionListener 定义处理按钮事件的方法public void actionPerformed(ActionEvent e)
注意: 由于Java的单一继承机制,为了实现多重继承的能力, Java用接口来实现,一个类可以实现多个接口. 一旦实现了接口, 就必须一一实现接口中已定义的所有方法,即便不发生某事件,也必须用空的方法体来代替. 事件适配器为用户一种简单实现监听器的手段,只需重写需要的方法,而无关方法不用实现.
4. 本讲的应用示例(字符串的查找与替换) 功能描述 在一段文字内容中查找指定的字符串,找到后,可用其他文字内容替换当前字符串. 总体设计 I. 主界面设计 (Panel的嵌套实现界面、处理鼠标单击事件) II. 查找和替换字符串算法 详细设计 1.界面设计(如下页)
面板1 面板5 面板2 面板3 面板4 (运行结果图) (界面分析图)
2.类的介绍 类名: TextFindReplace • 类功能简介:该类为主类,用于主界面设计 • 方法1:Create( ) • 功能:创建主界面和创建有关查找与替换信息的对话框 • 方法2:mouseClicked( ) • 功能:处理鼠标单击事件 类名: matchFun • 类功能简介:该类用于处理查找和替换字符串算法 • 方法1:strFind( ) • 功能:实现字符串查找功能 • 方法2:strReplace( ) • 功能:实现字符串替换功能
3.关键算法介绍 查找字符串算法 主要应用了String类的两个方法: getCaretPosition() //获得当前光标的位置,即开始比较的位置 char charAt(int index) //获取当前字符串index位置上的一个 字符 接着就是通过逐个字符比较,统计所查找到的相同字符的次数: while(i<s1.length()&&j<s2.length()) { if(s1.charAt(i)==s2.charAt(j)) { ++i; ++j; if(j==s2.length()) //匹配成功 { k=k+1; i=i-j+1; j=0;} } else{i=i-j+1; j=0;} }
字符串替换算法 重复前面的查找过程,找到要替换字符的位置,然后把要替换的主字符串转换成StringBuffer类,再应用其replace(int i, int j, String str)方法将查找到的字符串用指定的字符串替换。 StringBuffer类创建之后当对其字符串进行操作,则在缓冲中直接操作,并改变了该对象的值。 4. 总结:该示例主要使用Panel的嵌套以及多种布局管理器综合应用来设置主界面,以及鼠标处理事件,核心在于字符串查找与替换两个算法设计。 JDK帮助文档包括了Java中所有类,在程序设计过程, 无须记住类的具体方法调用,只须知道有这么一个类,该类能实现什么功能,多去查看JDK帮助文档会给我们编程带来很大方便.