Java之GUI编程(No.19)
GUI(Graphical User Interface,图形用户界面),是指采用图形方式显示的计算机操作用户界面。
GUI的核心技术:“AWT"与"Swing”。
- GUI缺点
- 1、界面不美观。
- 2、依赖JRE环境。
- 学习GUI目的
- 1、可以写出自定义的一些小工具。
- 2、可能会维护Swing界面(极小概率)。
- 3、了解MVC架构,了解监听。
1、AWT(Abstract Window Toolkit,抽象窗口工具包)
1.1、组件和容器(Component And Container)
1.1.1、示意图
1.1.2、Frame(框架窗口)
1.1.2.1、显示单个窗口(Show Single Window)
-
1.1.2.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui; import java.awt.*; /** * GUI(图像用户界面)窗口:显示单个Frame窗口 */ public class ShowSingleFrameWindow { public static void main(String[] args) { //创建Frame窗口 Frame frame=new Frame("显示单个Frame窗口"); //设置窗口可见性 frame.setVisible(true); //设置窗口大小 frame.setSize(300,300); //设置背景颜色 frame.setBackground(new Color(33, 65, 130)); //弹出的初始位置 frame.setLocation(150,150); //设置窗体大小的固定性 frame.setResizable(false); } }
-
1.1.2.1.2、运行结果(Run Result)
其运行结果,如下图所示。
1.1.2.2、显示多个窗口(Show Multiple Window)
- 1.1.2.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui;
import java.awt.*;
/**
* GUI(图像用户界面)窗口:显示多个Frame窗口
*/
public class ShowMultipleFrameWindow {
public static void main(String[] args) {
//创建Frame窗口
new InheritFrame(300,200,300,200,Color.red);
new InheritFrame(600,200,300,200,Color.green);
new InheritFrame(300,400,300,200,Color.blue);
new InheritFrame(600,400,300,200,Color.yellow);
}
}
//自定义继承Frame类的InheritFrame类
class InheritFrame extends Frame{
static int frameID=0;//Frame窗口ID
public InheritFrame(int x,int y,int width,int height,Color color){
super("Frame窗口"+(++frameID));//使用父类构造方法设置窗口标题名称
this.setBackground(color);//设置窗口背景颜色
this.setBounds(x,y,width,height);//设置窗口初始位置以及大小
this.setVisible(true);//设置窗口可见性
}
}
- 1.1.2.2.2、运行结果(Run Result)
其运行结果,如下图所示。
1.1.3、Panel(面板)
使用Panel(面板)时,其无法单独显示,必须添加到某个容器中。
-
1.1.3.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.componentandcontainer.panel; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * Panel(面板):无法单独显示,必须添加到某个容器中。 */ public class ShowPanel { public static void main(String[] args) { //创建窗口 Frame frame = new Frame("添加Panel(面板容器)至Frame(窗口容器)中显示"); //创建面板 Panel panel=new Panel(); //设置窗口布局 frame.setLayout(null);//默认流式布局 //设置窗口坐标与宽高 frame.setBounds(200,200,400,400); //设置窗口背景颜色 frame.setBackground(new Color(134, 37, 59)); //设置面板坐标与宽高 panel.setBounds(100,100,200,200); //设置面板背景颜色 panel.setBackground(new Color(18, 82, 18)); //窗口添加面板,即,将面板添加窗口容器中显示 frame.add(panel); //设置窗口可视性 frame.setVisible(true); //设置窗口固定性 frame.setResizable(false); //监听事件:监听窗口关闭事件(addWindowListener),且参数为“适配器模式(new WindowAdapter())” frame.addWindowListener(new WindowAdapter() { //窗口点击关闭时触发事件 @Override public void windowClosing(WindowEvent e) { System.exit(0);//结束程序 } }); } }
-
1.1.3.2、运行结果(Run Result)
其运行结果,如下图所示。
1.2、三种布局管理器(Three Layout Managers)
1.2.1、流程式布局(Flow Layout)
-
1.2.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.layout; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import java.io.UnsupportedEncodingException; /** * 流程式布局(即,流式布局) */ public class ShowFlowLayout { public static void main(String[] args) throws UnsupportedEncodingException { //创建窗口 Frame frame=new Frame("流程式布局(即,流式布局)"); //创建按钮 Button button1=new Button("button1"); Button button2=new Button("button2"); Button button3=new Button("button3"); Button button4=new Button("button4"); Button button5=new Button("button5"); Button button6=new Button("button6"); //设置窗口布局为“流程式布局” frame.setLayout(new FlowLayout()); //设置窗口坐标与宽高 frame.setBounds(100,100,300,300); //窗口添加按钮,即,将按钮添加窗口容器中显示 frame.add(button1); frame.add(button2); frame.add(button3); frame.add(button4); frame.add(button5); frame.add(button6); //设置窗口可视性 frame.setVisible(true); //设置窗口固定性 frame.setResizable(false); //监听事件:监听窗口关闭事件(addWindowListener),且参数为“适配器模式(WindowAdapter)” frame.addWindowListener(new WindowAdapter() { //窗口点击关闭时触发事件 @Override public void windowClosing(WindowEvent e) { System.exit(0);//结束程序 } }); } }
-
1.2.1.2、运行结果(Run Result)
其运行结果,如下图所示。
1.2.2、边框式布局(Border Layout)
-
1.2.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.layout; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 边框式布局 */ public class ShowBorderLayout { public static void main(String[] args) { //创建窗口 Frame frame=new Frame("边框式布局"); //创建按钮 Button button1=new Button("button1"); Button button2=new Button("button2"); Button button3=new Button("button3"); Button button4=new Button("button4"); Button button5=new Button("button5"); //设置窗口布局为“边框式布局” frame.setLayout(new BorderLayout()); //设置窗口坐标与宽高 frame.setBounds(100,100,300,300); //窗口添加按钮,即,将按钮添加窗口容器中显示 frame.add(button1,BorderLayout.NORTH); frame.add(button2,BorderLayout.WEST); frame.add(button3,BorderLayout.CENTER); frame.add(button4,BorderLayout.EAST); frame.add(button5,BorderLayout.SOUTH); //设置窗口可视性 frame.setVisible(true); //设置窗口固定性 frame.setResizable(false); //监听事件:监听窗口关闭事件(addWindowListener),且参数为“适配器模式(WindowAdapter)” frame.addWindowListener(new WindowAdapter() { //窗口点击关闭时触发事件 @Override public void windowClosing(WindowEvent e) { System.exit(0);//结束程序 } }); } }
-
1.2.2.2、运行结果(Run Result)
其运行结果,如下图所示。
1.2.3、网格式布局(Grid Layout)
-
1.2.3.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.layout; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 网格式布局 */ public class ShowGridLayout { public static void main(String[] args) { //创建窗口 Frame frame=new Frame("网格式布局"); //创建按钮 Button button1=new Button("button1"); Button button2=new Button("button2"); Button button3=new Button("button3"); Button button4=new Button("button4"); //设置窗口布局为“边框式布局” frame.setLayout(new GridLayout(2,2)); //窗口添加按钮,即,将按钮添加窗口容器中显示 frame.add(button1); frame.add(button2); frame.add(button3); frame.add(button4); // //使此窗口的大小适合其子组件的首选大小和布局 // frame.pack(); //设置窗口坐标与宽高 frame.setBounds(100,100,300,300); //设置窗口可视性 frame.setVisible(true); //设置窗口固定性 frame.setResizable(false); //监听事件:监听窗口关闭事件(addWindowListener),且参数为“适配器模式(WindowAdapter)” frame.addWindowListener(new WindowAdapter() { //窗口点击关闭时触发事件 @Override public void windowClosing(WindowEvent e) { System.exit(0);//结束程序 } }); } }
-
1.2.3.2、运行结果(Run Result)
其运行结果,如下图所示。
1.3、练习:嵌套布局组件(Exercise:Nest Layout Component)
-
1.3.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.exercise; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 练习题:嵌套布局组件(如“Frame、Panel等”) */ public class NestLayoutComponent { public static void main(String[] args) { //创建窗口 Frame frame=new Frame("嵌套布局组件"); //设置窗口布局为“边框式布局” frame.setLayout(new GridLayout(2,1));//网格式布局 //设置窗口坐标与宽高 frame.setBounds(200,200,400,400); //设置窗口背景颜色 frame.setBackground(new Color(35, 139, 139)); //设置窗口可视性 frame.setVisible(true); //设置窗口固定性 frame.setResizable(false); //监听事件:监听窗口关闭事件(addWindowListener),且参数为“适配器模式(WindowAdapter)” frame.addWindowListener(new WindowAdapter() { //窗口点击关闭时触发事件 @Override public void windowClosing(WindowEvent e) { System.exit(0);//结束程序 } }); //创建4个面板 Panel panel1=new Panel(new BorderLayout());//边框式布局 Panel panel2=new Panel(new GridLayout(2,1));//网格式布局 Panel panel3=new Panel(new BorderLayout());//边框式布局 Panel panel4=new Panel(new GridLayout(2,2));//网格式布局 //添加按钮至面板 panel1.add(new Button("WEST-1"),BorderLayout.WEST); panel1.add(new Button("EAST-1"),BorderLayout.EAST); for (int i = 0; i < 2; i++) { panel2.add(new Button("CENTER-1-"+(i+1))); } panel1.add(panel2,BorderLayout.CENTER); panel3.add(new Button("WEST-2"),BorderLayout.WEST); panel3.add(new Button("EAST-2"),BorderLayout.EAST); for (int i = 0; i < 4; i++) { panel4.add(new Button("CENTER-2-"+(i+1))); } panel3.add(panel4,BorderLayout.CENTER); //添加面板至窗口 frame.add(panel1); frame.add(panel3); } }
-
1.3.2、运行结果(Run Result)
其运行结果,如下图所示。
1.4、按钮事件监听(Button Event Listener)
-
1.4.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.listenerevent; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 事件监听:按钮事件监听 * 实现两个按钮“开始”与“停止”的同一个事件监听 */ public class ButtonEventListener { public static void main(String[] args) { //创建窗口 Frame frame = new Frame("实现两个按钮“开始”与“结束”的同一个事件监听"); //创建按钮 Button button1 = new Button("Start"); Button button2 = new Button("Stop"); /** * 事件监听:即,实现ActionListener接口类 * 可以显示定义触发会返回的命令,若不显示定义,则会返回默认值 * 多个按钮可以共用同一个监听类 */ button2.setActionCommand("停止");//设置此按钮触发的操作事件的命令名称 //监听按钮事件 ImplementActionListener implementActionListener = new ImplementActionListener(); button1.addActionListener(implementActionListener); button2.addActionListener(implementActionListener); //设置窗口布局为“边框式布局” frame.setLayout(new BorderLayout()); //设置窗口坐标与宽高 frame.setBounds(100, 100, 500, 500); //窗口添加按钮,即,将按钮添加窗口容器中显示 frame.add(button1, BorderLayout.NORTH); frame.add(button2, BorderLayout.SOUTH); //设置窗口可视性 frame.setVisible(true); // //设置窗口固定性 // frame.setResizable(false); //关闭窗口 closeWindow(frame); } //关闭窗口 private static void closeWindow(Frame frame) { //监听窗口关闭事件 frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } } //事件监听类 class ImplementActionListener implements ActionListener { //重写ActionListener接口actionPerformed方法 @Override public void actionPerformed(ActionEvent e) { System.out.println("当前点击了" + e.getActionCommand() + "按钮"); } }
-
1.4.2、运行结果(Run Result)
其运行结果,如下图所示。
1.5、单行文本输入框事件监听(TextField Event Listener)
-
1.5.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.listenerevent; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 事件监听:单行文本输入框事件监听 */ public class TextFieldEventListener { public static void main(String[] args) { //创建启动类对象:一般建议使用此方式。 new StartUpFrame(); } } //启动类 class StartUpFrame extends Frame{ //无参构造方法 public StartUpFrame(){ //设置窗口标题名称 super("单行文本输入框事件监听"); //创建单行文本输入框 TextField textField = new TextField(); //添加单行文本输入框至窗口 add(textField); //监听单行文本输入框事件:键盘按下Enter键时,就会触发单行文本输入框事件 textField.addActionListener(new ImplementTextFieldEventListener()); //设置替换编码字符 textField.setEchoChar('*'); //设置窗口坐标与宽高 setBounds(100, 100, 500, 500); //设置窗口可视性 setVisible(true); //关闭窗口 closeWindow(this); } //关闭窗口 private void closeWindow(Frame frame) { //监听窗口关闭事件 frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } } //单行文本输入框事件监听类 class ImplementTextFieldEventListener implements ActionListener{ //重写ActionListener接口actionPerformed方法 @Override public void actionPerformed(ActionEvent e) { TextField textField= (TextField) e.getSource();//获取事件最初发生的对象 System.out.println(textField.getText());//获取单行文本输入框的输入文本信息 textField.setText("");//设置单行文本输入框的输入文本信息为空字符串,即,“清空单行文本输入框” } }
-
1.5.2、运行结果(Run Result)
其运行结果,如下图所示。
1.6、练习:简易计算器(Exercise:Simple Calculator)
1.6.1、使用普通类实现(Use Common Class Implementation)
其类似于面向过程的编程思想。
-
1.6.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.exercise.calculator; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 使用普通类实现简易计算器 */ public class UseCommonClassImplementation { public static void main(String[] args) { new Calculator();//创建启动类对象 } } //计算器类 class Calculator extends Frame{ public Calculator(){ //设置窗口标题名称 super("使用普通类实现简易计算器"); //3个文本输入框 TextField textField1=new TextField(10);//被加数 TextField textField2=new TextField(10);//加数 TextField textField3=new TextField(20);//和 //1个按钮 Button button = new Button("=");//等号 //监听按钮事件 button.addActionListener(new CalculatorActionListener(textField1,textField2,textField3)); //1个标签 Label label = new Label("+");//加号 //设置窗口布局 setLayout(new FlowLayout());//流式布局 //添加组件 add(textField1); add(label); add(textField2); add(button); add(textField3); //设置窗口组件自适应大小 pack(); //设置窗口可见性 setVisible(true); //关闭窗口 closeWindow(this); } //关闭窗口 private void closeWindow(Frame frame){ frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } } //监听器类 class CalculatorActionListener implements ActionListener{ //属性 private TextField textField1,textField2,textField3; public CalculatorActionListener(TextField textField1, TextField textField2, TextField textField3) { this.textField1 = textField1; this.textField2 = textField2; this.textField3 = textField3; } @Override public void actionPerformed(ActionEvent e) { int add1=Integer.parseInt(textField1.getText());//被加数 int add2=Integer.parseInt(textField2.getText());//加数 textField3.setText(""+(add1+add2));//和 textField1.setText("");//清空被加数 textField2.setText("");//清空加数 } }
-
1.6.1.2、运行结果(Run Result)
其运行结果,如下图所示。
1.6.2、使用组合类实现(Use Composite Class Implementation)
面向对象,且组合类要优于继承类。
-
1.6.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.exercise.calculator; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 使用组合类实现简易计算器 */ public class UseCompositeClassImplementation { public static void main(String[] args) { new Calculator1();//创建启动类对象 } } //计算器类 class Calculator1 extends Frame { //属性 TextField textField1,textField2,textField3; //构造方法 public Calculator1(){ //设置窗口标题名称 super("使用组合类实现简易计算器"); startUpFrame();//调用启动方法 } //启动方法 public void startUpFrame(){ //3个文本输入框 textField1=new TextField(10);//被加数 textField2=new TextField(10);//加数 textField3=new TextField(20);//和 //1个按钮 Button button = new Button("=");//等号 //监听按钮事件 button.addActionListener(new CalculatorActionListener1(this)); //1个标签 Label label = new Label("+");//加号 //设置窗口布局 setLayout(new FlowLayout());//流式布局 //添加组件 add(textField1); add(label); add(textField2); add(button); add(textField3); //设置窗口组件自适应大小 pack(); //设置窗口可见性 setVisible(true); //关闭窗口 closeWindow(this); } //关闭窗口 private void closeWindow(Frame frame){ frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } } //监听器类 class CalculatorActionListener1 implements ActionListener { //组合类:即,在一个类中组合另一个类 Calculator1 calculator=null; //构造方法 public CalculatorActionListener1(Calculator1 calculator) { this.calculator = calculator; } //重写ActionListener接口actionPerformed方法 @Override public void actionPerformed(ActionEvent e) { int add1=Integer.parseInt(calculator.textField1.getText());//被加数 int add2=Integer.parseInt(calculator.textField2.getText());//加数 calculator.textField3.setText(""+(add1+add2));//和 calculator.textField1.setText("");//清空被加数 calculator.textField2.setText("");//清空加数 } }
-
1.6.2.2、运行结果(Run Result)
其运行结果,如下图所示。
1.6.3、使用内部类实现(Use Internal Class Implementation)
面向对象,且内部类要优于组合类,其最大好处为“可以任意访问外部类的属性与方法”。
-
1.6.3.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.exercise.calculator; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 使用内部类实现简易计算器 */ public class UseInternalClassImplementation { public static void main(String[] args) { new Calculator2();//创建启动类对象 } } //计算器类 class Calculator2 extends Frame { //属性 TextField textField1,textField2,textField3; //构造方法 public Calculator2(){ //设置窗口标题名称 super("使用内部类实现简易计算器"); startUpFrame();//调用启动方法 } //启动方法 public void startUpFrame(){ //3个文本输入框 textField1=new TextField(10);//被加数 textField2=new TextField(10);//加数 textField3=new TextField(20);//和 //1个按钮 Button button = new Button("=");//等号 //监听按钮事件 button.addActionListener(new CalculatorActionListener2()); //1个标签 Label label = new Label("+");//加号 //设置窗口布局 setLayout(new FlowLayout());//流式布局 //添加组件 add(textField1); add(label); add(textField2); add(button); add(textField3); //设置窗口组件自适应大小 pack(); //设置窗口可见性 setVisible(true); //关闭窗口 closeWindow(this); } //关闭窗口 private void closeWindow(Frame frame){ frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } //监听器类:即,内部类,可以更好的包装,其最大好处为“可以任意访问外部类的属性与方法”。 private class CalculatorActionListener2 implements ActionListener { //重写ActionListener接口actionPerformed方法 @Override public void actionPerformed(ActionEvent e) { int add1=Integer.parseInt(textField1.getText());//被加数 int add2=Integer.parseInt(textField2.getText());//加数 textField3.setText(""+(add1+add2));//和 textField1.setText("");//清空被加数 textField2.setText("");//清空加数 } } }
-
1.6.3.2、运行结果(Run Result)
其运行结果,如下图所示。
1.7、画笔(Paint Brush)
-
1.7.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.componentandcontainer.frame; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 画笔 */ public class PaintBrush { public static void main(String[] args) { new PaintClass();//创建启动类对象 } } //画笔类 class PaintClass extends Frame { public PaintClass() { super("画笔"); startUpFrame(); } public void startUpFrame() { setBounds(100, 100, 500, 500); setVisible(true); closeWindow(this);//关闭窗口 } /** * 重写Frame类paint方法 * 绘制组件:即,画笔. * * @param g */ @Override public void paint(Graphics g) { //画笔:需要有颜色,且可以绘画。 g.setColor(Color.BLUE);//蓝色颜色 g.draw3DRect(100, 100, 300, 300, true);//绘制一个3D的空心矩形 g.setColor(Color.GRAY);//灰色画笔 g.drawPolygon(new int[]{100, 250, 400,250}, new int[]{250, 100, 250,400}, 4);//绘制一个空心四边形(即,菱形) g.setColor(Color.GREEN);//绿色画笔 g.drawOval(150, 150, 200, 200);//绘制一个空心园 g.setColor(Color.RED);//红色画笔 g.fillOval(200, 200, 100, 100);//绘制一个实心园 //画笔用完后,建议还原为最初的颜色。 g.setColor(Color.BLACK);//默认画笔颜色为黑色 } //关闭窗口 private void closeWindow(Frame frame) { frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } }
-
1.7.2、运行结果(Run Result)
其运行结果,如下图所示。
1.8、鼠标事件监听(Mouse Event Listener)
模拟画图工具。
-
1.8.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.listenerevent; import java.awt.*; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; import java.util.ArrayList; import java.util.Iterator; /** * 鼠标事件监听:模拟画图工具 * 1、使用画笔 * 2、监听鼠标当前位置坐标 * 3、使用集合列表存储所有的监听鼠标位置坐标 * 4、重新绘制组件 */ public class MouseEventListener { public static void main(String[] args) { new PaintListenerMousePosition("模拟画图工具");//创建启动类对象 } } //画笔监听鼠标位置类 class PaintListenerMousePosition extends Frame{ //存储所有的监听鼠标位置坐标的集合列表 ArrayList mousePositionList; public PaintListenerMousePosition(String title){ super(title);//设置窗口标题 mousePositionList=new ArrayList<>(); setBounds(100,100,500,500);//设置窗口位置与大小 setVisible(true);//设置窗口可见 this.addMouseListener(new MouseActionListener());//添加鼠标事件监听 closeWindow(this);//关闭窗口 } //重写Frame类paint方法 @Override public void paint(Graphics g) { //画笔:即,绘制组件 Iterator iterator=mousePositionList.iterator(); while(iterator.hasNext()){ Point point= (Point) iterator.next(); g.setColor(Color.RED); g.fillOval(point.x, point.y, 20,20); } } //添加鼠标位置坐标至集合列表 public void addMousePositionList(Point point){ mousePositionList.add(point); } //适配器模式 private class MouseActionListener extends MouseAdapter{ //鼠标按下 @Override public void mouseClicked(MouseEvent e) { System.out.println("当前鼠标按下"); } //鼠标按下不放 @Override public void mousePressed(MouseEvent e) { System.out.println("当前鼠标按下不放"); PaintListenerMousePosition pLMP= (PaintListenerMousePosition) e.getSource(); pLMP.addMousePositionList(new Point(e.getX(),e.getY()));//添加当前鼠标坐标 pLMP.repaint();//重新绘制组件 } //鼠标释放 @Override public void mouseReleased(MouseEvent e) { System.out.println("当前鼠标释放"); } } //关闭窗口 private void closeWindow(Frame frame){ frame.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); } }
-
1.8.2、运行结果(Run Result)
其运行结果,如下图所示。
1.9、窗口事件监听(Window Event Listener)
分别使用内部类(Internal Class)与匿名内部类(Anonymous Internal Class)来实现,并且匿名内部类要比内部类更简洁方便”。
-
1.9.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.listenerevent; import java.awt.*; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 窗口事件监听:使用内部类或匿名内部类实现窗口事件监听,匿名内部类比内部类更简捷方便,一般建议使用匿名内部类。 * 局部内部类和匿名内部类最大的不同之处:局部内部类可以返回不止一个内部类的对象。 */ public class WindowEventListener { public static void main(String[] args) { new WindowFrame1("使用内部类实现窗口事件监听");//创建启动类对象 new WindowFrame2("使用匿名内部类实现窗口事件监听");//创建启动类对象 } } //外部类 class WindowFrame1 extends Frame{ public WindowFrame1(String title){ super(title);//设置窗口标题 setBounds(100,100,400,300);//设置窗口坐标及大小 setVisible(true);//设置窗口可见 addWindowListener(new WindowActionListener());//添加窗口事件监听 } //添加窗口事件监听:即,使用内部类实现 private class WindowActionListener extends WindowAdapter{ //窗口关闭事件 @Override public void windowClosing(WindowEvent e) { //setVisible(false);//设置窗口隐藏 System.exit(0);//关闭程序,正常退出 } } } //外部类 class WindowFrame2 extends Frame{ public WindowFrame2(String title){ super(title);//设置窗口标题 setBounds(100,100,400,300);//设置窗口坐标及大小 setVisible(true);//设置窗口可见 //添加窗口事件监听:即,使用匿名内部类实现 addWindowListener(new WindowAdapter() { //窗口关闭事件 @Override public void windowClosing(WindowEvent e) { //setVisible(false);//设置窗口隐藏 System.exit(0);//关闭程序,正常退出 } //窗口激活事件 @Override public void windowActivated(WindowEvent e) { WindowFrame2 windowFrame2= (WindowFrame2) e.getSource(); windowFrame2.setTitle("使用匿名内部类实现窗口事件监听:窗口激活"); System.out.println("使用匿名内部类实现窗口事件监听:窗口激活"); } }); } }
-
1.9.2、运行结果(Run Result)
其运行结果,如下图所示。
1.10、键盘事件监听(Keyboard Event Listener)
-
1.10.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.listenerevent; import java.awt.*; import java.awt.event.KeyAdapter; import java.awt.event.KeyEvent; import java.awt.event.WindowAdapter; import java.awt.event.WindowEvent; /** * 键盘事件监听 */ public class KeyboardEventListener { public static void main(String[] args) { new KeyboardFrame("键盘事件监听");//创建启动类对象 } } //外部类 class KeyboardFrame extends Frame { public KeyboardFrame(String title) { super(title); setBounds(100,100,300,300); setVisible(true); //添加窗口事件监听:即,使用匿名内部类实现 addWindowListener(new WindowAdapter() { //窗口关闭事件 @Override public void windowClosing(WindowEvent e) { System.exit(0);//关闭程序 } }); //添加键盘事件监听:即,使用匿名内部类实现 addKeyListener(new KeyAdapter() { //键盘按下不放事件 @Override public void keyPressed(KeyEvent e) { int keyCode=e.getKeyCode();//按键数值 int extendedKeyCode=e.getExtendedKeyCode();//按键扩展密钥代码 char keyChar=e.getKeyChar();//按键字符 int keyLocation=e.getKeyLocation();//按键位置 String keyText=KeyEvent.getKeyText(keyCode);//按键描述 System.out.println("按键字符("+keyChar+")按键数值("+keyCode+")按键位置("+keyLocation+")按键描述("+keyText+")按键扩展密钥代码("+extendedKeyCode+")"); } }); } }
-
1.10.2、运行结果(Run Result)
其运行结果,如下图所示。
2、Swing
Swing是一个用于开发Java应用程序用户界面的开发工具包。
Swing是以抽象窗口工具包(AWT)为基础 使跨平台应用程序可以使用任何可插拔的外观风格。Swing开发人员只用很少的代码就可以利用Swing丰富、灵活的功能和模块化组件来创建优雅的用户界面。
2.1、JFrame窗口(JFrame Window)
-
2.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * JFrame窗口 */ public class JFrameWindow { public static void main(String[] args) { new StartUpJFrame("JFrame窗口");//创建启动类对象 } } class StartUpJFrame extends JFrame{ public StartUpJFrame(String title){ super(title);//设置窗口标题 init();//调用启动方法 } public void init(){ setBounds(100,100,300,300);//设置窗口坐标及大小 setVisible(true);//设置窗口可见 JLabel jLabel=new JLabel("JLabel标签");//新增标签 this.add(jLabel);//添加标签至窗口 jLabel.setHorizontalAlignment(SwingConstants.CENTER);//设置标签水平居中对齐 Container container=this.getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);获取此窗口容器的背景颜色 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } }
-
2.1.2、运行结果(Run Result)
其运行结果,如下图所示。
2.2、JDialog弹出窗口(JDialog Popup Window)
-
2.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; /** * JDialog弹出窗口 */ public class JDialogPopupWindow { public static void main(String[] args) { new MainWindow("JDialog主窗口");//创建启动类对象 } } //主窗口类 class MainWindow extends JFrame{ public MainWindow(String title){ super(title);//设置窗口标题 init();//调用启动方法 } private void init(){ setBounds(100,100,300,300);//设置窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 Container container=this.getContentPane();//获取此窗口的容器 container.setLayout(null);//默认布局:即,绝对布局 container.setBackground(Color.RED);获取此窗口容器的背景颜色 JButton jButton=new JButton("弹出窗口按钮");//新增按钮 jButton.setBounds(50,50,150,100);//设置按钮坐标及大小 jButton.setHorizontalAlignment(SwingConstants.CENTER);//设置按钮水平居中对齐 //添加按钮事件监听 jButton.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { new PopupDialog("JDialog弹出窗口");//弹出窗口 } }); this.add(jButton);//添加按钮至窗口 } } //弹出窗口类 class PopupDialog extends JDialog{ public PopupDialog(String title){ setTitle(title);//设置弹出窗口标题 init();//调用启动方法 } private void init(){ setBounds(400,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置弹出窗口可见 //setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭弹出窗口:无需设置此功能,否则异常 Container container=this.getContentPane();//获取此弹出窗口的容器 container.setLayout(null);//默认布局:即,绝对布局 container.setBackground(Color.GREEN);获取此弹出窗口容器的背景颜色 JLabel jLabel=new JLabel("JDialog弹出窗口的JLabel标签");//新增标签 jLabel.setBounds(50,50,200,100);//设置标签坐标及大小 jLabel.setHorizontalAlignment(SwingConstants.CENTER);//设置标签水平居中对齐 container.add(jLabel);//添加标签至容器 } }
-
2.2.2、运行结果(Run Result)
其运行结果,如下图所示。
2.3、Icon与ImageIcon标签(Icon And ImageIcon Label)
2.3.1、Icon标签(Icon Label)
-
2.3.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * Icon:图标 * 1、继承JFrame类 * 2、实现Icon接口 * 特别注意:设置JFrame窗口为Container容器后,再设置JFrame窗口的参数(如坐标、大小、可见性等)才有效。 */ public class IconLabel extends JFrame implements Icon { private int width;//图标宽度 private int height;//图标高度 //无参构造方法 public IconLabel(){ } //有参构造方法 public IconLabel(int width, int height){ super("Icon(图标)"); this.width = width; this.height = height; } //主方法 public static void main(String[] args) { new IconLabel(20,20).init();//调用启动方法 } //启动方法 public void init(){ IconLabel iconLabel=new IconLabel(this.width,this.height);//设置图标宽高 //将图标放到标签上(也可以把图标放到按钮上) JLabel jLabel=new JLabel("图标标签",iconLabel,SwingConstants.CENTER); Container container=getContentPane();//获取此窗口的容器 //container.setLayout(null);//默认布局:即,绝对布局 container.setBackground(Color.RED);获取此窗口容器的背景颜色 container.add(jLabel);//添加标签至容器 setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 System.out.println("图标名称""+getTitle()+"",图标宽度""+getIconWidth()+"",图标高度""+getIconHeight()+"""); } //重写Icon接口的paintIcon方法 @Override public void paintIcon(Component c, Graphics g, int x, int y) { g.setColor(Color.GREEN);//绿色画笔 g.fillOval(x,y,this.width,this.height);//填充绘制一个圆形图标 } //重写Icon接口的getIconWidth方法 @Override public int getIconWidth() { return this.width;//返回图标宽度 } //重写Icon接口的getIconHeight方法 @Override public int getIconHeight() { return this.height;//返回图标高度 } }
-
2.3.1.2、运行结果(Run Result)
其运行结果,如下图所示。
2.3.2、ImageIcon标签(ImageIcon Label)
-
2.3.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; import java.net.URL; /** * ImageIcon:图像图标 * 1、继承JFrame类 * 特别注意:设置JFrame窗口为Container容器后,再设置JFrame窗口的参数(如坐标、大小、可见性等)才有效。 */ public class ImageIconLabel extends JFrame { private int width;//图标宽度 private int height;//图标高度 //无参构造方法 public ImageIconLabel(){ super("ImageIcon(图像图标)"); } //主方法 public static void main(String[] args) { new ImageIconLabel().init();//调用启动方法 } //启动方法 public void init(){ JLabel jLabel=new JLabel("图像图标标签");//新增标签 URL url=this.getClass().getResource("URLTest.jpg");//获取图像图标地址(URL) ImageIcon imageIcon=new ImageIcon(url);//新增图像图标 jLabel.setIcon(imageIcon);//添加图像图标到标签 jLabel.setHorizontalAlignment(SwingConstants.CENTER);//设置标签水平居中对齐 Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);获取此窗口容器的背景颜色 //container.setLayout(null);//默认布局:即,绝对布局 container.add(jLabel);//添加标签至容器 setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } }
-
2.3.2.2、运行结果(Run Result)
其运行结果,如下图所示。
2.4、按钮与面板、文本域与滚动面板(Button And Panel,Text Area And Scroll Panel)
2.4.1、按钮与面板(Button And Panel)
-
2.4.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 按钮与面板 */ public class ButtonAndPanel extends JFrame { public ButtonAndPanel(){ super("按钮与面板"); init(); } public void init(){ JPanel jPanel=new JPanel(new GridLayout(5,2,10,10));//新增面板,2行2列的网格布局,且上下左右间距为10 //新增按钮 jPanel.add(new JButton("按钮1")); jPanel.add(new JButton("按钮2")); jPanel.add(new JButton("按钮3")); jPanel.add(new JButton("按钮4")); jPanel.add(new JButton("按钮5")); jPanel.add(new JButton("按钮6")); jPanel.add(new JButton("按钮7")); jPanel.add(new JButton("按钮8")); jPanel.add(new JButton("按钮9")); jPanel.add(new JButton("按钮10")); Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);获取此窗口容器的背景颜色 container.setLayout(new GridLayout(2,2,20,20));//新增容器,2行2列的网格布局,且上下左右间距为20 container.add(jPanel);//添加面板至容器 setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new ButtonAndPanel();//创建启动类对象 } }
-
2.4.1.2、运行结果(Run Result)
其运行结果,如下图所示。
2.4.2、文本域与滚动面板(Text Area And Scroll Panel)
-
2.4.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 文本域与滚动面板 */ public class TextAreaAndScrollPanel extends JFrame { public TextAreaAndScrollPanel(String title){ super(title); init(); } public void init(){ //新增文本域 JTextArea jTextArea=new JTextArea("文本域",30,30); jTextArea.setText("文本域信息");//设置文本域信息 jTextArea.setToolTipText("文本域提示信息");//设置文本域提示信息 //新增滚动面板,且添加文本域到滚动面板 JScrollPane jScrollPane=new JScrollPane(jTextArea); Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);获取此窗口容器的背景颜色 container.add(jScrollPane);//添加滚动面板至容器 setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new TextAreaAndScrollPanel("文本域与滚动面板");//创建启动类对象 } }
-
2.4.2.2、运行结果(Run Result)
其运行结果,如下图所示。
2.5、图像按钮、单选框按钮、复选框按钮(Image Button,Radio Box Button,Check Box Button)
2.5.1、图像按钮(Image Button)
-
2.5.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; import java.net.URL; /** * 图像按钮 */ public class ImageButton extends JFrame{ public ImageButton(String title){ super(title); init(); } public void init(){ URL url=this.getClass().getResource("URLTest.jpg");//获取图像图标地址(URL) Icon icon=new ImageIcon(url);//设置图像图标 JButton jButton=new JButton();//新增按钮 jButton.setIcon(icon);//添加图像图标到按钮 //jButton.setText("图像按钮");//设置按钮文本信息 jButton.setToolTipText("图像按钮");//设置按钮提示信息 Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);获取此窗口容器的背景颜色 container.add(jButton);//添加按钮至容器 setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new ImageButton("图像按钮");//创建启动类对象 } }
-
2.5.1.2、运行结果(Run Result)
其运行结果,如下图所示。
2.5.2、单选框按钮(Radio Box Button)
-
2.5.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 单选框按钮 */ public class RadioBoxButton extends JFrame{ public RadioBoxButton(String title){ super(title); init(); } public void init(){ //新增单选框按钮 JRadioButton jRadioButton1=new JRadioButton("单选框按钮1"); JRadioButton jRadioButton2=new JRadioButton("单选框按钮2"); JRadioButton jRadioButton3=new JRadioButton("单选框按钮3"); //新增按钮组 ButtonGroup buttonGroup=new ButtonGroup(); //添加单选框按钮至按钮组:确保一组单选框按钮每次只能选择一个单选框按钮 buttonGroup.add(jRadioButton1); buttonGroup.add(jRadioButton2); buttonGroup.add(jRadioButton3); Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//获取此窗口容器的背景颜色 container.setLayout(new FlowLayout(FlowLayout.CENTER));//获取此窗口容器的布局 //添加单选框按钮至容器 container.add(jRadioButton1); container.add(jRadioButton2); container.add(jRadioButton3); setBounds(100,100,400,100);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new RadioBoxButton("单选框按钮");//创建启动类对象 } }
-
2.5.2.2、运行结果(Run Result)
其运行结果,如下图所示。
2.5.3、复选框按钮(Check Box Button)
-
2.5.3.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 复选框按钮 */ public class CheckBoxButton extends JFrame{ public CheckBoxButton(String title){ super(title); init(); } public void init(){ //新增复选框按钮 JCheckBox jCheckBox1=new JCheckBox("复选框按钮1"); JCheckBox jCheckBox2=new JCheckBox("复选框按钮2"); JCheckBox jCheckBox3=new JCheckBox("复选框按钮3"); Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//获取此窗口容器的背景颜色 container.setLayout(new FlowLayout(FlowLayout.CENTER));//获取此窗口容器的布局 //添加复选框按钮至容器 container.add(jCheckBox1); container.add(jCheckBox2); container.add(jCheckBox3); setBounds(100,100,400,100);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new CheckBoxButton("复选框按钮");//创建启动类对象 } }
-
2.5.3.2、运行结果(Run Result)
其运行结果,如下图所示。
2.6、组合框、列表框(Combo Box,List Box)
2.6.1、组合框(Combo Box)
-
2.6.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 组合框 */ public class ComboBoxContainer extends JFrame { public ComboBoxContainer(String title){ super(title); init(); } public void init(){ //新增组合框 JComboBox jComboBox=new JComboBox(); jComboBox.addItem(null); jComboBox.addItem("优秀"); jComboBox.addItem("良好"); jComboBox.addItem("及格"); jComboBox.addItem("不及格"); jComboBox.setBounds(50,50,200,100);//设置组合框坐标及大小 Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//设置此窗口容器的背景颜色 container.setLayout(null);//设置此窗口容器的布局 //添加组合框至容器 container.add(jComboBox); setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new ComboBoxContainer("组合框");//创建启动类对象 } }
-
2.6.1.2、运行结果(Run Result)
其运行结果,如下图所示。
2.6.2、列表框(List Box)
-
2.6.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; import java.util.Vector; /** * 下拉框 */ public class ListBoxContainer extends JFrame { public ListBoxContainer(String title){ super(title); init(); } public void init(){ //新增下拉框 JList jList1=new JList(new String[]{"","优秀","良好","及格","不及格"}); jList1.setBounds(30,50,100,100);//设置下拉框坐标及大小 Vector vector=new Vector();//可扩展的对象数组 JList jList2=new JList(vector); jList2.setBounds(160,50,100,100);//设置下拉框坐标及大小 vector.add(""); vector.add("1"); vector.add("2"); vector.add("3"); vector.add("4"); Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//设置此窗口容器的背景颜色 container.setLayout(null);//设置此窗口容器的布局 //添加下拉框至容器 container.add(jList1); container.add(jList2); setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new ListBoxContainer("下拉框");//创建启动类对象 } }
-
2.6.2.2、运行结果(Run Result)
其运行结果,如下图所示。
2.7、文本框、密码框、文本域(Text Field,Password Field,Text Area)
2.7.1、文本框(Text Field)
-
2.7.1.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 文本框 */ public class TextFieldContainer extends JFrame { public TextFieldContainer(String title){ super(title); init(); } public void init(){ //新增文本框 JTextField jTextField1=new JTextField("文本框1"); JTextField jTextField2=new JTextField("文本框2"); jTextField1.setBounds(30,50,100,100);//设置文本框坐标及大小 jTextField2.setBounds(150,50,100,100);//设置文本框坐标及大小 Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//设置此窗口容器的背景颜色 container.setLayout(null);//设置此窗口容器的布局 //添加文本框至容器 container.add(jTextField1); container.add(jTextField2); setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new TextFieldContainer("文本框");//创建启动类对象 } }
-
2.7.1.2、运行结果(Run Result)
其运行结果,如下图所示。
2.7.2、密码框(Password Field)
-
2.7.2.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 密码框 */ public class PasswordFieldContainer extends JFrame { public PasswordFieldContainer(String title){ super(title); init(); } public void init(){ //新增密码框 JPasswordField jPasswordField=new JPasswordField(); jPasswordField.setEchoChar('*');// jPasswordField.setBounds(30,50,100,100);//设置密码框坐标及大小 Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//设置此窗口容器的背景颜色 container.setLayout(null);//设置此窗口容器的布局 //添加密码框至容器 container.add(jPasswordField); setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new PasswordFieldContainer("密码框");//创建启动类对象 } }
-
2.7.2.2、运行结果(Run Result)
其运行结果,如下图所示。
2.7.3、文本域(Text Area)
-
2.7.3.1、示例代码(Sample Code)
其示例代码,如下所示。
package com.xueshanxuehai.gui.swing; import javax.swing.*; import java.awt.*; /** * 文本域 */ public class TextAreaContainer extends JFrame{ public TextAreaContainer(String title){ super(title); init(); } public void init(){ //新增文本域 JTextArea jTextArea1=new JTextArea("文本域1",20,20); JTextArea jTextArea2=new JTextArea("文本域2",20,20); //新增滚动面板,且添加文本域到滚动面板 JScrollPane jScrollPane1=new JScrollPane(jTextArea1); JScrollPane jScrollPane2=new JScrollPane(jTextArea2); //设置滚动面板坐标及大小 jScrollPane1.setBounds(30,50,100,100); jScrollPane2.setBounds(150,50,100,100); Container container=getContentPane();//获取此窗口的容器 container.setBackground(Color.RED);//设置此窗口容器的背景颜色 container.setLayout(null);//设置此窗口容器的布局 //添加滚动面板至容器 container.add(jScrollPane1); container.add(jScrollPane2); setBounds(100,100,300,300);//设置弹出窗口坐标及大小 setVisible(true);//设置窗口可见 setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口 } public static void main(String[] args) { new TextAreaContainer("文本域");//创建启动类对象 } }
-
2.7.3.2、运行结果(Run Result)
其运行结果,如下图所示。
3、练习:实现“贪吃蛇”游戏(Exercise:Realize The “Greedy Snake” Game)
3.1、游戏需求(Game Demand)
- 3.1.1、按空格键开始或暂停游戏。
- 3.1.2、按上、下、左、右键控制贪吃蛇的移动方向。
- 3.1.3、实时计算贪吃蛇的当前长度和当前积分。
3.2、示例代码(Sample Code)
- 3.2.1、游戏的启动类
GameStart类,其代码如下所示。
package com.xueshanxuehai.gui.swing.exercise.GreedySnake;
import javax.swing.*;
/**
* 游戏的启动类
*/
public class GameStart {
public static void main(String[] args) {
JFrame jFrame=new JFrame();//创建窗口对象
jFrame.setBounds(10,10,915,730);//设置窗口坐标及大小
jFrame.setResizable(false);//设置窗口固定
jFrame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口
jFrame.add(new GamePanel());//添加游戏面板至窗口
jFrame.setVisible(true);//设置窗口可见
}
}
- 3.2.2、游戏的面板类
GamePanel类,其代码如下所示。
package com.xueshanxuehai.gui.swing.exercise.GreedySnake;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.Random;
/**
* 游戏的面板类
* 1、继承JPanel类
* 2、实现KeyListener接口
* 3、实现ActionListener接口
*/
public class GamePanel extends JPanel implements KeyListener, ActionListener {
//定义蛇的数据结构
int length;//蛇的长度
int[] snakeX = new int[600];//蛇的X坐标(25*25)
int[] snakeY = new int[600];//蛇的Y坐标(25*25)
String snakeDirection;//蛇的方向
boolean gameState = false;//游戏的状态(默认为停止)
Timer timer = new Timer(100, this);//定时器,每100毫秒执行一次,且被事件监听
int foodX;//食物的X坐标(25*25)
int foodY;//食物的Y坐标(25*25)
Random random=new Random();//随机数:随机食物的坐标基数
boolean gameIsFail=false;//游戏是否失败,默认为成功
int score;//成绩积分
//无参构造方法
public GamePanel() {
init();//调用初始化方法
setFocusable(true);//获得焦点
addKeyListener(this);//获得键盘监听事件
timer.start();//开启定时器,即”开始游戏“
}
//初始化方法
public void init() {
length = 3;//蛇的初始长度
snakeX[0] = 100;//蛇头的X坐标
snakeY[0] = 100;//蛇头的Y坐标
snakeX[1] = 75;//蛇身1的X坐标
snakeY[1] = 100;//蛇身1的Y坐标
snakeX[2] = 50;//蛇身2的X坐标
snakeY[2] = 100;//蛇身2的Y坐标
snakeDirection = "RIGHT";//蛇的初始方向,默认为蛇头向右
foodX=25+25*random.nextInt(((int)(850/25)-1));//随机食物的X坐标(25*25)
foodY=75+25*random.nextInt(((int)(600/25)-1));//随机食物的Y坐标(25*25)
score=0;//初始成绩积分
}
//绘制面板:游戏中的所有东西都由此方法此画笔来绘制
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);//清屏
//绘制静态的游戏面板
setBackground(Color.WHITE);//白色背景
GameResource.header.paintIcon(this, g, 25, 15);//绘制头部广告栏图片按钮
g.fillRect(25, 75, 850, 600);//绘制默认的矩形游戏界面
//绘制成绩积分
g.setColor(Color.GREEN);//绿色背景
g.setFont(new Font("宋体", Font.BOLD, 20));//设置字体
g.drawString("当前长度"+length, 750, 37);//绘制当前长度文本提示信息及大小
g.drawString("当前积分"+score, 750, 57);//绘制成绩积分文本提示信息及大小
//绘制食物
GameResource.food.paintIcon(this,g,foodX,foodY);//绘制食物
//绘制蛇头
if (snakeDirection.equals("RIGHT")) {
GameResource.right.paintIcon(this, g, snakeX[0], snakeY[0]);//绘制向右的蛇头
} else if (snakeDirection.equals("LEFT")) {
GameResource.left.paintIcon(this, g, snakeX[0], snakeY[0]);//绘制向左的蛇头
} else if (snakeDirection.equals("UP")) {
GameResource.up.paintIcon(this, g, snakeX[0], snakeY[0]);//绘制向上的蛇头
} else if (snakeDirection.equals("DOWN")) {
GameResource.down.paintIcon(this, g, snakeX[0], snakeY[0]);//绘制向下的蛇头
}
//绘制蛇身
for (int i = 1; i < length; i++) {
GameResource.body.paintIcon(this, g, snakeX[i], snakeY[i]);//绘制蛇身
}
//绘制游戏状态
if (!gameState) {
g.setColor(Color.WHITE);//白色背景
g.setFont(new Font("宋体", Font.BOLD, 30));//设置字体
g.drawString("请按下空格开始游戏", 200, 200);//绘制游戏状态文本提示信息及大小
}
//绘制游戏失败
if(gameIsFail){
g.setColor(Color.RED);//红色背景
g.setFont(new Font("宋体", Font.BOLD, 30));//设置字体
g.drawString("游戏失败,请按下空格重新开始游戏", 200, 200);//绘制游戏失败文本提示信息及大小
}
}
//键盘按下不放监听事件
@Override
public void keyPressed(KeyEvent e) {
int keyCode = e.getKeyCode();//获取按键值
if (keyCode == KeyEvent.VK_SPACE) {//按下空格键
if(gameIsFail){//游戏失败
gameIsFail=false;//重新开始游戏
init();//重新初始化
}else{
gameState = !gameState;//取反
}
repaint();//重绘
} else if (keyCode == KeyEvent.VK_RIGHT) {//按下向右键
snakeDirection = "RIGHT";
repaint();//重绘
} else if (keyCode == KeyEvent.VK_LEFT) {//按下向左键
snakeDirection = "LEFT";
repaint();//重绘
} else if (keyCode == KeyEvent.VK_UP) {//按下向上键
snakeDirection = "UP";
repaint();//重绘
} else if (keyCode == KeyEvent.VK_DOWN) {//按下向下键
snakeDirection = "DOWN";
repaint();//重绘
}
}
//事件监听:即,通过监听定时器事件来刷新
@Override
public void actionPerformed(ActionEvent e) {
if (gameState && !gameIsFail) {//若游戏为开始状态,且游戏未失败,则让蛇移动起来
//蛇吃食物
if(snakeX[0]==foodX && snakeY[0]==foodY){
length++;//蛇的长度加1
score+=10;//成绩积分加10
foodX=25+25*random.nextInt(((int)(850/25)-1));//随机食物的X坐标(25*25)
foodY=75+25*random.nextInt(((int)(600/25)-1));//随机食物的Y坐标(25*25)
}
//绘制移动蛇身坐标:后一个坐标移动到前一个坐标
for (int i = length - 1; i > 0; i--) {
snakeX[i] = snakeX[i - 1];
snakeY[i] = snakeY[i - 1];
}
if (snakeDirection.equals("RIGHT")) {
snakeX[0] += 25;//绘制移动蛇头坐标
if (snakeX[0] > 850) {
snakeX[0] = 25;//边界判定,若超过边界,则从当前方向起始坐标重新开始移动
}
} else if (snakeDirection.equals("LEFT")) {
snakeX[0] -= 25;//绘制移动蛇头坐标
if (snakeX[0] < 25) {
snakeX[0] = 850;//边界判定,若超过边界,则从当前方向起始坐标重新开始移动
}
} else if (snakeDirection.equals("UP")) {
snakeY[0] -= 25;//绘制移动蛇头坐标
if (snakeY[0] < 75) {
snakeY[0] = 650;//边界判定,若超过边界,则从当前方向起始坐标重新开始移动
}
} else if (snakeDirection.equals("DOWN")) {
snakeY[0] += 25;//绘制移动蛇头坐标
if (snakeY[0] > 650) {
snakeY[0] = 75;//边界判定,若超过边界,则从当前方向起始坐标重新开始移动
}
}
//游戏失败判定:即,撞到自身就算游戏失败
for (int i = 1; i < length; i++) {
if(snakeX[0]==snakeX[i] && snakeY[0]==snakeY[i]){
gameIsFail=true;//游戏失败
}
}
repaint();//重绘
}
}
@Override
public void keyTyped(KeyEvent e) {
}
@Override
public void keyReleased(KeyEvent e) {
}
}
- 3.2.3、游戏的资源类
GameResource类,其代码如下所示。
package com.xueshanxuehai.gui.swing.exercise.GreedySnake;
import javax.swing.*;
import java.net.URL;
/**
* 游戏的资源类
*/
public class GameResource {
public static URL headerURL=GameResource.class.getResource("images/header.png");//获取头部广告栏图片URL地址
public static ImageIcon header=new ImageIcon(headerURL);//新增头部广告栏图片按钮
public static URL upURL=GameResource.class.getResource("images/up.png");//获取蛇头向上图片URL地址
public static ImageIcon up=new ImageIcon(upURL);//新增蛇头向上图片按钮
public static URL downURL=GameResource.class.getResource("images/down.png");//获取蛇头向下图片URL地址
public static ImageIcon down=new ImageIcon(downURL);//新增蛇头向下图片按钮
public static URL leftURL=GameResource.class.getResource("images/left.png");//获取蛇头向左图片URL地址
public static ImageIcon left=new ImageIcon(leftURL);//新增蛇头向左图片按钮
public static URL rightURL=GameResource.class.getResource("images/right.png");//获取蛇头向右图片URL地址
public static ImageIcon right=new ImageIcon(rightURL);//新增蛇头向右图片按钮
public static URL bodyURL=GameResource.class.getResource("images/body.png");//获取蛇身体图片URL地址
public static ImageIcon body=new ImageIcon(bodyURL);//新增蛇身体图片按钮
public static URL foodURL=GameResource.class.getResource("images/food.png");//获取食物图片URL地址
public static ImageIcon food=new ImageIcon(foodURL);//新增食物图片按钮
}
3.3、运行结果(Run Result)
其运行结果,如下图所示。