$scope saved 是嵌套层次结构中最后一个指令的范围
$scope saved is the scope of the last directive in a nested hierarchy
我想嵌套指令并让它们中的每一个都有自己独立的范围。但是,当我点击任何 ID 按钮时,我每次都会得到 ID = 3。
我的代码的实时副本在这里。
http://plnkr.co/edit/Lg29CkN7MkEBsI7uNXR3?p=info
这是我的 html 文件的一部分:
<tcp-widget id="1">
<tcp-widget-header>
<input type="button" value="ID = 1" ng-click="printId()"/>
</tcp-widget-header>
<tcp-widget-body>
<div style="text-align:left; margin:0 auto; border: 1px solid black; width: 300px; padding: 5px;">
<div style="color:red">RED by Taylor Swift</div>
</div>
</tcp-widget-body>
</tcp-widget>
<tcp-widget id="2">
<tcp-widget-header>
<input type="button" value="ID = 2" ng-click="printId()"/>
</tcp-widget-header>
<tcp-widget-body>
<div style="text-align:left; margin:0 auto; border: 1px solid black; width: 300px; padding: 5px;">
<div style="color:blue">BLUE by Big Bang</div>
</div>
</tcp-widget-body>
</tcp-widget>
<tcp-widget id="3">
<tcp-widget-header>
<input type="button" value="ID = 3" ng-click="printId()"/>
</tcp-widget-header>
<tcp-widget-body>
<div style="text-align:left; margin:0 auto; border: 1px solid black; width: 300px; padding: 5px;">
<div style="color:yellow">YELLOW by Coldplay</div>
</div>
</tcp-widget-body>
</tcp-widget>
这是我的小部件的代码:
(function(app) {
app.directive('tcpWidget', function() {
return {
restrict: 'E',
scope: {
id: "="
},
controller: function($scope, $element, $attrs) {
this.printId = function() {
alert("print id : " + $scope.id);
};
}
};
});
})(app);
这是我的小部件的代码 header:
(function(app) {
app.directive('tcpWidgetHeader', function() {
return {
restrict: 'E'
, require: "^tcpWidget"
, link: function(scope, iElem, iAttrs, ctrl){
scope.printId = ctrl.printId;
}
};
});
})(app);
您的 tcp-widget-header 没有隔离范围,因此当您在 link 函数中设置 scope.printId 时,您一直在修改相同的(外部)范围。
这里发生的是 tcp-widget-header
共享范围 - 即它使用默认值 scope: false
。这意味着当你在示波器上设置一些东西时,就像你对
所做的那样
scope.printId = ctrl.printId;
最后一个 tcp-widget-header
"wins" 并将 scope.printId
- 所有人都将使用 - 设置为 "its" tcp-widget
控制器。因此,所有人都会调用控制器函数,其中 $scope.Id === 3
.
因此,一个快速解决方法是将 scope: true
添加到指令定义中。这将为每个 tcpWidgetHeader
:
创建一个子作用域
.directive('tcpWidgetHeader', function() {
return {
scope: true,
// ... whatever you have
}
});
但是,等等!!! 为什么 tcp-widget-header
指令共享相同的范围开始,而不是在其父级的独立范围内?
原因是指令的 DOM 子元素的范围不在该指令范围的范围层次结构中 - 与该指令 template
中的指令和表达式不同。因此,从范围的角度来看,它们都在外部范围内 "live",由所有 tcp-widget
、tcp-widget-header
和 tcp-widget-body
指令共享。
我想嵌套指令并让它们中的每一个都有自己独立的范围。但是,当我点击任何 ID 按钮时,我每次都会得到 ID = 3。
我的代码的实时副本在这里。 http://plnkr.co/edit/Lg29CkN7MkEBsI7uNXR3?p=info
这是我的 html 文件的一部分:
<tcp-widget id="1">
<tcp-widget-header>
<input type="button" value="ID = 1" ng-click="printId()"/>
</tcp-widget-header>
<tcp-widget-body>
<div style="text-align:left; margin:0 auto; border: 1px solid black; width: 300px; padding: 5px;">
<div style="color:red">RED by Taylor Swift</div>
</div>
</tcp-widget-body>
</tcp-widget>
<tcp-widget id="2">
<tcp-widget-header>
<input type="button" value="ID = 2" ng-click="printId()"/>
</tcp-widget-header>
<tcp-widget-body>
<div style="text-align:left; margin:0 auto; border: 1px solid black; width: 300px; padding: 5px;">
<div style="color:blue">BLUE by Big Bang</div>
</div>
</tcp-widget-body>
</tcp-widget>
<tcp-widget id="3">
<tcp-widget-header>
<input type="button" value="ID = 3" ng-click="printId()"/>
</tcp-widget-header>
<tcp-widget-body>
<div style="text-align:left; margin:0 auto; border: 1px solid black; width: 300px; padding: 5px;">
<div style="color:yellow">YELLOW by Coldplay</div>
</div>
</tcp-widget-body>
</tcp-widget>
这是我的小部件的代码:
(function(app) {
app.directive('tcpWidget', function() {
return {
restrict: 'E',
scope: {
id: "="
},
controller: function($scope, $element, $attrs) {
this.printId = function() {
alert("print id : " + $scope.id);
};
}
};
});
})(app);
这是我的小部件的代码 header:
(function(app) {
app.directive('tcpWidgetHeader', function() {
return {
restrict: 'E'
, require: "^tcpWidget"
, link: function(scope, iElem, iAttrs, ctrl){
scope.printId = ctrl.printId;
}
};
});
})(app);
您的 tcp-widget-header 没有隔离范围,因此当您在 link 函数中设置 scope.printId 时,您一直在修改相同的(外部)范围。
这里发生的是 tcp-widget-header
共享范围 - 即它使用默认值 scope: false
。这意味着当你在示波器上设置一些东西时,就像你对
scope.printId = ctrl.printId;
最后一个 tcp-widget-header
"wins" 并将 scope.printId
- 所有人都将使用 - 设置为 "its" tcp-widget
控制器。因此,所有人都会调用控制器函数,其中 $scope.Id === 3
.
因此,一个快速解决方法是将 scope: true
添加到指令定义中。这将为每个 tcpWidgetHeader
:
.directive('tcpWidgetHeader', function() {
return {
scope: true,
// ... whatever you have
}
});
但是,等等!!! 为什么 tcp-widget-header
指令共享相同的范围开始,而不是在其父级的独立范围内?
原因是指令的 DOM 子元素的范围不在该指令范围的范围层次结构中 - 与该指令 template
中的指令和表达式不同。因此,从范围的角度来看,它们都在外部范围内 "live",由所有 tcp-widget
、tcp-widget-header
和 tcp-widget-body
指令共享。