angularjs - 如何从指令模板访问Object.keys(object).length?

标签 angularjs angularjs-directive

我正在尝试创建一条指令,该指令将列出错误对象({phone: ["is required"])中列出的所有错误,但是仅当对象为非空时,才列出。(说“以下错误……是没有意义的”。当没有的时候。)

我想出了如何通过测试Object.keys(errors).length来检查对象是否为空。 问题是我不知道如何从指令模板访问Object.keys。 这可能吗?

由于Angular表达式是在$parse上下文中而不是eval()上下文中“求值”(使用scope,而不是window),因此我们无法从指令模板访问Object之类的东西,因为Object不是属性范围。 (文档:Expressions)

到目前为止是有道理的。继续说:“与JavaScript默认名称是全局window属性的情况不同,Angular表达式必须显式使用$window来引用全局window对象。例如,如果要在表达式中调用alert(),则必须使用$window.alert()

但是,即使我执行Object,我似乎也无法访问$window.Object。我想念什么?

这是我正在调试的指令的代码(这是jsfiddle):

app.js.coffee:

…
.directive 'displayErrorsAllKeys', ->
  {
    restrict: 'A',
    scope: {
      errors: '='
      debug: '@debug'
    }
    templateUrl: 'templates/display-errors-all-keys'
  }

.run(['$rootScope', ($rootScope) ->
  $rootScope.nonEmpty = (object) ->
    !! Object.keys(object).length
])

.controller('TestDisplayErrorsAllKeys',
['$scope',
( $scope ) ->

  $scope.other_errors = {}

  $scope.add_errors = ->
    $scope.other_errors = {"surname":["is required"],"phone":["is required"]}

  $scope.clear_errors = ->
    $scope.other_errors = {}
])

display-errors-all-keys.ngt.haml:

.errors(ng-show="$window.Object.keys(errors).length > 0")
  %p The following errors prevented this from saving:
  %div(ng-repeat="(key, error_messages) in errors") {{key}}: {{error_messages | toSentence}}

test_ng_display-errors-all-keys.html.haml

:scss
  .errors {
    color: red;
  }

%div(ng-app='MyApp')
  %form(ng-controller="TestDisplayErrorsAllKeys")
    %p errors: {{ other_errors }}
    %p nonEmpty(other_errors): {{ nonEmpty(other_errors) }}
    %hr/

    %div(display-errors-all-keys errors="other_errors")

    %input(type="button" value="Add errors" ng-click="add_errors()")/
    %input(type="button" value="Clear errors" ng-click="clear_errors()")/

通过在我的作用域中定义一个辅助方法并调用该方法($root.nonEmpty(errors)),我终于使它起作用了(有关工作示例,请参见jsfiddle)。

这可能是一个很好的解决方案,但是:
  • 是否有更好的方法来解决此问题?您将如何完成(编写ng-show表达式)?
  • 如何直接在Object.keys(errors).length中使用ng-show使其工作?
  • 最佳答案

    我将在指令范围(独立的)中提供helper函数。通常,通过为指令提供链接功能:

    .directive('displayErrorsAllKeys', function() {
        return {
            restrict: 'A',
            scope: {
                errors: '=',
                debug: '@debug'
            },
            link: function (scope) {
                scope.errorsExists = function(object) {
                    return object && Object.keys(object).length;
                };
            },
            templateUrl: 'templates/display-errors-all-keys'
        };
    })
    

    很少将逻辑和数据放在根范围内是一个好习惯。另请注意,我将函数命名为errorExists,该函数根据错误的实际表示形式提供抽象。

    至于第二个问题,您可以在链接函数中添加scope.Object = Object;,但是不要!这样的特定逻辑不属于您的模板。模板应该关注是否显示错误,而不是为什么。

    关于angularjs - 如何从指令模板访问Object.keys(object).length?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22852388/

    相关文章:

    asp.net - 成功调用ajax后ng-repeat不绑定(bind)

    javascript - 一起使用 .map(.range(1)) 的目的是什么? range 总是返回 [0]?

    javascript - AngularJS DOM 选择器

    angularjs - 指令定义对象的 "require"代表什么?

    AngularJS 在 $http 响应返回后执行链接功能

    javascript - $timeout 如何解决这个问题?

    javascript - 使用 Angular JS ionic 中的 Soap 请求获取 XML 响应

    javascript - 如何从 Angular 日期选择器中禁用分钟和文本(东部标准时间)?

    javascript - AngularJS : ngRepeat in Directive with transcluded content

    javascript - 如何测试 angular 指令的 templateUrl 指向的 HTML?