【问题标题】:Angular 1.2: Is it possible to exclude an input on form dirty checking?Angular 1.2:是否可以排除表单脏检查的输入?
【发布时间】:2015-04-27 14:53:19
【问题描述】:

在下面的示例中,是否可以忽略下拉列表的脏状态?现在,如果用户更改选定的人,它会变得很脏。但我不在乎这个字段在我的表单验证中是否脏。

function TestingCtrl($scope) {
  $scope.company = '';
  $scope.persons = [{
    name: 'Alice'
  }, {
    name: 'Bob'
  }];


  $scope.selectedPerson = $scope.persons[0];

  $scope.checkForm = function() {
    if ($scope.personForm.$dirty) {
      alert('Form is dirty');
    } else {
      alert('Form is clean');
    }
  }

}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.7/angular.min.js"></script>


<div ng-app>

  <div ng-controller="TestingCtrl">

    <form name="personForm" novalidate>
      Company:
      <input type="text" ng-model="company" required>
      <br>Persons:
      <select ng-options="p.name for p in persons" ng-model="selectedPerson"></select>

    </form>

    <br>
    <button ng-click="checkForm()">Check if dirty</button>

  </div>

</div>

【问题讨论】:

  • 如果您不需要验证,请不要将这些控件放在表单旁边
  • 如果你想部分验证你的表单 - 使用 ng-form 指令并检查它的状态(validi/dirty/pristine 等)

标签: angularjs forms validation


【解决方案1】:

boindiil 的基于指令的解决方案有效,但有一个缺陷:如果手动执行表单的$setPritine,它将停止工作。这可以通过添加额外的行来消除输入的方法行为来解决:

angular.module('myApp', []).directive('ignoreDirty', [function() {
    return {
    restrict: 'A',
    require: 'ngModel',
    link: function(scope, elm, attrs, ctrl) {
      ctrl.$setPristine = function() {};
      ctrl.$pristine = false;
    }
  }
}]);

【讨论】:

  • 更新很好:)
【解决方案2】:

我不知道您的表单中是否还有其他输入元素。但在您的情况下,您可以明确检查公司输入是否有问题:

function TestingCtrl($scope) {
  $scope.company = '';
  $scope.persons = [{
    name: 'Alice'
  }, {
    name: 'Bob'
  }];


  $scope.selectedPerson = $scope.persons[0];

  $scope.checkForm = function() {
    var isDirty = false;

    angular.forEach($scope.personForm, function (value, key) {
        // Input element
        if (value.hasOwnProperty('$modelValue') && value.$name!='person') {
            isDirty = isDirty || value.$dirty;
        }
    });
    if (isDirty ) {
      alert('Form is dirty');
    } else {
      alert('Form is clean');
    }
  }

}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.7/angular.min.js"></script>


<div ng-app>

  <div ng-controller="TestingCtrl">

    <form name="personForm" novalidate>
      Company:
      <input name="company" type="text" ng-model="company" required>
      <br>Persons:
      <select name="person" ng-options="p.name for p in persons" ng-model="selectedPerson"></select>

    </form>

    <br>
    <button ng-click="checkForm()">Check if dirty</button>

  </div>

</div>

更新 我已经更新了我的解决方案,现在您可以排除特定的输入字段。但是,每个输入字段都必须设置属性名称

更新 II

一个更简洁的解决方案是使用一个指令,如果设置了特定输入的值,该指令会阻止表单将状态设置为脏。这里有一个例子:

angular.module('myApp', []).directive('ignoreDirty', [function() {
    return {
    restrict: 'A',
    require: 'ngModel',
    link: function(scope, elm, attrs, ctrl) {
      ctrl.$pristine = false;
    }
  }
}]);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="myApp">
  <form name="test">
    Watching dirty: <input ng-model="name" /><br />
    Ignoring dirty: <select ng-model="gender" ignore-dirty>
      <option>male</option>
      <option>female</option>
    </select><br />
    dirty: {{test.$dirty}}
  </form>
</div>

【讨论】:

  • 好主意,但在我的实际应用中,我有很多输入字段,所以这不是一个好的解决方案。
  • 我已经更新了我的解决方案,现在您可以排除特定的输入字段。但是,每个输入字段都必须设置属性名称
  • 我现在发布了一个更好的解决方案
  • Update II 非常好。将使用该解决方案。
  • 我的方法有效,因为只有在值发生更改且当前状态为原始状态时,angular 才会设置脏标志。通过将 pristine 的初始值设置为 false,永远不会设置脏标志。看一下angularjs代码的$commitViewValue函数
猜你喜欢
  • 1970-01-01
  • 2019-04-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-01-13
  • 2021-03-15
  • 2013-10-29
  • 2017-09-25
相关资源
最近更新 更多