第 10章 综合实例
综合实例 1:计算器本节通过一个计算器的设计来综合运用所学的相关知识,达到巩固知识的目的 。
程序功能一个简单的计数器程序 。 用户可以利用鼠标单击数值或操作符按钮完成计算,
计算的结果被显示在窗口上部的文本框中 。
知识点
1,AWT包;
2,Java的数据类型;
3.用户自定义类;
4.窗体的布局;
5.窗口的字体设置。
设计步骤
1.创建一个空的窗口;
2.定义用于显示结果的文本显示类;
3.完成窗口的布局;
4.为窗口添加事件处理。
基础知识同 Java的其他功能一样,窗口的实现同样需要类库中类的支持,Java中的 AWT
包,就包含了实现窗口应用程序的各种元素以及事件的处理。
下面我们介绍一下 AWT包以及有关变量数据类型的基础知识。
1,AWT
AWT( Abstract Window Toolkit) 即抽象窗口工具集,作为 Java中的一个包,
它提供了各种用于 GUI( 图形用户界面)
设计的标准构件。每个构件都有自己特定的用法,如按钮、列表框等,这些构件都是通过继承 AWT中的 Component类来实现的。总体上来讲,AWT中的构件分为两大类:基础构件和容器。
( 1)基础构件基础构件是构成图形用户界面的基础元素。通过这些构件,我们可以向 Java应用程序发出自己的控制命令,向程序输入各种数据,甚至可以在这些构件基础上生成符合我们特殊需要的自定义构件等。这些基础构件包括:
Button,按钮,用于完成一个命令。
CheckBoxGroup,复选框,用于同时进行多个选择。
CheckBox,单选框,用于在一组中选取一项。
Choice,组合框,用于创建一个弹出式的选择菜单。
List,列表框,用于创建一个选择列表。
Menu,菜单,用于创建菜单系统。
TextField,文本框,用于输入单行文本。
TextArea,多行文本框,用于输入多行文本。
Canvas,画布,用于进行绘图。
ScrollBar,滚动条,用于在指定范围内选择一个值来浏览窗口。
( 2)容器容器是一类特殊的构件,它是用来包含其他构件的,构件必须放在容器中才能构成界面。用户可以把构件放在容器中,
也可以把容器放在另一个容器中。
AWT中提供了 4个容器类,对它们分别介绍如下。
Window类:最高级别地显示窗口。
它的实例不能附加或嵌入另一个容器中,
它的实例是没有边框和标题的。
Frame类:具有边框和标题的最高级别显示窗口。可以添加菜单。
Dialog类:具有边框和标题的最高级别显示窗口。 Dialog类的实例只有在一个相关的 Frame类的实例存在时才能存在。
Panel类:容纳构件的通用容器。
当然将构件放入容器中是需要一定的布局方式的,这种布局方式是由布局管理器来确定的。每一个容器都有自己的一个布局管理器。
为了让大家能够更好地完成计算器这个程序,下面我们介绍一下 Java中有关数据类型的知识。
2,Java的数据类型概括地说,Java中存在两大数据类型:
简单数据类型和复杂数据类型。简单数据类型又可以分为数值类型、布尔类型、字符类型等。其中简单数据类型可以直接被编译器所理解,而不需要借助于特殊的库来定义。复杂数据类型主要有两种:数组类型和字符串类型。它的情况则刚好相反,
需要一个特殊的库来为这些数据类型作出定义,以便编译器编译时调用。
编程思路在这个计算器程序中,我们用到了
AWT中的按钮构件,Canvas构件,Frame
和 Panel容器 。 同时,我们还使用了一个
Label对象用于显示一些标识性文字 。 其中
Canvas构件主要用于显示计算的结果以及用户的输入,为了使用的方便,Canvas构件进行了继承,生成了一个新的文本显示区域,可以直接进行数字的显示 。
下面,让我们看一下具体的实施步骤 。
操作步骤步骤 1,创 建 一 个 新 的 应 用 程 序
AwtCalcJava,首先创建一个空的窗口 。
package Calc;
import java.awt.* ;
import java.awt.event.* ;
import java.awt.Graphics ;
public class AwtCalc extends Frame
implements ActionListener
{
public AwtCalc(){
super("计算器 ");
setBackground(Color.lightGray);
resize(235,210);
show();
}
public void actionPerformed(ActionEvent e)
{
}
public void paint(Graphics g)
{
g.drawRect(0,0,size().width-
1,size().height-1);
g.drawLine(0,0,0,size().height);
}
public static void main(String args[])
{
AwtCalc ca=new AwtCalc();
}
}
这里的几个方法都是一个窗口程序所必须要有的。
在构造函数 AwtCalc()中,super()是用来调用父类 Frame的构造函数,它的参数
“计算器”作为窗口的标题来显示。另外我们也可以调用 Frame类的 setTitle(String)
函数来设置窗口的标题。
SetBackground() 方法是从
java.awt.Component类继承而来的,用于设置窗口的背景色,resize(235,210)将窗口的大小设置为宽 235个像素,高 210个像素 。 最后调用 show()方法显示窗口 。
Paint()方法用一个 Graphics对象作为参数,根据当前窗口的状态画出了该窗口 。
窗口被打开,改变大小或交换至前台显示的时候,就会自动调用 Paint()方法 。
ActionPerformed()方法用于对窗口应用程序进行事件处理,目前窗口上没有任何构件,所以事件处理也为空。
最后,在 Main()函数中,只要将我们创建的 AwtCalc类进行实例化就可以运行窗口程序了。
步骤 2:我们定义用于显示结果的文本显示类,用来继承 Canvas 构件 。
package Calc;
import java.awt.*;
public class ETextField extends Canvas {
String message="";
Boolean firstTime=true;
Int x;
public ETextField(int width,int height)
{
setSize(width,height);
}
public void setText(String text)
{
firstTime=false;
message=text;
x+=3;
repaint();
}
public void paint (Graphics g)
{
g.drawRect(0,0,size().width-
1,size().height-1);
g.drawString(message,3,13);
}
}
我们可以利用 setText()方法来设置需要显示的字符串。程序将调用
paint()方法来将文本显示在屏幕上。
步骤 3:在窗口上添加需要的构件,用来完成窗口的布局 。
首先,添加必要的变量定义:
private Button[] buttons = new
Button[19];
private String[] buttonText = { " 1
"," 2 "," 3 "," + "," - ",
" 4 "," 5 "," 6 "," x
"," / ",
" 7 "," 8 "," 9 ","^
","sqrt",
" C "," 0 ",",","
= "};
private ETextField result; // 结果显示框
private String input = ""; // 用户的输入
private Label label;
private Color forecolor,// 前景色
backcolor,// 背景色
fieldcolor; // 显示框颜色
private Font font,
buttonfont;
然后在构造函数中添加如下代码,将构件添加到窗口上。
buttonfont = new Font( "Courier",
Font.PLAIN,12 );
setBackground( Color.lightGray );
result = new ETextField( 125,18 );
font = new Font( "宋体 ",Font.ITALIC,
10 );
label = new Label( "结果 " );
label.setFont( font );
result.setBackground( Color.white );
setLayout( new FlowLayout() );
//初始化按钮
Panel mainPanel=new Panel();
mainPanel.setLayout(new
GridLayout(5,1));
for ( int i = 0; i < 19; i++ ) {
buttons[i] = new
Button( buttonText[i] );
buttons[i].setFont( buttonfont );
buttons[i].addActionListener( this );
}
Panel panel1=new Panel();
panel1.add( result );
panel1.add( label );
mainPanel.add(panel1);
Panel panel2=new Panel();
panel2.add(buttons[0]);
panel2.add(buttons[1]);
panel2.add(buttons[2]);
panel2.add(new Label( " " ));
panel2.add(buttons[3]);
panel2.add(buttons[4]);
mainPanel.add(panel2);
Panel panel3=new Panel();
panel3.add(buttons[5]);
panel3.add(buttons[6]);
panel3.add(buttons[7]);
panel3.add(new Label( " " ));
panel3.add(buttons[8]);
panel3.add(buttons[9]);
mainPanel.add(panel3);
Panel panel4=new Panel();
panel4.add(buttons[10]);
panel4.add(buttons[11]);
panel4.add(buttons[12]);
panel4.add(new Label( " " ));
panel4.add(buttons[13]);
panel4.add(buttons[14]);
mainPanel.add(panel4);
Panel panel5=new Panel();
panel5.add(buttons[15]);
panel5.add(buttons[16]);
panel5.add(buttons[17]);
panel5.add(new Label( " " ));
panel5.add(buttons[18]);
mainPanel.add(panel5);
add("Center",mainPanel);
buttons[15].setForeground( Color.red );
步骤 4:添加事件的处理部分 。
package test;
import java.awt.*;
import java.awt.event.*;
import java.awt.Graphics;
public class AwtCalc extends Frame
implements ActionListener
{
private Button[] buttons = new
Button[19];
private String[] buttonText = { " 1 ",
" 2 "," 3 "," + "," - ",
" 4 "," 5 "," 6 "," x "," / ",
" 7 "," 8 "," 9 ","^ ","sqrt",
" C "," 0 ",","," = "};
private ETextField result; // 结果显示框
private String input = ""; // 用户的输入
private Label label;
private Color forecolor,// 前景色
backcolor,// 背景色
fieldcolor; // 显示框颜色
private Font font,
buttonfont;
private int oper = 0,
// 记录运算过程中的运算符
oldoper = 0,
newoper = 0;
private double answer,
num1 = 0.0,
num2 = 0.0,
num3 = 0.0;
private final int ADD=1,
// 用于记录运算符的常量
SUB = 2,
MULT = 3,
DIVI = 4,
POW = 5,
SQRT = 6;
private boolean firstpress = true,//是否按下第一个按键
morenums = false,
//是否多个数值被输入
equals = false,
//等于是否已经被按下
clearscreen = false,
//是否清屏
decnumber = false,
//是否输入一个浮点数
doubleclick = false;
//是否双击
public AwtCalc(){
super("计算器 ");
//初始化颜色
buttonfont = new Font( "Courier",
Font.PLAIN,12 );
setBackground( Color.lightGray );
result = new ETextField( 125,18 );
font = new Font( "宋体 ",Font.ITALIC,
10 );
label = new Label( "结果 " );
label.setFont( font );
result.setBackground( Color.white );
setLayout( new FlowLayout() );
//初始化按钮
Panel mainPanel=new Panel();
mainPanel.setLayout(new
GridLayout(5,1));
for ( int i = 0; i < 19; i++ ) {
buttons[i] = new
Button( buttonText[i] );
buttons[i].setFont( buttonfont );
buttons[i].addActionListener( this );
}
Panel panel1=new Panel();
panel1.add( result );
panel1.add( label );
mainPanel.add(panel1);
Panel panel2=new Panel();
panel2.add(buttons[0]);
panel2.add(buttons[1]);
panel2.add(buttons[2]);
panel2.add(new Label( " " ));
panel2.add(buttons[3]);
panel2.add(buttons[4]);
mainPanel.add(panel2);
Panel panel3=new Panel();
panel3.add(buttons[5]);
panel3.add(buttons[6]);
panel3.add(buttons[7]);
panel3.add(new Label( " " ));
panel3.add(buttons[8]);
panel3.add(buttons[9]);
mainPanel.add(panel3);
Panel panel4=new Panel();
panel4.add(buttons[10]);
panel4.add(buttons[11]);
panel4.add(buttons[12]);
panel4.add(new Label( " " ));
panel4.add(buttons[13]);
panel4.add(buttons[14]);
mainPanel.add(panel4);
Panel panel5=new Panel();
panel5.add(buttons[15]);
panel5.add(buttons[16]);
panel5.add(buttons[17]);
panel5.add(new Label( " " ));
panel5.add(buttons[18]);
mainPanel.add(panel5);
add("Center",mainPanel);
buttons[15].setForeground( Color.red );
resize(235,210);
show();
}
//===============================
================================
================================
=========
// 处理按钮被按下时的动作,进行相应的处理
//===============================
================================
================================
========
public void actionPerformed( ActionEvent
e )
{
// 判断是否按下一个运算符键
if ( e.getSource() != buttons[3] &&
e.getSource() != buttons[4]
&& e.getSource() != buttons[8] &&
e.getSource() != buttons[9]
&& e.getSource() != buttons[13] &&
e.getSource() != buttons[14]
&& e.getSource() != buttons[15] &&
e.getSource() != buttons[18] ) {
//按下一个数字键
if ( clearscreen ) {
// 在完成一次运算后再次按下运算符之前清屏
clearScreen();
clearscreen = false;
}
if ( e.getSource() == buttons[0] ) {
input += "1"; // 输入为 "1"
result.setText( input );
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[1] ) {
input += "2"; // 输入为 "2"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[2] ) {
input += "3"; // 输入为 "3"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[5] ) {
input += "4"; // 输入为 "4"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[6] ) {
input += "5";
// 输入为 "5"
showAnswer( input );
} // end if
else if ( e.getSource() == buttons[7] ) {
input += "6";
// 输入为 "6"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[10] ) {
input += "7";
// 输入为 "7"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[11] ) {
input += "8";
// 输入为 "8"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[12] ) {
input += "9";
// 输入为 "9"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[16] ) {
input += "0";
// 输入为 "0"
showAnswer( input );
} // end else if
else if ( e.getSource() == buttons[17] ) {
if ( decnumber == false ) {
//设置输入为浮点数
decnumber = true;
input += ".0";
// 输入为小数点
showAnswer( input );
}
}
} // end if
// 检查是否按下加法按钮
if ( e.getSource() == buttons[3] ) {
clearscreen = false;
decnumber = false;
oper = ADD;
// 将运算符设置为加
clickCheck( input );
// 检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
// 如果没有双击,继续处理
input = "";
// 记录输入值的变量清空
} // end if
// 检查是否按下减法按钮
else if (e.getSource() == buttons[4] ) {
clearscreen = false;
decnumber = false;
oper = SUB;
// 将运算符设置为减
clickCheck( input );
// 检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
// 如果没有双击,继续处理
input = "";
// 记录输入值的变量清空
} // end else if
// 检查是否按下乘法按钮
else if (e.getSource() == buttons[8] ) {
clearscreen = false;
decnumber = false;
oper = MULT;
// 将运算符设置为乘法
clickCheck( input );
// 检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
// 如果没有双击,继续处理
input = "";
// 记录输入值的变量清空
} //end else if
// 检查是否按下除法按钮
else if (e.getSource() == buttons[9] ) {
clearscreen = false;
decnumber = false;
oper = DIVI;
// 将运算符设置为除法
clickCheck( input );
// 检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
// 如果没有双击,继续处理
input = "";
// 记录输入值的变量清空
} // end else if
// 检查是否按下幂运算按钮
else if ( e.getSource() == buttons[13] ) {
clearscreen = false;
decnumber = false;
oper = POW;
// 将运算符设置为幂
clickCheck( input );
// 检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
// 如果没有双击,继续处理
input = "";
// 记录输入值的变量清空
} // end else if
// 检查是否按下开方运算按钮
else if ( e.getSource() == buttons[14] ) {
clearscreen = false;
oper = SQRT;
// 将运算符设置为开方
clickCheck( input );
// 检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
// 如果没有双击,继续处理
input = "";
// 记录输入值的变量清空
} // end else if
// 检查是否按下清零按钮
if (e.getSource() == buttons[15] ) {
clearScreen();
} // end if
// 检查是否按下等于按钮
if (e.getSource() == buttons[18] ) {
equals = true;
clearscreen = true;
clickCheck( input );
//检查是否为双击运算符
if ( doubleclick == false )
processNumbers();
//如果没有双击,继续处理
input = Double.toString( answer );
} // end if
} // end actionPerformed()
//===============================
================================
================================
===============
//该方法处理用户的这种输入
//===============================
================================
================================
==============
public void processNumbers() {
// 判断运算符是否被第一次按下
if ( firstpress ) {
if ( equals ) {
num1 = answer; //结果被保存
equals = false; //等待另外的输入
} // end if
else
num1 =
Double.valueOf( input ).doubleValue();
oldoper = oper;
// 将当前运算符保存
// 如果进行开方运算
if ( oper == SQRT ) {
answer = calculate( oldoper,num1,0.0 );
showAnswer( Double.toString( answer ) );
morenums = true;
}
firstpress = false;
} // end if
else if ( !morenums ) {
num2 =
Double.valueOf( input ).doubleValue();
answer = calculate( oldoper,num1,
num2 );
showAnswer( Double.toString( answer) );
newoper = oper;
if ( !equals )
morenums = true;
//标识已经有至少两个数值被输入
else {
morenums = false;
//如果等号被按下,firstpress将被置为 true
firstpress = true;
} // end else
} // end if
else if (morenums) {
//输入多个数值
if ( equals ) {
newoper = oper;
morenums = false;
firstpress = true;
} // end if
num3 =
Double.valueOf( input ).doubleValue();
answer = calculate( newoper,answer,
num3 );
showAnswer( Double.toString(answer) );
newoper = oper;
} // end else if
} // end processNumbers()
//===============================
================================
================================
=======
//该方法用于根据输入的数值或运算符进行计算
//===============================
================================
================================
=======
public double calculate( int oper,double
number1,double number2 )
{
double answer = 0.0;
switch( oper ) {
case ADD:
answer = number1 + number2;
break;
case SUB:
answer = number1 - number2;
break;
case MULT:
answer = number1 * number2;
break;
case DIVI:
answer = number1 / number2;
break;
case POW:
answer = Math.pow( number1,
number2 );
break;
case SQRT:
answer = Math.sqrt( number1 );
break;
} // end switch
return answer;
} // end calculate()
//===============================
================================
================================
=====
//该方法用于将计算的结果输出到结果框中
//===============================
================================
================================
=====
public void showAnswer( String s )
{
double answer;
answer =
Double.valueOf(s).doubleValue();
if ( decnumber )
result.setText( Double.toString(answer) );
else
result.setText( s );
} // end showAnswer
//===============================
================================
================================
==========
//该方法检查是否双击运算符
//===============================
================================
================================
==========
public boolean clickCheck( String s ) {
if ( s == "" )
doubleclick = true;
else
doubleclick = false;
return doubleclick;
}
//===============================
================================
================================
==========
//清屏
//===============================
================================
================================
==========
public void clearScreen()
{
oper = 0;
// 初始化各个变量
input = "";
answer = 0;
decnumber = false;
morenums = false;
firstpress = true;
equals = false;
showAnswer( Integer.toString( (int)answer) );
}
public void paint( Graphics g )
{
//绘制边界
g.drawRect( 0,0,size().width - 1,
size().height - 1 );
g.drawLine( 0,0,0,size().height );
}
public static void main(String[] args){
AwtCalc ca=new AwtCalc();
}
} // end program