Chinaunix首页 | 论坛 | 博客
  • 博客访问: 5174592
  • 博文数量: 1696
  • 博客积分: 10870
  • 博客等级: 上将
  • 技术积分: 18357
  • 用 户 组: 普通用户
  • 注册时间: 2007-03-30 15:16
文章分类
文章存档

2017年(1)

2016年(1)

2015年(1)

2013年(1)

2012年(43)

2011年(17)

2010年(828)

2009年(568)

2008年(185)

2007年(51)

分类:

2010-07-20 14:55:11

需求:

 

现实生活中,我们有这样的需求,某一个事物的状态发生了改变,我们就需要通知另外跟这个事物息息相关的一些事物

可以认为,这些事物共同监视着这个它们都很感兴趣的事物,如果这个事物状态发生变化,那么它们接到通知,

并作出相应的改变,整个过程,叫做观察者模式。

类图:

一种实现:


另一种实现方式:



 
 参照上面的类图,我们采用第二种实现方式,也是java种支持的模式,实现一个定时器:

Subject:

 

Java代码
  1. package com.javaeye.cantellow.behavioral.observer;  
  2.   
  3. import java.util.ArrayList;  
  4. import java.util.Enumeration;  
  5. import java.util.EventObject;  
  6. import java.util.Iterator;  
  7.   
  8. /** 
  9.  *  
  10.  * @本代码的所有权和解释权归cantellow个人所有 2007-2010 
  11.  * @author xuze 
  12.  * @Since 2010-7-10下午06:42:07 
  13.  * @类功能描述:抽象主题角色,维护一系列的观察者 
  14.  * @修改记录: 
  15.  */  
  16. public abstract class Subject {  
  17.     final private ArrayList listeners = new ArrayList();  
  18.   
  19.     public void addListener(Observer o) {  
  20.         listeners.add(o);  
  21.     }  
  22.   
  23.     public void removeListener(Observer o) {  
  24.         listeners.remove(o);  
  25.     }  
  26.   
  27.     public void fireListener(EventObject e, String s) {  
  28.         Iterator i = listeners.iterator();  
  29.         while (i.hasNext()) {  
  30.             Observer observer = (Observer) i.next();  
  31.             observer.update(e, s);  
  32.         }  
  33.     }  
  34. }  

 Observer:

 

Java代码
  1. package com.javaeye.cantellow.behavioral.observer;  
  2.   
  3. import java.util.EventObject;  
  4.   
  5. /** 
  6.  *  
  7.  * @本代码的所有权和解释权归cantellow个人所有 2007-2010 
  8.  * @author xuze 
  9.  * @Since 2010-7-10下午06:33:45 
  10.  * @类功能描述:抽象观察者,为什么抽象为一个接口,那是因为在发布事件的时候,为了统一调用方法, 所以注册在 组建上的所有观察者 
  11.  *                                                都 必须实现这个抽象观察者的方法。 
  12.  * @修 改记录: 
  13.  */  
  14. public interface Observer {  
  15.     public void update(EventObject e, String s);  
  16. }  

 ConcreteObserver:

 

Java代码
  1. package com.javaeye.cantellow.behavioral.observer;  
  2.   
  3.   
  4. import java.util.EventObject;  
  5.   
  6. import javax.swing.JTextField;  
  7. import javax.swing.SwingUtilities;  
  8.   
  9. /** 
  10.  *  
  11.  * @本代码的所有权和解释权归cantellow个人所有 2007-2010 
  12.  * @author xuze 
  13.  * @Since 2010-7-10下午06:38:15 
  14.  * @类功能描述:具体观察者类,实现抽象观察者的方法。 
  15.  * @修改记录: 
  16.  */  
  17. public class ConcreteObserver implements Observer {  
  18.     int i = 0;  
  19.   
  20.     public void update(EventObject e, final String s) {  
  21.         Object o = e.getSource();  
  22.         if (o instanceof JTextField) {  
  23.             final JTextField jt = (JTextField) o;  
  24.             SwingUtilities.invokeLater(new Runnable() {  
  25.                 public void run() {  
  26.                     jt.setText("");  
  27.                     jt.setText(s);  
  28.                 }  
  29.             });  
  30.         }  
  31.     }  
  32. }  

 ConcreteSubject:

 

