AngularJS自定义指令详解(有分页插件代码)


Posted in Javascript onJune 12, 2017

前言

除了 AngularJS 内置的指令外,我们还可以创建自定义指令。

通过 .directive() 函数来添加自定义的指令。

调用自定义指令时,需要在HTMl 元素上添加自定义指令名。

自定义指令命名规则:使用驼峰命名法来命名,即除第一个单词外的首字母需大写。如: myDirective。

在html页面调用该指令时需要以 - 分割,如: my-directive。示例代码:

<body ng-app="myApp">

<my-directive></my-directive>

<script>
 var app = angular.module("myApp", []);
 app.directive("myDirective", function() {
  return {
   template : "<h1>模板:可以写自己的html页面代码</h1>"
  };
 });
</script>

</body>

html页面调用自定义指令的四种方式

通过在自定义指令里添加 restrict 属性,根据设置不同的值来决定html页面的调用方式,如:

var app = angular.module("myApp", []);
app.directive("myDirective", function() {
 return {
  restrict : "A",//只能通过属性调用
  template : "<h1>自定义指令!</h1>"
 };
});

restrict值的不同,决定了调用方式的不同

属性值 调用方式 示例
A (Attribute首字母) 属性名
C (Class 首字母) 类名
E (Element 首字母) 元素名
M 注释

restrict 默认值为 EA, 即在html页面可通过元素名和属性名来调用自定义指令。

自定义指令属性详解

属性 值类型 说明
restrict string 指令的调用方式,A、C、E、M
priority number 指令执行的优先级
template string 指令使用的模板,可将html页面代码写于此。只能与templateUrl二选其一
templateUrl string 从指定的url地址加载模板。只能与template二选其一
replace boolean 是否用模板替换当前元素。true : 将指令标签替换成temple中定义的内容,页面上不会再有标签;false :则append(追加)在当前元素上,即模板的内容包在标签内部。默认false。
transclude boolean 是否将当前元素的内容转移到模板中
scope boolean /object 指定指令的作用域。false(默认值): 使用父作用域作为自己的作用域(每个引用自定义指令的标签若其中一个标签改变某一变量值,则会影响其他标签的值 )。true: 新建一个作用域,该作用域继承父作用域(两个引用自定义指令的标签之间的变量互不影响)。JavaScript对象:与父作用域隔离,并指定可以从父作用域访问的变量
controller function 定义与其他指令进行交互的接口函数
require string 指定需要依赖的其他指令
link function 以编程的方式操作DOM,包括添加监听器等
compile function 编程的方式修改DOM模板的副本,可以返回链接函数

对表格里的知识进行延伸

1.templateUrl

如果template里拼写的html页面代码十分的多页复杂,拼字符串的话就太麻烦啦,这里我们就可以选择templateUrl。我们可以将要拼写的html页面代码独立到一个页面里,如template.html;然后再指定该html文件所在的路径即可,如templateUrl:”template.html”。用到该自定义指令时,会自动发一个http请求来获取template.html对应的模板内容。这样做的缺点是,多了一个http请求。别急,可以改进的:

angularjs规定了模板还可以用<Script>标签定义:

<script type="text/ng-template" id="template.html">
   <div>自定义指令模板用Script标签定义的方式,须放在html页面ng-controller指令所在标签的内部</div>
</script>

上面代码写在html页面的ng-controller指令所在标签的里面,这样就不用再去请求它了。示例:

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<script src="http://apps.bdimg.com/libs/angular.js/1.4.6/angular.min.js"></script> 
</head>
<body >
 <div ng-app="myApp" ng-controller="myController">

  <!-- 引用自定义指令 -->
  <my-directive></my-directive>

  <!-- 模板代码:须放在myController所在标签内部 -->
  <script type="text/ng-template" id="template.html">
   <div> 自定义指令模板的templateUrl形式</div>
  </script>
 </div>

 <script>
  //创建模块
  var app = angular.module('myApp', []);
  //创建控制器
  app.controller('myController', function($scope) { });
  //创建自定义指令
  app.directive("myDirective", function() {
   return {
    restrict:'E',
    templateUrl : "template.html"
   };
  });
 </script>
