angularjs自定义ng-model标签的属性


Posted in Javascript onJanuary 21, 2016

有的时候我们需要为非input类型的元素添加ng-model来实现双向的数据绑定,从而减少冗余代码,那么可以尝试一下的方式

例如:我页面中使用了contenteditable这个属性来实现用户可直接编译的div元素

html:

<style>
    .text{
      margin:0 auto;
      width:100px;
      height:50px;
      border:1px solid red;
    }
  </style>
</head>
<body>
<div ng-controller="selectController">
  <div ng-repeat="pop in citylist">
    <div class="text" contenteditable="true" ng-model="pop.pop"></div>
  </div>
  <button ng-click="cs()">输出新数据</button>
</div>
</body>

但是直接绑定ng-model是肯定得不到数据的,这时就需要为其增加自定义的属性,如下所示。

js:

<script>
  var app = angular.module('app', []);
  app.controller('selectController', function ($scope) {
    $scope.citylist=[{id:1,pop:"北京"},{id:1,pop:"上海"},{id:1,pop:"广州"}];
    $scope.p={};
    $scope.cs=function(){
      console.log($scope.citylist);
    }
  }).directive('contenteditable', function() {//自定义ngModel的属性可以用在div等其他元素中
    return {
      restrict: 'A', // 作为属性使用
      require: '?ngModel', // 此指令所代替的函数
      link: function(scope, element, attrs, ngModel) {
        if (!ngModel) {
          return;
        } // do nothing if no ng-model
        // Specify how UI should be updated
        ngModel.$render = function() {
          element.html(ngModel.$viewValue || '');
        };
        // Listen for change events to enable binding
        element.on('blur keyup change', function() {
          scope.$apply(readViewText);
        });
        // No need to initialize, AngularJS will initialize the text based on ng-model attribute
        // Write data to the model
        function readViewText() {
          var html = element.html();
          // When we clear the content editable the browser leaves a <br> behind
          // If strip-br attribute is provided then we strip this out
          if (attrs.stripBr && html === '<br>') {
            html = '';
          }
          ngModel.$setViewValue(html);
        }
      }
    };
  })
</script>

其中参数类别如下:

angularjs自定义ng-model标签的属性

部分参数解释

restrict:

(字符串)可选参数,指明指令在DOM里面以什么形式被声明;

取值有:E(元素),A(属性),C(类),M(注释),其中默认值为A;

E(元素):<directiveName></directiveName>
A(属性):<div directiveName='expression'></div>
C(类):   <div class='directiveName'></div>
M(注释):<--directive:directiveName expression-->

2.require

字符串代表另一个指令的名字,它将会作为link函数的第四个参数

具体用法我们可以举个例子说明

假设现在我们要编写两个指令,两个指令中的link链接函数中(link函数后面会讲)存在有很多重合的方法,

这时候我们就可以将这些重复的方法写在第三个指令的controller中(上面也讲到controller经常用来提供指令间的复用行为)

然后在这两个指令中,require这个拥有controller字段的的指令(第三个指令),

最后通过link链接函数的第四个参数就可以引用这些重合的方法了。

<!doctype html>
<html ng-app="myApp">
<head>
 <script src="http://cdn.staticfile.org/angular.js/1.2.10/angular.min.js"></script>
</head>
<body>
 <outer-directive>
   <inner-directive></inner-directive>
   <inner-directive2></inner-directive2>
 </outer-directive>
 <script>
  var app = angular.module('myApp', []);
  app.directive('outerDirective', function() {
     return {
        scope: {},
        restrict: 'AE',
        controller: function($scope) {   
         this.say = function(someDirective) { 
           console.log('Got:' + someDirective.message);
         };
        }
      };
  });
  app.directive('innerDirective', function() {
     return {
        scope: {},
        restrict: 'AE',
        require: '^outerDirective',
        link: function(scope, elem, attrs, controllerInstance) {
            scope.message = "Hi,leifeng";
            controllerInstance.say(scope);
        }
     };
  });
  app.directive('innerDirective2', function() {
     return {
        scope: {},
        restrict: 'AE',
        require: '^outerDirective',
        link: function(scope, elem, attrs, controllerInstance) {
            scope.message = "Hi,shushu";
            controllerInstance.say(scope);
        }
     };
  });
 </script>
</body>
</html>

上面例子中的指令innerDirective和指令innerDirective2复用了定义在指令outerDirective的controller中的方法

也进一步说明了,指令中的controller是用来让不同指令间通信用的。

另外我们可以在require的参数值加上下面的某个前缀,这会改变查找控制器的行为:

