加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

AngularJS通用控制器功能 – 在需要的地方混合或在$rootScope上

发布时间:2020-12-17 10:21:52 所属栏目:安全 来源:网络整理
导读:我正在使用AngularJS的v1.2.0 rc2,并想知道为多个控制器提供通用功能的最佳方法是什么. 我有以下验证功能,我想在编辑模型的所有控制器中使用: $scope.canSave = function (formController) { return formController.$dirty formController.$valid;};$scope.
我正在使用AngularJS的v1.2.0 rc2,并想知道为多个控制器提供通用功能的最佳方法是什么.

我有以下验证功能,我想在编辑模型的所有控制器中使用:

$scope.canSave = function (formController) {
    return formController.$dirty && formController.$valid;
};

$scope.validationClasses = function (modelController) {
    return {
        'has-error': modelController.$invalid && modelController.$dirty,'has-success': modelController.$valid && modelController.$dirty
    };
};

我想保持我的控制器干,所以我定义了一个工厂如下:

angular.module('myModule',[])
    .factory('validationFactory',[function () {
        return {
            validationClasses: function (modelController) {
                return {
                    'has-error': modelController.$invalid && modelController.$dirty,'has-success': modelController.$valid && modelController.$dirty
                };
            },isFormValid: function (formController) {
                return formController.$dirty && formController.$valid;
            }
        };
    }]);

最初,我只是将工厂混合到需要它的控制器中,如下所示:

$scope.canSave = validationFactory.isFormValid;

$scope.validationClasses = validationFactory.validationClasses;

但我意识到我可以将它们添加到模块的run方法中的$rootScope中,如下所示:

angular.module('myModule',[])
    .run([
        '$rootScope','validationFactory',function ($rootScope,validationFactory) {
            $rootScope.canSave = $rootScope.canUpdate = validationFactory.isFormValid;
            $rootScope.validationClasses = validationFactory.validationClasses;
        }]);

现在,它们可以在每个控制器中随意使用,并且可以减少布线.

这些函数在视图模板中使用如下:

<form name="questionForm" novalidate>
    <div class="form-group" ng-class="validationClasses(questionForm.question)">
        <label for="questionText" class="control-label">Text</label>
        <input type="text" ng-model="question.text" name="question"
               id="questionText" class="form-control" required/>
        <span ng-show="questionForm.question.$error.required"
              class="help-block">Question text is required</span>
    </div>
    ...
    <div class="form-group" ng-switch on="action">
        <button type="button" ng-switch-when="New" ng-click="save()" 
                ng-disabled="!canSave(questionForm)" 
                class="btn btn-primary">Save</button>
        <button type="button" ng-switch-default ng-click="update()" 
                ng-disabled="!canUpdate(questionForm)" 
                class="btn btn-primary">Update</button>
        <button type="button" ng-click="cancel()"
                class="btn btn-default">Cancel</button>
    </div>
</form>

我的问题是:

>我应该避免在$rootScope中添加常用功能吗?如果是这样,有什么陷阱?
>仅在必要时混合使用常见功能更好吗?
>有没有更好的方法来实现相同的结果?

更新方案

我选择使用自定义指令而不是向$rootScope添加函数,这些函数有一个令人讨厌的气味.

我创建了自定义属性validation-class-for =“< input.name>”和disabled-when-invalid所以标记看起来像这样:

<div class="form-group" validation-class-for="question">
    <label for="questionText" class="control-label">Text</label>
    <input type="text" ng-model="question.text" name="question"
           id="questionText" class="form-control" required/>
    <span ng-show="questionForm.question.$error.required"
          class="help-block">Question text is required</span>
</div>

<button type="button" ng-click="save()" disabled-when-invalid 
    class="btn btn-primary">Save</button>

指令只需要一个表单祖先并观察一个函数来确定状态.

angular.module('myModule',[])
    .directive('validationClassFor',function () {
        return {
            require: '^form',link: function (scope,element,attributes,formController) {
                scope.$watch(function () {
                    var field = formController[attributes.validationClassFor];
                    if (field.$invalid && field.$dirty) {
                        element.removeClass('has-success').addClass('has-error');
                    } else if (field.$valid && field.$dirty) {
                        element.removeClass('has-error').addClass('has-success');
                    } else {
                        element.removeClass('has-error').removeClass('has-success');
                    }
                });
            }
        };
    })
    .directive('disabledWhenInvalid',formController) {
                scope.$watch(function () {
                    return formController.$dirty && formController.$valid;
                },function (value) {
                    element.prop('disabled',!value);
                });
            }
        };
    });

现在也不需要验证工厂.

你是如何使用这个validationFactory的?是否要更改提交按钮的外观?如果是这样,我建议为按钮本身创建自定义组件,并让组件引用validationFactory.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读