角形式。如何获得一些重新评估他人的投入?

时间:2016-01-20 16:34:12

标签: javascript angularjs forms angular-ngmodel

我有一个角度形式,表示分类文本输入和ID输入。该ID必须是该类别的唯一ID。如果我有Cat1的以下项目:

Cat1 - 123
Cat1 - 245
Cat1 - 456

然后,如果我尝试输入类别为Cat1且ID为123的新项目,则该输入对该类别不具有唯一性,且无法提交表单。如果ID更改为1234,那么它将有效。

为实现这一点,我有一个名为unique的自定义指令,需要ngModel。它看起来像这样 -

HTML -

<input name="ID"
       required
       unique="id in getItemsByCategory(newCategory)"
       type="text"
       ng-model="newId"></input>

JS -

.directive('unique', function() {
    return {
      require: '^ngModel',
      link: function(scope, ele, attr, ngModelController) {
        ngModelController.$validators.unique = function(val) {
          var uniqueInRegex = /([^\s]+)\s+in\s([^\s]+)/i;

          var matches = attr.unique.match(uniqueInRegex);
          var property = matches[1];
          var collection = scope.$eval(matches[2]);

          for(var i = 0; i < collection.length; i++) {
            var item = collection[i];
            if(item[property] === val) {
              console.log('not unique');
              return false;
            }
          }

          console.log('unique');
          return true;
        };
      }
    };
  });

哪种方法正常:

enter image description here

但是如果验证器根据类别发现字段不唯一,并且类别字段发生变化,则验证器不会重新审核。

enter image description here

以下是这些GIF中看到的内容的JSBin:

http://jsbin.com/wubesutugo/edit?html,js,output

无论如何我可以有一个输入&#34;触摸&#34;变化时的另一个输入?我希望这个验证指令是通用的,因为我有多个地方我想使用它。所以我不想在控制器中使用这个逻辑。

1 个答案:

答案 0 :(得分:0)

使用ng-change的解决方案就足够了。另一种方法是使用手表(确切地说是$watchCollection):

.directive('unique', function() {
    var uniqueInRegex = /([^\s]+)\s+in\s([^\s]+)/i;
    return {
      require: '^ngModel',
      link: function(scope, ele, attr, ngModelController) {
        var matches = attr.unique.match(uniqueInRegex);
        var property = matches[1];
        var collectionExpr = matches[2];

        scope.$watchCollection(collectionExpr, function(newval) {
          ngModelController.$validate();
        });

        ngModelController.$validators.unique = function(val) {
          var collection = scope.$eval(collectionExpr);
          for(var i = 0; i < collection.length; i++) {
            var item = collection[i];
            if(item[property] === val) {
              console.log('not unique');
              return false;
            }
          }

          console.log('unique');
          return true;
        };
      }
    };
})

(还演示了只计算一次正则表达式。)

试一试:http://jsbin.com/wiyugozuje/1/edit?js,console,output