(十四)监听器

监听器的介绍

  1. 监听器的概念
    监听器就是实现特定接口的一个普通java类,这个类专门用于监听另一个java对象的方法调用或属性改变,当被监听对象发生上述事件后,监听器的某个方法就会被执行。
  2. 监听器案例–监听window窗口的事件监听器
package lister;

import java.awt.Frame;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;

public class ListerDemo1 {
    /**
     * java事件监听机制
     * 1.事件监听涉及到三个组件:事件源、事件对象、事件监听器
     * 2.当事件源上发生一个动作时,它会调用事件监听器的一个方法,并
     * 在调用该方式时把事件对象传过去
     * 开发人员在监听器中通过事件对象,就可以拿到事件源,从而对事件源进行操作
     * @param args
     */
    public static void main(String[] args) {
        Frame f = new Frame();
        f.setSize(400, 400);
        f.setVisible(true);

        //注册事件监听器,因为监听器是接口,所以这里使用了匿名内部类
        f.addWindowListener(new WindowListener() {

            @Override
            public void windowOpened(WindowEvent e) {}

            @Override
            public void windowIconified(WindowEvent e) {}

            @Override
            public void windowDeiconified(WindowEvent e) {}

            @Override
            public void windowDeactivated(WindowEvent e) {}

            /**
             * 当window窗体关闭时就会被WindowListener这个监听器听到
             * 监听器就会调用WindowClosing方法处理窗体关闭时的动作
             */
            @Override
            public void windowClosing(WindowEvent e) {
                Frame f = (Frame)e.getSource();//通过事件对象拿到事件源
                System.out.println(f+"窗体正在关闭");//模拟对事件源处理
                f.dispose();

            }
            @Override
            public void windowClosed(WindowEvent e) {}

            @Override
            public void windowActivated(WindowEvent e) {}
        });     
    }
}
. 

3. 设计一个可以被别的监听对象监听的对象
一般我们都是写监听器去监听其它对象,现在我们设计一个对象可以被其它对象监听。我们可以按照严格的事件处理模型来设计一个对象,它就可以被监听,事件处理模型涉及到三个组件:事件源、时间对象、事件监听器。
下面我们按照事件处理模型来设计一个Person对象,代码如下:

package beanListen;



/**
 * 设计一个Person类作为事件源,这个类的对象的行为可以被
 * 其它的对象监听
 * @author flb
 *
 */
public class Person {
    /**
     * 在Person类中定义一个PersonListener变量来传递进来的监听器
     */
    private PersonListener listener;

    /**
     * 设计Person的行为:eat
     */
    public void eat() {
        if(listener!=null) {
            /**
             * 调用监听器的doeat方法来监听Person类对象eat这个行为
             * 将事件对象Event传递给doeat方法
             * 事件对象封装了事件源,new Event(this)中的this代表的
             * 的就是事件源(也就是Person对象)
             */
            listener.doeat(new Event(this));
        }

    }
    public void run() {
        if(listener!=null) {
            listener.dorun(new Event(this));
        }
    }

    /**
     * 这个方法是用来注册对Person类对象的行为进行监听的监听器
     * @param listener
     */
    public void registerListener(PersonListener listener) {
        this.listener = listener;
    }

}
/*一般监听器都是一个单独接口,这里就直接和事件源在一个类里了*/
interface PersonListener{
    /**
     * 这个方法是用来监听Person对象eat这个行为动作
     * 当实现类实现doeat方法时就可以监听到Person对象eat这个行为
     * @param e
     */
    void doeat(Event e);

    /**
     * 这个方法是用来监听Person对象run这个行为的
     * @param e
     */
    void dorun(Event e);

}

/**
 * 此类被用作事件对象:封装事件源
 * 一般事件源也是一个单独的类,这里为了方便就和事件源在一个类了
 * @author flb
 *
 */
class Event{
    /**
     * 事件源(Person就是事件源)
     */
    private Person source;

    public Event() {

    }

    public Event(Person source) {
        this.source = source;
    }
    public Person getSource() {
        return source;
    }
    public void setSource(Person source) {
        this.source = source;
    }

}

经过这样的设计之后,Person对象就可以被其它对象监听了,测试代码如下:

package beanListen;

public class PersonTest {
    public static void main(String[] args) {
        Person p = new Person();
        p.registerListener(new PersonListener() {

            @Override
            public void dorun(Event e) {
                Person p = e.getSource();
                System.out.println(p+"在跑步");

            }

            @Override
            public void doeat(Event e) {
                Person p = e.getSource();
                System.out.println(p+"在吃东西");

            }
        });
        p.eat();
        p.run();
    }

}

运行结果:
这里写图片描述
总结:

  • 事件源要想被监听,就得注册事件监听器,然后在要被监听的方法(行为)中去调用监听器的响应方法,并把事件对象传过去

  • 一个监听器通常只能监听一个对象,所以我们要根据监听的事件类型实现相应的监听器接口。

猜你喜欢

转载自blog.csdn.net/parade0393/article/details/78976318
今日推荐