0

ページが最初に読み込まれたときとフォームが送信されたときに、コントローラーが $scope で定義されたメソッドを 2 回トリガーするという問題があります。

これがフィドルです:http://jsfiddle.net/scabro/pQb6q/5/

<div data-ng-app="app" data-ng-controller="AppCtrl">

<form method="post" data-ng-submit="submitForm()">

    <span data-ng-show="showWarning('email')">Please provide valid email address</span>
    <input type="email" name="email" placeholder="Email address" data-ng-model="fields.email.value" />

    <span data-ng-show="showWarning('telephone')">Please provide your telephone number</span>
    <input type="text" name="telephone" placeholder="Telephone" data-ng-model="fields.telephone.value" />

    <span data-ng-show="showWarning('name')">Please provide your name</span>
    <input type="text" name="name" placeholder="Name" data-ng-model="fields.name.value" />

    <button type="submit">Submit</button>

</form>

</div>

そして、ここに 2 つの AngularJs モジュールがあります。最初はコントローラー付きで、もう 1 つは「isValid」ファクトリー サービス付きです。

 angular.module('app', ['validation'])

.controller('AppCtrl', function($scope, $log, isValid) {

    $scope.fields = {

        email : {
            type : 'email',
            value : '',
            required : true
        },
        telephone : {
            type : 'number',
            value : '',
            required : true
        },
        name : {
            type : 'string',
            value : '',
            required : true
        }

    };

    $scope.warnings = [];

    $scope.showWarning = function(field) {

        $log.info($scope.warnings);

        return ($scope.warnings.indexOf(field) !== -1);

    };


    $scope.submitForm = function() {

        $scope.warnings = [];

        isValid.run($scope.fields);

        if (isValid.errors.length > 0) {

            $scope.warnings = isValid.errors;

        }

    };

});


 angular.module('validation', [])

.factory('isValid', function() {

    return {

        errors : [],

        isEmail : function(emailValue) {

          return (
              emailValue.indexOf("@") != -1
          );

        },

        isNumber : function(numberValue) {

            return (
                !isNaN(parseFloat(numberValue)) &&
                isFinite(numberValue)
            );

        },

        isEmpty : function(emptyValue) {

            return (
                emptyValue === '' ||
                emptyValue === 'undefined'
            );

        },

        validateEmail : function(fieldObject, fieldName) {

            if (!this.isEmail(fieldObject.value)) {

                this.errors.push(fieldName);

            }

        },

        validateNumber : function(fieldObject, fieldName) {

            if (!this.isNumber(fieldObject.value)) {

                this.errors.push(fieldName);

            }

        },

        validateEmpty : function(fieldObject, fieldName) {

            if (this.isEmpty(fieldObject.value)) {

                this.errors.push(fieldName);

            }

        },

        type : function(fieldObject, fieldName) {

            switch(fieldObject.type) {

                case 'email':
                    if (fieldObject.required || !this.isEmpty(fieldObject.value)) {
                        this.validateEmail(fieldObject, fieldName);
                    }
                    break;

                case 'number':
                    if (fieldObject.required || !this.isEmpty(fieldObject.value)) {
                        this.validateNumber(fieldObject, fieldName);
                    }
                    break;

                default:
                    if (fieldObject.required) {
                        this.validateEmpty(fieldObject, fieldName);
                    }
                    break;

            }

        },

        resetErrors : function() {

            this.errors = [];

        },

        run : function(fields) {

            this.resetErrors();

            for (var fieldName in fields) {

                if (fields.hasOwnProperty(fieldName)) {

                    this.type(fields[fieldName], fieldName);

                }

            }

        }

    };

});

また、何らかの理由で、検証は最初の 2 つのフィールドに対してのみ機能し、空のフィールドを検証していないようです。

ページが最初にロードされたとき (空の配列) とフォームが最初に送信されたときに、コンソールに表示される内容は次のとおりです。

ここに画像の説明を入力

また、フィールド内で入力するときに、「keydown」イベントごとに showWarning() メソッドを呼び出しているようです。

何が原因でしょうか?

4

2 に答える 2

0

angular標準検証を使用していません。

これは非常に粗雑な電話のカスタム検証の例です

<div data-ng-app="app" data-ng-controller="AppCtrl">
  <form method="post" name="form" data-ng-submit="submitForm()">

    <input required="" type="email" name="email" placeholder="Email address" data-ng-model="fields.email.value" />
    <div data-ng-show="form.email.$dirty && form.email.$invalid">Please provide valid email address</div>
    <br />
    <input required="" valid-telephone type="text" name="telephone" placeholder="Telephone" data-ng-model="fields.telephone.value" />
    <div data-ng-show="form.telephone.$dirty && form.telephone.$invalid">Please provide your telephone number</div>
    <br />
    <input required="" type="text" name="name" placeholder="Name" data-ng-model="fields.name.value" />
    <div data-ng-show="form.name.$dirty && form.name.$invalid">Please provide your name</div>
    <br />
    <button type="submit">Submit</button>
  </form>
</div>

angular.module('app', [])

.controller('AppCtrl', function($scope, $log) {
    $scope.fields = {
        email : {
            value : ''
        },
        telephone : {
            value : ''
        },
        name : {
            value : ''
        }
    };
    $scope.submitForm = function() {

    };

})
.directive('validTelephone', [function() {
  return {
    require: 'ngModel',
    link: function(scope, ele, attrs, c) {
      scope.$watch(attrs.ngModel, function() {
          c.$setValidity('unique', /^\d{10}$/.test(c.$viewValue));
      });
    }
  };
}]);

input.ng-invalid {
  border: 1px solid red;
}

input.ng-valid {
  border: 1px solid green;
}

ここにコードがあります

http://plnkr.co/edit/Y9DzmBNlu9wNiJ1Odljc?p=preview

ここにいくつかのドキュメントがあります

http://scotch.io/tutorials/javascript/angularjs-form-validation

于 2014-03-28T07:11:33.867 に答える