Java实例---计算器实例

1.计算器上的键的显示名字

1.0 继承JFrame

1 public class Calculate extends JFrame {
2 
3 }
View Code

1.1定义常量

 1 /** 计算器上的键的显示名字 */
 2 
 3 public final String[] KEYS = { "7", "8", "9", "/", "sqrt", "4", "5", "6", "*", "%", "1", "2", "3", "-", "1/x", "0", "+/-", ".", "+", "=" };
 4 
 5 /** 计算器上的功能键的显示名字 */
 6 
 7 public final String[] COMMAND = { "Backspace", "CE", "C" };
 8 
 9 /** 计算器左边的M的显示名字 */
10 
11 private final String[] M = { " ", "MC", "MR", "MS", "M+" };
View Code

1.2 为对应的按键开辟空间

 1 /** 计算器上的功能键的按钮 */
 2 
 3 private JButton commands[] = new JButton[COMMAND.length];
 4 
 5 /** 计算器左边的M的按钮 */
 6 
 7 private JButton m[] = new JButton[M.length];
 8 
 9 /** 计算结果文本框 */
10 
11 private JTextField resultText = new JTextField("0");
View Code

1.3 最终效果图:

wpsAD5F.tmp_thumb

2 内部布局代码

2.1 按键按钮代码

 1 // 初始化计算器上键的按钮,将键放在一个画板内
 2 
 3 JPanel keyPanel = new JPanel();
 4 
 5 // 用网格布局器,4行,5列的网格,网格之间的水平方向间隔为3个象素,垂直方向间隔为3个象素
 6 
 7 keyPanel.setLayout(new GridLayout(4, 5, 3, 3));
 8 
 9 for (int i = 0; i < KEYS.length; i++) {
10 
11 // 数字放入到按键中
12 
13 keys[i] = new JButton(KEYS[i]);
14 
15 // 将按键添加到面板
16 
17 keyPanel.add(keys[i]);
18 
19 // 设置颜色为淡蓝色
20 
21 keys[i].setForeground(Color.blue);
22 
23 }
24 
25 // 运算符键用红色标示,其他键用蓝色表示
26 
27 keys[3].setForeground(Color.red);
28 
29 keys[8].setForeground(Color.red);
30 
31 keys[13].setForeground(Color.red);
32 
33 keys[18].setForeground(Color.red);
34 
35 keys[19].setForeground(Color.red);
View Code

wpsAD70.tmp_thumb

2.2 初始化功能键代码

 1 // 初始化功能键,都用红色标示。将功能键放在一个画板内
 2 
 3 JPanel commandsPanel = new JPanel();
 4 
 5 // 用网格布局器,1行,3列的网格,网格之间的水平方向间隔为3个象素,垂直方向间隔为3个象素
 6 
 7 commandsPanel.setLayout(new GridLayout(1,3,3,3));
 8 
 9 for(int i = 0; i < COMMAND.length; i++){
10 
11 commands[i] = new JButton(COMMAND[i]);
12 
13 commandsPanel.add(commands[i]);
14 
15 commands[i].setForeground(Color.red);
16 
17 }
View Code

wpsAD71.tmp_thumb

2.3 初始化M键代码

 1 // 初始化M键,用红色标示,将M键放在一个画板内
 2 
 3 JPanel calmsPanel = new JPanel();
 4 
 5 calmsPanel.setLayout(new GridLayout(5,1,3,3));
 6 
 7 for(int i = 0 ; i < M.length; i++){
 8 
 9 m[i] = new JButton(M[i]);
10 
11 calmsPanel.add(m[i]);
12 
13 m[i].setForeground(Color.red);
14 
15 }
View Code

wpsAD81.tmp_thumb

2.3 设置文本框代码

 1 // 文本框中的内容采用右对齐方式
 2 
 3 resultText.setHorizontalAlignment(JTextField.RIGHT);
 4 
 5 // 不允许修改结果文本框
 6 
 7 resultText.setEditable(false);
 8 
 9 // 设置文本框背景颜色为白色