</body>

</html>

有多个模板时,我们可以将所有的模板集中在一个文件中,只需加载一次,然后根据id的不同调用不同的模板。

2.transclude

定义是否将当前元素(html页面的自定义指令)的内容转移到模板中。
模板中要接收当前元素内容的标签需要使用ng-transclude指令。

<body >
 <div ng-app="myApp" ng-controller="myController">
  <!-- 引用自定义指令 -->
  <my-directive>自定义指定令内容</my-directive>

  <!-- 模板代码 -->
  <script type="text/ng-template" id="template.html">
   <div> 模板内容</div>
   <div ng-transclude></div>//模板接收上面自定义指令间的内容
  </script>
 </div>

 <script>
  //创建模块
  var app = angular.module('myApp', []);
  //创建控制器
  app.controller('myController', function($scope) { });
  //创建自定义指令
  app.directive("myDirective", function() {
   return {
    templateUrl : "template.html",
     transclude : true//转移到模板中
   };
  });
 </script>
</body>

3.什么是scope的父作用域

引用自定义指令的html页面的控制器所能控制的范围。下面代码的父作用域就是myController所控制的范围

<body >
 <div ng-app="myApp" ng-controller="myController">  
  <my-directive></my-directive><!-- 引用自定义指令 -->
 </div>

 <script>
  //创建模块
  var app = angular.module('myApp', []);
  //创建控制器
  app.controller('myController', function($scope){ });
  //创建自定义指令
  app.directive("myDirective", function() {
   return {
    template : "<h1>自定义指令!</h1>"
   };
  });
 </script>
</body>

4.scope属性的值是对象(object)时的用法

AngularJS内置指令的用法:ng-model=”obj”,通过obj这个变量双向绑定值,controller里变了,html页面也跟着变化。这说明,内置指令不仅可作为属性,还可动态改变值,这个要是不懂的,看看基础语法。如下代码:

<div ng-app="myApp" ng-controller="myController">
 要动态变化的内容: <input ng-model="obj">
</div>

<script>
 var app = angular.module('myApp', []);
 app.controller('myController', function($scope) {
  $scope.obj = "这个字符串值会同步到html里";
 });
</script>

自定义指令当然也需要实现这种功能啦。scope属性为对象时,可为自定义指令指定一个可以绑定值的属性。这里还得说明一下的是,这个scope属性与自定义指令里link属性里的scope参数是一个变量。

<!-- =符号的用法-->
<body >
 <div ng-app="myApp" ng-controller="myController">
  <!-- 引用自定义指令:obj变量与控制器里的objc变量双向绑定了值 -->
  <my-directive speak="obj"></my-directive>
 </div>

 <script>
  //创建模块
  var app = angular.module('myApp', []);

  //创建控制器
  app.controller('myController', function($scope) { 
   $scope.obj="父作用域";//父作用域给自定义指令属性赋的值
  });

  //创建自定义指令
  app.directive("myDirective", function() {
   return {
    template : "<p>模板内容</p>",
    scope:{
     title:"=speak"//定义一个speak属性供html页面的自定义指令用。如果写成title:"="格式,则自定义指令里的属性名就是title。
    },
    link: function postLink(scope, iElement, iAttrs) {
     console.log(scope.title)//这里打印的值与控制器里的值一样
    }
   };
  });
 </script>
</body>

有了前面的一个示例,下面再来说说绑定策略:即用符号前缀给自定义指令传值。它是一个键值对,键是在自定义指令中使用的,值里符号后面的字符串是html页面自定义指令的属性名;如果值里只有符号,则html页面自定义指令的属性名就是键名。