Java代码
  1. package com.javaeye.cantellow.behavioral.observer;  
  2.   
  3. import java.awt.BorderLayout;  
  4. import java.awt.event.ActionEvent;  
  5. import java.awt.event.ActionListener;  
  6. import java.text.SimpleDateFormat;  
  7. import java.util.Date;  
  8. import java.util.EventObject;  
  9.   
  10. import javax.swing.JFrame;  
  11. import javax.swing.JPanel;  
  12. import javax.swing.JTextField;  
  13. import javax.swing.Timer;  
  14.   
  15. public class ConcreteSubject extends Subject implements ActionListener {  
  16.   
  17.     private JTextField jt;  
  18.   
  19.     public JTextField getJt() {  
  20.     return jt;  
  21.     }  
  22.   
  23.     public void setJt(JTextField jt) {  
  24.     this.jt = jt;  
  25.     }  
  26.   
  27.     public ConcreteSubject() {  
  28.     Observer o = new ConcreteObserver();  
  29.     this.addListener(o);  
  30.     }  
  31.   
  32.     public void actionPerformed(ActionEvent e) {  
  33.     SimpleDateFormat formatter = new SimpleDateFormat("yyyy年MM月dd日 HH时mm分ss秒");  
  34.     String strDate = formatter.format(new Date());  
  35.     EventObject eo = new EventObject(jt);  
  36.     this.fireListener(eo, strDate);  
  37.     }  
  38.   
  39.     public static void main(String[] args) {  
  40.     JFrame jf = new JFrame();  
  41.     jf.setSize(300300);  
  42.     jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);  
  43.     jf.setLocationRelativeTo(null);  
  44.     jf.setVisible(true);  
  45.     jf.setLayout(new BorderLayout());  
  46.   
  47.     JPanel jp = new JPanel();  
  48.     jp.setLayout(new BorderLayout());  
  49.     jf.add(jp, BorderLayout.NORTH);  
  50.   
  51.     JTextField jt = new JTextField();  
  52.     jt.setVisible(true);  
  53.     jt.setEditable(false);  
  54.     jp.add(jt, BorderLayout.NORTH);  
  55.     ConcreteSubject cs = new ConcreteSubject();  
  56.     cs.setJt(jt);  
  57.     new Timer(1000, cs).start();  
  58.     }  
  59.   
  60. }  

 

 

AWT事件处理模型就应用了观察者模式,组件componet是很多listeners都感兴趣的的事物,这些listeners都注册在这个 组件上
实际上,componet自身维护了一个listener列表,当这个组建发生状态变化(键盘、鼠标,你知道的。。)
那么就会通知所有这些listeners更新它们自己的状态(一个for循环,调用共同接口的方法)。
====================================================================
另外,说明一下AWT中的事件类型:
(1)低级事件
低级事件是指形成那些事件的事件。在点击按钮时,包含了按下鼠标,移动鼠标 ,等等。
—  ComponentEvent(组件事件:组件尺寸的变化、移动);

—  ContainerEvent(容器事件:组件增加、移动);

—  WindowEvent(窗口事件:关闭窗口、窗口闭合、图标化);

—  FocusEvent(焦点事件:焦点的获得和丢失);

—  KeyEvent(键盘事件:键按下、释放);

—  MouseEvent(鼠标事件:鼠标单击、移动)。

(2)高级事件(语义事件)
语义事件是指表达用户动作的事件。如:点击按钮,因此ActionEvent是一种语义事件。
—  ActionEvent(动作事件:按钮按下,TextField中按Enter键);

—  AdjustmentEvent(调节事件:在滚动条上移动滑块以调节数值);

—  ItemEvent(项目事件:选择项目,不选择“项目改变”);

—  TextEvent(文本事件:文本对象改变)。 
阅读(835) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~