项目解释GUI编程-----后端终于能看到东西了!!

GUI编程—一个项目看懂

怎么shuo呢?其实很久之前就想学GUI,因为每天面对着idea的控制台或者终端不免有些乏味,在假期的时候其实学校的进度就已经把GUI学完了,但是讲的内容着实懵懂,恍惚的我以为这玩意儿应该不考,而且后端做的画面未免有些许丑,虽然对JAVA保持一颗极其热爱的内心但是还是非常的期冀能做出来和前端一样炒鸡好看的页面,所以在假期的时候我就愉快的把这个搁下了。

你见苍天饶过谁?前两天我做了一份学校老师发的期末试卷,虽然当时我已经知道要考GUI但是最后算了一下GUI居然有道20分的大题,而且一份卷子关于GUI的内容居然有32分????我承认当时我慌了,我相信很多哥们看到我写到这的时候你也有点慌,没事,不慌,所以这里我用一个项目来讲GUI

项目分析:

我也是突发奇想,想要把目前所有学到的GUI的内容做到一个项目里面,虽然几乎用了三个小时搞这个小程序,但是还是有部分内容没有放进去,但是和小程序中用到的内容本质是相同的,读者可以自行比对学习,具体的内容可以查看我最后附上的笔记中的内容。

分析:

基本构图:
在这里插入图片描述

介绍
首先我们需要在创建好的Frame类中创建两个面板,其中一个放到WEST方位(简称p1,之后同理),另一面板放到EAST方位(简称p2,之后同理),并把面板p2设置成GridLayout布局管理器,分别添加四个标签五个按钮。这样基本的构图就完成了。
为p1添加点击事件:当鼠标点击的位置即可让红点转移到点击位置。
为四个按钮添加鼠标事件监听:当鼠标点击相应的按钮时,对应小红点会上下左右移动,以20像素为单位变动。
为back按钮添加键盘事件监听:当点击back按钮时,小红点会自动的变动到p1的中心。
为窗体添加键盘事件,当点击上下左右按钮时,触发小红点上下左右变动,键击空格键时,则可控制小红点回到p1的中心位置。
为窗体添加窗体事件监听:当点击窗体上的×时退出程序,关闭窗体。
综上就是我们要在这次项目中完成的内容。

知识点罗列:
Frame窗体
Panel面板
GridLayout和BorderLayout布局管理器
JButton组件
鼠标事件监听
键盘事件监听
窗体事件监听
内部类
匿名类
Color类
Graphics类

代码奉上,讲解就在注释中:

package GUItest;

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;

public class FinalTest {
    public static void main(String[] args) {
        new MnFrame("FinalFrameTest");
    }
}
//
1)用一个类来继承Frame类并创建相应的构造方法

