我试图通过ngModel绑定一个属性,在3层深度的指令层中。这样就可以了,除了中间级别包含ng-if
,我相信它会创建一个新的范围。此时绑定已丢失。
我创建了一个jsfiddle来解释这种情况: http://jsfiddle.net/5fmck/2/
请注意,如果删除了ng-if
指令,它会有效,但出于性能原因,我使用的是ng-if
而不是ng-show
有没有人知道如何从小提琴中的'inputDirective'模板更新原始ngModel?
答案 0 :(得分:5)
简单:3
请记住,创建了子范围=使用对$ parent的引用:)
<div ng-if='someCondition'>
<span>In Wrapper</span>
<input-directive ng-model='$parent.ngModel'></input-directive>
</div>
// upd
据我所知,只有当ngModel是原始的而不是对象时才需要使用$ parent的引用。
答案 1 :(得分:0)
我怀疑这是由于范围如何从彼此继承的性质,因此您应该使用范围上的对象,而不是基元,并且如果要使用它们,则始终通过属性将对象传递给指令在另一个范围内。所以而不是:
$scope.test = "test";
和
<wrapper-directive ng-model="test" some-condition="true">
使用:
$scope.userInput = {
test: "Test"
}
和
<wrapper-directive user-input="userInput" some-condition="true">
可以在http://jsfiddle.net/4RBaN/1/看到(我也将ngModel中的所有一个更改为另一个自定义属性,就好像你没有使用ngModel特定的东西,比如ngModelController,或者与ngForm集成) ,那我觉得KISS更好。
原因是如果父/子关系中有2个范围(通过原型继承),例如ngIf
创建的范围,如果执行(或者如果Angular执行):
$parentScope.test = 'test';
$childScope.test = 'My new value';
然后$parentScope.test
仍将等于'test'
。但是,如果您使用对象:
$parentScope.userInput = {test: 'test'}
$childScope.userInput.test = 'My new value';
然后$parentScope.userInput.test
将等于'My new value'
。
Angular的原始作者(我认为是)的标准引用是“如果你的模型中没有一个点,你做错了”。关于此,还有其他问题,例如If you are not using a .(dot) in your AngularJS models you are doing it wrong?
编辑:如果你确实想使用ng-model,并且总是将一个原语传递给指令而不是一个对象,那么有一种方法允许这样做。你需要:
始终确保在每个指令中传递给ngModel
的模型中都有一个点。因此,每个指令都需要在其控制器(或链接函数)的作用域上创建一个新对象。因此,“中间”指令的模板将是:
<input-directive ng-model='userInput.test'>
在其控制器中:
$scope.userInput = {
test: $scope.ngModel
}
其中ngModel绑定到指令属性中指定的值:
"scope" : {
"ngModel" : "="
}
在每个指令中设置手动观察者,以便从内部指令对模型的更改传播回链中:
$scope.$watch('userInput.test', function(newTest) {
$scope.ngModel = newTest;
});
可以在http://jsfiddle.net/zT9sD/看到。我不得不说,感觉有点复杂,所以我不太确定我能推荐它。尽管如此(在我看来)比使用$parent
更好,因为随着事情变得更复杂,引入新范围很容易发生,然后你将不得不使用像$parent.$parent
这样的东西。