基于angular的分页组件插件,使用directive,将directive的内容放到js文件中,直接引用即可

Posted 风起了,风停了

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了基于angular的分页组件插件,使用directive,将directive的内容放到js文件中,直接引用即可相关的知识,希望对你有一定的参考价值。

目录

1、序言

2、分页组件directive的实现

 

内容

1、序言

  在刚学习angular的时候,尝试过自己写html页面,然后使用angular的控制器写一些分页组件的交互就完成了一个基本的分页组件。但是这样对于用户来说操作过程过于繁琐,不仅要关心前端页面的书写,还要处理后台分页组件的逻辑。

  由于之前没有接触过自定义指令,所以去github上download一个demo,这里主要是给出自己的一些理解,以后有类似的需求就可以自行定义插件了。(https://github.com/317482454/tm.pagination 作者项目的链接)

  在这个时候看到angular的自定义指令:directive.自定义指令,通俗一点来讲就是在html中自定义一些东西。

2、分页组件directive的实现

2.1、自定义指令相关的js代码:

angular.module(angular.pagination, []).directive(tmPagination, [function () {
    return {
        restrict: EA,
        template: <div class="page-list"> +
        <ul class="pagination" ng-show="conf.totalItems > 0"> +
        <li ng-class="{disabled: conf.currentPage == 1}" ng-click="prevIndex()"><span>首页</span></li> +
        <li ng-class="{disabled: conf.currentPage == 1}" ng-click="prevPage()"><span>上一页</span></li> +
        <li ng-repeat="item in pageList track by $index" ng-class="{active: item == conf.currentPage, separate: item == \‘...\‘}"  +
        ng-click="changeCurrentPage(item)"> +
        <span>{{ item }}</span> +
        </li> +
        <li ng-class="{disabled: conf.currentPage == conf.numberOfPages}" ng-click="nextPage()"><span>下一页</span></li> +
        <li ng-class="{disabled: conf.currentPage == conf.numberOfPages}" ng-click="nextBack()"><span>尾页</span></li> +
        <li><div>跳转至<input type="text" ng-model="jumpPageNum" ng-keyup="jumpPageKeyUp($event)"</div></li>+
        </ul> +
        <div class="no-items" ng-show="conf.totalItems <= 0">暂无数据</div> +
        </div>,
        replace: true,
        scope: {
            conf: =
        },
        //link 可以简单理解为,当directive被angular 编译后,执行该方法
        //element简单说就是$(‘my-dialog‘)
        //attrs是个map,内容是你这个directive上的所有属性
        link: function (scope, element, attrs) {
            var conf = scope.conf;
            // 默认分页长度
            var defaultPagesLength = 9;
            // 默认分页选项可调整每页显示的条数
            var defaultPerPageOptions = [10, 15, 20, 30, 50];
            // 默认每页的个数
            var defaultPerPage = 11;
            // 获取分页长度
            if (conf.pagesLength) {
                // 判断一下分页长度
                conf.pagesLength = parseInt(conf.pagesLength, 10);

                if (!conf.pagesLength) {
                    conf.pagesLength = defaultPagesLength;
                }

                // 分页长度必须为奇数,如果传偶数时,自动处理
                if (conf.pagesLength % 2 === 0) {
                    conf.pagesLength += 1;
                }

            } else {
                conf.pagesLength = defaultPagesLength
            }

            // 分页选项可调整每页显示的条数
            if (!conf.perPageOptions) {
                conf.perPageOptions = defaultPagesLength;
            }
            if (!conf.totalItems) {
                conf.totalItems=0;
            }
            // pageList数组
            function getPagination(newValue, oldValue) {

                // conf.currentPage
                if (conf.currentPage) {
                    conf.currentPage = parseInt(scope.conf.currentPage, 10);
                }

                if (!conf.currentPage) {
                    conf.currentPage = 1;
                }

                // conf.totalItems
                if (conf.totalItems) {
                    conf.totalItems = parseInt(conf.totalItems, 10);
                }

                // conf.totalItems
                if (!conf.totalItems) {
                    conf.totalItems = 0;
                    return;
                }

                // conf.itemsPerPage
                if (conf.itemsPerPage) {
                    conf.itemsPerPage = parseInt(conf.itemsPerPage, 10);
                }
                
                if (!conf.itemsPerPage) {
                    conf.itemsPerPage = defaultPerPage;
                }

                // numberOfPages 拿到总页数
                conf.numberOfPages = Math.ceil(conf.totalItems / conf.itemsPerPage);
               

                // 如果分页总数>0,并且当前页大于分页总数
                if (scope.conf.numberOfPages > 0 && scope.conf.currentPage > scope.conf.numberOfPages) {
                    scope.conf.currentPage = scope.conf.numberOfPages;
                }

                // 如果itemsPerPage在不在perPageOptions数组中,就把itemsPerPage加入这个数组中
                var perPageOptionsLength = scope.conf.perPageOptions.length;




                // 页码相关
                scope.pageList = [];
                if (conf.numberOfPages <= conf.pagesLength) {
                    // 判断总页数如果小于等于分页的长度,若小于则直接显示
                    for (i = 1; i <= conf.numberOfPages; i++) {
                        scope.pageList.push(i);
                    }
                } else {
                    // 总页数大于分页长度(此时分为三种情况:1.左边没有...2.右边没有...3.左右都有...)
                    // 计算中心偏移量
                    var offset = (conf.pagesLength - 1) / 2;
                    if (conf.currentPage <= offset) {
                        // 左边没有...
                        for (i = 1; i <= offset + 1; i++) {
                            scope.pageList.push(i);
                        }
                    } else if (conf.currentPage > conf.numberOfPages - offset) {
                        for (i = offset + 1; i >= 1; i--) {
                            scope.pageList.push(conf.numberOfPages - i);
                        }
                        scope.pageList.push(conf.numberOfPages);
                    } else {
                        // 最后一种情况,两边都有...
                        for (i = Math.ceil(offset / 2); i >= 1; i--) {
                            scope.pageList.push(conf.currentPage - i);
                        }
                        scope.pageList.push(conf.currentPage);
                        for (i = 1; i <= offset / 2; i++) {
                            scope.pageList.push(conf.currentPage + i);
                        }
                    }
                }
                scope.$parent.conf = conf;
            }

            // prevPage
            scope.prevPage = function () {
                if (conf.currentPage > 1) {
                    conf.currentPage -= 1;
                    getPagination();
                    if (conf.onChange) {
                        conf.onChange();
                    }
                }

            };
            scope.prevIndex = function () {
                if (scope.conf.currentPage > 1) {
                    scope.conf.currentPage = 1;
                    getPagination();
                    if (conf.onChange) {
                        conf.onChange();
                    }
                }

            };
            // nextPage
            scope.nextPage = function () {
                if (conf.currentPage < conf.numberOfPages) {
                    conf.currentPage += 1;
                    getPagination();
                    if (conf.onChange) {
                        conf.onChange();
                    }
                }

            };
            scope.nextBack = function () {
                if (scope.conf.currentPage < scope.conf.numberOfPages) {
                    scope.conf.currentPage = scope.conf.numberOfPages ;
                    getPagination();
                    if (conf.onChange) {
                        conf.onChange();
                    }
                }

            };
            // 变更当前页
            scope.changeCurrentPage = function (item) {

                if (item == ...) {
                    return;
                } else {
                    conf.currentPage = item;
                    getPagination();
                    // conf.onChange()函数
                    if (conf.onChange) {
                        conf.onChange();
                    }
                }
            };

            // 修改每页展示的条数
            scope.changeItemsPerPage = function () {

                // 一发展示条数变更,当前页将重置为1
                conf.currentPage = 1;

                getPagination();
                // conf.onChange()函数
                if (conf.onChange) {
                    conf.onChange();
                }
            };

            // 跳转页
            scope.jumpToPage = function () {
                num = scope.jumpPageNum;
                if (num.match(/\d+/)) {
                    num = parseInt(num, 10);

                    if (num && num != conf.currentPage) {
                        if (num > conf.numberOfPages) {
                            num = conf.numberOfPages;
                        }

                        // 跳转
                        conf.currentPage = num;
                        getPagination();
                        // conf.onChange()函数
                        if (conf.onChange) {
                            conf.onChange();
                        }
                        scope.jumpPageNum = ‘‘;
                    }
                }

            };

            scope.jumpPageKeyUp = function (e) {
                var keycode = window.event ? e.keyCode : e.which;

                if (keycode == 13) {
                    scope.jumpToPage();
                }
            }

            scope.$watch(conf.totalItems, function (value, oldValue) {
                // 在无值或值相等的时候,去执行onChange事件
                if (!value || value == oldValue) {
                    if (conf.onChange) {
                        conf.onChange();
                    }
                }
                getPagination();
            })

        }
    };
}]);

 

2.2、用户调用指令的代码:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>angular分页</title>
    <link rel="stylesheet" href="https://cdn.bootcss.com/bootstrap/3.3.7/css/bootstrap.min.css">
    <link href="css/pagination.css"  rel="stylesheet" >
    <script src="http://code.jquery.com/jquery-3.2.1.js"></script>
    <script src="js/angular.min.js"></script>
    <script src="js/tm.pagination.js"></script>
    <style type="text/css">
        *{
            font: "微软雅黑";
        }
        .page-tip{
            float: left;
            margin: 20px 0;
        }
        .page-pagination{
            float: right;
        }
        .pagination>li>span {
            border: none;
        }
    </style>
</head>
<body ng-app="myApp" ng-controller="testController">
    <div class="col-md-9 page-pagination">
      <tm-pagination conf="paginationConf"></tm-pagination>
  </div> </body> <script> //totalItems 数据的总条数 //itemsPerPage 每页显示数据的条数 angular.module(myApp, [angular.pagination]).controller(testController, [$scope,$location,function ($scope,$location) { $scope.paginationConf = { currentPage: $location.search().currentPage ? $location.search().currentPage : 1, totalItems: 8000, itemsPerPage: 15, pagesLength: 19, perPageOptions: [10, 20, 30, 40, 50], onChange: function(){ console.log($scope.paginationConf.currentPage); $location.search(currentPage, $scope.paginationConf.currentPage); } }; $scope.totalCountNum=8000; $scope.totalPageNum=Math.ceil(8000/15); }]) </script> </html>

2.3 关于自定义指令的说明:

2.3.1 restrict参数

  restrict有三个可选值E/A/C

  E:表示element  调用自定义指令的时候:<my-dir></my-dir>

  A:表示attribute 调用自定义指令的时候:<any my-dir></any>

  C:表示class 调用自定义指令的时候:<any class="my-dir"></any>

2.3.2 replace参数

  replace是一个可选参数,默认值为false,当replace设置为true的时候,会替换directive指向的元素,当replace为默认或者设置为false的时候,directive的内容会作为子元素插入到directive指向的元素。

2.3.3 scope参数

  可选值:false,true,{}

  当值为false的时候:

    在指令模板中可以直接使用父作用域中的变量,函数。代码点击链接:https://codepen.io/mafeifan/pen/kXORKN?editors=1010

    当scope的值设置为false的时候,我们创建的指令和父作用域共享同一个model模型,所以在指令中修改模型数据,它会反映到父作用域的模型中。

  当值为true的时候:

    创建了一个新的作用域,只不过这个作用域继承了我们的父作用域。我们创建的这个作用域是一个新的作用域,只不过在初始化的时候,用了父作用域的属性和方法去填充我们的新作用域,但是父作用域不随着新作用域的改变而改变。

  当值为{}的时候:

    当将scope的值设置为{}的时候,意味着我们创建一个新的与父作用域隔离的新的作用域,用户就可以自定义属性的值来修改数据。上面的2.2的代码就是用户自定义作用域中的数据的实例。

2.3.4 template

  定义的html模板

2.3.5 link函数

  link函数:可以简单的理解为,当directive被angular编译后,就会直接执行link函数。

  link函数包括三个参数:scope、element、attrs

    scope:作用域

    element:类似jQuery对象,这里就是指分页组件这个对象

    attrs:是以map集合的形式存在的,这里指的是用户自定义属性的集合

 

具体的项目地址(找到index.html可直接运行):https://github.com/0513Cassie/angular-pager


以上是关于基于angular的分页组件插件,使用directive,将directive的内容放到js文件中,直接引用即可的主要内容,如果未能解决你的问题,请参考以下文章

采用Vue2.0开发的分页js组件

angularjs中的分页指令

基于 jQuery公司的分页组件

一款基于jQuery的分页插件

基于jQuery封装的分页组件(可自定义设置)

基于springboot+thymeleaf+springDataJpa自带的分页插件实现完整的动态分页