10 
11 resultText.setBackground(Color.WHITE);
View Code

wpsAD82.tmp_thumb

2.4 整体布局代码

1 JPanel panel1 = new JPanel();
2 
3 // 画板采用边界布局管理器,画板里组件之间的水平和垂直 间隔都为3象素
4 
5 panel1.setLayout(new BorderLayout(3, 3));
6 
7 panel1.add("Center", keyPanel);
8 
9 panel1.add("North",commandsPanel);
View Code

wpsAD83.tmp_thumb

1 // 建立一个画板放文本框
2 
3 JPanel top = new JPanel();
4 
5 top.setLayout(new BorderLayout());
6 
7 top.add("Center", resultText);
View Code

wpsAD84.tmp_thumb

 1 // 整体布局
 2 
 3 //画板里组件之间的水平间隔都为3象素,垂直方向上间隔都为5象素
 4 
 5 getContentPane().setLayout(new BorderLayout(3, 5));
 6 
 7 getContentPane().add("North", top);
 8 
 9 getContentPane().add("Center", panel1);
10 
11 getContentPane().add("West", calmsPanel);
View Code

wpsAD95.tmp_thumb

2.5 添加事件监听

 1 实现ActionListener类,复写actionPerformed方法
 2 
 3 public class Test1 extends JFrame implements ActionListener {...
 4 
 5 //为各按钮添加事件侦听器
 6 
 7 //都使用同一个事件侦听器,即本对象。本类的声明中有implements ActionListener
 8 
 9 for(int i = 0; i < KEYS.length; i++){
10 
11 keys[i].addActionListener(this);
12 
13 }
14 
15 for(int i = 0; i < COMMAND.length; i++){
16 
17 commands[i].addActionListener(this);
18 
19 }
20 
21 for(int i = 0; i < M.length; i++){
22 
23 m[i].addActionListener(this);
24 
25 }
26 
27 }
View Code