(1)没有前缀,指令会在自身提供的控制器中进行查找,如果找不到任何控制器,则会抛出一个error

(2)?如果在当前的指令没有找到所需的控制器,则会将null传给link连接函数的第四个参数

(3)^如果在当前的指令没有找到所需的控制器,则会查找父元素的控制器

(4)?^组合

Javascript 相关文章推荐
javascript天然的迭代器
Oct 29 Javascript
奉献给JavaScript初学者的编写开发的七个细节
Jan 11 Javascript
javascript计算用户打开网页的停留时间
Jan 09 Javascript
JQuery+Ajax实现数据查询、排序和分页功能
Sep 27 Javascript
Node.js中JavaScript操作MySQL的常用方法整理
Mar 01 Javascript
浅谈JQuery+ajax+jsonp 跨域访问
Jun 25 Javascript
详解用node编写自己的cli工具
May 23 Javascript
动态创建Angular组件实现popup弹窗功能
Sep 15 Javascript
深入理解Vue Computed计算属性原理
May 29 Javascript
vue上传图片到oss的方法示例(图片带有删除功能)
Sep 27 Javascript
解决Layui数据表格显示无数据提示的问题
Nov 14 Javascript
JS apply用法总结和使用场景实例分析
Mar 14 Javascript
angularjs在ng-repeat中使用ng-model遇到的问题
Jan 21 #Javascript
js实现的二分查找算法实例
Jan 21 #Javascript
jQuery模拟物体自由落体运动(附演示与demo源码下载)
Jan 21 #Javascript
angularjs表格分页功能详解
Jan 21 #Javascript
使用angularjs创建简单表格
Jan 21 #Javascript
Jquery中巧用Ajax的beforeSend方法
Jan 20 #Javascript
Javascript中神奇的this
Jan 20 #Javascript
You might like
PHP substr()函数参数解释及用法讲解
2017/11/23 PHP
PHP设计模式之装饰器(装饰者)模式(Decorator)入门与应用详解
2019/12/13 PHP
ExtJS 简介 让你知道extjs是什么
2008/12/29 Javascript
在模板页面的js使用办法
2010/04/01 Javascript
使用AOP改善javascript代码
2015/05/01 Javascript
jquery.validate使用时遇到的问题
2015/05/25 Javascript
JQuery zClip插件实现复制页面内容到剪贴板
2015/11/02 Javascript
JQuery动态添加Select的Option元素实现方法
2016/08/29 Javascript
Windows环境下npm install 报错: operation not permitted, rename的解决方法
2016/09/26 Javascript
jquery配合.NET实现点击指定绑定数据并且能够一键下载
2016/10/28 Javascript
解决vue页面刷新或者后退参数丢失的问题
2018/03/13 Javascript
解决vue-cli创建项目的loader问题
2018/03/13 Javascript
解决vue-cli webpack打包开启Gzip 报错问题
2019/07/24 Javascript
Vue-axios-post数据后端接不到问题解决
2020/01/09 Javascript
jquery实现鼠标悬浮弹出气泡提示框
2020/12/23 jQuery
vant时间控件使用方法详解
2020/12/24 Javascript
JavaScript实现滚动加载更多
2020/12/27 Javascript
Javascript实现关闭广告效果
2021/01/29 Javascript
20招让你的Python飞起来!
2016/09/27 Python
python pandas 组内排序、单组排序、标号的实例
2018/04/12 Python
python bmp转换为jpg 并删除原图的方法
2018/10/25 Python
Python3.5 处理文本txt,删除不需要的行方法
2018/12/10 Python
python getpass模块用法及实例详解
2019/10/07 Python
关于Tensorflow使用CPU报错的解决方式
2020/02/05 Python
python判断元素是否存在的实例方法
2020/09/24 Python
Django数据统计功能count()的使用
2020/11/30 Python
Bose加拿大官方网站:美国知名音响品牌
2019/03/21 全球购物
Java里面StringBuilder和StringBuffer有什么区别
2016/06/06 面试题
类成员函数的重载、覆盖和隐藏区别
2016/01/27 面试题
机械电子工程专业推荐信范文
2013/11/20 职场文书
工作表扬信范文
2015/01/17 职场文书
党员个人承诺书
2015/04/27 职场文书
2016读书月活动心得体会
2016/01/14 职场文书
Vue和Flask通信的实现
2021/05/19 Vue.js
浅谈Python中的函数(def)及参数传递操作
2021/05/25 Python
漫画「处刑少女的生存之道」第3卷封面公开
2022/03/21 日漫