最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Angular: how to bind to requiredngRequired - Stack Overflow

programmeradmin2浏览0评论

I have this directive which can be required or not. It can be used in two ways (as far as I know)

<my-foo required></my-foo>

or

<my-foo ng-required="data.value > 10"></my-foo>

So, because require and ngRequire are basically the same thing you would think that the directive could do this

HTML:

<my-foo ng-require="data.isRequired"></my-foo>

JS:

...
.directive('myFoo', function () {
    return {
    restrict: 'E',
    scope: {
       required: '='
    }
    ...

DEMO

Well, nope, this doesn't work, scope.require is undefined. You actually have to change the scope definition to

scope: {
    required: '=ngRequired'
}

So the question is what is the preferred way to handle both situation such that the value gets stored in scope.required ? Should I defined both or use attrs from the link function ?

I have this directive which can be required or not. It can be used in two ways (as far as I know)

<my-foo required></my-foo>

or

<my-foo ng-required="data.value > 10"></my-foo>

So, because require and ngRequire are basically the same thing you would think that the directive could do this

HTML:

<my-foo ng-require="data.isRequired"></my-foo>

JS:

...
.directive('myFoo', function () {
    return {
    restrict: 'E',
    scope: {
       required: '='
    }
    ...

DEMO

Well, nope, this doesn't work, scope.require is undefined. You actually have to change the scope definition to

scope: {
    required: '=ngRequired'
}

So the question is what is the preferred way to handle both situation such that the value gets stored in scope.required ? Should I defined both or use attrs from the link function ?

Share Improve this question edited May 23, 2017 at 12:10 CommunityBot 11 silver badge asked Jan 7, 2016 at 16:30 Jeanluca ScaljeriJeanluca Scaljeri 29.2k66 gold badges235 silver badges382 bronze badges 3
  • 1 why would you expect this to work? As soon as you use ng-require, you are invoking a separate directive, not passing a parameter to YOUR directive. – David L Commented Jan 7, 2016 at 16:37
  • What does it mean that you have a "directive which can be required or not"? – miensol Commented Jan 7, 2016 at 16:38
  • Its a custom form element, which can have the required attribute. For example you can you require.ngRequire on the input element, why not on my custom element ? – Jeanluca Scaljeri Commented Jan 7, 2016 at 16:39
Add a ment  | 

1 Answer 1

Reset to default 5

There are basically 2 approaches you can pick:

1. Custom form element supporting ng-model

If you peek at the ng-required directive source code you'll find it only deals with ng-model controller:

restrict: 'A',
require: '?ngModel',
link: function(scope, elm, attr, ctrl) {
  if (!ctrl) return;
  attr.required = true; // force truthy in case we are on non input element

  ctrl.$validators.required = function(modelValue, viewValue) {
    return !attr.required || !ctrl.$isEmpty(viewValue);
  };

  attr.$observe('required', function() {
    ctrl.$validate();
  });
}

Thus if you custom directive supports ng-model you already have support for ng-required i.e.:

angular.module('test', [])
.directive('myInput', function(){
  return {
    restrict: 'E',
    require: 'ngModel',
    scope: true,
    template: '<div><button ng-click="changeValue()">Change Value from: {{currentValue}}</button></div>',
    link: function (scope, element, attrs, ngModelCtrl) {
        ngModelCtrl.$parsers.push(function(val){
          if(!val){
            return null;
          }
          return parseFloat(val, 10) * 100;
        });
        ngModelCtrl.$render = function() {
           scope.currentValue = ngModelCtrl.$viewValue || 'No value';
        };
        scope.changeValue = function read(){
          var newValue = Math.random();
          if(newValue > 0.5){
            ngModelCtrl.$setViewValue(newValue + "");
          } else {
            ngModelCtrl.$setViewValue(null);
          }
          ngModelCtrl.$render();
        };
    }
  };
});

2. Wrap existing directive and pass ng-required:

angular.module('test', [])
  .directive('myFormElement', function() {
      return {
        restrict: 'E',
        scope: {
          model: '=',
          required: '='
        },
        template: '<div>Enter number: <input type="number" ng-model="data.number" ng-required="required"></div>'
  };

  });
<script src="https://ajax.googleapis./ajax/libs/angularjs/1.2.23/angular.min.js"></script>


<div ng-app="test" ng-init="data={value:'Initial', required: false}">
  <form>
    Is required: <input type="checkbox" ng-model="data.required">
    <my-form-element required="data.required" model="data"></my-form-element>
  </form>
</div>

发布评论

评论列表(0)

  1. 暂无评论