Loading

几种web数据渲染模板对比

在web开发,实现视图、数据的分离,由前端工程师专门负责编写html页面,有php后台工程师写php接口返回json数字,那么中间如何将json数据绑定到html页面上有几种方法呢。基于这种需求大体上尝试了几种方法:

1)用jQuery加载json数据,操作DOM:

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title>1、测试传统的数据绑定</title>
    <!--引入jquery.js-->
    <script type="text/javascript" src="jquery.js"></script>
    <script type="text/javascript">
        $(document).ready(function(){
            alert("点击之后,修改p1");
            document.getElementById("p1").innerHTML="修改了p1:javascript的DOM操作";
            $("#btn").click(function(){
                showMessage("信息提示:正在请求网络");
                getJSON2();
            });
        });

        function showMessage(msg){
            alert(msg)
        }

        function getJSON2() {
            //jQuery.post()方法
            $.post("http://192.168.1.122/yne_siteM/index.php/Home/Interface/mess2","username=188888",
                    function(data,status) {
                        alert("status="+status);
                        try{
                            /*测试解析json
                            var jsontext = '{"firstname":"Jesper","surname":"Aaberg","phone":["555-0100","555-0120"]}';
                            var data0 = JSON.parse(jsontext);
                            alert(data0.surname);*/
                            //如果取到的已经是json对象,再JSON.parse就可能出错
                           // var data = JSON.parse(json);
                        }catch (e){
                            alert(e.message);
                        }

                        document.getElementById("p1").innerHTML=data.status;  //Y
                        var dataArray = data.data;   //data包含的json数组
                        var contents;
                        for(var i=0 ; i<dataArray.length ; i++) {
                            var jsonObject = dataArray[i];      //这里可以直接取数组下索引
                            var id = jsonObject.id;
                            var title = jsonObject.title;
                            var content = jsonObject.content;
                            contents = "<li>"+title+" "+title+" "+content+"</li>";
                            $("#ol").append(contents);
                        }
                    },
                    "json"
            );
        }

    </script>
</head>
<body>
<h2>This is a heading</h2>
<p id="p1">This is a paragraph.</p>
<p id="p2">This is another paragraph.3333</p>
<div id="newDiv">
    <ol id="ol">
    </ol>
</div>
<button type="button" id="btn">Click me</button>
</body>
</html>

 

2)用jsRender/jsView操作DOM,绑定数据:

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title>2、测试jsView的数据绑定</title>

</head>

<body>
<h2>This is a heading</h2>
<p id="p1">This is a paragraph.</p>
<p id="p2">This is another paragraph.3333</p>
<div id="newDiv">

</div>
<div id="newDiv2">
</div>
<button type="button" id="btn">Click me</button>

<!--官方demo-->
<script id="theTmpl" type="text/x-jsrender">
        <b>{{:title}}</b>
        <ul>
          {{for members}}
              <li >{{:name}} lives in <b>{{:address.city}}</b></li>
          {{/for}}
        </ul>
</script>

<script>
    var data = {
        "title": "The A team",
        "members": [
            {
                "name": "Pete",
                "address": {
                    "city": "Seattle"
                }
            },
            {
                "name": "Heidi",
                "address": {
                    "city": "Sidney"
                }
            }
        ]
    };
    var template = $.templates("#theTmpl");
    var htmlOutput = template.render(data);
    $("#newDiv").html(htmlOutput);
</script>

<script id="theTmpl2" type="text/x-jsrender">
    <b>status={{:status}}</b>
    <b>msg={{:msg}}}</b>
    <ul id="ul1">
        {{for data}}
        <a href="/id={{:id}}">
        <li id="{{:id}}">id={{:id}} title={{:title}} content={{:content}}</li>
        </a>
        {{/for}}
    </ul>

    <ul id="ul2">
        {{for data}}
        <li class="xx.css" id="{{:id}}">id={{:id}} title={{:title}} content={{:content}}</li>
        {{/for}}
    </ul>
</script>

