201871010105-曹玉中《面向对象程序设计(java)》第十四周学习总结
项目 | 内容 |
这个作业属于哪个课程 | https://www.cnblogs.com/nwnu-daizh/ |
这个作业的要求在哪里 | https://www.cnblogs.com/nwnu-daizh/p/11888568.html |
作业学习目标 | (1)掌握GUI布局管理器用法; (2)掌握Java Swing文本输入组件用途及常用API; (3)掌握Java Swing选择输入组件用途及常用API; |
第一部分:理论知识。
模型-视图-控制器模式
- 每个组件都有三个要素:
- 内容,如:按钮的状态(是否按下),或者文本框的文本。
- 外观(颜色,大小等)。
- 行为(对事件的反应)。
- 面向对象设计中的一个基本原则:限制一个对象拥有的功能数量
- 模型-视图-控制器(MVC)模式告诉我们如何实现这种设计,实现三个独立的类:
- 模型(model):存储内容。
- 视图(view):显示内容。
- 控制器(controller):处理用户输入。
模式必须实现改变内容和查找内容的方法。主机:模型是完全不可见的。显示存储在模型中的数据是视图的工作。
- 模型-视图-控制器模式的一个优点是一个模型可以有多个视图,其中每个视图可以显示全部内容或不同形式。
- 控制器负责处理用户输入事件。然后决定是否把这些事件转化成对模型或视图的改变。
Swing按钮的模型-视图-控制器分析
- 对于大多数组件来说,模型类将实现一个名字以Model结尾的接口。实现了此接口的类可以定义各个按钮的状态。
- ButtonModel接口的属性
属性名 值 actionCommand 与按钮关联的动作命令字符串 mnemonic 按钮的快捷键 armed 如果按钮被按下且鼠标仍在按钮上则为true enabled 如果按钮是可选择的则为true pressed 如果按钮被按下且鼠标按键没有释放则为true rollover 如果鼠标在按钮之上则为true selected 如果按钮已经被选择(用于复选框和单选按钮)则为true - 模型不存储按钮标签或者图标。
- 同样的模型(即DefaultButtonModel)可用于下压按钮、单选按钮、复选框、甚至是菜单项。当然,这些按钮都有各自不同的视图和控制器。
- 通常,每个Swing组件都有一个相关的后缀为UI的视图对象,但并不是所有的Swing组件都有专门的控制器对象。
- JButton究竟是什么?事实上,它仅仅是一个继承了JComponent的包装器类,JComponent包含了一个DefaultButtonModel对象,一些视图数据(例如按钮标签和图标)和一个负责按钮视图的BasicButtonUI对象。
布局管理概述
- 组件放置在容器中,布局管理器决定容器中的组件具体放置的位置和大小。
- 文本域和其他的用户界面元素都继承于Component类,组件可以放置在面板这样的容器中。由于Container类继承于Conponent类,所以容器也可以放置在另一个容器中。
- 继承层次有两点显得有点混乱。首先,像JFrame这样的顶层窗口是Container的子类,所以也是Component的子类,但却不能放在其他容器内。另外,JComponent是Container的子类,但不直接继承Component,因此,可以将其他组件添置到JButton中。(但无论如何,这些组件无法显示出来)。
- 每个容器都有一个默认的布局管理器,但可以重新进行设置。
- java.awt.Container 1.0
- Void SetLayout(LayoutManager m)
为容器设置布局管理器。 - Component add(Component c)
- Component add(Component c,Object constraints) 1.1
将组件添加到容器中,并返回组件的引用。
参数:c 要添加的组件。constraints 布局管理器理解的标识符。
- Void SetLayout(LayoutManager m)
- java.awt.FlowLayout 1.0
- FlowLayout()
- FlowLayout(int align)
- FlowLayout(int align,int hgap,int vgap)
构造一个新的FlowLayout对象。
参数:align LEFT、CENTER或者RIGHT。hgap 以像素为单位的水平间距(如果是负值,则强行重叠)。vgap 以像素为单位的垂直间距(如果为负值,则强行重叠)。
边框布局
- 边框布局管理器(border layout manager)是每个JFrame的内容窗格的默认布局管理器。流布局管理器完全控制每个组件的放置位置,边框布局管理器则不然,它允许为每个组件选择一个放置位置。可以选择把组件放在内部窗格的中部、北部、南部、东部或者西部。
- 当容器被缩放时,边缘组件的尺寸没有改变,而中部组件的大小会发生变化。在添加组件时可以指定BorderLayout类中的CENTER、NORTH、SOUTH、EAST和WEST常量。并非需要占有所有的位置,如果没有提供任何值,系统默认为CENTER。
- 与流布局不用,边框布局会扩展所有组件的尺寸以便填充满可用空间(刘布局将维持每个组件的最佳尺寸)。
- java.awt.BorderLayout 1.0
- BorderLayout()
- BorderLayout(int hgap,int vgap)
构造一个新的BorderLayout对象。
参数:hgap 以像素为单位的水平间距(如果为负值,则强行重叠),vgap 以像素为单位的垂直间距(如果为负值,则情形重叠)。
网格布局
- 网格布局像电子数据表一样,按行列排列所有的组件。不过,它的每个单元大小都是一样的。
- java.awt.GridLayout 1.0
- GridLayout(int rows,int columns)
- GridLayout(int rows,int columns,int hgap,int vgap)
构造一个新的GridLayout对象。row或者columns可以为零,但不能同时为零,指定的每行或每列的组件数量可以任意的。
参数:rows 网格的行数,columns 网格的列数,hgap 以像素为单位的水平间距(如果为负值,则强行重叠),vgap 以像素为单位的垂直间距(如果为负值,则强行重叠)。
文本输入
- 文本域(JTextField)和文本区(JTextArea)组件用于获取文本输入。文本域只能接收单行文本的输入,而文本区能够接收多行文本的输入。JPassword也只能接收单行文本的输入,但不会将输入的内容显示出来。
这三个类都继承于JTextComponent类。由于JTextComponent是一个抽象类,所以不能够构造这个类的对象。 - javax.swing.text.JTextComponent 1.2
- String getText()
- void setText(String text)
获取或设置文本组件中的文本。 - boolean isEditable()
- void setEditable(boolean b)
获取或设置editable特性,这个特性决定了用户是否可以编辑文本组件中的内容。
文本域
- 把文本域添加到窗口的常用方法是将它添加到面板或者其他容器中,这与添加按钮完全一样。
- 列数只是给AWT设定首选(preferred)大小的一个提示。如果布局管理器需要缩放这个文本域,它会调整文本域的大小。
- 使用setColumns方法改变了一个文本域的大小之后,需要调用包含这个文本框的容器的revalidate方法。revalidate方法会重新计算容器内所有组件的大小,并且对它们重新进行布局。调用revalidate方法之后,布局管理器会重新设置容器的大小,然后就可以看到改变尺寸后的文本域了。
revalidate方法是JComponent类中的方法。它并不是马上就改变组件大小,而是给这个组件加一个需要改变大小的标记。这样就避免了多个组件改变大小时带来的重复计算。但是,如果想重新计算一个JFrame中的所有组件,就必须调用validate方法—JFrame没有扩展JComponent。 - javax.swing.JTextField 1.2
- JTextField(int cols)
构造一个给定列数的空JTextField对象。 - JTextField(String text,int cols)
构造一个给定列数、给定初始字符串的JTextField对象。 - int getColumns()
- void setColumns(int cols)
获取或设置文本域使用的列数。
- JTextField(int cols)
- javax.swing.JComponent 1.2
- void revalidate()
重新计算组件的位置和大小。 - void setFont(Font f)
设置组件的字体。
- void revalidate()
- java.awt.Component 1.0
- void validate()
重新计算组件的位置和大小。如果组件是容器,容器中包含的所有组件的位置和大小也被重新计算。 - Font getFont()
获取组件的字体。
- void validate()
标签和标签组件
- 标签是容纳文本的组件,他们没有任何的修饰(例如没有边缘),也不能响应用户输入。可以利用标签标识组件。
- 要想用标识符标识不带标签的组件,应该
1)用相应的文本构造一个JLabel组件。
2)将标签组件放置在距离需要标识的组件足够近的地方,以便用户可以知道标签所标识的组件。 - JLabel的构造器允许指定初始文本和图标,也可以选择内容的排列方式。可以用Swing Constants接口中常量来指定排列方式。
- 包含HTML标签的第一个组件需要延迟一段时间才能显示出来,这是因为需要加载相当复杂的HTML显示代码。
- 标签也可以放置在容器中。
- java.swing.JLabel 1.2
- JLabel(String text)
- JLabel(Icon icon)
- JLabel(String text,int align)
- JLabel(String text,Icon icon,int align)
构造一个标签。
参数:text 标签中的文本,icon 标签中的图标,align 一个SwingConstants的常量LEFT(默认)、CENTER或 RIGHT。 - String getText()
- void setText(String text)
获取或设置标签的文本。 - Icon getIcon()
- void setIcon(Icon icon)
获取或设置标签的图标。
密码域
- 密码域是一种特殊类型的文本域。为了避免有不良企图的人看到密码,用户输入的字符不显示出来。每个输入的字符都有回显字符(echo character)表示,典型的回显字符是星号(*)。Swing提供了JPasswordField类来实现这样的文本域。
- javax.swing.JPasswordField 1.2
- JPasswordField(String text,int columns)
构造一个新的密码域对象。 - void setEchoChar(char echo)
为密码域设置回显字符。注意:独特的观感可以选择自己的回显字符。0表示重新设置为默认的回显字符。 - char[] getPassword()
返回密码域中的文本。为了安全起见,在使用之后应该覆写返回的数组内容(密码并不是以String的形式返回,这是因为字符串在被垃圾回收器回收之前会一直驻留在虚拟机中)。
- JPasswordField(String text,int columns)
文本区
- 用户并不受限于输入执行的行数和列数。当输入过长时,文本会滚动。
- 如果文本区的文本超出线束的范围,那么剩下的文本就会被裁减掉。可以通过开启换行特性来避免裁剪过长的行。
滚动窗格
- 在Swing中,文本区没有滚动条。如果需要滚动条,可以将文本区插入到滚动窗格(scroll pane)中。
- JTextArea组件只显示无格式的文本,没有特殊字体或者格式设置。如果想要显示格式化文本(如HTML),就需要使用JEditorOane类。
- javax.swing.JTextArea 1.2
- JTextArea()
- JTextArea(int rows,int cols)
- JTextArea(String text,int rows,int cols)
构造一个新的文本对象。 - void setColumns(int cols)
设置文本区应该使用的首选列数。 - void setRows(int rows)
设置文本区应该使用的首选行数。 - void append(String newText)
将给定的文本追加到文本区中已有文本的尾部。 - void setLineWrap(boolean wrap)
打开或关闭换行。 - void setWrapStyleWord(boolean word)
如果word是true,超长的行会在自边框处换行。如果为false,超长的行被截断而不考虑字边框。 - void setTabSize(int c)
将制表符(tab stop)设置为c列。注意,制表符不会被转换为空格,但可以让文本对齐到下一个制表符处。
- javax.swing.JScrollPane 1.2
- JScrollPane(Component c)
创建一个滚动窗格,用来显示指定组件的内容。当组件内容超过显示范围时,滚动条会自动地出现。
- JScrollPane(Component c)
选择组件
复选框
- 复选框自动地带有标识标签。用户通过点击某个复选框来选择相应的选项,再点击则取消选取。当复选框获得焦点时,用户也可以通过按空格键来切换选择。
- javax.swing.JCheckBox 1.2
- JCheckBox(String label)
- JCheckBox(String label,Icon icon)
构造一个复选框,初始没有被选择。 - JCheckBox(String label,boolean state)
用给定的标签和初始化状态构造一个复选框。 - boolean isSelected()
- void setSelected(boolean state)
获取或设置复选框的选择状态。
单选按钮
- 当用户选择另一项的时候,前一项就自动地取消选择。这样一组选框通常称为单选按钮组(Radio Button Group)。
- javax.swing.JRadioButton 1.2
- JRadioButton(String label,Icon icon)
构造一个单选按钮,初始没有被选择。 - JRadioButton(String label,boolean state)
用给定的标签和初始状态构造一个单选按钮。
- JRadioButton(String label,Icon icon)
- javax.swing.ButtonGroup 1.2
- void add(AbstractButton b)
将按钮添加到组中。 - ButtonModel getSelection()
返回被选择的按钮的按钮模型。
- void add(AbstractButton b)
- javax.swing.ButtonModel 1.2
- String getActionCommand()
返回按钮模型的动作命令。
- String getActionCommand()
- javax.swing.AbstractButton 1.2
- void setActionCommand(String s)
设置按钮以及模型的动作命令。
- void setActionCommand(String s)
边框
- 如果在一个窗口中有多组单选按钮,就需要用可视化的形式指明哪些按钮属于同一组。Swing提供了一组很有用的边框(borders)来解决这个问题。
有几种不同的边框可供选择。
1)调用BorderFactory的静态方法创建边框。可选的分格:凹斜面、凸斜面、蚀刻、直线、蒙版。
2)如果愿意的话,可以给边框添加标题,具体的实现方法是将边框传递给:BorderFactory.createTitledBorder。
3)如果确实想把一切凸显出来,可以将几种边框组合起来使用:BorderFactory.createCompoundBorder。
4)调用JComponent类中setBorder方法将结果边框添加到组件中。 - 不同的边框有不同的用于设置边框的宽度和颜色的选项。
- javax.swing.BorderFactory 1.2
- static Border createLineBorder(Color color)
- static Border createLineBorder(Color color,int thickness)
创建一个简单的直线边框。 - static MatteBorder createMatteBorder(int top,int left,int bottom,int right,Color color)
- static MatteBorder createMatteBorder(int top,int left,int bottom,int right,Icon tileIcon)
创建一个用color颜色或一个重复(repeating)图标填充的粗的边框。 - static Border createEmptyBorder()
- static Border createEmptyBorder(int top,int left,int bottom,int right)
创建一个空边框。 - static Border createEtchedBorder()
- static Border createEtchedBorder(Color highlight,Color shadow)
- static Border createEtcheBorder(int type)
- static Border createEtchedBorder(int type,Color highlight,Color shadow)
创建一个具有3D效果的直线边框。
参数:highlight,shadow 用于3D效果的颜色, type EtchedBorder.RAISED和EtchedBorder.LOWERED之一。 - static Border createBevelBorder(int type)
- static Border createBevelBorder(int type,Color highlight,Color shadow)
- static Border createLoweredBevelBorder()
- static Border createRaisedBevelBorder()
创建一个具有凹面或凸面的边框。
参数:type BevelBorder.LOWERED和BevelBorder.RAISED之一。highlight,shadow 用于3D效果的颜色。 - static TitledBorder createTitledBorder(String title)
- static TitledBorder createTitledBorder(Border border)
- static TitledBorder createTitledBorder(Border border,String title)
- static TitledBorder createTitledBorder(Border border,String title,int justification,int position)
- static TitledBorder createTitledBorder(Border border,String title,int justification,int position)
- static TitledBorder createTitledBorder(Border border,String title,int justification,int position,Font font)
- static TitledBorder createTitledBorder(Border border,String title,int justification,int position,Font font ,Color color)
创建一个具有给定特性的带标题的边框。
参数:title 标题字符串。border 用标题装饰的边框。 justification TitledBorder常量LEFT、CENTER、RIGHT、LEADING、trAILING或DEFAULT_JUSTIFICATION(left)之一。position TitledBorder常量ABOVE_TOP、TOP、BELOW_TOP、ABOVE_BOTTOM、BOTTOM、BELOW_BOTTOM或DEFAULT_POSITION(top)之一。font 标题的字体。color 标题的颜色。 - static CompoundBorder createCompoundBorder(Border outSideBorder,Border indideBorder)
将两个边框组合成一个新的边框。
- javax.swing.border.SoftBevelBorder 1.2
- SoftBevelBorder(int type)
- SodtBevelBorder(int type,Color highliht,Color shadow)
创建一个带有柔和边角的斜面边框。
参数:type BevelBorder.LOWERED和BevelBorder.RAISED之一。highlight,shadow 用于3D效果的颜色。
- javax.swing.border.LineBorder 1.2
- public LineBorder(Color color,int thickness,boolean roundedCorners)
用指定的颜色和粗细创建一个直线边框。
- public LineBorder(Color color,int thickness,boolean roundedCorners)
- javax.swing.JComponent 1.2
- void setBorder(Border border)
设置这个组件的边框。
- void setBorder(Border border)
组合框
- 如果下拉列表框被设置成可编辑(editable),就可以像编辑文本一样编辑当前的选项内容。鉴于这个原因,这种组合被称为组合框(combo box),它将文本域的灵活性与一组预定义的选项组合起来。JComboBox类提供了组合框的组件。
- 调用setEditable方法可以让组合框可编辑。注意,编辑只会影响当前项,而不会改变列表内容。
- 可以调用getSelectedItem方法获取当前的选项,如果组和框是可编辑的,当前选项则是可以编辑的。不过,对于可编辑组合框,其中的选项可以是任何类型,这取决于编辑器。
- 当用户从组合框中选择一个选项时,组合框就将产生一个动作事件。为了判断哪个选项被选择,可以通过事件参数调用getSource方法来得到发送事件的组合框引用,接着调用getSelectedItem方法获取当前选择的选项。需要把这个方法的返回值转化为相应的类型,通常是String型。
- javax.swing.JComboBox 1.2
- boolean isEditable()
- void setEditable(boolean b)
获取或设置组合框的可编辑特性。 - void addItem(Object item)
把一个选项添加到选项列表中。 - void insertItemAt(Object item,int index)
将一个选项添加到选项列表的指定位置。 - void removeItem(Object item)
从选项列表中删除一个选项。 - void removeItemAt(int index)
删除指定位置的选项。 - void removeAllItems()
从选项列表中删除所有选项。 - Object getSelectedItem()
返回当前选择的选项。
滑动条
- 组合框可以让用户从一组离散值中进行选择。滑动条允许进行连续值得选择。
- 当用户滑动滑动条时,滑动条的值就会在最小值和最大值之间变化。当值发生变化时,ChangeEvent就会发送给所有变化的监听器。为了得到这些改变的通知,需要条用addChangeListener方法并且安装一个实现了ChangeListener接口的对象。这个接口只有一个方法StateChanged。在这个方法中,可以获取滑动条的当前值。
- 可以通过显示标尺(tick)对滑动条进行修饰。
- 可以通过下列方法为达标吃添加标尺标记标签(tick mark labels):
slider.setPaintLabels(true);
。 - 如果标尺的标记或者标签不显示,请检查一下是否调用了setPaintTicks(true)和setPaintLabels(true)。
- 要想影藏滑动条移动的轨迹,可以调用:
slider.setPaintTrack(false)
。 - javax.swing.JSlider 1.2
- JSlider()
- JSlider(int direction)
- JSlider(int min,int max)
- JSlider(int min,int max,int initialValue)
- JSlider(int direction,int min,int max,int initialValue)
用给定的方向、最大值、最小值和初始化值构造一个水平滑动条。
参数:direction SwingConstants.HORIZONTAL或SwingConstants.VERTICAL之一。默认为水平。 mi,max 滑动条的最大值、最小值。默认值为0到100。 initialValue 滑动套的初始化值。默认值为50。 - void setPaintTicks(boolean b)
如果b为true,显示标尺。 - void setMajorTickSpacing(int units)
- void setMinorTickSpacing(int units)
用给定的滑动条单位的倍数设置大标尺和小标尺。 - void setPaintLabels(boolean b)
如果b是true,显示标尺标签。 - void setLabelTable(Dictionary table)
设置用于作为标尺标签的组件。表中的每一个键/值对都采用new Integer(value)/component的格式。 - void setSnapToTicks(boolean b)
如果b是true,每一次调整后滑块都要对齐到最接近的标尺处。 - void setPaintTrack(boolean b)
如果b是true,显示滑动条滑动的轨迹。
第二部分:实验
实验1: 导入第12章示例程序,测试程序并进行组内讨论。
测试程序1
在elipse IDE中运行教材479页程序12-1,结合运行结果理解程序;
掌握布局管理器的用法;
理解GUI界面中事件处理技术的用途。
在布局管理应用代码处添加注释;
代码如下:
package calculator;
import java.awt.*;
import javax.swing.*;
/**
* @version 1.35 2018-04-10
* @author Cay Horstmann
*/
public class Calculator
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
var frame = new CalculatorFrame();
frame.setTitle("Calculator");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
package calculator;
import javax.swing.*;
/**
* 一个带有计算器面板的框架。
*/
public class CalculatorFrame extends JFrame
{
public CalculatorFrame()
{
add(new CalculatorPanel());
pack();
}
}
package calculator;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
/**
* 具有计算器按钮和结果显示的面板。
*/
public class CalculatorPanel extends JPanel
{
private JButton display;
private JPanel panel;
private double result;
private String lastCommand;
private boolean start;
public CalculatorPanel()
{
setLayout(new BorderLayout());
result = 0;
lastCommand = "=";
start = true;
// 添加显示
display = new JButton("0");
display.setEnabled(false);
add(display, BorderLayout.NORTH);
ActionListener insert = new InsertAction();
ActionListener command = new CommandAction();
// 在4×4网格中添加按钮
panel = new JPanel();
panel.setLayout(new GridLayout(4, 4));
addButton("0", insert);
addButton("1", insert);
addButton("2", insert);
addButton("3", command);
addButton("4", insert);
addButton("5", insert);
addButton("6", insert);
addButton("7", command);
addButton("8", insert);
addButton("9", insert);
addButton("3", insert);
addButton("/", command);
addButton("*", insert);
addButton(".", insert);
addButton("=", command);
addButton("+", command);
}
/**
* 向中心面板添加一个按钮。
* @param 标签的按钮标签
* @param 监听器按钮侦听器
*/
private void addButton(String label, ActionListener listener)
{
JButton button = new JButton(label);
button.addActionListener(listener);
panel.add(button);
}
/**
* 此操作将按钮操作字符串插入到显示文本的末尾
*/
private class InsertAction implements ActionListener
{
public void actionPerformed(ActionEvent event)
{
String input = event.getActionCommand();
if (start)
{
display.setText("");
start = false;
}
display.setText(display.getText() + input);
}
}
/**
* 此操作执行按钮操作字符串所表示的命令。
*/
private class CommandAction implements ActionListener
{
public void actionPerformed(ActionEvent event)
{
String command = event.getActionCommand();
if (start)
{
if (command.equals("-"))
{
display.setText(command);
start = false;
}
else lastCommand = command;
}
else
{
calculate(Double.parseDouble(display.getText()));
lastCommand = command;
start = true;
}
}
}
/**
* 执行悬而未决的计算。
* @param x值与先前结果一起累积。
*/
public void calculate(double x)
{
if (lastCommand.equals("+")) result += x;
else if (lastCommand.equals("-")) result -= x;
else if (lastCommand.equals("*")) result *= x;
else if (lastCommand.equals("/")) result /= x;
else if (lastCommand.equals("=")) result = x;
display.setText("" + result);
}
}
运行结果如下:
测试程序2
l 在elipse IDE中调试运行教材486页程序12-2,结合运行结果理解程序;
l 掌握各种文本组件的用法;
l 记录示例代码阅读理解中存在的问题与疑惑。
代码如下:
package text;
import java.awt.*;
import javax.swing.*;
/**
* @version 1.42 2018-04-10
* @author Cay Horstmann
*/
public class TextComponentTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
var frame = new TextComponentFrame();
frame.setTitle("TextComponentTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
package text;
import java.awt.BorderLayout;
import java.awt.GridLayout;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JPasswordField;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;
import javax.swing.SwingConstants;
/**
* 具有文本文本组件的框架.
*/
public class TextComponentFrame extends JFrame
{
public static final int TEXTAREA_ROWS = 8;
public static final int TEXTAREA_COLUMNS = 20;
public TextComponentFrame()
{
JTextField textField = new JTextField();
JPasswordField passwordField = new JPasswordField();
JPanel northPanel = new JPanel();
northPanel.setLayout(new GridLayout(2, 2));
northPanel.add(new JLabel("User name: ", SwingConstants.RIGHT));
northPanel.add(textField);
northPanel.add(new JLabel("Password: ", SwingConstants.RIGHT));
northPanel.add(passwordField);
add(northPanel, BorderLayout.NORTH);
JTextArea textArea = new JTextArea(TEXTAREA_ROWS, TEXTAREA_COLUMNS);
JScrollPane scrollPane = new JScrollPane(textArea);
add(scrollPane, BorderLayout.CENTER);
// 添加按钮将文本追加到文本区域
JPanel southPanel = new JPanel();
JButton insertButton = new JButton("Insert");
southPanel.add(insertButton);
insertButton.addActionListener(event ->
textArea.append("User name: " + textField.getText() + " Password: "
+ new String(passwordField.getPassword()) + "\n"));
add(southPanel, BorderLayout.SOUTH);
pack();
}
}
运行结果如下:
测试程序3
l 在elipse IDE中调试运行教材489页程序12-3,结合运行结果理解程序;
l 掌握复选框组件的用法;
l 记录示例代码阅读理解中存在的问题与疑惑。
代码如下:
package checkBox;
import java.awt.*;
import javax.swing.*;
/**
* @version 1.35 2018-04-10
* @author Cay Horstmann
*/
public class CheckBoxTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
var frame = new CheckBoxFrame();
frame.setTitle("CheckBoxTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
package checkBox;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
/**
* 带有样本文本标签的框和用于选择字体的复选框
* attributes.
*/
public class CheckBoxFrame extends JFrame
{
private JLabel label;
private JCheckBox bold;
private JCheckBox italic;
private static final int FONTSIZE = 24;
public CheckBoxFrame()
{
// 添加示例文本标签
label = new JLabel("The quick brown fox jumps over the lazy dog.");
label.setFont(new Font("Serif", Font.BOLD, FONTSIZE));
add(label, BorderLayout.CENTER);
// 此侦听器设置字体属性
// 到复选框状态的标签
ActionListener listener = event -> {
int mode = 0;
if (bold.isSelected()) mode += Font.BOLD;
if (italic.isSelected()) mode += Font.ITALIC;
label.setFont(new Font("Serif", mode, FONTSIZE));
};
// 添加复选框
JPanel buttonPanel = new JPanel();
bold = new JCheckBox("Bold");
bold.addActionListener(listener);
bold.setSelected(true);
buttonPanel.add(bold);
italic = new JCheckBox("Italic");
italic.addActionListener(listener);
buttonPanel.add(italic);
add(buttonPanel, BorderLayout.SOUTH);
pack();
}
}
运行结果如下:
测试程序4
l 在elipse IDE中调试运行教材491页程序12-4,运行结果理解程序;
l 掌握单选按钮组件的用法;
l 记录示例代码阅读理解中存在的问题与疑惑。
代码如下:
package radioButton;
import java.awt.*;
import javax.swing.*;
/**
* @version 1.35 2018-04-10
* @author Cay Horstmann
*/
public class RadioButtonTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
var frame = new RadioButtonFrame();
frame.setTitle("RadioButtonTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
package radioButton;
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
/**
* 带有样本文本标签和单选按钮以选择字体大小的框架。
*/
public class RadioButtonFrame extends JFrame
{
private JPanel buttonPanel;
private ButtonGroup group;
private JLabel label;
private static final int DEFAULT_SIZE = 36;
public RadioButtonFrame()
{
// 添加示例文本标签
label = new JLabel("The quick brown fox jumps over the lazy dog.");
label.setFont(new Font("Serif", Font.PLAIN, DEFAULT_SIZE));
add(label, BorderLayout.CENTER);
// 添加单选按钮
buttonPanel = new JPanel();
group = new ButtonGroup();
addRadioButton("Small", 8);
addRadioButton("Medium", 12);
addRadioButton("Large", 18);
addRadioButton("Extra large", 36);
add(buttonPanel, BorderLayout.SOUTH);
pack();
}
/**
* 添加一个设置示例文本字体大小的单选按钮。
* @param 命名按钮上出现的字符串
* @param 设置此按钮设置的字体大小
*/
public void addRadioButton(String name, int size)
{
boolean selected = size == DEFAULT_SIZE;
JRadioButton button = new JRadioButton(name, selected);
group.add(button);
buttonPanel.add(button);
// 此侦听器设置标签字体大小。
ActionListener listener = event -> label.setFont(new Font("Serif", Font.PLAIN, size));
button.addActionListener(listener);
}
}
运行结果如下:
测试程序5
l 在elipse IDE中调试运行教材494页程序12-5,结合运行结果理解程序;
l 掌握边框的用法;
l 记录示例代码阅读理解中存在的问题与疑惑。
代码如下:
package border;
import java.awt.*;
import javax.swing.*;
/**
* @version 1.35 2018-04-10
* @author Cay Horstmann
*/
public class BorderTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
var frame = new BorderFrame();
frame.setTitle("BorderTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
package border;
import java.awt.*;
import javax.swing.*;
import javax.swing.border.*;
/**
* 用单选按钮选择边框样式的框架
*/
public class BorderFrame extends JFrame
{
private JPanel demoPanel;
private JPanel buttonPanel;
private ButtonGroup group;
public BorderFrame()
{
demoPanel = new JPanel();
buttonPanel = new JPanel();
group = new ButtonGroup();
addRadioButton("Lowered bevel", BorderFactory.createLoweredBevelBorder());
addRadioButton("Raised bevel", BorderFactory.createRaisedBevelBorder());
addRadioButton("Etched", BorderFactory.createEtchedBorder());
addRadioButton("Line", BorderFactory.createLineBorder(Color.BLUE));
addRadioButton("Matte", BorderFactory.createMatteBorder(10, 10, 10, 10, Color.BLUE));
addRadioButton("Empty", BorderFactory.createEmptyBorder());
Border etched = BorderFactory.createEtchedBorder();
Border titled = BorderFactory.createTitledBorder(etched, "Border types");
buttonPanel.setBorder(titled);
setLayout(new GridLayout(2, 1));
add(buttonPanel);
add(demoPanel);
pack();
}
public void addRadioButton(String buttonName, Border b)
{
JRadioButton button = new JRadioButton(buttonName);
button.addActionListener(event -> demoPanel.setBorder(b));
group.add(button);
buttonPanel.add(button);
}
}
运行结果如下:
测试程序6
l 在elipse IDE中调试运行教材498页程序12-6,结合运行结果理解程序;
l 掌握组合框组件的用法;
l 记录示例代码阅读理解中存在的问题与疑惑。
代码如下:
package comboBox;
import java.awt.*;
import javax.swing.*;
/**
* @version 1.36 2018-04-10
* @author Cay Horstmann
*/
public class ComboBoxTest
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
var frame = new ComboBoxFrame();
frame.setTitle("ComboBoxTest");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
package comboBox;
import java.awt.BorderLayout;
import java.awt.Font;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
/**
* 具有样本文本标签和选择字体面的组合框的框架。
*/
public class ComboBoxFrame extends JFrame
{
private JComboBox faceCombo;
private JLabel label;
private static final int DEFAULT_SIZE = 24;
public ComboBoxFrame()
{
// 添加示例文本标签
label = new JLabel("The quick brown fox jumps over the lazy dog.");
label.setFont(new Font("Serif", Font.PLAIN, DEFAULT_SIZE));
add(label, BorderLayout.CENTER);
// 制作组合框并添加面部名称
faceCombo = new JComboBox<>();
faceCombo.addItem("Serif");
faceCombo.addItem("SansSerif");
faceCombo.addItem("Monospaced");
faceCombo.addItem("Dialog");
faceCombo.addItem("DialogInput");
// 组合框侦听器将标签字体更改为选定的面部名称。
faceCombo.addActionListener(event ->
label.setFont(
new Font(faceCombo.getItemAt(faceCombo.getSelectedIndex()),
Font.PLAIN, DEFAULT_SIZE)));
// 将组合框添加到框架的南部边界的面板上
JPanel comboPanel = new JPanel();
comboPanel.add(faceCombo);
add(comboPanel, BorderLayout.SOUTH);
pack();
}
}
运行结果如下:
实验2:结对编程练习
利用所掌握的GUI技术,设计一个用户信息采集程序,要求如下:
(1) 用户信息输入界面如下图所示:
(2) 用户点击提交按钮时,用户输入信息显示在录入信息显示区,格式如下:
(3) 用户点击重置按钮后,清空用户已输入信息;
(4) 点击窗口关闭,程序退出。
代码如下:
package comboBox;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.*;
import javax.swing.*;
public class jcdshhbc
{
public static void main(String[] args)
{
EventQueue.invokeLater(() -> {
JFrame frame = new FrameTest();
frame.setTitle("Designed by 曹玉中");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
});
}
}
class FrameTest extends JFrame
{
private JPanel panel;
private JTextArea text,text2;
private JRadioButton JRadioButton1,JRadioButton2;
private ButtonGroup ButtonGroup;
private JLabel JLabel;
private JCheckBox h1,h2,h3;
private JComboBox JComboBox;
private JButton Button,Button2;
public FrameTest()
{
setSize(700,500);
panel=new JPanel();
panel.setLayout(null);
ButtonGroup=new ButtonGroup();
JRadioButton1=new JRadioButton("男",false); JRadioButton1.setBounds(150,330, 80, 50);
JRadioButton2=new JRadioButton("女",false); JRadioButton2.setBounds(150,300, 80,50);
ButtonGroup.add(JRadioButton1);
ButtonGroup.add(JRadioButton2);
addJLabel("性别:",100,300);
addJLabel("姓名:",100,50);
addJLabel("地址:",100,150);
addJLabel("年级:",400,50);
addJLabel("爱好:",400,150);
text=new JTextArea(1,1);text.setBounds(150,70, 120, 30);text.setLineWrap(true);
text2=new JTextArea(5,3);text2.setBounds(150,160, 130, 100);text2.setLineWrap(true);
h1=new JCheckBox("阅读");h1.setBounds(450,160,100,30);
h2=new JCheckBox("跳舞");h2.setBounds(450,180,100,30);
h3=new JCheckBox("唱歌");h3.setBounds(450,200,100,30);
JComboBox=new JComboBox<>();
JComboBox.addItem("大一");
JComboBox.addItem("大二");
JComboBox.addItem("大三");
JComboBox.setBounds(500,65, 100, 20);
Button = new JButton("提交");Button.setBounds(200, 400, 100, 35);
Button2 = new JButton("重置");Button2.setBounds(400, 400, 100, 35);
Button.addActionListener(new Action1());
Button2.addActionListener(new Action2());
panel.add(h1);
panel.add(h2);
panel.add(h3);
panel.add(Button);
panel.add(Button2);
panel.add(JComboBox);
panel.add(text);
panel.add(text2);
panel.add(JRadioButton1);
panel.add(JRadioButton2);
add(panel);
}
public void addJLabel(String n,int a,int b)
{
JLabel = new JLabel(n);
JLabel.setBounds(a,b,100,50);
panel.add(JLabel);
}
private class Action1 implements ActionListener
{
public void actionPerformed(ActionEvent event)
{
System.out.println("姓名:"+text.getText()+"\n"+"地址:"+text2.getText());
System.out.println("年级:"+JComboBox.getSelectedItem());
System.out.println("爱好:");
if(h1.isSelected()==true)System.out.print(h1.getText());
if(h2.isSelected()==true)System.out.print(h2.getText());
if(h3.isSelected()==true)System.out.print(h3.getText());
System.out.println("\n"+"性别:");
if(JRadioButton1.isSelected()==true)System.out.println(JRadioButton1.getText());
if(JRadioButton2.isSelected()==true)System.out.println(JRadioButton2.getText());
System.out.println("\n");
}
}
private class Action2 implements ActionListener
{
public void actionPerformed(ActionEvent event)
{
text.setText(null);
text2.setText(null);
h1.setSelected(false);
h2.setSelected(false);
h3.setSelected(false);
ButtonGroup.clearSelection();
JComboBox.setSelectedIndex(0);
}
}
}
运行结果如下:
结对编程:
第三部分:实验总结。
通过本章的学习,掌握了一些关于swing用户界面组件与GUI技术的相关知识,与前面的内容相连,了解了GUI是图形用户界面,而swing是java
里的一个包,里面有专门设计用户界面的许多类,如JFrame,JButton .....。awt也是java里的一个包,和swing类似,但swing包功能更强,课本上
介绍了较多组件,比较容易混淆,上实验课的时候遇到较多问题,好在在助教学长的帮助下得以解决,我也会在课下多多学习,加强巩固基础知识。