```java
class MnFrame extends Frame{
    Point point = new Point(125,250);
    MnFrame mnFrame;
    //2)这里重写类父类的构造方法为字符串的构造方法
    public MnFrame(String s){
        //3)Frame类中参数为字符串的构造方法的内部是将传入的参数s设置为窗口的title
        super(s);
        mnFrame=this;
        //从Frame的父类Window的继承的setBounds用于设置窗口页面的大小
            //注意这里的x,y都是以窗口的左上角为原点设置的
        setBounds(100,100,500,500);
        //**其实Frame的默认布局管理器就是BorderLayOut(这是考点!!!!)
        //**这里的设置是为了更为清楚的看出
        setLayout(new BorderLayout());
        //p1 作为Frame的左侧画板
        Panel p1 =new Panel();
        //**对于panel的默认布局管理器是FlowLayout,这里也是为了说明清楚(这是考点!!!)
        p1.setLayout(new FlowLayout());
        //p2 作为Frame的右侧位
        Panel p2 =new Panel();
        /*
        设置p2的布局管理器是GridLayout
        GridLayout是一个将空间划分为均匀的矩形网格
        这里的构造方法是将区域均匀的划分为三行三列
         */
        p2.setLayout(new GridLayout(3,3));

        //这里创建了五个按钮,用到了参数为字符串的构造方法,产生的效果是将字符串的内容显示在按钮上
        Button bUp = new Button("UP");
        Button bDown = new Button("Down");
        Button bLeft = new Button("Left");
        Button bRight = new Button("Right");
        Button bBack  = new Button("Back");
        //这里创建了四个标签,用到了参数为字符串的构造方法,产生的效果是将字符串的内容显示在标签上
        /*
        为什么要将awt组件中的Label换成Swing组件中的Jlabel?
            答:因为在AWT组件当中默认是无法显示中文(它太太太老了)
         */
        JLabel lLao = new JLabel("老");
            //这句话有兴趣话可以查一些API文档,就是简单的设置文字在Jlabel中居中
            //这里设置也只是为了让它美观一点

            /* **注意:这里我并没有将代码对齐主要是为了显示重要的代码(不要骂我啊啊啊啊!),
                 虽然JAVA不是像Python一样强制要求代码规范的编程语言,
                 但是为了代码的可读性和更加美观,良好的书写习惯是非常必要的。
                 所以一定要注意对齐!对齐!对齐!
             */
            lLao.setHorizontalAlignment(JLabel.CENTER);
        JLabel lWang = new JLabel("王");

            lWang.setHorizontalAlignment(JLabel.CENTER);
        JLabel lTong = new JLabel("同");

            lTong.setHorizontalAlignment(JLabel.CENTER);
        JLabel lXue = new JLabel("学");

            lXue.setHorizontalAlignment(JLabel.CENTER);

        //调用add方法将标签和按钮加入到p2里面
            //第一行
        p2.add(lLao);
        p2.add(bUp);
        p2.add(lWang);
            //第二行
        p2.add(bLeft);
        p2.add(bBack);
        p2.add(bRight);
            //第三行
        p2.add(lTong);
        p2.add(bDown);
        p2.add(lXue);

        //setBackGroud同样是从父类继承用于设置窗口的背景颜色
        setBackground(Color.PINK);
        //将两个面板加入到frame中
        add(p1,BorderLayout.WEST);
        add(p2,BorderLayout.EAST);
        //添加鼠标事件监听器
        addMouseListener(new MouseMonitor1());
        //添加键盘事件监听器
        /*
        这句话是因为在编写的过程当中遇到了问题,当鼠标监听器和键盘监听器同时存在时
        就会发生键盘监听器不被触发的效果
        查了csdn中之后,发现了问题的存在:
            无论哪个控件,想要接受键盘事件都需要获取焦点
            而获取焦点的方式就是通过setFocusable(true)方法
         */
        this.setFocusable(true);
        addKeyListener(new KeyMonitor());

        //**注意:这里用到了匿名类的知识!!!(考点!!!!)
        /*
        对于匿名类来说:
            简单来说匿名类就是在方法中的类,是没有名字的类,使用匿名类的目的是为了简化建类
            匿名类里面包装的是并不重要的逻辑,很少修改甚至不需要修改的代码
            而相应的在编译时也不会多创建.class文件
         */
        //为bUp按钮添加鼠标事件监听
        bUp.addMouseListener(new MouseAdapter() {

            @Override
            public void mousePressed(MouseEvent e) {
                point.y-=20;
                mnFrame.repaint();
            }
        });
        bDown.addMouseListener(new MouseAdapter() {
            @Override
            public void mousePressed(MouseEvent e) {
                point.y+=20;
                mnFrame.repaint();
            }
        });
        bLeft.addMouseListener(new MouseAdapter() {
            @Override
            public void mousePressed(MouseEvent e) {
                point.x-=20;
                mnFrame.repaint();
            }
        });
        bRight.addMouseListener(new MouseAdapter() {
            @Override
            public void mousePressed(MouseEvent e) {
                point.x+=20;
                mnFrame.repaint();
            }
        });
        bBack.addMouseListener(new MouseAdapter() {
            @Override
            public void mousePressed(MouseEvent e) {
                point.x=125;
                point.y=250;
                mnFrame.repaint();
            }
        });
        /*
        窗体事件监听事件
        这里用匿名类来实现窗体事件监听,重写windowClosing方法
        当窗体处于关闭状态时触发窗体事件监听
         */
        this.addWindowListener(new WindowAdapter() {
            @Override
            public void windowClosing(WindowEvent e) {
                mnFrame.setVisible(false);
                System.exit(0);
            }
        });
        //设置面板可视化,这句话一定要写在最后,在这个方法之后添加的组件或者操作都无法显示
        //**没有这个方法则无法出现窗口
        setVisible(true);

    }

    //重写paint方法
    @Override
    public void paint(Graphics g) {
        /*

         */
        g.setColor(Color.red);
        g.fillOval(point.x,point.y,20,20);
    }

    /*
            **注意:这里用到了内部类的知识哟!内部类可以任意访问包装类当中的成员变量
             内部类的使用情况是:该类不允许或者不希望别的类访问,使用内部类更方便访问成员变量
             在编译时内部类也会产生相应的.class文件而文件命名会是:【外部类类名(也称为包装类)$内部类类名.class】(!!!考点)
         */
    //在p1处的鼠标事件监听器
    class MouseMonitor1 extends MouseAdapter{
        /*
        这里实现了鼠标事件的监听器:
            鼠标事件的监听器主要应该实现MosueListener类但是由于
            MouseListener类有五个方法,如果要实现的话就会非常麻烦的实现五个方法
            J2EE提供了一种变通的方式就是直接提供了实现MouseListener接口的类
            也就是MouseAdapter类,在这个类当中方法其实都是空方法
            但是便利于我们可以只重写一个我们需要用的方法。
         */
        @Override
        public void mousePressed(MouseEvent e) {
            /*
            这里重写了mousePressed 方法,这个方法是在父类MouseAdapter中的方法
            会对鼠标的单击做出反应
            这里产生的效果结合之前的paint方法,鼠标点击哪里就会在那里画出一个实心红色的圆
             */
            MnFrame mf =(MnFrame) e.getSource();
            //注:
            point.x=e.getX();
            point.y=e.getY();
            mf.repaint();
        }
    }




    //定义键盘事件监听器
    /*
    对于键盘监听器和之前的鼠标监听器的原理相似,这里就不多加赘述了
    读者可以看之前写的鼠标事件监听器的内容对照学习
     */
    class KeyMonitor extends KeyAdapter{
        //重写父类的keyPressed方法,当键盘某一键被按下时,则触发键盘事件监听器
        @Override
        public void keyPressed(KeyEvent e) {
            /*
              当我们每一次敲击键盘时其实是向电脑发送了一段信号码
              而在KeyEvent中将每一个按钮都定义成了常量,常量值为信号码
              keyEvent.getKeyCode则是获取敲击键盘上某一键的型号码
              这里通过getKeyCode方法和定义的常量进行比对达到成功匹配的效果
             */
            MnFrame mf = (MnFrame)e.getSource();
            int keyCode = e.getKeyCode();
            if(keyCode==KeyEvent.VK_UP){
                point.y-=20;
            }
            if (keyCode==KeyEvent.VK_DOWN){
                point.y+=20;
            }
            if (keyCode==KeyEvent.VK_LEFT){
                point.x-=20;
            }
            if (keyCode==KeyEvent.VK_RIGHT){
                point.x+=20;
            }
            if(keyCode==KeyEvent.VK_SPACE){
                point.x=125;
                point.y=250;
            }
            mf.repaint();
        }
    }

}

## 最后奉上最近学习GUI的笔记供读者参考:

链接:https://pan.baidu.com/s/1M–mdx2ssHHzdJ-6pt-KVw
提取码:n3z2




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值