<!--引入jquery.js-->
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="jsviews.js"></script>
<script type="text/javascript">
    var dataArray;
    $(document).ready(function(){
        alert("点击之后,修改p1");
        document.getElementById("p1").innerHTML="修改了p1:javascript的DOM操作";
        $("#btn").click(function(){
            showMessage("信息提示:正在请求网络");
            getJSON2();
        });
    });

    function showMessage(msg){
        alert(msg)
    }


    function getJSON2() {
        //jQuery.post()方法
        $.post("http://192.168.1.122/yne_siteM/index.php/Home/Interface/mess2","username=1888888",
                function(data,status) {
                    alert("status="+status);
                    //绑定UI
                    var template = $.templates("#theTmpl2");
                    var htmlOutput = template.render(data);
                    $("#newDiv2").html(htmlOutput);

                    //监听UI
                    //选取id=ul2 的ul组件下的所有li
                    $("ul#ul2 li").click(function() {
                        alert("id="+$(this).attr("id"));
                    });

                    //监听所有id以a开头的li
//                        $("li[id^='a']").click(function() {
//                            alert("id="+$(this).attr("id"));
//                        })

                },
                "json"
        );
    }

</script>

</body>
</html>

3)用angularJS绑定数据:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <script src="angular.js"></script>
    <script src="jquery.js"></script>
</head>
<body>

<body>

<div ng-app="app1">
    <div id="A1">
        <input ng-model="name" type="text" placeholder="请输入姓名">
        <p>我的姓名: {{name}}</p>
    </div>

    <div id="A2">
        <input ng-model="age" type="number" placeholder="请输入年龄">
        <p>我的年龄: {{age}}</p>
    </div>

    <div id="A3" ng-init="names=['Jani','Hege','Kai']">
        <p>使用 ng-repeat 来循环数组</p>
        <ul>
            <li ng-repeat="x in names">
                {{ x }}
            </li>
        </ul>
    </div>

    <div id="A4" ng-init="names=[
{name:'Jani',country:'Norway'},
{name:'Hege',country:'Sweden'},
{name:'Kai',country:'Denmark'}]">

        <p>循环对象:</p>
        <ul>
            <li ng-repeat="x in names">
                {{ x.name + ', ' + x.country }}
            </li>
        </ul>

    </div>

    <div id="A5" ng-controller="myCtrl1">
        名字: <input ng-model="name">
        <h1>你输入了: {{name}}</h1>
    </div>

    <!--get方法-->
    <div id="A6" ng-controller="myCtrl2">
        <p>ssss {{msg}}</p>
        <ul>
            <li ng-repeat="x in data">id={{x.id}},picurl={{x.picurl}}</li>
        </ul>
    </div>

    <!--post方法-->
    <div id="A7" ng-controller="myCtrl3">
        <p>ssss {{msg}}</p>
        <ul>
            <li ng-repeat="x in data">id={{x.id}},picurl={{x.picurl}}</li>
        </ul>
    </div>
</div>

<!--尽量一个html里面只声明一个ng-app-->
<div id="div2" ng-app="app2" ng-init="points=[1,15,19,2,40]">
    <p>第三个值为 {{ points[2] }}</p>
    <button type="button" id="btn">Click me</button>
</div>


<script> <!--这里不能引入jQuery,会冲突-->
    var app1 = angular.module("app1",[]);
    var app2 = angular.module("app2",[]);
    angular.bootstrap(document.getElementById("div2"),['app2']);

    app1.controller("myCtrl1",function($scope){
        $scope.name = "Joker";
    });

    //get方法
    app1.controller('myCtrl2', function($scope, $http) {
        $http.get("http://192.168.1.122/yne_siteM/index.php/Home/Interface/GetBanner")
            .success(function(response) {
                    $scope.status = response.status;
                    $scope.msg = response.msg;
                    $scope.data = response.data;
                });
    });

//    $.get("http://192.168.1.122/yne_siteM/index.php/Home/Interface/GetBanner")
//            .success(function(){
////                app1.controller("myCtrl2",function($scope){
////                    $scope.msg = "jQuery Get";
////                });
//                alert("ok");
//            });

</script>


</body>


</body>
</html>

 