符号 说明 示例
@ 值传递,单向绑定。html页面自定义指令里的val属性的值可传给link的scope使用。第一种写法——str : “@”,这种写法html页面的指令属性名为str str : “@val”,属性名为val
= 双向绑定数据到指令的属性中,数据值可以是任意类型的。第一种写法:name : “=”,这种写法html页面的自定义指令属性名就是name name : “=username”,属性名是username
& 使用父作用域中的一个函数,可以在指令中调用。第一种写法:getName:”&”,这种写法html页面的自定义指令属性名就是gegName getName : “&getUserName”,属性名是getUserName

其余两种符号用法:

<!-- @符号的用法 -->
<body >
 <div ng-app="myApp" ng-controller="myController">
  <!-- 引用自定义指令 -->
  <my-directive title="obj" str="abcd">自定义指定令的内容555</my-directive>
 </div>

 <script>
  //创建模块
  var app = angular.module('myApp', []);
  //创建控制器
  app.controller('myController', function($scope) { 
   $scope.obj="父作用域";//父作用域给自定义指令属性赋的值
  });
  //创建自定义指令
  app.directive("myDirective", function() {
   return {
    template : "<p >模板内容</p>",
    scope:{
     title:"=",
     str:"@"
    },
    link: function postLink(scope, iElement, iAttrs) {
     console.log(scope.str)
     console.log(scope.title)
    }
   };
  });
 </script>
</body>
<!-- &符号的用法 -->
<body >
 <div ng-app="myApp" ng-controller="myController">
  <!-- 引用自定义指令 -->
  <my-directive fun="test()"></my-directive>
 </div>

 <script>
  //创建模块
  var app = angular.module('myApp', []);
  //创建控制器
  app.controller('myController', function($scope) { 
   $scope.test = function(){
     console.log('自定义指令会调用该法,所以这句话会打印到控制台上')
   }
  });
  //创建自定义指令
  app.directive("myDirective", function() {
   return {
    template : "<p >模板内容</p>",
    scope:{
     fun:"&"//属性名直接是fun
    },
    link: function postLink(scope, iElement, iAttrs) {
     scope.fun();//调用父作用域的方法,好似不能传参,未深究。
    }
   };
  });
 </script>
</body>

5.controller属性

controller属性用于提供对外的接口,即该自定义指令会被其他自定义指令调用。所谓的接口,就是this后的变量或方法。

controller可以使用的参数,作用域、节点、节点的属性、节点内容的迁移,这些都可以通过依赖注入被传进来,所以你可以根据需要只写要用的参数,有$scope,Z$element, $attrs, $transclude。

调用该自定义指令的指令需要放在该指令之间。假定firstDirective指令是要被调用的自定义指令,expander是调用者指令。如下:

<first-directive>
  <expander ng-repeat="item in list" attribute="list">{{item.title}}:{{item.text}}</expander>
 </first-directive>

既然firstDirective内部还有指令,则firstDirective必须配置transclude属性为true。代码如下:

//用于被调用的自定义指令
 app.directive('firstDirective',function(){
  return {
   template : '<div ng-transclude></div>',
   replace : true,
   transclude : true,
   controller :function(){
    this.getData = function(val){
      var data = 3 * val;
     return data;
    }
    this.a = "abc";
   }
  }
 });

调用其他指令的自定义指令必须配置require属性指定指令名。然后在link函数里就可注入要调用的指令。

//自定义指令
 app.directive('expander',function(){
  return {
   templateUrl : 'template.html',
   replace : true,
   transclude : true,
   require : '^?firstDirective',//引用其他自定义指令,^表示从父节点开始找,?表示将告诉$compile服务,如果所需的指令没找到,不要抛出异常
   scope : {
    title : '=attribute'
   },
   link : function(scope,element,attris,firstDirct){//注入
    console.log(firstDirct.a)//调用其他指令的变量
    console.log(firstDirct.getData(6)) //调用其他指令的方法    
   }
  };
 });

