• jQuery的观察者模式详解 转载


    jQuery的观察者模式详解

    投稿:hebedich

    本文主要是介绍了jQuery中on方法及trigger方法,以及围绕这个方法来体验的观察者模式,是篇非常不错的文章,对我们理解观察者模式很有帮助。

    undefined

    undefined

    ■ on方法绑定内置事件,自然触发

    比如,我们给页面的body元素绑定一个click事件,这样写。

     <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>     <title></title>     <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function() {             $('body').on('click', function () {                 console.log('被点击了~~');             });         });          </script> </head> <body>     <h1>hello</h1> </body>

    以上,我们只有点击body,才能触发click事件。也就是说,当给页面元素绑定内置事件后,事件的触发是在内置事件发生的那刻。

    ■ on方法绑定内置事件,手动触发

    使用trigger方法,也可以手动触发元素绑定的内置事件。

         <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function() {             $('body').on('click', function () {                 console.log('被点击了~~');             });             $('body').trigger('click');         });          </script> 以上,无需点击body,在页面加载完毕,body自动触发了click事件。

    ■ on方法绑定自定义事件,手动触发

    我们知道,click是jquery内置的事件,那么,是否可以自定义事件,并手动触发呢?

        <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function() {             $('body').on('someclick', function () {                 console.log('被点击了~~');             });             $('body').trigger('someclick');         });          </script>

    以上,我们自定义了一个someclick事件,得到的结果和上面一样。

    于是,我们发现:我们可以为元素绑定自定义事件,并且用trigger方法触发该事件。

    当然,自定义事件的名称可以按照"命名空间.自定义事件名称"的形式来写,比如app.someclick,这在大型项目中尤其有用,这样可以有效避免自定义事件名称冲突。

    如果从"发布订阅"这个角度来看,on方法相当于订阅者、观察者,trigger方法相当于发布者。

    ■ 从"异步获取json数据"来体验jQuery观察者模式

    在根目录下,有一个data.json的文件。

    {     "one" : "Hello",     "two" : "World" } 现在,通过异步的方式来获取json数据。

        <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function () {             $.getJSON('data.json', function(data) {                 console.log(data);             });         });          </script>

     

    如果用一个全局变量来接收异步获取的json数据。

        <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function () {             var data;             $.getJSON('data.json', function(results) {                 data = results;             });             console.log(data);         });          </script>

    这次,我们得到的结果却是undefined,这是为什么? --因为,当$.getJSON方法还在获取数据的时候,就已经执行console.log(data),而此时data还没有数据。

    如何解决这个问题呢? --如果在$.getJSON方法之外先定义好需要执行的方法,然后在$.getJSON方法的回调函数里真正触发这个方法,不就解决了吗?

        <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function () {             $.getJSON('data.json', function(results) {                 $(document).trigger('app.myevent', results); //相当于发布             });             $(document).on('app.myevent', function(e, results) { //相当于订阅                 console.log(results);             });         });          </script>

    以上,on方法就像一个订阅者,它订阅了自定义事件app.myevent;而trigger方法就像一个发布者,它发布事件和参数后,才真正让订阅者方法得以执行。

    ■ jQuery观察者模式的扩展方法

    为此,我们还可以为jQuery观察者模式专门写一个扩展方法。

        <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function () {             $.getJSON('data.json', function (results) {                 $.publish('app.myevent', results);             });             $.subscribe('app.myevent', function(e, results) {                 console.log(results);             });         });         (function($) {             var o = $({});//自定义事件对象             $.each({                 trigger: 'publish',                 on: 'subscribe',                 off: 'unsubscribe'             }, function(key, val) {                 jQuery[val] = function() {                     o[key].apply(o, arguments);                 };             });         })(jQuery);     </script>

    以上,定义了全局的publish和subscribe方法,我们在任何时候都可以调用。

        <script src="Scripts/jquery-2.1.1.min.js"></script>     <script type="text/javascript">         $(function () {             $.getJSON('data.json', function (results) {                 $.publish('app.myevent', results);             });             $.subscribe('app.myevent', function(e, results) {                 $('body').html(                     results.one                 );             });         });


    引用这个

    /* jQuery Tiny Pub/Sub - v0.7 - 10/27/2011 
    * http://benalman.com/ 
    * Copyright (c) 2011 "Cowboy" Ben Alman; Licensed MIT, GPL */ 
    
     
     (function($) { 
     
     
      var o = $({}); 
     
     
       $.subscribe = function() { 
         o.on.apply(o, arguments); 
       }; 
     
     
       $.unsubscribe = function() { 
         o.off.apply(o, arguments); 
       }; 
    
     
       $.publish = function() { 
         o.trigger.apply(o, arguments); 
       }; 
     
     
    }(jQuery)); 
  • 相关阅读:
    BZOJ 2034 【2009国家集训队】 最大收益
    vijos P1780 【NOIP2012】 开车旅行
    BZOJ 2115 【WC2011】 Xor
    BZOJ 3631 【JLOI2014】 松鼠的新家
    BZOJ 4717 改装
    BZOJ 2957 楼房重建
    BZOJ 4034 【HAOI2015】 T2
    BZOJ 1834 【ZJOI2010】 network 网络扩容
    BZOJ 2440 【中山市选2011】 完全平方数
    BZOJ 2733 【HNOI2012】 永无乡
  • 原文地址:https://www.cnblogs.com/AngryXiaopeng/p/5369143.html
Copyright © 2020-2023  润新知