2.6 处理回退事件

 1 /** 处理Backspace键被按下的事件 */
 2 
 3 private void handleBackspace() {
 4 
 5 //获取文本框的内容
 6 
 7 String text = resultText.getText();
 8 
 9 int len  = text.length();
10 
11 if( len > 0){
12 
13 //表示有数字写入
14 
15 text = text.substring(0, len - 1);
16 
17 if(text.length() == 0){
18 
19 // 如果文本没有了内容,则初始化计算器的各种值
20 
21 resultText.setText("0");
22 
23 }else{
24 
25 resultText.setText(text);
26 
27 }
28 
29 }
View Code

2.7 处理CE按键

1 // 用户按了"CE"键
2 
3 resultText.setText("0");
View Code

2.8 处理数字

 1 定义变量:
 2 
 3 // 标志用户按的是否是整个表达式的第一个数字,或者是运算符后的第一个数字
 4 
 5 private boolean firstDigit = true;
 6 
 7 /**
 8 
 9 * 处理数字键被按下的事件
10 
11 */
12 
13 private void handleNumber(String label) {
14 
15 //firstDigit 默认是true
16 
17 if(firstDigit){
18 
19 //用户按的是第一个是数字
20 
21 resultText.setText(label);
22 
23 }else if((label.equals(".")) && (resultText.getText().indexOf(".") < 0) ){
24 
25 // 输入的是小数点,并且之前没有小数点,则将小数点附在结果文本框的后面
26 
27 resultText.setText(resultText.getText() + ".");
28 
29 }else if(! label.equals(".")){
30 
31 // 如果输入的不是小数点,则将数字附在结果文本框的后面
32 
33 resultText.setText(resultText.getText() + label);
34 
35 }
36 
37 // 以后输入的肯定不是第一个数字了
38 
39 firstDigit = false;
40 
41 }
View Code

2.9 处理运算符键被按下的事件

  1 0. 设置操作是否正常标志位operateValidFlag = true
  2 
  3 设置中间变量resultNum = 0.0
  4 
  5 设置操作符变量operator = "" 主要数获取当前页显示的数字
  6 
  7 1.  "="  主要是用来显示数字,可以是当前输入的数字,
  8 
  9 也可以是用算后赋值给界面的数字
 10 
 11 2. 赋值当前的操作符号给变量 operator
 12 
 13 3. 设置  firstDigt = true  用于下次界面的显示
 14 
 15 //当前运算的运算符
 16 
 17 private String operator = "=";
 18 
 19 //设置一个标志位,判断是否合法
 20 
 21 private boolean operateValidFlag = true;
 22 
 23 // 计算的中间结果。
 24 
 25 private double resultNum = 0.0;
 26 
 27 * 处理运算符键被按下的事件
 28 
 29 * @param key
 30 
 31 */
 32 
 33 private void handleOperator(String label) {
 34 
 35 // 除法运算
 36 
 37 if (operator.equals("/")) {
 38 
 39 if (getNumberFromText() == 0.0) {
 40 
 41 // 操作不合法
 42 
 43 operateValidFlag = false;
 44 
 45 resultText.setText("除数不能为零");
 46 
 47 } else {
 48 
 49 resultNum /= getNumberFromText();
 50 
 51 }
 52 
 53 // 倒数运算
 54 
 55 } else if (operator.equals("1/x")) {
 56 
 57 if (resultNum == 0.0) {
 58 
 59 operateValidFlag = false;
 60 
 61 resultText.setText("除数不能为零");
 62 
 63 } else {
 64 
 65 resultNum = 1 / resultNum;
 66 
 67 }
 68 
 69 } else if (operator.equals("+")) {
 70 
 71 // 加法运算
 72 
 73 resultNum += getNumberFromText();
 74 
 75 } else if (operator.equals("-")) {
 76 
 77 // 减法运算
 78 
 79 resultNum -= getNumberFromText();
 80 
 81 } else if (operator.equals("*")) {
 82 
 83 // 乘法运算
 84 
 85 resultNum *= getNumberFromText();
 86 
 87 } else if (operator.equals("sqrt")) {
 88 
 89 // 开方运算
 90 
 91 resultNum = Math.sqrt(resultNum);
 92 
 93 } else if (operator.equals("+/-")) {
 94 
 95 // 正数负数运算
 96 
 97 resultNum = resultNum * (-1);
 98 
 99 } else if (operator.equals("=")) {
100 
101 // 赋值运算
102 
103 resultNum = getNumberFromText();
104 
105 }
106 
107 if(operateValidFlag){
108 
109 // 双精度浮点数的运算
110 
111 long t1 ;
112 
113 double t2;
114 
115 t1 = (long) resultNum;
116 
117 t2 = resultNum - t1;
118 
119 if(t2 == 0){
120 
121 resultText.setText(String.valueOf(t1));
122 
123 System.out.println("resultText.setText(String.valueOf(t1))" + String.valueOf(t1));
124 
125 }else{
126 
127 resultText.setText(String.valueOf(resultNum));
128 
129 System.out.println("resultText.setText(String.valueOf(resultNum))" + String.valueOf(resultNum));
130 
131 }
132 
133 }
134 
135 // 运算符等于用户按的按钮
136 
137 operator = label;
138 
139 firstDigit = true;
140 
141 operateValidFlag = true;
142 
143 }
144 
145 /**
146 
147 * 从结果文本框中获取数字
148 
149 */
150 
151 private double getNumberFromText() {
152 
153 double result = 0;
154 
155 result = Double.valueOf(resultText.getText());
156 
157 return result;
158 
159 }
View Code

2.10 处理 C 按键

 1 /**
 2 
 3 * 处理C键被按下的事件
 4 
 5 */
 6 
 7 private void handleC() {
 8 
 9 // 初始化计算器的各种值
10 
11 resultText.setText("0");
12 
13 this.firstDigit = true;
14 
15 }
View Code

3. 完整代码

  1 package test;
  2 
  3 import java.awt.BorderLayout;
  4 import java.awt.Color;
  5 import java.awt.GridLayout;
  6 import java.awt.event.ActionEvent;
  7 import java.awt.event.ActionListener;
  8 
  9 import javax.swing.JButton;
 10 import javax.swing.JFrame;
 11 import javax.swing.JPanel;
 12 import javax.swing.JTextField;
 13 
 14 /**
 15  * 一个计算器,与Windows附件自带计算器的标准版功能、界面相仿。 但还不支持键盘操作。
 16  */
 17 public class Calculator extends JFrame implements ActionListener {
 18     /** 计算器上的键的显示名字 */
 19     private final String[] KEYS = { "7", "8", "9", "/", "sqrt", "4", "5", "6",
 20             "*", "%", "1", "2", "3", "-", "1/x", "0", "+/-", ".", "+", "=" };
 21     /** 计算器上的功能键的显示名字 */
 22     private final String[] COMMAND = { "Backspace", "CE", "C" };
 23     /** 计算器左边的M的显示名字 */
 24     private final String[] M = { " ", "MC", "MR", "MS", "M+" };
 25     /** 计算器上键的按钮 */
 26     private JButton keys[] = new JButton[KEYS.length];
 27     /** 计算器上的功能键的按钮 */
 28     private JButton commands[] = new JButton[COMMAND.length];
 29     /** 计算器左边的M的按钮 */
 30     private JButton m[] = new JButton[M.length];
 31     /** 计算结果文本框 */
 32     private JTextField resultText = new JTextField("0");
 33 
 34     // 标志用户按的是否是整个表达式的第一个数字,或者是运算符后的第一个数字
 35     private boolean firstDigit = true;
 36     // 计算的中间结果。
 37     private double resultNum = 0.0;
 38     // 当前运算的运算符
 39     private String operator = "=";
 40     // 操作是否合法
 41     private boolean operateValidFlag = true;
 42 
 43     /**
 44      * 构造函数
 45      */
 46     public Calculator() {
 47         super();
 48         // 初始化计算器
 49         init();
 50         // 设置计算器的背景颜色
 51         this.setBackground(Color.LIGHT_GRAY);
 52         this.setTitle("计算器");
 53         // 在屏幕(500, 300)坐标处显示计算器
 54         this.setLocation(500, 300);
 55         // 不许修改计算器的大小
 56         this.setResizable(false);
 57         // 使计算器中各组件大小合适
 58         this.pack();
 59     }
 60 
 61     /**
 62      * 初始化计算器
 63      */
 64     private void init() {
 65         // 文本框中的内容采用右对齐方式
 66         resultText.setHorizontalAlignment(JTextField.RIGHT);
 67         // 不允许修改结果文本框
 68         resultText.setEditable(false);
 69         // 设置文本框背景颜色为白色
 70         resultText.setBackground(Color.WHITE);
 71 
 72         // 初始化计算器上键的按钮,将键放在一个画板内
 73         JPanel calckeysPanel = new JPanel();
 74         // 用网格布局器,4行,5列的网格,网格之间的水平方向间隔为3个象素,垂直方向间隔为3个象素
 75         calckeysPanel.setLayout(new GridLayout(4, 5, 3, 3));
 76         for (int i = 0; i < KEYS.length; i++) {
 77             keys[i] = new JButton(KEYS[i]);
 78             calckeysPanel.add(keys[i]);
 79             keys[i].setForeground(Color.blue);
 80         }
 81         // 运算符键用红色标示,其他键用蓝色表示
 82         keys[3].setForeground(Color.red);
 83         keys[8].setForeground(Color.red);
 84         keys[13].setForeground(Color.red);
 85         keys[18].setForeground(Color.red);
 86         keys[19].setForeground(Color.red);
 87 
 88         // 初始化功能键,都用红色标示。将功能键放在一个画板内
 89         JPanel commandsPanel = new JPanel();
 90         // 用网格布局器,1行,3列的网格,网格之间的水平方向间隔为3个象素,垂直方向间隔为3个象素
 91         commandsPanel.setLayout(new GridLayout(1, 3, 3, 3));
 92         for (int i = 0; i < COMMAND.length; i++) {
 93             commands[i] = new JButton(COMMAND[i]);
 94             commandsPanel.add(commands[i]);
 95             commands[i].setForeground(Color.red);
 96         }
 97 
 98         // 初始化M键,用红色标示,将M键放在一个画板内
 99         JPanel calmsPanel = new JPanel();
100         // 用网格布局管理器,5行,1列的网格,网格之间的水平方向间隔为3个象素,垂直方向间隔为3个象素
101         calmsPanel.setLayout(new GridLayout(5, 1, 3, 3));
102         for (int i = 0; i < M.length; i++) {
103             m[i] = new JButton(M[i]);
104             calmsPanel.add(m[i]);
105             m[i].setForeground(Color.red);
106         }
107 
108         // 下面进行计算器的整体布局,将calckeys和command画板放在计算器的中部,
109         // 将文本框放在北部,将calms画板放在计算器的西部。
110 
111         // 新建一个大的画板,将上面建立的command和calckeys画板放在该画板内
112         JPanel panel1 = new JPanel();
113         // 画板采用边界布局管理器,画板里组件之间的水平和垂直方向上间隔都为3象素
114         panel1.setLayout(new BorderLayout(3, 3));
115         panel1.add("North", commandsPanel);
116         panel1.add("Center", calckeysPanel);
117 
118         // 建立一个画板放文本框
119         JPanel top = new JPanel();
120         top.setLayout(new BorderLayout());
121         top.add("Center", resultText);
122 
123         // 整体布局
124         getContentPane().setLayout(new BorderLayout(3, 5));
125         getContentPane().add("North", top);
126         getContentPane().add("Center", panel1);
127         getContentPane().add("West", calmsPanel);
128         // 为各按钮添加事件侦听器
129         // 都使用同一个事件侦听器,即本对象。本类的声明中有implements ActionListener
130         for (int i = 0; i < KEYS.length; i++) {
131             keys[i].addActionListener(this);
132         }
133         for (int i = 0; i < COMMAND.length; i++) {
134             commands[i].addActionListener(this);
135         }
136         for (int i = 0; i < M.length; i++) {
137             m[i].addActionListener(this);
138         }
139     }
140 
141     /**
142      * 处理事件
143      */
144     public void actionPerformed(ActionEvent e) {
145         // 获取事件源的标签
146         String label = e.getActionCommand();
147         if (label.equals(COMMAND[0])) {
148             // 用户按了"Backspace"键
149             handleBackspace();
150         } else if (label.equals(COMMAND[1])) {
151             // 用户按了"CE"键
152             resultText.setText("0");
153         } else if (label.equals(COMMAND[2])) {
154             // 用户按了"C"键
155             handleC();
156         } else if ("0123456789.".indexOf(label) >= 0) {
157             // 用户按了数字键或者小数点键
158             handleNumber(label);
159             // handlezero(zero);
160         } else {
161             // 用户按了运算符键
162             handleOperator(label);
163         }
164     }
165 
166     /**
167      * 处理Backspace键被按下的事件
168      */
169     private void handleBackspace() {
170         String text = resultText.getText();
171         int i = text.length();
172         if (i > 0) {
173             // 退格,将文本最后一个字符去掉
174             text = text.substring(0, i - 1);
175             if (text.length() == 0) {
176                 // 如果文本没有了内容,则初始化计算器的各种值
177                 resultText.setText("0");
178                 firstDigit = true;
179                 operator = "=";
180             } else {
181                 // 显示新的文本
182                 resultText.setText(text);
183             }
184         }
185     }
186 
187     /**
188      * 处理数字键被按下的事件
189      * 
190      * @param key
191      */
192     private void handleNumber(String key) {
193         if (firstDigit) {
194             // 输入的第一个数字
195             resultText.setText(key);
196         } else if ((key.equals(".")) && (resultText.getText().indexOf(".") < 0)) {
197             // 输入的是小数点,并且之前没有小数点,则将小数点附在结果文本框的后面
198             resultText.setText(resultText.getText() + ".");
199         } else if (!key.equals(".")) { 
200             // 如果输入的不是小数点,则将数字附在结果文本框的后面
201             System.out.println("resultText.getText()" + resultText.getText());
202             resultText.setText(resultText.getText() + key);
203             System.out.println("resultText.getText()" + resultText.getText() + key);
204         }
205         // 以后输入的肯定不是第一个数字了
206         firstDigit = false;
207     }
208 
209     /**
210      * 处理C键被按下的事件
211      */
212     private void handleC() {
213         // 初始化计算器的各种值
214         resultText.setText("0");
215         firstDigit = true;
216         operator = "=";
217     }
218 
219     /**
220      * 处理运算符键被按下的事件
221      */
222     private void handleOperator(String key) {
223         System.out.println(operator.equals("/"));
224         if (operator.equals("/")) {
225             System.out.println("进入到除法里面");
226             // 除法运算
227             // 如果当前结果文本框中的值等于0
228             if (getNumberFromText() == 0.0) {
229                 // 操作不合法
230                 operateValidFlag = false;
231                 resultText.setText("除数不能为零");
232             } else {
233                 System.out.println("resultNum:" + resultNum);
234                 resultNum /= getNumberFromText();
235                 System.out.println("resultNum /= getNumberFromText():" + resultNum);
236 
237             }
238         } else if (operator.equals("1/x")) {
239             // 倒数运算
240             if (resultNum == 0.0) {
241                 // 操作不合法
242                 operateValidFlag = false;
243                 resultText.setText("零没有倒数");
244             } else {
245                 resultNum = 1 / resultNum;
246             }
247         } else if (operator.equals("+")) {
248             // 加法运算
249             resultNum += getNumberFromText();
250         } else if (operator.equals("-")) {
251             // 减法运算
252             resultNum -= getNumberFromText();
253         } else if (operator.equals("*")) {
254             // 乘法运算
255             resultNum *= getNumberFromText();
256         } else if (operator.equals("sqrt")) {
257             // 平方根运算
258             resultNum = Math.sqrt(resultNum);
259         } else if (operator.equals("%")) {
260             // 百分号运算,除以100
261             resultNum = resultNum / 100;
262         } else if (operator.equals("+/-")) {
263             // 正数负数运算
264             resultNum = resultNum * (-1);
265         } else if (operator.equals("=")) {
266             // 赋值运算
267             resultNum = getNumberFromText();
268         }
269         if (operateValidFlag) {
270             // 双精度浮点数的运算
271             long t1;
272             double t2;
273             t1 = (long) resultNum;
274             System.out.println(t1);
275             t2 = resultNum - t1;
276             System.out.println(t2);
277             if (t2 == 0) {
278                 resultText.setText(String.valueOf(t1));
279             } else {
280                 resultText.setText(String.valueOf(resultNum));
281                 System.out.println("resultText.setText(String.valueOf(resultNum))" + String.valueOf(resultNum));
282             }
283         }
284         // 运算符等于用户按的按钮
285         operator = key;
286         firstDigit = true;
287         operateValidFlag = true;
288     }
289 
290     /**
291      * 从结果文本框中获取数字
292      * 
293      * @return
294      */
295     private double getNumberFromText() {
296         double result = 0;
297         try {
298             result = Double.valueOf(resultText.getText()).doubleValue();
299         } catch (NumberFormatException e) {
300         }
301         return result;
302     }
303 
304     public static void main(String args[]) {
305         Calculator calculator1 = new Calculator();
306         calculator1.setVisible(true);
307         calculator1.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
308     }
309 }
View Code

 

点击下载

posted @ 2018-07-17 22:28  小a玖拾柒  阅读(1102)  评论(0编辑  收藏  举报