6.link属性用法

link后的方法在指令中负责执行DOM 操作和注册事件监听器等。link函数有五个参数(scope,element,attrs,controller,linker)。link 方法的参数解释:

scope: 它与自定义指令里的scope属性是一个东西。它是指令scope的引用,所以可改名为sco等其他名字。scope 变量在初始化时是不被定义的,link 方法会注册监视器监视值变化事件。

element: 包含指令的DOM元素的引用, link 方法一般通过jQuery 操作实例(如果没有加载jquery,还可以使用Angular's jqLite )。

controller: 在有嵌套指令的情况下使用。这个参数作用在于把子指令的引用提供给父指令,允许指令之间进行交互,如前面的例子。

注意:当调用link 方法时, 通过值传递(”@”)的scope 变量将不会被初始化,它们将会在指令的生命周期中另一个时间点进行初始化,如果你需要监听这个事件,可以使用scope.$watch 方法。

7.link与compile的区别

compile函数有三个参数(cElement,cAttrs,cLinker),使用compile函数可以在ng创建原始dom实例以及创建scope实例之前,改变原始的dom(template element);可以应用于当需要生成多个element实例但只有一个template element的情况,ng-repeat就是一个最好的例子。它就在是compile函数阶段改变原始的dom生成多个原始dom节点,然后每个又生成element实例。因为compile只会运行一次,所以当你需要生成多个element实例的时候是可以提高性能的。

link函数有五个参数(scope,element,attrs,ctrl,linker)。

link又分为pre-link和post-link,在代码里直接用pre和post表示,当我们直接使用link时,默认跟post一样。我在网上找了个例子来说明一下区别,代码如下:

<body>
 <div ng-app="myApp" ng-controller="myController">
  <level-one>
   <level-two>
    <level-three> Hello </level-three>
   </level-two>
  </level-one>
 </div>
 <script>
   //创建模块
  var app = angular.module('myApp', []);
  //创建控制器
  app.controller('myController', function($scope) { 

  });
  //自定义指令
  function createDirective(name){
   return function(){
   return {
    restrict: 'E',
    compile: function(tElem, tAttrs){
    console.log(name + ': compile => ' + tElem.html());
    return {
     pre: function(scope, iElem, iAttrs){
     console.log(name + ': pre link => ' + iElem.html());
     },
     post: function(scope, iElem, iAttrs){
     console.log(name + ': post link => ' + iElem.html());
     }
    }
    }
   }
   }
  }

  app.directive('levelOne', createDirective('levelOne'));
  app.directive('levelTwo', createDirective('levelTwo'));
  app.directive('levelThree', createDirective('levelThree'));
 </script>
</body>

注意打印结果:

levelOne: compile => 
  <level-two>
   <level-three>
    Hello 
   </level-three>
  </level-two>
 levelTwo: compile => 
   <level-three>
    Hello 
   </level-three>
 levelThree: compile => 
    Hello 
 levelOne: pre link => 
  <level-two>
   <level-three>
    Hello 
   </level-three>
  </level-two>

levelTwo: pre link => 
   <level-three>
    Hello 
   </level-three>

levelThree: pre link => 
    Hello 

levelThree: post link => 
    Hello 
levelTwo: post link => 
   <level-three>
    Hello 
   </level-three>

levelOne: post link => 
  <level-two>
   <level-three>
    Hello 
   </level-three>
  </level-two>

分析打印结果:

运行levelone指令中的compile函数,ng就会递归遍历它的dom节点,然后在level-two与level-three上面重复这些操作。所以会依次打印连续三个compile。

pre会在所有compile执行完后且在所有post之前执行。这样可以在执行post前执行一些其他代码,有些类似AOP。

由上面结果可知,post的执行顺序却是先levelthree最后levelone,即反向调用相关联的post-link函数。这么做的好处是,当我们运行levelone时,保证leveltwo与levelthree都已经执行过了,这样就会更安全。所以默认的link就是post。

一个我做过的分页例子

之所以展示这个代码,主要是给一些朋友看看真实的项目,,多余的东西删掉了,具体的注入这里就不在讲了。

html页面代码:

<div class="wp-20" ng-controller="AppStatisticController" ng-cloak>
 <div class="panel-footer">
  <s-pagination conf="paginationConf"></s-pagination>
 </div>
</div>

控制器代码:

"use strict";//严格

define(["application-configuration", "s-pagination", "tableDataService"], function (app) {
 app.register.controller("AppStatisticController", ["$scope", "$rootScope", "$stateParams","$http", "tableDataService",
  function($scope, $rootScope, $stateParams, $http, tableDataService) {  

   var getTableDataSuccess = function(result) {
    if(result.c == 1) {
     $scope.title = result.title;
     $scope.lists = result.pageList;
     $scope.total = result.data;
     $scope.paginationConf.totalItems = result.total;
    }else if(result.c == 2){
     //弹出框,没有查到数据 
    } else {
     alert(result.i);
    }
   };

   var getTableDataError = function(result) {
    alert(result);
   };
   /*重要的代码,这个paginationConf与自定义指令双向绑定数据*/
   $scope.paginationConf = {
    currentPage: 1,
    itemsPerPage: 10,
    pagesLength: 9,
    search: false,
    onChange: function() {
     var param = {
      "pageNo": this.currentPage,
      "pageSize": this.itemsPerPage,
      "timeType": $scope.formData.timeType,
      "adStyle":$scope.formData.adStyle,
     };
     param.appId = $stateParams.appId;
     tableDataService.getTableData(
      param,
      "ims/appStat.do",
      getTableDataSuccess,
      getTableDataError
     );
    }
   };

   $scope.$watch("formData",function(newValue,oldValue, scope) {
    if(newValue.keywords == oldValue.keywords) {
      $scope.paginationConf.search = true;
    }
   }, true);

  }]);
});

自定义指令代码:也算是angularJS的分页插件

/**
 * 分页插件封装s-pagination.js
 * @date 2016-05-06
 * @author Peter
 */

angular.module('s.pagination', []).directive('sPagination',[function(){//自定义指令
 return {
  restrict: 'E',//仅限元素名调用
  template: '<div class="page-list">' +
  '<ul class="pagination" ng-show="conf.totalItems > 0">' +
  '<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>' +
  '</ul>' +
  '<div class="page-total" ng-show="conf.totalItems > 0">' +
  '第<input type="text" ng-model="jumpPageNum" ng-keyup="jumpToPage($event)"/>页 ' +
  '每页<select ng-model="conf.itemsPerPage" ng-options="option for option in conf.perPageOptions "></select>' +
  '/共<strong>{{ conf.totalItems }}</strong>条' +
  '</div>' +
  '<div class="no-items" ng-show="conf.totalItems <= 0">暂无数据</div>' +
  '</div>',
  replace: true,
  scope: {
   conf: '='//双向绑定数据
  },
  link: function(scope, element, attrs){
   // 变更当前页
   scope.changeCurrentPage = function(item) {
    if(item == '...'){
     return;
    }else{
     scope.conf.currentPage = item;
    }
   };

   // 定义分页的长度必须为奇数 (default:5)
   scope.conf.pagesLength = parseInt(scope.conf.pagesLength) ? parseInt(scope.conf.pagesLength) : 5 ;
   if(scope.conf.pagesLength % 2 === 0){
    // 如果不是奇数的时候处理一下
    scope.conf.pagesLength = scope.conf.pagesLength -1;
   }

   // conf.erPageOptions
   if(!scope.conf.perPageOptions){
    scope.conf.perPageOptions = [10, 20, 30, 40, 50];
   }

   // pageList数组
   function getPagination(newValue, oldValue) {
    //新增属性search 用于附加搜索条件改变时触发
    if(newValue[1] != oldValue[1] || newValue[2] != oldValue[2]) {
     scope.conf.search = true;
    }
    // conf.currentPage
    scope.conf.currentPage = parseInt(scope.conf.currentPage) ? parseInt(scope.conf.currentPage) : 1;

    // conf.totalItems
    scope.conf.totalItems = parseInt(scope.conf.totalItems) ? parseInt(scope.conf.totalItems) : 0;

    // conf.itemsPerPage (default:15)
    scope.conf.itemsPerPage = parseInt(scope.conf.itemsPerPage) ? parseInt(scope.conf.itemsPerPage) : 15;

    // numberOfPages
    scope.conf.numberOfPages = Math.ceil(scope.conf.totalItems/scope.conf.itemsPerPage);

    // judge currentPage > scope.numberOfPages
    if(scope.conf.currentPage < 1){
     scope.conf.currentPage = 1;
    }

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

    // jumpPageNum
    scope.jumpPageNum = scope.conf.currentPage;

    // 如果itemsPerPage在不在perPageOptions数组中,就把itemsPerPage加入这个数组中
    var perPageOptionsLength = scope.conf.perPageOptions.length;
    // 定义状态
    var perPageOptionsStatus;
    for(var i = 0; i < perPageOptionsLength; i++){
     if(scope.conf.perPageOptions[i] == scope.conf.itemsPerPage){
      perPageOptionsStatus = true;
     }
    }
    // 如果itemsPerPage在不在perPageOptions数组中,就把itemsPerPage加入这个数组中
    if(!perPageOptionsStatus){
     scope.conf.perPageOptions.push(scope.conf.itemsPerPage);
    }

    // 对选项进行sort
    scope.conf.perPageOptions.sort(function(a, b){return a-b});

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

      for(i = Math.ceil(offset/2) ; i >= 1; i--){
       scope.pageList.push(scope.conf.currentPage - i);
      }
      scope.pageList.push(scope.conf.currentPage);
      for(i = 1; i <= offset/2; i++){
       scope.pageList.push(scope.conf.currentPage + i);
      }

      scope.pageList.push('...');
      scope.pageList.push(scope.conf.numberOfPages);
     }
    }

    if(scope.conf.onChange){
     //请求数据
     if(scope.conf.search) {
      scope.conf.onChange();
      scope.conf.search = false;
     }

    }
    scope.$parent.conf = scope.conf;
   }

   // prevPage
   scope.prevPage = function(){
    if(scope.conf.currentPage > 1){
     scope.conf.currentPage -= 1;
    }
   };
   // nextPage
   scope.nextPage = function(){
    if(scope.conf.currentPage < scope.conf.numberOfPages){
     scope.conf.currentPage += 1;
    }
   };

   // 跳转页
   scope.jumpToPage = function(){
    scope.jumpPageNum = scope.jumpPageNum.replace(/[^0-9]/g,'');
    if(scope.jumpPageNum !== ''){
     scope.conf.currentPage = scope.jumpPageNum;
    }
   };

   scope.$watch(function() {

    if(!scope.conf.totalItems) {
     scope.conf.totalItems = 0;
    }
    if(angular.isUndefined(scope.conf.search)) {
     scope.conf.search = false;
    }

    var newValue = [scope.conf.totalItems, scope.conf.currentPage, scope.conf.itemsPerPage, scope.conf.search];
    return newValue;
   }, getPagination, true);
  }
 };
}]);

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
利用WebBrowser彻底解决Web打印问题(包括后台打印)
Jun 22 Javascript
js过滤数组重复元素的方法
Sep 05 Javascript
动态加载jquery库的方法
Feb 12 Javascript
js实现编辑div节点名称的方法
Dec 17 Javascript
JQuery实现动态添加删除评论的方法
May 18 Javascript
JavaScript实现点击自动选择TextArea文本的方法
Jul 02 Javascript
轻松搞定jQuery.noConflict()
Feb 15 Javascript
jQuery获取选中单选按钮radio的值
Dec 27 Javascript
JS原型与原型链的深入理解
Feb 15 Javascript
js+canvas实现滑动拼图验证码功能
Mar 26 Javascript
JavaScript实现数字前补“0”的五种方法示例
Jan 03 Javascript
微信小程序实现简易table表格
Jun 19 Javascript
前端构建工具之gulp的语法教程
Jun 12 #Javascript
前端构建工具之gulp的配置与搭建详解
Jun 12 #Javascript
微信小程序 自定义Toast实例代码
Jun 12 #Javascript
Angular4 中常用的指令入门总结
Jun 12 #Javascript
Node.js 8 中的 util.promisify的详解
Jun 12 #Javascript
jquery处理checkbox(复选框)是否被选中实例代码
Jun 12 #jQuery
实现微信小程序的wxml文件和wxss文件在webstrom的支持
Jun 12 #Javascript
You might like
饭制《星际争霸》Mod:优化游戏机制 增加新单位
2017/07/02 星际争霸
PHP register_shutdown_function函数的深入解析
2013/06/03 PHP
ThinkPHP实现多数据库连接的解决方法
2014/07/01 PHP
php mailer类调用远程SMTP服务器发送邮件实现方法
2016/03/04 PHP
简单谈谈php浮点数精确运算
2016/03/10 PHP
php输出形式实例整理
2020/05/05 PHP
分享几种好用的PHP自定义加密函数(可逆/不可逆)
2020/09/15 PHP
基于jquery的3d效果实现代码
2011/03/23 Javascript
js面向对象设计用{}好还是function(){}好(构造函数)
2011/10/23 Javascript
JQuery AJAX 中文乱码问题解决
2013/06/05 Javascript
多种js图片预加载实现方式分享
2016/02/19 Javascript
JS中对Cookie的操作详解
2016/08/05 Javascript
easyui datagrid 大数据加载效率慢,优化解决方法(推荐)
2016/11/09 Javascript
javascript实现简单的可随机变色网页计算器示例
2016/12/30 Javascript
微信小程序实现动态设置placeholder提示文字及按钮选中/取消状态的方法
2017/12/14 Javascript
jquery.onoff实现简单的开关按钮功能(推荐)
2018/05/24 jQuery
vue组件中的样式属性scoped实例详解
2018/10/30 Javascript
微信小程序实现星星评价效果
2018/11/02 Javascript
vue2.0 解决抽取公用js的问题
2020/07/31 Javascript
[36:14]DOTA2上海特级锦标赛D组小组赛#1 EG VS COL第二局
2016/02/28 DOTA
[01:05:41]EG vs Optic Supermajor 败者组 BO3 第二场 6.6
2018/06/07 DOTA
[44:33]EG vs Liquid 2018国际邀请赛小组赛BO2 第二场 8.18
2018/08/19 DOTA
Python命名空间详解
2014/08/18 Python
Python、Javascript中的闭包比较
2015/02/04 Python
Python制作简易注册登录系统
2016/12/15 Python
Python 闭包的使用方法
2017/09/07 Python
Pandas:Series和DataFrame删除指定轴上数据的方法
2018/11/10 Python
对python pandas 画移动平均线的方法详解
2018/11/28 Python
详解python selenium 爬取网易云音乐歌单名
2019/03/28 Python
Python with语句用法原理详解
2020/07/03 Python
python输出国际象棋棋盘的实例分享
2020/11/26 Python
AE美国鹰美国官方网站:American Eagle Outfitters
2016/08/22 全球购物
一些Unix笔试题和面试题
2013/01/22 面试题
《那片绿绿的爬山虎》教学反思
2014/02/27 职场文书
好听的队名和口号
2014/06/09 职场文书
教师年度考核自我评鉴
2015/08/11 职场文书