Javascript Angular.js:作用域中的指令对象始终未定义

Javascript Angular.js:作用域中的指令对象始终未定义,javascript,angularjs,angularjs-directive,angularjs-scope,Javascript,Angularjs,Angularjs Directive,Angularjs Scope,编辑:分叉@EliteOctagon的插销,奇怪的是它在工作!无法理解为什么下面的代码不是 EDIT2:分叉上一个Plunk并在控制器逻辑中添加$timeout,控制器停止工作!我猜这真的是装货单。请查看: 我是一个新来的角度,不能让我的头缠绕在望远镜周围 我需要创建一个指令,在我的页面中打印一个,其中包含有关视图控制器中的对象和信息 我试图做的是隔离指令范围并通过具有双向绑定的属性传递对象(请参见下面的代码)。但是,当尝试访问指令的链接函数中的对象时,它总是显示为未定义 我错过了什么 提前谢谢

编辑:分叉@EliteOctagon的插销,奇怪的是它在工作!无法理解为什么下面的代码不是

EDIT2:分叉上一个Plunk并在控制器逻辑中添加$timeout,控制器停止工作!我猜这真的是装货单。请查看:

我是一个新来的角度,不能让我的头缠绕在望远镜周围

我需要创建一个指令,在我的页面中打印一个
,其中包含有关视图控制器中的对象和信息

我试图做的是隔离指令范围并通过具有双向绑定的属性传递对象(请参见下面的代码)。但是,当尝试访问指令的
链接
函数中的对象时,它总是显示为未定义

我错过了什么

提前谢谢各位

指令在html视图模板中的使用:

指令JS代码

.directive('partyStarts', function(){
    return {
        restrict: 'E',
        template: '<div id="partyStart><i class="icon ion-pin"></i> </div>',
        scope: {
            party: '='
        },
        link: function(scope, el) {
            var party = scope.party;
            var icon = el.find('i');
            var statusStr = angular.element('<span/>');
            var final;

            console.log('scope '+scope);

            if(party.Diatodo){
                if(party.datahora.isSame(moment(), 'day') || party.datahora.isSame(moment().add(1, 'd'), 'day')){
                    icon.css({
                        'color': 'green'            
                    });
                    statusStr.text(' É hoje');
                    el.append(statusStr);
                }else{
                    icon.css({
                        'color': '#999'            
                    });
                    statusStr.text(' Começa em '+party.datahora.fromNow());
                    el.append(statusStr);
                }
                return;
            }

            if(party.datahora.unix() == party.datahoraf.unix()){
                final = party.datahora.clone().add(1, 'd').hour(6);
            }else{
                final = party.datahoraf;
            }

            if(party.datahora.twix(final).isCurrent()){
                icon.css({
                    'color': 'green'            
                });
                statusStr.text(' Começou há '+party.datahora.fromNow());
                el.append(statusStr);
            }else if(party.datahora.twix(final).isFuture()){
                icon.css({
                    'color': '#999'            
                });
                statusStr.text(' Começa em '+party.datahora.fromNow());
                el.append(statusStr);
            }else{
                icon.css({
                    'color': 'red'            
                });
                statusStr.text(' Já terminou');
                el.append(statusStr);
            }
        }
    };
})
.directive('partystart',function(){
返回{
限制:'E',

模板:“将指令的party scope变量包装在观察程序中,等待其初始化。在您的情况下,您不这样做,因此在分配scope.party之前,所有逻辑都将运行

link: function(scope, el) {

  var watcher = scope.$watch('party', function() {
    if(scope.party === undefined) return;

    // at this point it is defined, do work

    // delete watcher if appropriate
    watcher();
  })
}

我不认为这是加载顺序的问题。根据我所知,您提供的代码应该可以正常工作。下面是一个plunker,其中有一个工作示例: 还有登录到控制台的日志记录,以验证
scope.party
是否在加载时使用正确的值初始化

单击实时预览(右侧边栏上的眼睛图标)查看示例

另外,前几天在我的推特提要中显示了一个图表,我发现它对于以一种可以理解的方式解释隔离范围非常有用


在我的例子中,未定义的原因是时间不正确。假设您有一个显示产品列表的指令:

<my-products products='httpLoadedProducts'>/<my-products>
如果产品列表来自HTTP请求,则指令很可能在加载产品之前实例化,因此
控制台.log
打印
未定义的

一种解决方案是在加载项后实例化指令。这将确保
链接
函数在加载项后运行

因此,如果
,则用
ng包装指令,如下所示:

<div ng-if='httpLoadedProducts'>
   <my-products products='httpLoadedProducts'>/<my-products>
</div>

/

或者使用wbeange的答案来观察模型的变化。

你能用一些代码创建一个plunker吗?这里是一个空白模板,只要$scope.parent在父控制器内定义,就应该没有问题。你是否可能使用ng if或ng repeat中的party start,从而不必要地创建一个新的子范围?no ng repeat在这里循环,只传递控制器作用域中的一个常规对象$scope.party的父控制器是什么样子?@EliteOctagon刚刚用等效代码分叉了你的plunker,它就工作了…根本无法理解它:(谢谢!我想你是对的。因为我已经将另一个plunker包装在超时中,它停止工作。$timeout可以使它工作,如果超时足够长,但是使用$watch而不是$timeout,因为你不能定义时间。是的,就是这样!非常感谢你看到EDIT2I中更新的plunker我刚刚包装了控制器逻辑。)$timeout是为了验证你的假设,而不是为了解决问题,因为我按照你的建议使用了$watch!:)@wbeange为什么你要用自定义函数包装$watch并反复调用它自己?$watch不是已经在做了吗?很棒的信息图表,真的很有用!谢谢!:D不能投票(没有足够的代表)但我会把它留在这里
+1
:)
<div ng-if='httpLoadedProducts'>
   <my-products products='httpLoadedProducts'>/<my-products>
</div>