4)用vue.js绑定数据:

<!DOCTYPE html>
<html xmlns:v-on="http://www.w3.org/1999/xhtml">
<head lang="en">
    <meta charset="UTF-8">
    <title>测试vue.js</title>
</head>
<body>
    <div id="app">
        {{message}}
    </div>

    <!--双向绑定-->
    <div id="app2">
        <p>{{message}}</p>
        <input v-model="message">
    </div>

    <!--渲染列表-->
    <div id="app3">
        <ul>
            <li v-for="todo in todos">
                {{ todo.text }}
            </li>
        </ul>
    </div>

    <!--处理用户输入-->
    <div id="app4">
        <p>{{ message }}</p>
        <button v-on:click="reverseMessage">Reverse Message</button>
    </div>

    <div id="app5">
        <input v-model="newTodo" v-on:keyup.enter="addTodo">
        <ul>
            <li v-for="todo in todos">
                <span>{{ todo.text }}</span>
                <button v-on:click="removeTodo($index)">X</button>
            </li>
        </ul>
    </div>

    <div id="app6">
        <ul>
            <li v-for="todo in todos">
                {{ todo.id }}  {{ todo.title }}
            </li>
        </ul>
    </div>

<!--引入vue.js框架-->
<script type="text/javascript" src="vue.js"></script>
<!--引入jQuery框架-->
<script type="text/javascript" src="jquery.js"></script>

<script>
    new Vue({
        el:"#app",
        data:{
            message: 'Hello Vue.js!'
        }
    });

    new Vue({
        el:"#app2",
        data:{
            message: 'Hello Vue.js!'
        }
    });

    new Vue({
        el:"#app3",
        data:{
            todos:[
                {
                    text: 'Learn JavaScript',
                    title:"111"

                },
                {
                    text: 'Learn Vue.js',
                    title:"222"
                },
                {
                    text: 'Build Something Awesome',
                    title:"333"
                }
            ]
        }
    });

    new Vue({
        el:"#app4",
        data:{
            message: 'Hello Vue.js'
        },
        methods:{
            reverseMessage: function(){
                this.message = this.message.split('').reverse().join('')
            }
        }
    });

    new Vue({
        el:'#app5',
        data:{
            newTodo:'',
            todos:[
                { text:'Add some todos'}
            ]
        },
        methods:{
            addTodo:function() {
                var text = this.newTodo.trim();
                if(text) {
                    this.todos.push({text:text});
                    this.newTodo = ''
                }
            },
            removeTodo: function (index) {
                this.todos.splice(index,1)
            }

        }
    });

     //使用jQuery的post方法获取数据
    $(document).ready(
            function getJSON(){
        $.post('http://192.168.1.122/yne_siteM/index.php/Home/Interface/mess2','username=1888888',function(data,status){
            var todos = data.data;
            //绑定数据
            new Vue({
                el: "#app6",
                data: {
                    todos: todos
                }
            });
        },'json');
    }
    );

</script>
</body>
</html>

 

 

总结一下几种方法的体验:

方法一,jQuery直接操作DOM,会使原来HTML内容不完整,并且数据绑定之后用到大量的字符拼接,在可读性和可维护性上较差;

方法二,一定程度上改善了HTML的可读性,但是也是将一整块html标签抽离了放到<script id="theTmpl2" type="text/x-jsrender"></script>里面,也不够直观。

方法三,angularJS扩展了html,在兼容原来html的基础上通过模型绑定、控制器回调等方法,可以实现不破坏原来html内容的基础上实现数据绑定。但是,测试demo过程中,觉得写起来不够自然和有一定复杂性,而且框架比较大,和jQuery混用的效果也不好,会有一定冲突,在移动端性能可能不太好。

方法四,vue.js一定程度上融合了angularJS的一些优点,如不破坏html结果的前提绑定数据,更加轻量,可以同时用在移动端上,个人觉得比较合适快速开发使用。

 

具体项目demo已上传至github:

https://github.com/chq3272991/testJS.git

 

posted @ 2016-06-20 16:55  集君  阅读(632)  评论(0编辑  收藏  举报