欢迎欢迎

解耦UI层-可维护的Javascript 编写指南

 

可维护的Javascript 编写指南-解耦UI层                       

 

回到目录

本节规则比较好掌握,实用,就是一句话:该写的哪的,就应该写在哪。

这句话解释下:Dom的css样式,就应该写在css样式表里,js代码就该写在js代码中。

 

让我正式给各位看官介绍下主要内容吧。

  • 不要在Css中写js
  • 不要在Js中写Css
  • 不要在Html中写js


在做过项目中,遵循上面三点的少之又少。

那为啥还要这么要求呢?

目的只有一个就是解耦代码,便于维护,特别是针对那么多页面,多js的项目。

不要在Css中写js

/* 不推荐的代码 如果expression出错,在浏览器很难跟踪问题 */
.box {
  width:expression(document.body.offsetWidth+"px");
}

不要在Js中写Css

在页面中出现Css需要进行样式调整时,不需要考虑Js代码,只需要去改css就可以了。

// 不推荐
element.style.color="red";

// 不推荐
element.style.color="red";
element.style.left="10px";
element.style.top="10px";
element.style.visibility="visible";

// 不推荐
element.style.cssText = "color: red; left: 10px; top: 100px; visibility: hidden";

需要样式调整的,可以在Css中定义class 

.reveal {
color: red;
left: 10px;
top: 100px;
visibility: visible;
}

然后在Js中,可以通过操作class控制样式调整

// 推荐 - 原生
element.className += " reveal";

// 推荐 - HTML5
element.classList.add("reveal");

// 推荐 - jQuery
$(element).addClass("reveal");

这样一来,样式一旦需要调整,可直接通过css修改

不要在Html中写Js

一个页面经常有多个js代码,也就造就了多个js同时操作一个Dom,同一个事件。

<!-- 不推荐 -->
<button onclick="doSomething()" id="action-btn">Click Me</button>

这是常见的写法,这种写法在很多场景下,应用都没问题。但是有几个不易发现的问题

首先,当按钮被点击时,doSomething()事件必须存在,否则,Js就报错.doSomething()可能是从外部Js中加载的,或者出现在Html代码后面。无论哪种方式,用户都可以在函数可用之前单击按钮,造成一个JavaScript错误。出现Js错误,直接导致按钮操作不了,这两种情况下是不可取的。

 

第二个问题是维护问题。如果你想改变doSomething()的名字吗?当点击按钮的时候,调用一个不同的函数会发生什么?在这两种情况下,你都在修改JavaScript和HTML;这就是紧密耦合代码的本质。

因此把事件绑定,直接写在<script></script>里,才是上策。

function doSomething() 
{
// code } var btn = document.getElementById("action-btn"); btn.addEventListener("click", doSomething, false); // IE8之前的版本不支持 addEventListener事件,可以这样写 function addListener(target, type, handler)
{
if(target.addEventListener){ target.addEventListener(type, handler, false); }else if (target.attachEvent){ target.attachEvent("on" + type, handler); }else{ target["on" + type] = handler; } }

目前,Jquery是常用的Js库,你可以这样写:

function doSomeThing()
{
   // code  
}

$("#btn1").on("click",doSomeThing);

//或者
$(document).on("#btn1","click",doSomeThing);

另外,最好不要单独把方法的引用放在Js中

<!-- 不推荐 -->
<script>
   doSomething();
</script>

 

避免把HTML掺杂在Js中

  • 简单客户端模版
  • 复杂的客户端模版

前面提倡,不要把Js写在HTML中,同理,不要把Html写在Js中。坚持JS,HTML,CSS解耦,对后期页面维护,debug都有更好的作用。

// 这是项目中常见的代码,并不推荐这样用
var div = document.getElementById("my-div");
div.innerHTML = "<h3>Error</h3><p>Invalid e-mail address.</p>";

 简单客户端模版

将模版直接固定,每次生成时,都是通过调用方法,去生成HTML

function sprintf(text) 
       {
        var i=1, args=arguments;
        return text.replace(/%s/g
                            , function()
                              {
                                 return (i < args.length) ? args[i++] : "";
                              });
       }
       
       var templateText='<li><a href="%s">%s</a></li>';
       var result=sprintf(templateText, "/item/4", "Fourth item");

 还可以这样写

<html lang="en" xmlns="http://www.w3.org/1999/xhtml">
<head>
    <meta charset="utf-8" />
    <title></title>
    <script>
            function sprintf(text) {
                var i = 1, args = arguments;
                return text.replace(/%s/g, function () {
                    return (i < args.length) ? args[i++] : "";
                });
            }

            function addItem(url, text) {
                var mylist = document.getElementById("mylist"),
                    templateText = mylist.firstChild.nodeValue,
                    result = sprintf(templateText, url, text);
                mylist.innerHTML += result;

            }
            addItem("/item/4", "Fourth item");
    </script>
</head>
<body>
    <ul id="mylist">
        <!--<li><a href="%s">%s</a></li>-->
        <li><a href="/item/1">First item</a></li>
        <li><a href="/item/2">Second item</a></li>
        <li><a href="/item/3">Third item</a></li>
    </ul>

</body>
</html>

 另一种写法

<html lang="en" xmlns="http://www.w3.org/1999/xhtml">
<head>
    <meta charset="utf-8" />
    <title></title>
    <script type="text/x-my-template" id="list-item">
        <li><a href="%s">%s</a></li>
    </script>
</head>
<body>
    <ul id="mylist">
        <!--<li><a href="%s">%s</a></li>-->
        <li><a href="/item/1">First item</a></li>
        <li><a href="/item/2">Second item</a></li>
        <li><a href="/item/3">Third item</a></li>
    </ul>
    <script>
        function sprintf(text) {
            var i = 1, args = arguments;
            return text.replace(/%s/g, function () {
                return (i < args.length) ? args[i++] : "";
            });
        }
        function addItem(url, text) {
            var mylist = document.getElementById("mylist"),
                script = document.getElementById("list-item"),
                templateText = script.text,
                result = sprintf(templateText, url, text),
                div = document.createElement("div");
            div.innerHTML = result.replace(/^\s*/, "");
            mylist.innerHTML += result.replace(/^\s*/, "");
        }
        // usage
        addItem("/item/4", "Fourth item");
    </script>

</body>
</html>

复杂的客户端模版

例如 dataTable,knockout.js

如knockout.js 地址: http://knockoutjs.com/

这种模版,也是项目中常用到的。这里就不赘述了,想了解的,可以通过上面的链接,去访问官方网站。

 

posted @ 2017-10-18 14:25  田间的守望  阅读(348)  评论(0编辑  收藏  举报