Angularjs 当以异步方式填充作用域时,应如何将数据传递到指令中

Angularjs 当以异步方式填充作用域时,应如何将数据传递到指令中,angularjs,asynchronous,coffeescript,angularjs-directive,Angularjs,Asynchronous,Coffeescript,Angularjs Directive,我有一个控制器,它异步填充一些数据。该数据由指令使用 不幸的是,该指令没有显示数据。如果我删除超时(这是模拟异步进程的),那么一切都会正常工作 我想知道最好的解决办法是什么。我很确定这是一种常见的情况——我的做法是错误的。是否有办法将指令从“加载”延迟到填充范围中的数据 HTML: html head link( href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css",rel="styleshe

我有一个控制器,它异步填充一些数据。该数据由指令使用

不幸的是,该指令没有显示数据。如果我删除超时(这是模拟异步进程的),那么一切都会正常工作

我想知道最好的解决办法是什么。我很确定这是一种常见的情况——我的做法是错误的。是否有办法将指令从“加载”延迟到填充范围中的数据

HTML:

html
  head
    link(
  href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css",rel="stylesheet",type="text/css")  
    title Hello World
  body(ng-app="app")
    .container

      .well.
        How should data be passed into a directive when a scope is populated asyncronysly

      div(ng-controller="StoogeCtrl")

       .panel.panel-default
          .panel-heading
            | All 
          .panel-body
            ul
              li(ng-repeat="stooge in stooges") {{stooge.name}}

        .panel.panel-default
          .panel-heading
            | Noe Moe
          .panel-body
            div(filter-stooge except="Moe" stooges="stooges")
app = angular.module 'app', []

app.controller 'StoogeCtrl', ($scope, $q, $timeout)->
  stooges = [
    {name: "Moe"}
    {name: "Larry"}
    {name: "Curly"}
  ]

  getPromise = ()->
    dfd = $q.defer()
    dfd.resolve(bars)
    dfd.promise

  $timeout ()->
    $scope.stooges = stooges




app.directive 'filterStooge', ()->
  scope:
    stooges: '='
    except: '@'
  template: "<ul )><li ng-repeat='stooge in filtered'>{{stooge.name}}</li></ul>"
  link: (scope)->
    filtered = []
    for stooge in scope.stooges
      filtered.push stooge if stooge.name != scope.except
    scope.filtered = filtered
JavaScript(咖啡脚本):

html
  head
    link(
  href="//maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css",rel="stylesheet",type="text/css")  
    title Hello World
  body(ng-app="app")
    .container

      .well.
        How should data be passed into a directive when a scope is populated asyncronysly

      div(ng-controller="StoogeCtrl")

       .panel.panel-default
          .panel-heading
            | All 
          .panel-body
            ul
              li(ng-repeat="stooge in stooges") {{stooge.name}}

        .panel.panel-default
          .panel-heading
            | Noe Moe
          .panel-body
            div(filter-stooge except="Moe" stooges="stooges")
app = angular.module 'app', []

app.controller 'StoogeCtrl', ($scope, $q, $timeout)->
  stooges = [
    {name: "Moe"}
    {name: "Larry"}
    {name: "Curly"}
  ]

  getPromise = ()->
    dfd = $q.defer()
    dfd.resolve(bars)
    dfd.promise

  $timeout ()->
    $scope.stooges = stooges




app.directive 'filterStooge', ()->
  scope:
    stooges: '='
    except: '@'
  template: "<ul )><li ng-repeat='stooge in filtered'>{{stooge.name}}</li></ul>"
  link: (scope)->
    filtered = []
    for stooge in scope.stooges
      filtered.push stooge if stooge.name != scope.except
    scope.filtered = filtered
app=angular.module'app',[]
app.controller'StoogeCtrl',($scope,$q,$timeout)->
走狗=[
{名称:“Moe”}
{姓名:“拉里”}
{name:“Curly”}
]
getPromise=()->
dfd=$q.defer()
dfd.resolve(条形图)
承诺
$timeout()->
$scope.stooges=stooges
应用程序指令'filterStooge',()->
范围:
斯多格斯:'='
除了:“@”
模板:“
  • {{stooge.name}
  • ” 链接:(范围)-> 过滤=[] 适用于范围内的stooge。stooges 如果stooge.name!=范围 scope.filtered=filtered
    基于ExpertSystem(以下)的回答。我这样做:

    app = angular.module 'app', []
    
    app.controller 'StoogeCtrl', ($scope, $q, $timeout)->
      stooges = [
        {name: "Moe"}
        {name: "Larry"}
        {name: "Curly"}
      ]
    
      getPromise = ()->
        dfd = $q.defer()
        dfd.resolve(bars)
        dfd.promise
    
      $timeout ()->
        $scope.stooges = stooges
        $scope.done = true
      ,
      3000
    
    
    
    
    app.directive 'filterStooge', ()->
      scope:
        stooges: '='
        except: '@'
        done: '='
      template: "<ul><li ng-repeat='stooge in filtered'>{{stooge.name}}</li></ul>"
      link: (scope)->    
        scope.$watch 'done', (newVal, oldVal)->
          if newVal
            filtered = []
            for stooge in scope.stooges
              filtered.push stooge if stooge.name != scope.except
            scope.filtered = filtered
    
    app=angular.module'app',[]
    app.controller'StoogeCtrl',($scope,$q,$timeout)->
    走狗=[
    {名称:“Moe”}
    {姓名:“拉里”}
    {name:“Curly”}
    ]
    getPromise=()->
    dfd=$q.defer()
    dfd.resolve(条形图)
    承诺
    $timeout()->
    $scope.stooges=stooges
    $scope.done=true
    ,
    3000
    应用程序指令'filterStooge',()->
    范围:
    斯多格斯:'='
    除了:“@”
    完成:'='
    模板:“
    • {{stooge.name}
    ” 链接:(范围)-> 范围。$watch'done',(newVal,oldVal)-> 如果纽瓦尔 过滤=[] 适用于范围内的stooge。stooges 如果stooge.name!=范围 scope.filtered=filtered
    数据不显示,因为您显示过滤后的数据,并且在创建
    过滤后的
    时,
    $scope.stooges中没有数据(因此您是某种过滤和空数组,这当然会导致空数组)

    您有以下选择:

    • $watch
      覆盖
      $scope.stooges
      并在其更改后重新构建过滤后的

    • 在视图中使用过滤(这可能是更好的做法)。创建自己的过滤器(如果需要高级过滤功能)或使用内置的
      过滤器
      过滤器

    例如:

    app.directive('filterStooge', function () {
        return {
            scope: {
                stooges: '=',
                except:  '@'
            },
            template:
                '<ul>' +
                '    <li ng-repeat="stooge in stooges | filter:filterSpec">' +
                '        {{stooge.name}}' +
                '    </li>' +
                '</ul>',
            link: function filterStoogePostLink(scope, elem) {
                // If `except` is specified, exclude items by name.
                // If `except` is not specified, show all items.
                scope.filterSpec = scope.except ?
                    {name: '!' + scope.except} : 
                    '';
            }
        };
    });
    
    应用程序指令('filterStooge',函数(){ 返回{ 范围:{ stooges:“=”, 除了:“@” }, 模板: “
      ”+ “
    • ”+ “{stooge.name}”+ “
    • ”+ “
    ”, 链接:函数过滤器ToogePostLink(范围,元素){ //如果指定了'except',则按名称排除项目。 //如果未指定'except',则显示所有项目。 scope.filterSpec=scope.except? {name:'!'+作用域。除了}: ''; } }; });

    另请参见此


    顺便说一句,您可以在其中重复
      元素(这将导致多个
        s.
        我假设您想要重复
      • 元素。

        为什么添加一个过滤器能让它工作呢?如果我不需要过滤器,你会采取什么方法呢?@ek_ny:我在回答的顶部解释了所有这些。基本上,你就是这样发生的:1.
        stooges
        是空的2.
        过滤的
        是从(空的)中的数据创建的
        stooges
        3.
        stooges
        被分配到一个新的非空数组。此时
        stooges
        包含数据,但
        filtered
        对它一无所知(它是基于以前的
        stooges
        的空版本创建的)。“为什么添加筛选器会使它工作?”:与视图中的过滤器不同的是,Angular足够聪明,可以在数据更改时重新过滤数据。“如果我不需要过滤器如何”:那么我猜您不会使用过滤器:)(只需在视图中使用
        stooges
        )。“你会采取什么方法”:我会在我的答案中采用这种方法(这就是为什么我把它作为一个答案发布的原因)。在我的答案的顶部,我还提到了其他的选择。