• 第十七章、GUI编程


    GUI编程

    1. GUI(图形用户界面)

    • GUI:Graphical User Interface(图形用户接口)。
      • 用图形的方式,来显示计算机操作的界面,这样使得界面更加美观
    • CLI:Command line User Interface (命令行用户接口)
      • 常用的是Dos命令行操作,需要记忆一些常用的命令,操作不方便
    • 举例
      • 创建文件夹,删除文件夹等

    2. AWT和swing包的概述

    • AWT:Abstract Window ToolKit (抽象窗口工具包),需要调用本地系统方法实现功能,属重量级控件。
      • 控件:窗口、弹窗、面板、文本框、列表框、按钮、图片、监听事件、鼠标监听、键盘监听
    • Swing:在AWT的基础上,建立的一套图形界面系统,其中提供了更多的组件,而且完全由Java实现。增强了移植性,属轻量级控件
      • 控件:窗口、弹窗、面板、文本框、列表框、按钮、图片、监听事件、鼠标监听、键盘监听

    3. GUI继承体系图

    img

    4. AWT包

    4.1 Frame窗体

    • setVisible(boolean b):设置窗体可见与否

    • setSize(int x,int y):设置窗体大小

    • setLocation((int x,int y):设置窗体在屏幕上显示的位置

    • setBackground(Color color):设置窗体背景颜色

    • setTitle(String title):设置窗体的名称

    • setBounds(int x, int y, int width, int height):设置窗体大小、和屏幕上显示的位置

    • pack():窗体自动适应屏幕

    • setLayout():设置窗体的布局样式

    • setResizable(boolean b):设置窗口大小固定

    • 示例代码

      package FrameDemo;
      
      import java.awt.Color;
      import java.awt.Frame;
      
      public class TestFrame {
      	public static void main(String[] args) {
      
      		Frame frame = new Frame("我的第一个Java图形界面");
      		
              // 设置窗体的名称
              frame.setTitle("我的第一个Java图形界面");
              
      		// 要设置可见 true false
      		frame.setVisible(true);
      
      		// 设置窗口大小
      		frame.setSize(400, 400);
      		// 弹框的初始位置
      		frame.setLocation(200, 200);
              // 上述两个方法相当于下面这个方法
              frame.setBouns(200,200,400,400);
              
      		// 设置窗口背景颜色
      		frame.setBackground(Color.BLUE);
      	}
      }
      
      
    • 效果图

      image-20201221193429320

    4.2 面板Panel

    • setSize(int x,int y):设置面板大小,相对于窗体来说的

    • setLocation((int x,int y):设置面板在屏幕上显示的位置,相对于窗体来说的

    • setBackground(Color color):设置面板背景颜色

    • setBounds(int x, int y, int width, int height):设置面板大小、和屏幕上显示的位置,相对于窗体来说的

    • setLayout():设置面板的布局样式

    • 示例代码

      package PanelDemo;
      
      import java.awt.Color;
      import java.awt.Frame;
      import java.awt.Panel;
      import java.awt.event.WindowAdapter;
      import java.awt.event.WindowEvent;
      
      // Panel可以看做一个空间,但是不能单独使用
      public class TestPanel {
      	public static void main(String[] args) {
      		Frame frame = new Frame("我的第一个Java图像化界面");
      		// Panel布局的概念
      		Panel panel = new Panel();
      		// frame设置布局
      		frame.setLayout(null);
      		
      		frame.setBounds(300, 300, 500, 500);
      		frame.setBackground(new Color(40,161,35));
      		
      		// Panel社会自己坐标,相对于frame 
      		panel.setBounds(50, 50, 400, 400);
      		panel.setBackground(Color.red);
      		panel.setVisible(true);
      		
      		frame.add(panel);
      		frame.setVisible(true);
             
      		// 监听事件,监听窗口关闭事件  System.exit(0)
      		// 适配器模式
      		frame.addWindowListener(new WindowAdapter() {
      			
      			// 窗口点击关闭的时候需要做的是事情
      			@Override
      			public void windowClosing(WindowEvent e) {
      				System.exit(0);
      			}
      		});
      	}
      }
      
    • 效果图

      image-20201221193547302

    4.3 布局管理器Layout

    1. 流式布局FLowLayout

      • 布局规则:将容器中的组件按照加入的先后顺序从左向右排列,如果一行排满转下一行继续,每行均采取居中排列。

      • 代码示例

        package LayoutDemo;
        
        import java.awt.Button;
        import java.awt.Color;
        import java.awt.FlowLayout;
        import java.awt.Frame;
        
        public class TestFlowLayout {
        	public static void main(String[] args) {
        		Frame frame = new Frame();
        		Button button1 = new Button("按钮一");
        		Button button2 = new Button("按钮二");
        		Button button3 = new Button("按钮三");
        		Button button4 = new Button("按钮一");
        		Button button5 = new Button("按钮二");
        		Button button6 = new Button("按钮三");
        		Button button7 = new Button("按钮一");
        		Button button8 = new Button("按钮二");
        		Button button9 = new Button("按钮三");
        		frame.setLayout(new FlowLayout(FlowLayout.LEFT));
        		
        		frame.setBounds(100, 100, 200, 200);
        		
        		frame.setBackground(Color.blue);
        		
        		frame.add(button1);
        		frame.add(button2);
        		frame.add(button3);
        		frame.add(button4);
        		frame.add(button5);
        		frame.add(button6);
        		frame.add(button7);
        		frame.add(button8);
        		frame.add(button9);
        		frame.setVisible(true);
        	}
        }
        
      • 效果图

        image-20201221193737461
    2. 边界式布局BorderLayout

      • 布局规则:把容器内的空间划分为东(EAST)、西(WEST)、南(SOUTH)、北(NORTH)、中(CENTER)5个区域分别用英文的East、 West、 South、 North、Center表示,向容器中加入每个组件都要指明在容器的区域。

      • 示例代码

        package LayoutDemo;
        
        import java.awt.BorderLayout;
        import java.awt.Button;
        import java.awt.Color;
        import java.awt.Frame;
        
        public class TestBorderLayout {
        	public static void main(String[] args) {
        		Frame frame = new Frame();
        		
        		Button east = new Button("East");
        		Button west = new Button("Wast");
        		Button south = new Button("South");
        		Button north = new Button("North");
        		Button center = new Button("Center");
        		
        		frame.setLayout(new BorderLayout());
        		frame.setBounds(100, 100, 500, 500);
        		
        		frame.setBackground(Color.BLUE);
        		
        		frame.add(east,BorderLayout.EAST);		
        		frame.add(west,BorderLayout.WEST);		
        		frame.add(south,BorderLayout.SOUTH);		
        		frame.add(north,BorderLayout.NORTH);		
        		frame.add(center,BorderLayout.CENTER);
        		
        		frame.setVisible(true);
        	}
        }
        
      • 效果图

        image-20201221194003371

    3. 方格式布局GridLayout

      • 布局规则:把容器划分成若干行乘若干列的网格区域,组件就位于这些划分出来的小格中。

      • 示例代码

        package LayoutDemo;
        
        import java.awt.Button;
        import java.awt.Frame;
        import java.awt.GridLayout;
        
        public class TestGridLayout {
        	public static void main(String[] args) {
        		Frame frame = new Frame();
        		
        		Button btn1 = new Button("btn1");
        		Button btn2 = new Button("btn2");
        		Button btn3 = new Button("btn3");
        		Button btn4 = new Button("btn4");
        		Button btn5 = new Button("btn5");
        		Button btn6 = new Button("btn6");
        		
        		frame.setLayout(new GridLayout(3,2));
        		
        		frame.add(btn1);
        		frame.add(btn2);
        		frame.add(btn3);
        		frame.add(btn4);
        		frame.add(btn5);
        		frame.add(btn6);
        		
        		frame.pack();
        		frame.setVisible(true);
        	}
        }
        
      • 效果图

        image-20201221194331659

    4. 作业:实现下列布局

      • 操作一:

        • 效果图

        image-20201221194831780

        • 示例代码

          package LayoutDemo;
          
          import java.awt.BorderLayout;
          import java.awt.Button;
          import java.awt.Frame;
          import java.awt.GridLayout;
          import java.awt.Panel;
          import java.awt.event.WindowAdapter;
          import java.awt.event.WindowEvent;
          
          /*实现下面的布局:
           * 		-----------------------------
           * 		|	|					|	|
           * 		|	|-------------------|	|
           * 		|	|					|	|
           * 		|---------------------------|
           * 		|	|		 |    		|	|
           * 		|   ---------------------   |
           * 		|	|		 |    		|	|
           * 		-----------------------------
           * 
           */
          public class HomeWork {
          	public static void main(String[] args) {
          		// 创建一个窗口
          		Frame frame = new Frame();
          		// 设置窗口的长宽
          		frame.setSize(400, 300);
          		// 设置窗口的位置
          		frame.setLocation(200, 200);
          		// 设置窗口的布局样式----->东西南北中布局
          		frame.setLayout(new GridLayout(2,1));
          		// 设置窗口可见
          		frame.setVisible(true);
          		
          		// 创建四个面板   
          		// p1、p3---->frame中的面板
          		// p2、p4---->分别为p1、p3中的面板
          		Panel p1 = new Panel(new BorderLayout());
          		Panel p2 = new Panel(new GridLayout(2,1));
          		Panel p3 = new Panel(new BorderLayout());
          		Panel p4 = new Panel(new GridLayout(2,2));
          		
          		// p1中左边的按钮
          		p1.add(new Button("btn-west-1"),BorderLayout.WEST);
          		// p1中右边的按钮
          		p1.add(new Button("btn-east-1"),BorderLayout.EAST);
          		// p1中的中间的面板p2
          		p1.add(p2,BorderLayout.CENTER);
          		// p2中上面的按钮
          		p2.add(new Button("p2-center-top"),BorderLayout.NORTH);
          		// p2中下面的按钮
          		p2.add(new Button("p2-center-bottom"),BorderLayout.SOUTH);
          
          		
          		
          		// p3中左边的按钮
          		p3.add(new Button("btn-west-2"),BorderLayout.WEST);
          		// p3中右边的按钮
          		p3.add(new Button("btn-east-2"),BorderLayout.EAST);
          		// p3中的中间的面板p4
          		p3.add(p4,BorderLayout.CENTER);
          		// 循环向p4中添加按钮
          		for (int i = 0; i < 4; i++) {
          			p4.add(new Button("p4-"+i));
          		}
          		
          		// 将p1、p3添加到frame中
          		frame.add(p1);
          		frame.add(p3);
          		
          		// 设置监听
          		frame.addWindowListener(new WindowAdapter() {
          			@Override
          			public void windowClosing(WindowEvent e) {
          				System.exit(0);
          			}
          		});
          	}
          }
          
      • 操作二:

        • 效果图

          image-20201221195854802

        • 示例代码

          package TextFieldDemo;
          
          import java.awt.BorderLayout;
          import java.awt.Button;
          import java.awt.Frame;
          import java.awt.GridLayout;
          import java.awt.Panel;
          import java.awt.TextField;
          import java.awt.event.ActionEvent;
          import java.awt.event.ActionListener;
          import java.awt.event.WindowAdapter;
          import java.awt.event.WindowEvent;
          
          public class HomeWorkDemo {
          	public static void main(String[] args) {
          		Frame frame = new Frame("简易计算器");
          		frame.setLayout(new BorderLayout(3,1));
          		
          		TextField textField = new TextField();
          		Panel panel = new Panel(new GridLayout(4,4));
          		
          		// 创建ActionListener对象
          		MyActionListener1 myActionListener1 = new MyActionListener1(textField);
          		
          		
          		// 创建计算器的按钮
          		Button btn_1 = new Button("1");
          		Button btn_2 = new Button("2");
          		Button btn_3 = new Button("3");
          		Button btn_4 = new Button("4");
          		Button btn_5 = new Button("5");
          		Button btn_6 = new Button("6");
          		Button btn_7 = new Button("7");
          		Button btn_8 = new Button("8");
          		Button btn_9 = new Button("9");
          		Button btn_0 = new Button("0");
          		Button btn_jia = new Button("+");
          		Button btn_jian = new Button("-");
          		Button btn_chen = new Button("*");
          		Button btn_chu = new Button("/");
          		Button btn_deng = new Button("=");
          		Button btn_dian = new Button(".");
          		
          		// 将计算器的按钮添加到panel面板中
          		panel.add(btn_1);
          		panel.add(btn_2);
          		panel.add(btn_3);
          		panel.add(btn_jia);
          		panel.add(btn_4);
          		panel.add(btn_5);
          		panel.add(btn_6);
          		panel.add(btn_jian);
          		panel.add(btn_7);
          		panel.add(btn_8);
          		panel.add(btn_9);
          		panel.add(btn_chen);
          		panel.add(btn_dian);
          		panel.add(btn_0);
          		panel.add(btn_deng);
          		panel.add(btn_chu);
          		
          		// 给按钮绑定点击事件
          		btn_1.addActionListener(myActionListener1);
          		btn_2.addActionListener(myActionListener1);
          		btn_3.addActionListener(myActionListener1);
          		btn_4.addActionListener(myActionListener1);
          		btn_5.addActionListener(myActionListener1);
          		btn_6.addActionListener(myActionListener1);
          		btn_7.addActionListener(myActionListener1);
          		btn_8.addActionListener(myActionListener1);
          		btn_9.addActionListener(myActionListener1);
          		btn_0.addActionListener(myActionListener1);
          		btn_jia.addActionListener(myActionListener1);
          		btn_jian.addActionListener(myActionListener1);
          		btn_chen.addActionListener(myActionListener1);
          		btn_chu.addActionListener(myActionListener1);
          		btn_deng.addActionListener(myActionListener1);
          		btn_dian.addActionListener(myActionListener1);
          		
          		
          		frame.add(textField,BorderLayout.NORTH);
          		frame.add(panel,BorderLayout.SOUTH);
          		
          		frame.pack();
          		ActionClose(frame);
          		frame.setVisible(true);
          		
          	}
          	
          	// 监听关闭窗口事件
          	private static void ActionClose(Frame frame){
          		frame.addWindowListener(new WindowAdapter() {
          
          			@Override
          			public void windowClosing(WindowEvent e) {
          				System.exit(0);
          			}
          		});
          	}
          }
          }
          

    4.4 上述总结

    • Frame是一个顶级窗口。

    • Panel无法单独显示,必须添加到某个容器中。

    • 布局管理器

      • 流式布局
      • 边界式布局
      • 方格式布局
    • 大小,定位,背景颜色,定位,监听。

    4.5 画笔Paint

    package PaintDemo;
    
    import java.awt.Color;
    import java.awt.Frame;
    import java.awt.Graphics;
    
    public class TestPaint {
    	public static void main(String[] args) {
    		new MyPaint().loadFrame();
    	}
    }
    
    class MyPaint extends Frame{
    	public void loadFrame(){
    		setBounds(200,200,600,500);
    		setVisible(true);
    	}
    	// 画笔
    	@Override
    	public void paint(Graphics g) {
    		// 画笔,需要有颜色,画笔可以画画
    		g.setColor(Color.red);
    		g.drawOval(100, 100, 100, 100);
    		
    		g.fillOval(100, 100, 100, 100); // 实心的圆
    		
    		g.setColor(Color.GREEN);
    		g.fillRect(150,200, 200, 200);
    		
    		// 养成习惯,画笔用完,将他还原到最初的颜色
    		g.setColor(Color.BLACK);
    	}	
    }
    

    image-20201221204508064

    4.6 事件监听ActionListener

    4.6.1 事件监听:当某个时候,触发器被触发而做出的反应

    package ActionDemo;
    
    import java.awt.BorderLayout;
    import java.awt.Button;
    import java.awt.Frame;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import java.awt.event.WindowAdapter;
    import java.awt.event.WindowEvent;
    
    public class TestActionEvent {
    	public static void main(String[] args) {
    		// 按下按钮,触发一些事件
    		Frame frame = new Frame();
    		Button button = new Button();
    		// 因为,addActionListener()需要一个ActionListener对象,所以我们需要构架一个ActionListener的实现类(ActionListener是一个接口)
    		MyActionListener myActionListener = new MyActionListener();
    		
    		button.addActionListener(myActionListener);
    		
    		frame.add(button,BorderLayout.CENTER);
    		frame.pack();
    		
    		WindowClose(frame); // 关闭窗口
    		frame.setVisible(true);
    	}
    	
    	// 关闭窗口事件
    	private static void WindowClose(Frame frame){
    		frame.addWindowListener(new WindowAdapter() {
    
    			@Override
    			public void windowClosing(WindowEvent e) {
    				// TODO Auto-generated method stub
    				System.exit(0);
    			}
    			
    		});
    	}
    }
    
    // 事件监听
    class MyActionListener implements ActionListener{
    
    	@Override
    	public void actionPerformed(ActionEvent e) {
    		System.out.println("aaa");
    	}
    }
    

    image-20201221201046749

    4.6.2 多个按钮共用一个监听器

    package ActionDemo;
    
    import java.awt.BorderLayout;
    import java.awt.Button;
    import java.awt.Frame;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import java.awt.event.WindowAdapter;
    import java.awt.event.WindowEvent;
    
    public class TestActionEvent2 {
    	public static void main(String[] args) {
    		// 两个按钮,实现同一个监听
    		// 开始      停止
    		Frame frame = new Frame();
    		frame.setLayout(new BorderLayout(3,1));
    		Button button1 = new Button("start");
    		Button button2 = new Button("stop");
    		
    		MyActionListener1 myActionListener1 = new MyActionListener1();
    		
    		button1.addActionListener(myActionListener1);
    		button2.addActionListener(myActionListener1);
    		
    		// button1.setActionCommand("btn_one");
    		
    		frame.add(button1,BorderLayout.NORTH);
    		frame.add(button2,BorderLayout.SOUTH);
    		
    		frame.pack();
    		
    		WindowClose(frame); // 关闭窗口
    		frame.setVisible(true);
    	}
    	
    	// 关闭窗口事件
    	private static void WindowClose(Frame frame){
    		frame.addWindowListener(new WindowAdapter() {
    
    			@Override
    			public void windowClosing(WindowEvent e) {
    				// TODO Auto-generated method stub
    				System.exit(0);
    			}
    		});
    	}
    }
    
    // 事件监听
    class MyActionListener1 implements ActionListener{
    	@Override
    	public void actionPerformed(ActionEvent e) {
    		// 功能实现的关键
            if(e.getActionCommand().equals("start")){
    			System.out.println("开始啦!");
    		}else {
    			System.out.println("结束啦!");
    			System.exit(0);
    		}
    	}
    }
    

    image-20201221201438130

    按下stop键,窗口就会消失

    4.6.3 输入框监听TextField

    package TextFieldDemo;
    
    import java.awt.Frame;
    import java.awt.TextField;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    
    public class TestTextField {
    	public static void main(String[] args) {
    		// 开启窗口 
    		new MyFrame();
    	}
    }
    class MyFrame extends Frame{
    	public MyFrame(){
    		TextField textField = new TextField();
    		add(textField);
    		// 监听这个文本框输入的内容
    		MyActionListener myActionListener = new MyActionListener();
    		// 按下enter 就会触发这个输入框的事件
    		textField.addActionListener(myActionListener);
    		
    		// 设置替换代码,将文本框中输入的文字替换成*
    		textField.setEchoChar('*');
    		pack();
    		setVisible(true);
    		
    	}
    }
    class MyActionListener implements ActionListener{
    	@Override
    	public void actionPerformed(ActionEvent e) {
    		// 获得一些资源,返回的是该调用者的对象
    		TextField textField = (TextField) e.getSource();
    		// 获得输入框中的文本
    		System.out.println(textField.getText());
    		// 下次再次输入,文框中的文字就会消失
    		textField.setText("");
    	}
    }
    

    image-20201221201627544

    4.6.4 作业:简易计算器

    image-20201221202108941

    1. 面条版代码

      package TextFieldDemo;
      
      import java.awt.Button;
      import java.awt.FlowLayout;
      import java.awt.Frame;
      import java.awt.Label;
      import java.awt.TextField;
      import java.awt.event.ActionEvent;
      import java.awt.event.ActionListener;
      import java.awt.event.WindowAdapter;
      import java.awt.event.WindowEvent;
      
      /*
       * 改进版的计算器
       * 	效果图:
       *	     -----	   -----     -----------
       *	   	|  1  | + |  2  | = |     3     |
       *	  	 -----     -----     -----------
       */
      public class HomeWorkPlusOne {
      	public static void main(String[] args) {
      		
      		new Calculator();
      		
      	}
      }
      
      // 简易计算器类
      class Calculator extends Frame{
      	public Calculator(){
      		// 三个文本框 1、2、3
      		TextField textField1 = new TextField(10);
      		TextField textField2 = new TextField(10);
      		TextField textField3 = new TextField(20);
      		// 一个标签 +
      		Label label = new Label("+");
      		// 一个按钮 =
      		Button button = new Button("=");
      		button.addActionListener(new MyCalculatorListener1(textField1, textField2, textField3));
      		
      		setLayout(new FlowLayout());
      		add(textField1);
      		add(label);
      		add(textField2);
      		add(button);
      		add(textField3);
      
      		pack();		
      		setVisible(true);
      		
      		WindowClosed(this);
      	}
      	
      	public static void WindowClosed(Calculator calculator){
      		calculator.addWindowListener(new WindowAdapter() {
      			@Override
      			public void windowClosing(WindowEvent e) {
      				System.exit(0);
      			}
      		});
      	}
      }
      
      // 监听器类
      class MyCalculatorListener1 implements ActionListener{
      	// 获取三个变量
      	private TextField textField1,textField2,textField3;
      
      	public MyCalculatorListener1(TextField textField1,TextField textField2,TextField textField3) {
      		this.textField1 = textField1;
      		this.textField2 = textField2;
      		this.textField3 = textField3;
      	}
      	
      	@Override
      	public void actionPerformed(ActionEvent e) {
      		// 1.获取加数和被加数
      		int num1 = Integer.parseInt(textField1.getText());
      		int num2 = Integer.parseInt(textField2.getText());
      		
      		// 2.将加数和被加数进行+法运算后,放到第三个框中
      		textField3.setText(""+(num1+num2));
      		
      		// 3.清除前两个框中的数据
      		textField1.setText("");
      		textField2.setText("");
      	}
      }
      
    2. 面向对象版

      package TextFieldDemo;
      
      import java.awt.Button;
      import java.awt.FlowLayout;
      import java.awt.Frame;
      import java.awt.Label;
      import java.awt.TextField;
      import java.awt.event.ActionEvent;
      import java.awt.event.ActionListener;
      import java.awt.event.WindowAdapter;
      import java.awt.event.WindowEvent;
      
      /*
       * 全部面向对象版
       * 	效果图:
       *	     -----	   -----     -----------
       *	   	|  1  | + |  2  | = |     3     |
       *	  	 -----     -----     -----------
       */
      
      // 简易计算器
      public class HomeWorkPlusTwo {
      	public static void main(String[] args) {
      		new Calculator().loadFrame();
      	}
      }
      
      // 简易计算器类
      class Calculator extends Frame{
      	
      	TextField textField1,textField2,textField3;
      
      	public void loadFrame(){
      		
      		textField1 = new TextField(10);
      		textField2 = new TextField(10);
      		textField3 = new TextField(20);
      		
      		Label label = new Label("+");
      		Button button = new Button("=");
      		button.addActionListener(new MyCalculatorListener2(this));
      		
      		setLayout(new FlowLayout());
      		add(textField1);
      		add(label);
      		add(textField2);
      		add(button);
      		add(textField3);
      
      		pack();		
      		setVisible(true);
      		
      		WindowClosed(this);
      	}
      	
      	public static void WindowClosed(Calculator calculator){
      		calculator.addWindowListener(new WindowAdapter() {
      			@Override
      			public void windowClosing(WindowEvent e) {
      				System.exit(0);
      			}
      		});
      	}
      }
      
      //监听器类
      class MyCalculatorListener2 implements ActionListener{
      	private Calculator calculator = null;
      
      	public MyCalculatorListener2(Calculator calculator) {
      		this.calculator = calculator;
      	}
      
      	@Override
      	public void actionPerformed(ActionEvent e) {
      		// 1.获取加数和被加数
      		int num1 = Integer.parseInt(calculator.textField1.getText());
      		int num2 = Integer.parseInt(calculator.textField2.getText());
      		
      		// 2.将加数和被加数进行+法运算后,放到第三个框中
      		calculator.textField3.setText(""+(num1+num2));
      		
      		// 3.清除前两个框中的数据
      		calculator.textField1.setText("");
      		calculator.textField2.setText("");
      	}
      }
      
    3. 内部类版

      package TextFieldDemo;
      
      import java.awt.Button;
      import java.awt.FlowLayout;
      import java.awt.Frame;
      import java.awt.Label;
      import java.awt.TextField;
      import java.awt.event.ActionEvent;
      import java.awt.event.ActionListener;
      import java.awt.event.WindowAdapter;
      import java.awt.event.WindowEvent;
      
      /*
       * 内部类版
       * 	效果图:
       *	     -----	   -----     -----------
       *	   	|  1  | + |  2  | = |     3     |
       *	  	 -----     -----     -----------
       */
      
      // 简易计算器
      public class HomeWorkPlusThree {
      	public static void main(String[] args) {
      		new Calculator().loadFrame();
      	}
      }
      
      // 简易计算器类
      class Calculator extends Frame{
      	// 属性
      	TextField textField1,textField2,textField3;
      	// 方法
      	public void loadFrame(){
      		
      		textField1 = new TextField(10); // 字符数 
      		textField2 = new TextField(10); // 字符数
      		textField3 = new TextField(20); // 字符数
      		
      		Label label = new Label("+");
      		Button button = new Button("=");
      		button.addActionListener(new MyCalculatorListener3());
      		
      		setLayout(new FlowLayout());
      		add(textField1);
      		add(label);
      		add(textField2);
      		add(button);
      		add(textField3);
      
      		pack();		
      		setVisible(true);
      		
      		WindowClosed(this);
      	}
      	// 关闭窗口监听事件
      	public static void WindowClosed(Calculator calculator){
      		calculator.addWindowListener(new WindowAdapter() {
      			@Override
      			public void windowClosing(WindowEvent e) {
      				System.exit(0);
      			}
      		});
      	}
      	// 内部类--->监听器类
      	class MyCalculatorListener3 implements ActionListener{
      		@Override
      		public void actionPerformed(ActionEvent e) {
      			// 1.获取加数和被加数
      			int num1 = Integer.parseInt(textField1.getText());
      			int num2 = Integer.parseInt(textField2.getText());
      			
      			// 2.将加数和被加数进行+法运算后,放到第三个框中
      			textField3.setText(""+(num1+num2));
      			
      			// 3.清除前两个框中的数据
      			textField1.setText("");
      			textField2.setText("");
      		}
      	}
      }
      

    image-20201221202428443

    image-20201221202511404

    image-20201221202539380

    4.7 窗口监听Window

    package ListenerDemo;
    
    import java.awt.Color;
    import java.awt.Frame;
    import java.awt.event.WindowAdapter;
    import java.awt.event.WindowEvent;
    
    /*
     * 窗口监听事件
     */
    public class TestWindowListener {
    	public static void main(String[] args) {
    		new MyWindowFrame();
    	}
    }
    class MyWindowFrame extends Frame{
    	public MyWindowFrame(){
    		setBounds(100, 100, 300, 300);
    		setBackground(Color.blue);
    		setVisible(true);
    		// 匿名内部类版
    		this.addWindowListener(new WindowAdapter() {
    			// 关闭窗口事件
    			@Override
    			public void windowClosing(WindowEvent e) {
    				MyWindowFrame frame = (MyWindowFrame) e.getSource();
    				// frame.setVisible(false); // 设置窗口隐藏
    				System.out.println("窗口关闭了");
    				System.exit(0);
    			}
    			// 窗口激活事件
    			@Override
    			public void windowActivated(WindowEvent e) {
    				MyWindowFrame frame = (MyWindowFrame) e.getSource();
    				frame.setTitle("窗口激活了");
    			}
    		});
    	}
    }
    // 内部类版
    class MyWindowListener extends WindowAdapter{
    	// 关闭窗口事件
    	@Override
    	public void windowClosing(WindowEvent e) {
    		MyWindowFrame frame = (MyWindowFrame) e.getSource();
    		// frame.setVisible(false);
    		System.out.println("窗口关闭了");
    		System.exit(0);
    	}
    	// 激活窗口事件
    	@Override
    	public void windowActivated(WindowEvent e) {
    		MyWindowFrame frame = (MyWindowFrame) e.getSource();
    		frame.setTitle("窗口激活了");
    	}
    }
    

    初始状态

    image-20201221203718437

    触发后状态

    image-20201221203837783

    4.8 键盘监听Key

    package ListenerDemo;
    
    import java.awt.Frame;
    import java.awt.event.KeyAdapter;
    import java.awt.event.KeyEvent;
    
    public class TestKeyListener {
    	public static void main(String[] args) {
    		new KeyFrame();
    	}
    }
    
    class KeyFrame extends Frame{
    	public KeyFrame(){
    		setBounds(100,100,400,400);
    		setVisible(true);
    		this.addKeyListener(new KeyAdapter() {
    			// 键盘按下监听事件
    			@Override
    			public void keyPressed(KeyEvent e) {
    				// 获得键盘按下的键是一个
    				int keyCode = e.getKeyCode();
    				System.out.println(e.getKeyCode());
    				if(keyCode == KeyEvent.VK_UP){
    					System.out.println("你按下了上键");
    				}
    			}
    		});
    	}
    }
    

    image-20201221204135571

    4.9 鼠标监听Mouse

    package ListenerDemo;
    
    import java.awt.Color;
    import java.awt.Frame;
    import java.awt.Graphics;
    import java.awt.Point;
    import java.awt.event.MouseAdapter;
    import java.awt.event.MouseEvent;
    import java.util.ArrayList;
    import java.util.Iterator;
    
    /*
     * 鼠标监听事件
     */
    public class TestMouseListener {
    	public static void main(String[] args) {
    		new MyFrame("画图");
    	}
    }
    
    // 自己的类
    class MyFrame extends Frame{
    	// 画画需要画笔,需要监听鼠标当前的位置,需要集合来存储这个点
    	private ArrayList points;
    	
    	public MyFrame(String name){
    		super(name);
    		setBounds(100, 100, 500, 400);
    		// 存鼠标点击的点
    		points = new ArrayList<>();
    		
    		setVisible(true);
    		// 鼠标监听器,针对当前这个窗口
    		this.addMouseListener(new MyMouseListener());
    	}
    	
    	@Override
    	public void paint(Graphics g) {
    		// 画画,监听鼠标的事件
    		Iterator iterator = points.iterator();
    		while(iterator.hasNext()){
    			Point point = (Point) iterator.next();
    			g.setColor(Color.BLUE);
    			g.fillOval(point.x, point.y, 10, 10);
    		}
    	}
    	
    	// 添加一个点到界面上
    	public void addPoint(Point point){
    		points.add(point);
    	}
    	
    	// 适配器模式
    	private class MyMouseListener extends MouseAdapter{
    		// 鼠标按下、弹起、按住不放
    		@Override
    		public void mousePressed(MouseEvent e) {
    			MyFrame frame = (MyFrame) e.getSource();
    			// 我们点击的时候,就会在页面上产生一个点
    			// 这个点就是鼠标的点
    			frame.addPoint(new Point(e.getX(),e.getY()));
    			
    			// 每次点击鼠标都需要重新画一遍
    			frame.repaint(); // 刷新
    		}
    	}
    }
    

    repaint():在类Container及其子类(如:Frame,Panel)的对象需要重绘repaint时,JVM会自动调用它的public void paint(Graphics g)方法。

    image-20201221204254681

    代码思路

    image-20201222110632124

    5.Swing包

    5.1 窗口JFrame

    • 概念:java的GUI程序的基本思路是以JFrame为基础,它是屏幕上window的对象,能够最大化、最小化、关闭。

    • 代码实现1

      package JFrameDemo;
      
      import java.awt.Color;
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.JLabel;
      import javax.swing.WindowConstants;
      
      public class JFrameDemoOne {
      	// 初始化
      	private void init() {
      		// JFrame是一个顶级窗口
      		JFrame jf = new JFrame("这是一个JFrame窗口");
      		jf.setVisible(true);
      		jf.setBounds(100,100,400,400);
      
      		jf.setBackground(Color.BLUE); // 这样设置不生效
      		// 获得该窗口容器,只有给该窗口容器才能设置背景色    container包含JFrame
      		Container container = jf.getContentPane();
      		container.setBackground(Color.CYAN);
      
      		// 设置文字JLabel
      		JLabel label = new JLabel("欢迎来到GUI编程之Swing");
      		
      		jf.add(label);
      
      		// 关闭窗口事件
      		jf.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	
      	public static void main(String[] args) {
      		// 建立一个窗口
      		new JFrameDemoOne().init();
      	}
      }
      
    • 效果图1

      image-20201223105923796

    • 代码实现2:文本居中,窗口背景

      package JFrameDemo;
      
      import java.awt.Color;
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.JLabel;
      import javax.swing.SwingConstants;
      import javax.swing.WindowConstants;
      
      public class JFrameDemoTwo {
      	public static void main(String[] args) {
      		new MyJFrame().init();
      	}
      }
      class MyJFrame extends JFrame{
      	public void init(){
      		// 设置窗口大小位置
      		this.setBounds(100,100,400,400);
      		// 获取该窗口容器,并设置背景色
      		Container container = this.getContentPane();
      		container.setBackground(Color.cyan);
      		// 设置窗口可见
      		this.setVisible(true);
      		// 关闭窗口事件。直接使用JFrame封装好的
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      		
      		JLabel jlabel = new JLabel("欢迎来到GUI编程之Swing");
      		// 设置文本标签居中SwingConstants
      		jlabel.setHorizontalAlignment(SwingConstants.CENTER);
      	
      		this.add(jlabel);
      	}
      }
      
    • 效果图2

      image-20201223110120728

    5.2 弹窗JDialog

    • 概念:JDialog,用来弹出窗口(报错界面等等)

    • 注意:其自带关闭事件(不需要在写关闭事件)

    • 代码实现

      package DialogDemo;
      
      import java.awt.Container;
      import java.awt.Label;
      import java.awt.event.ActionEvent;
      import java.awt.event.ActionListener;
      
      import javax.swing.JButton;
      import javax.swing.JDialog;
      import javax.swing.JFrame;
      import javax.swing.WindowConstants;
      
      public class DialogDemoOne extends JFrame{
      	public DialogDemoOne(){
      		
      		this.setVisible(true);
      		this.setBounds(100,100,400,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      		
      		// JFrame  放东西,容器
      		Container container = this.getContentPane();
      		// 绝对布局
      		container.setLayout(null);
      		
      		// 创建按钮
      		JButton button = new JButton("点击弹出一个对话框");
      		button.setBounds(30,30,200,50);
      	
      		// 点击这个按钮的时候,踏出一个对话框
      		button.addActionListener(new ActionListener() { // 监听器
      			
      			@Override
      			public void actionPerformed(ActionEvent e) {
      				// 弹窗
      				new MyDialog();
      			}
      		});
      	
      		container.add(button);
      	}
      	public static void main(String[] args) {
      		new DialogDemoOne();
      	}
      }
      // 弹窗的窗口
      class MyDialog extends JDialog{
      	public MyDialog(){
      		this.setVisible(true);
      		this.setBounds(100,100,500,500);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      		
      		Container container = this.getContentPane();
      		container.setLayout(null);
      		container.add(new Label("小骚老师带你学java"));
      	}
      }
      
    • 效果图

      image-20201223110410513

      image-20201223110556555

    5.3 面板JPanel

    • 概念:Java图形用户界面(GUI)工具包swing中的面板容器类,包含在javax.swing 包中,可以进行嵌套,功能是对窗体中具有相同逻辑功能的组件进行组合,是一种轻量级容器,可以加入到JFrame窗体中。

    • 代码实现(普通面板)

      package JPanelDemo;
      
      import java.awt.Button;
      import java.awt.Container;
      import java.awt.GridLayout;
      
      import javax.swing.JFrame;
      import javax.swing.JPanel;
      import javax.swing.WindowConstants;
      
      /*
       * 普通面板
       */
      public class JPanelDemoOne extends JFrame{
      	public JPanelDemoOne(){
      		Container container = this.getContentPane();
      		
      		container.setLayout(new GridLayout(2,1,10,10)); // 后面的参数的意思是,间距
      		
      		JPanel panel1 = new JPanel(new GridLayout(1,3));
      		JPanel panel2 = new JPanel(new GridLayout(2,1));
      		JPanel panel3 = new JPanel(new GridLayout(2,2));
      		JPanel panel4 = new JPanel(new GridLayout(3,2));
      
      		panel1.add(new Button("1"));
      		panel1.add(new Button("1"));
      		panel1.add(new Button("1"));
      		panel2.add(new Button("2"));
      		panel2.add(new Button("2"));
      		panel3.add(new Button("3"));
      		panel3.add(new Button("3"));
      		panel3.add(new Button("3"));
      		panel3.add(new Button("3"));
      		panel4.add(new Button("4"));
      		panel4.add(new Button("4"));
      		panel4.add(new Button("4"));
      		panel4.add(new Button("4"));
      		panel4.add(new Button("4"));
      		panel4.add(new Button("4"));
      		
      		container.add(panel1);
      		container.add(panel2);
      		container.add(panel3);
      		container.add(panel4);
      		
      		this.setVisible(true);
      		this.setSize(500,500);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	
      	public static void main(String[] args) {
      		new JPanelDemoOne();
      	}
      }
      
    • 效果图(普通面板)

      image-20201223170202493

    • 代码示例(滚动面板)JScrollPane

      package JPanelDemo;
      
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.JScrollPane;
      import javax.swing.JTextArea;
      import javax.swing.WindowConstants;
      
      /*
       * 滚动面板
       */
      public class JPanelDemoTwo extends JFrame{
      	
      	public JPanelDemoTwo(){
      		Container container = this.getContentPane();
      		
      		// 文本域
      		JTextArea textArea = new JTextArea(20,50);
      		textArea.setText("欢迎学习GUI之Swing编程");
      		
      		// Scroll面板
      		JScrollPane scrollPane = new JScrollPane(textArea);
      		container.add(scrollPane);
      		
      		this.setVisible(true);
      		this.setBounds(100,100,300,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	
      	public static void main(String[] args) {
      		new JPanelDemoTwo();
      	}
      }
      
    • 效果图(滚动面板)

      image-20201223170327415

    5.4 按钮JButton

    • 概念: JButton 类的实例。用于创建按钮类似实例中的 "Login"。

    5.4.1 图片按钮ImageIcon

    • 代码示例

      package JButtonDemo;
      
      import java.awt.Container;
      import java.net.URL;
      
      import javax.swing.ImageIcon;
      import javax.swing.JButton;
      import javax.swing.JFrame;
      import javax.swing.WindowConstants;
      
      /*
       * 图片按钮
       */
      public class JButtonDemoOne extends JFrame{
      	public JButtonDemoOne(){
      		Container container = this.getContentPane();
      		
      		// 讲一个图片变成图标
      		URL url = JButtonDemoOne.class.getResource("头像.png");
      		ImageIcon icon = new ImageIcon(url);
      		
      		// 把这个图标放在按钮上
      		JButton button = new JButton();
      		button.setIcon(icon);
      		// 鼠标悬浮上去显示的提示信息
      		button.setToolTipText("图片按钮");
      		// 向容器中添加按钮
      		container.add(button);
      	
      		this.setVisible(true);
      		this.setBounds(100,100,400,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      
      	}
      	
      	public static void main(String[] args) {
      		new JButtonDemoOne();
      	}
      }
      
    • 效果图

      image-20201223170558689

    5.4.2 单选框JRadioButton

    • 示例代码

      package JButtonDemo;
      
      import java.awt.BorderLayout;
      import java.awt.Container;
      
      import javax.swing.ButtonGroup;
      import javax.swing.JFrame;
      import javax.swing.JRadioButton;
      import javax.swing.WindowConstants;
      
      public class JButtonDemoTwo extends JFrame{
      	public JButtonDemoTwo(){
      		Container container = this.getContentPane();
      		
      		// 单选框
      		JRadioButton radiobutton1 = new JRadioButton("radiobutton1");
      		JRadioButton radiobutton2 = new JRadioButton("radiobutton2");
      		JRadioButton radiobutton3 = new JRadioButton("radiobutton3");
      		
      		// 由于单选框只能选择一个,所以需要给按钮分组
      		ButtonGroup group = new ButtonGroup();
      		group.add(radiobutton1);
      		group.add(radiobutton2);
      		group.add(radiobutton3);
      		
      		// 向容器中添加单选框按钮
      		container.add(radiobutton1,BorderLayout.NORTH);
      		container.add(radiobutton2,BorderLayout.CENTER);
      		container.add(radiobutton3,BorderLayout.SOUTH);
      
      		this.setVisible(true);
      		this.setBounds(100,100,400,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
          
      	public static void main(String[] args) {
      		new JButtonDemoTwo();
      	}
      }
      
    • 效果图

      image-20201223170739117

    5.4.3 多选框Checkbox

    • 示例代码

      package JButtonDemo;
      
      import java.awt.BorderLayout;
      import java.awt.Checkbox;
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.WindowConstants;
      
      public class JButtonDemoThree extends JFrame{
      	public JButtonDemoThree(){
      		Container container = this.getContentPane();
      		
      		// 多选框
      		Checkbox checkbox1 = new Checkbox("记住密码");
      		Checkbox checkbox2 = new Checkbox("忘记密码");
      		Checkbox checkbox3 = new Checkbox("设置密码");
      		
      		// 向容器中添加多选框
      		container.add(checkbox1,BorderLayout.NORTH);
      		container.add(checkbox2,BorderLayout.CENTER);
      		container.add(checkbox3,BorderLayout.SOUTH);
      		
      		this.setVisible(true);
      		this.setBounds(100,100,400,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      
      	}
      	
      	public static void main(String[] args) {
      		new JButtonDemoThree();
      	}
      }
      
    • 效果图

      image-20201223170854573

    5.5 列表

    5.5.1 下拉框JComboBox

    • 代码示例

      package ComboboxDemo;
      
      import java.awt.Container;
      
      import javax.swing.JComboBox;
      import javax.swing.JFrame;
      import javax.swing.WindowConstants;
      
      /*
       * 下拉框
       */
      public class ComboboxDemoOne extends JFrame{
      	public ComboboxDemoOne() {
      		Container container = this.getContentPane();
      		
      		// 下拉框
      		JComboBox status = new JComboBox();
      		
      		status.addItem(null);
      		status.addItem("正在上映");
      		status.addItem("即将上映");
      		status.addItem("即将下架");
      		
      		// 获取下拉框中的内容,需要绑定一个点击事件,然后通过e.getSource()获取status对象,通过getText()方法即可获取文本信息
      		// status.addActionListener();
      		
      		container.add(status);
      
      		this.setVisible(true);
      		this.setBounds(100,100,500,500);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      
      	public static void main(String[] args) {
      		new ComboboxDemoOne();
      	}
      }
      
    • 效果图

      image-20201223171656116

      image-20201223171758518

    5.5.2 列表框JList

    • 示例代码

      package ComboboxDemo;
      
      import java.awt.Container;
      import java.util.Vector;
      
      import javax.swing.JFrame;
      import javax.swing.JList;
      import javax.swing.WindowConstants;
      
      /*
       * 列表框
       */
      public class ComboboxDemoTwo extends JFrame{
      	public ComboboxDemoTwo() {
      		Container container = this.getContentPane();
      		
      		// 列表框
      		
      		/*方式一:
      			 生成了列表的内容        	此方法是稀疏数组,压缩数据(本质上还是数组)
      			此方法将列表中的数据写死了,所以不可取
      			String[] contents = {"1","2","3","4","5"};
      			
      			列表中需要放入内容
      			JList jList = new JList(contents);
      		*/
      		
      		// 方式二:推荐(看情况使用)
      		Vector contents = new Vector();
      		
      		// 动态向contents数组中添加数据
      		contents.add("1");
      		contents.add("2");
      		contents.add("3");
      		contents.add("4");
      		contents.add("5");
      		
      		// 列表中需要放入内容
      		JList jList = new JList(contents);
      		
      		container.add(jList);
      		this.setVisible(true);
      		this.setBounds(100,100,500,500);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      
      	public static void main(String[] args) {
      		new ComboboxDemoTwo();
      	}
      }
      
    • 效果图

      image-20201223171910784

    5.6 文本框

    5.6.1 文本框JTextField

    • 示例代码

      package TextDemo;
      
      import java.awt.BorderLayout;
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.JTextField;
      import javax.swing.WindowConstants;
      
      /*
       * 文本框
       */
      public class TextDemoOne extends JFrame{
      	public TextDemoOne(){
      		Container container = this.getContentPane();
      		
      		// 创建文本框
      		JTextField textField1 = new JTextField("hello");
      		JTextField textField2 = new JTextField("world",20);
      		
      		// 添加文本框到窗口容器中
      		container.add(textField1,BorderLayout.NORTH);
      		container.add(textField2,BorderLayout.SOUTH);
      		
      		this.setVisible(true);
      		this.setBounds(100,100,400,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	
      	public static void main(String[] args) {
      		new TextDemoOne();
      	}
      }
      
    • 效果图

      image-20201223174402543

    5.6.2 密码框JPasswordField

    • 代码样式

      package TextDemo;
      
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.JPasswordField;
      import javax.swing.WindowConstants;
      
      /*
       * 密码框:输入的密码默认是居中显示
       */
      public class TextDemoTwo extends JFrame{
      	public TextDemoTwo(){
      		Container container = this.getContentPane();
      		
      		// 创建密码框对象
      		JPasswordField passwordField = new JPasswordField();
      		// 设置密码的样式
      		passwordField.setEchoChar('*');
      		
      		// 添加密码框到窗口容器中
      		container.add(passwordField);
      		
      		this.setVisible(true);
      		this.setBounds(100,100,400,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	
      	public static void main(String[] args) {
      		new TextDemoTwo();
      	}
      }
      
    • 效果图

      image-20201223174546885

    5.6.3 文本域

    • 示例代码

      package TextDemo;
      
      import java.awt.Container;
      
      import javax.swing.JFrame;
      import javax.swing.JScrollPane;
      import javax.swing.JTextArea;
      import javax.swing.WindowConstants;
      
      public class TextDemoThree extends JFrame{
      	
      	public TextDemoThree(){
      		Container container = this.getContentPane();
      		
      		// 文本域
      		JTextArea textArea = new JTextArea(20,50);
      		textArea.setText("欢迎学习GUI之Swing编程");
      		
      		// Scroll面板
      		JScrollPane scrollPane = new JScrollPane(textArea);
      		container.add(scrollPane);
      		
      		this.setVisible(true);
      		this.setBounds(100,100,300,400);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	
      	public static void main(String[] args) {
      		new TextDemoThree();
      	}
      
      }
      
    • 效果图

      image-20201223174637091

    5.7 图标

    5.7.1 标签图标

    • 示例代码

      package IconDemo;
      
      import java.awt.Component;
      import java.awt.Container;
      import java.awt.Graphics;
      
      import javax.swing.Icon;
      import javax.swing.JFrame;
      import javax.swing.JLabel;
      import javax.swing.SwingConstants;
      import javax.swing.WindowConstants;
      
      /*
       * 标签图标,图标添加到标签上
       */
      
      // 图标,需要实现类,继承JFrame
      public class IconDemoOne extends JFrame implements Icon{
      	private int width;
      	private int height;
      	
      	// 无参构造
      	public IconDemoOne(){
      		
      	}
      	// 有参构造
      	public IconDemoOne(int width, int height){
      		this.width = width;
      		this.height = height;
      	}
      	// 初始化
      	public void init(){
      		// 图标放在标签上,也可以放在按钮上
      		JLabel label = new JLabel("icontest",this,SwingConstants.CENTER);
      		
      		Container container = this.getContentPane();
      		container.add(label);
      		
      		this.setVisible(true);
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	// 程序主入口
      	public static void main(String[] args) {
      			new IconDemoOne(10,10).init();
      	}
      
      	// 实现Icon所需要的重写的方法
      	@Override
      	public void paintIcon(Component c, Graphics g, int x, int y) {
      		g.fillOval( x, y, this.height, this.width);
      	}
      	@Override
      	public int getIconWidth() {
      		return this.width;
      	}
      	@Override
      	public int getIconHeight() {
      		return this.height;
      	}
      }
      
    • 效果图

      image-20201223172159648

    5.7.2 图片图标

    • 示例代码

      package IconDemo;
      
      import java.awt.Container;
      import java.net.URL;
      
      import javax.swing.ImageIcon;
      import javax.swing.JFrame;
      import javax.swing.JLabel;
      import javax.swing.SwingConstants;
      import javax.swing.WindowConstants;
      
      /*
       * 图片图标,图标是一张图片
       */
      
      public class IconDemoTwo extends JFrame{
      	// 构造方法	
      	public IconDemoTwo(){
      		// 创建一个标签,用于添加图标
      		JLabel label = new JLabel("ImageIcon");
      		// 获取图片地址,是当前类的位置
      		// URL url = ImageIcon.class.getResource("头像.png");
      		URL url = IconDemoTwo.class.getResource("头像.png");
      		// 创建一个图片图标对象
      		ImageIcon imageIcon = new ImageIcon(url);
      		// 将图片图标对象添加到标签中
      		label.setIcon(imageIcon);
      		// 设置标签中的内容居中显示
      		label.setHorizontalAlignment(SwingConstants.CENTER);
      		// 获取当前的窗口容器
      		Container container = this.getContentPane();
      		// 将标签添加到窗口容器中
      		container.add(label);
      		// 设置窗口可见
      		this.setVisible(true);
      		// 关闭窗口点击事件
      		this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      	}
      	// 程序主入口
      	public static void main(String[] args) {
      		new IconDemoTwo();
      	}
      }
      
    • 效果图

      image-20201223172634684

    6. 贪吃蛇案例

    • StartGame.java

      package Snake;
      
      import javax.swing.JFrame;
      import javax.swing.WindowConstants;
      
      /*
       * 游戏设计步骤
       * 		1.定义数据
       * 		2.画上去信息
       * 		3.监听事件
       * 			(1)、键盘监听
       * 			(2)、事件监听
       */
      
      // 游戏的主启动类
      public class StartGame {
      	public static void main(String[] args) {
      		JFrame frame = new JFrame();
      		
      		frame.setBounds(10,10,900,720);
      		frame.setResizable(false); // 设置窗口大小不可变化
      		frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      		
      		// 正常的游戏界面应该放在面板上
      		frame.add(new GamePanel());
      		
      		frame.setVisible(true);
      	}
      }
      
    • GamePanel.java

      package Snake;
      
      import java.awt.Color;
      import java.awt.Font;
      import java.awt.Graphics;
      import java.awt.event.ActionEvent;
      import java.awt.event.ActionListener;
      import java.awt.event.KeyEvent;
      import java.awt.event.KeyListener;
      import java.util.Random;
      
      import javax.swing.JPanel;
      import javax.swing.Timer;
      
      // 游戏的面板
      public class GamePanel extends JPanel implements KeyListener,ActionListener{
      	// 定义蛇的数据结构
      	int length;
      	int[] snakeX = new int[600];
      	int[] snakeY = new int[500];
      	String direction; // 定义蛇的方向
      	 // 食物的坐标
      	int foodX;
      	int foodY;
      	
      	Random random = new Random();
      	int score; // 成绩
      	
      	boolean isStart = false; // 游戏当前状态,开始or停止       默认是停止的 
      	boolean isFail = false; // 游戏失败状态
      	
      	// 定时器    以毫秒为单位	  1000ms = 1s
      	Timer timer = new Timer(100, this); // 100毫秒执行一次	
      	
      	// 构造器
      	public GamePanel(){
      		init();
      		// 获得焦点和键盘事件
      		this.setFocusable(true); // 获得焦点事件
      		this.addKeyListener(this); // 获得键盘监听事件
      		timer.start(); // 游戏一开始定时器就启动
      	}
      	
      	// 初始化方法
      	public void init(){
      		length = 3;
      		snakeX[0] = 100;snakeY[0] = 100; // 蛇脑袋坐标
      		snakeX[1] = 75;snakeY[1] = 100; // 第一个身体的坐标
      		snakeX[2] = 50;snakeY[2] = 100; // 第二个身体的坐标
      		direction = "R"; // 初始方向向右
      		
      		// 把食物随机分配在界面上
      		foodX = 25 + 25*random.nextInt(34);
      		foodY = 75 + 25*random.nextInt(24);
      		
      		score = 0; // 初始化成绩为0
      		
      	}
      
      	// 绘制面板,我们游戏中的所有东西,都是用这个画笔来画的
      	@Override
      	protected void paintComponent(Graphics g) {
      		super.paintComponent(g); // 清屏
      		// 绘制静态的面板
      		this.setBackground(Color.WHITE);
      		Data.header.paintIcon(this, g, 25, 11); // 头部广告栏画上去
      		g.fillRect(25, 75, 850, 600); // 默认的游戏界面
      		
      		// 画积分
      		g.setColor(Color.white);
      		g.setFont(new Font("微软雅黑",Font.BOLD,18));
      		g.drawString("长度   "+length, 750, 35);
      		g.drawString("分数    "+score, 750, 50);
      		
      		
      		// 把食物画上面板
      		Data.food.paintIcon(this, g, foodX, foodY);
      		
      		
      		// 把小蛇画上去
      		if(direction.equals("R")){
      			Data.right.paintIcon(this, g, snakeX[0], snakeY[0]); // 蛇的初始化方向向右,需要通过方向来判断
      		}else if(direction.equals("L")){
      			Data.left.paintIcon(this, g, snakeX[0], snakeY[0]); // 蛇的初始化方向向左,需要通过方向来判断
      		}else if(direction.equals("U")){
      			Data.up.paintIcon(this, g, snakeX[0], snakeY[0]); // 蛇的初始化方向向上,需要通过方向来判断
      		}else if(direction.equals("D")){
      			Data.down.paintIcon(this, g, snakeX[0], snakeY[0]); // 蛇的初始化方向向下,需要通过方向来判断
      		}
      		
      		
      		
      		
      		for (int i = 1; i < length; i++) {
      			Data.body.paintIcon(this, g, snakeX[i], snakeY[i]); // 第一个身体的坐标
      		}
      		
      		// 游戏状态
      		if(isStart == false){
      			g.setColor(Color.WHITE);
      			g.setFont(new Font("微软雅黑", Font.BOLD, 40)); // 设置字体
      			g.drawString("按下空格开始游戏", 300,300);
      		}
      		
      		if(isFail){
      			g.setColor(Color.RED);
      			g.setFont(new Font("微软雅黑", Font.BOLD, 18)); // 设置字体
      			g.drawString("失败,按下空格重新开始", 300,300);
      		}
      	}
      
      	// 键盘监听事件
      	@Override
      	public void keyPressed(KeyEvent e) {
      		int keyCode = e.getKeyCode(); // 获得键盘按下的是哪个键
      		if(keyCode == KeyEvent.VK_SPACE){ // 如果按下的是空格键
      			if(isFail){
      				// 重新开始
      				isFail = false;
      				init();
      			}else {
      				isStart = !isStart; // 取反
      			}
      			repaint();
      		}
      		// 小蛇移动
      		if(keyCode == KeyEvent.VK_UP){
      			direction = "U";
      		}else if(keyCode == KeyEvent.VK_DOWN){
      			direction = "D";
      		}else if(keyCode == KeyEvent.VK_LEFT){
      			direction = "L";
      		}else if(keyCode == KeyEvent.VK_RIGHT){
      			direction = "R";
      		}
      		
      		
      	}
      
      	// 事件监听------需要通过固定事件来刷新  1s=10次
      	@Override
      	public void actionPerformed(ActionEvent e) {
      		if(isStart && isFail == false){ // 如果游戏是开始状态,就让小蛇动起来
      			
      			// 吃食物
      			if(snakeX[0] == foodX && snakeY[0] == foodY){
      				// 长度 +1
      				length++;
      				
      				score += 10; // 分数+10
      				
      				// 再次随机食物出现
      				foodX = 25 + 25*random.nextInt(34);
      				foodY = 75 + 25*random.nextInt(24);
      				
      			}
      			
      			
      			// 移动
      			for(int i = length - 1; i>0;i--){ // 后一节移动到前一节的位置 snakeX[0] = snakeX[1]
      				snakeX[i] = snakeX[i-1];
      				snakeY[i] = snakeY[i-1];
      			}
      			// 走向
      			if(direction.equals("R")){
      				snakeX[0] = snakeX[0] + 25;
      				if(snakeX[0]>850){snakeX[0] = 25;} // 边界判断
      			}else if(direction.equals("L")){
      				snakeX[0] = snakeX[0] - 25;
      				if(snakeX[0]<25){snakeX[0] = 850;} // 边界判断
      			}else if(direction.equals("U")){
      				snakeY[0] = snakeY[0] - 25;
      				if(snakeY[0]<75){snakeY[0] = 650;} // 边界判断
      			}else if(direction.equals("D")){
      				snakeY[0] = 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]){
      					isFail = true;
      				}
      			}
      			
      			repaint(); // 重画页面
      		}
      		timer.start(); // 定时器开启
      	}
      
      	@Override
      	public void keyReleased(KeyEvent e) {
      	}
      	
      	@Override
      	public void keyTyped(KeyEvent e) {
      	}
      }
      
    • Data.java

      package Snake;
      
      import java.net.URL;
      
      import javax.swing.ImageIcon;
      
      // 数据中心 录入游戏所需的数据
      public class Data {
      	
      	// 相对路径   tx.txt
      	// 绝对路径  /相当于当前的项目
      	public static URL headerURL = Data.class.getResource("statics/header.jpg");
      	public static ImageIcon header = new ImageIcon(headerURL);
      	
      	public static URL bodyURL = Data.class.getResource("statics/body.png");
      	public static ImageIcon body = new ImageIcon(bodyURL);
      	
      	public static URL downURL = Data.class.getResource("statics/down.png");
      	public static ImageIcon down = new ImageIcon(downURL); 
      	
      	public static URL upURL = Data.class.getResource("statics/up.png");
      	public static ImageIcon up = new ImageIcon(upURL); 
      	
      	public static URL leftURL = Data.class.getResource("statics/left.png");
      	public static ImageIcon left = new ImageIcon(leftURL); 
      	
      	public static URL rightURL = Data.class.getResource("statics/right.png");
      	public static ImageIcon right = new ImageIcon(rightURL); 
      	
      	public static URL foodURL = Data.class.getResource("statics/food.png");
      	public static ImageIcon food = new ImageIcon(foodURL); 
      }
      
      
    • 效果图

      • 开始状态

        image-20201225121223485

      • 死亡状态

        image-20201224215158419

  • 相关阅读:
    Windows netstat
    LOIC Download
    Open CV 环境配置
    C++ strcat_s
    c++ strlen() 函数
    css实现1px 像素线条_解决移动端1px线条的显示方式
    css中line-height的理解_介绍line-height实际应用
    css 分割线样式_css实现文章分割线的多种方法总结
    css获取除第一个之外的子元素
    css实现div多边框_box-shadow模拟多边框、outline描边实现
  • 原文地址:https://www.cnblogs.com/borntodie/p/14188306.html
Copyright © 2020-2023  润新知