• 读《编写可维护的JavaScript》第七章总结


     

    第七章 事件处理

    7.1 典型用法

    作者首先给了个我们一个处理事件的方法。看起来也没啥俩样,不过后来给出的优化方法很值得学习:

             // 不好的写法
             function handleClick(event) {
                var popup = document.getElementById("popup");
                popup.style.left = event.clientX + "px";
                popup.style.top = event.clientY + "px";
                pop.className = "reveal";
             }
             
             // 一个事件绑定事件(第5章的)
             addListener(element, "click", handleClick);

    作者补充了一句:这段代码只用到了event对象的俩个属性:clientX和clientY。在将元素显示在页面里之前先用这俩个属性给它做定位。

                           尽管这段代码开起来非常简单且没有什么问题,但实际上是不好的写法,因为这种做法有其局限性。

     7.2 规则 1:隔离应用逻辑

    首先,这段代码的应用逻辑(application logic)和用户行为混在一起了。就是说:这个事件的处理方法和点击事件连在一起了,从而导致耦合度的提高。

    这个情况其他语言中也很常见,通常我们将处理逻辑封装起来从而可以把代码重用,所以作者提出了很重要的思想:

    将应用逻辑从所有事件处理程序中抽离出来的做法是一种最佳实践。

     将代码重构一下变成这样:

             // 好的写法 - 拆分应用逻辑
             var MyApplication = {
                 handleClick: function(event){
                       this.showPopUp(event);
                 },
    
                 showPopUp: function(event) {
                      var popup = document.getElementById("popup");
                      popup.style.left = event.clientX + "px";
                      popup.style.top = event.clientY + "px";
                      popup.className = "reveal";
                 }
             };
             
             addListener(element, "click", function(event) {
                     MyApplication.handleClick(event);
             });

     

    7.3 规则2:不要分发事件对象

    上述代码还存在一个问题:即event对象被无节制地分发。event对象上包含很多的和事件相关的额外信息,而这段代码只用到了其中俩个而已。

    作者提供了俩个理由:

    1. 方法接口并没有表明那些数据是必要的。好的API一定是对于期望和依赖都是透明的。(译者在此也加了译注:大多数情况并不理想,主要看第二点)。
    2. 方便测试

    最佳的办法是让事件处理程序使用event对象来处理事件,然后拿到所有需要的数据传给应用逻辑。

    将代码重构一下:

             // 好的写法
             var MyApplication = {
    
                 handleClick: function(event){
                       this.showPopUp(event.clientX,event.clientY); // 这里标明所期待传入的参数
                 },
    
                 showPopUp: function(x,y) { // 这里的参数就不再依赖event咯
                      var popup = document.getElementById("popup");
                      popup.style.left = x + "px"; 
                      popup.style.top = y + "px";
                      popup.className = "reveal";
                 }
             };
    
             addListener(element, "click", function(event) {
                     MyApplication.handleClick(event);
             });

    测试时或者代码的任意位置都很轻易调用这段逻辑:

             // 这样调用非常棒
             MyApplication.showPopUp(10, 10);

    最后,当处理事件时,最好让事件处理程序成为接触到event对象的唯一的函数。事件处理程序应当在进入应用逻辑之前针对event对象执行任何必要的操作,包括阻止默认事件或阻止事件冒泡,都应当直接包含在事件程序中。

             // 好的写法
             var MyApplication = {
    
                 handleClick: function(event){
    
                       // 假设事件支持DOM Level2
                       event.preventDefault();
                       event.stopPropagation();
    
                       // 传入应用逻辑
                       this.showPopUp(event.clientX,event.clientY);
                 },
    
                 showPopUp: function(x,y) {
                      var popup = document.getElementById("popup");
                      popup.style.left = x + "px";
                      popup.style.top = y + "px";
                      popup.className = "reveal";
                 }
             };

    在这段代码中,MyApplication.handleClick()是事件处理程序,因此它在数据传入应用逻辑之前调用 event.preventDefault()和 event.stopPropagation(),这清楚的展示了事件处理程序和应用逻辑之间的分工。因为应用逻辑不需要对event产生依赖,进而在很多地方都可以轻松地使用相同的业务逻辑,包括写测试代码。

  • 相关阅读:
    Unable to lock the administration directory (/var/lib/dpkg/)解决办法
    Linux实训——搭建动态网站
    Linux实训——搭建HTTP服务器
    小程序学习视频教程
    数组的所有方法
    小程序组件封装步骤
    微信小程序生成图片学习
    小程序组件封装学习地址
    开发者在 onPageNotFound 回调中进行重定向处理onPageNotFound(Object)
    小程序中view的自定义属性获取
  • 原文地址:https://www.cnblogs.com/xhy-steve/p/5132793.html
Copyright © 2020-2023  润新知