控制器到指令和指令到控制器的正确通信方式
Controller to Directive and Directive to controller correct way of communcation
我有一个页面,其中包含pageNavigator
带页面显示的内容。根据相应按钮(链接)上的用户 click
我正在更新页面。
我将 :page 导航器的指令设为 'docNavigation' 并包含在我的 home
html.
中
现在我需要,
页面加载时,
我的文档页面应该显示 count
正如我在 homeController
中提到的那样,最后的 switch
案例应该设置为 20
我设置在 homeController
.
当用户交互时我想更新homeController
中的count
以更新页面内容。
得到这个的正确方法是什么?
这是我的指令:
"use strict";
angular.module("docNaviDir", [])
.directive("docNavigation", function () {
return {
restrict : "E",
replace : true,
templateUrl : '/views/directiveViews/docNavigation.html',
link : function (scope, element, attr, controller) {
var count = 0;
element.find('a').on('click', function () {
var Id = $(this).prop('id');
switch(Id) {
case 'first':
count = 1; //update to `homeController`
break;
case 'prev':
count -= 1; //update to `homeController`
break;
case 'next':
count += 1; //update to `homeController`
break;
case 'last':
count = scope.totalPages; //get from `homeController`
break;
}
scope.$apply(function () {
count = count;
})
})
}
}
})
我的家庭控制器:
"user strict";
angular.module("ngTenderDocument")
.controller('homeController', function ($scope) {
$scope.count = 0; //pass to directive and update by user
$scope.totalPages = 20; //pass to directive
})
我的看法:
<doc-navigation></doc-navigation> //directive
<h1>This is from home! Now you start to count, count is : {{count}}</h1> //count need to show the appropriate updates here.
我的导航视图:
<nav class="navbar navbar-inverse">
<ul class="nav navbar-nav">
<li class="active"><a id="first" href="#">First</a></li>
<li><a id="prev" href="#">Previous</a></li>
<li><a id="next" href="#">Next</a></li>
<li><a id="last" href="#">Last</a></li>
</ul>
</nav>
使用独立作用域并将计数值从指令属性传递给它。在隔离范围内,您需要提及 scope: { count: '=' },
,它将执行与 count
属性中指定的控制器变量和 directive
计数变量的两种方式绑定。
标记
<doc-navigation count="count"></doc-navigation>
指令
angular.module("docNaviDir", [])
.directive("docNavigation", function () {
return {
restrict : "E",
replace : true,
scope: {
count: '=' //specified two way binding here
},
templateUrl : '/views/directiveViews/docNavigation.html',
link : function (scope, element, attr, controller) {
element.find('a').on('click', function () {
var count = 0;
var Id = $(this).prop('id');
switch(Id) {
case 'first':
count = 1; //update to `homeController`
break;
case 'prev':
count -= 1; //update to `homeController`
break;
case 'next':
count += 1; //update to `homeController`
break;
case 'last':
count = scope.totalPages; //get from `homeController`
break;
}
scope.count = count;
});
}
}
})
我将使用像
这样的对象定义和范围映射
$scope.page = {
totalPages: 10,
count: 4
};
然后
app.directive("docNavigation", function () {
return {
restrict: "E",
replace: true,
//use your url
template: '<div>' + '<a data-type="first" href="">first</a>' + '<a data-type="prev" href="">prev</a>' + '<a data-type="next" href="">next</a>' + '<a data-type="last" href="">last</a>' + '</div>',
scope: {
page: '='
},
link: function (scope, element, attr, controller) {
element.find('a').on('click', function () {
//using hard coded ids in a directive is dangerous as there can be other elements with the same id
var type = angular.element(this).attr('data-type');
switch (type) {
case 'first':
scope.page.count = 1; //update to `homeController`
break;
case 'prev':
scope.page.count -= 1; //update to `homeController`
break;
case 'next':
scope.page.count += 1; //update to `homeController`
break;
case 'last':
scope.page.count = scope.page.totalPages; //get from `homeController`
break;
}
scope.$apply(function () {})
})
}
}
});
演示:Fiddle
另一个答案中提供的解决方案是正确的,即您可以将变量传递给您的指令。
我想指出,尽管您混淆了 vanilla 和 AngularJS。在您的指令中,您在 Angular 的意识之外附加了一个点击事件处理程序,这将导致以后出现问题。因此,我建议将您的指令代码更新为:
app.directive("docNavigation", function () {
return {
restrict: "E",
replace: true,
templateUrl: '/views/directiveViews/docNavigation.html',
scope: {
page: '='
},
link: function (scope, element, attr, controller) {
scope.goToPrevious = function(){
scope.page.count -= 1;
};
scope.goToNext = function(){
scope.page.count += 1;
};
scope.goToFirst = function(){
scope.page.count = 1;
};
scope.goToLast = function(){
scope.page.count = scope.page.totalPages;
}
}
}
});
然后将您的模板更新为
<nav class="navbar navbar-inverse">
<ul class="nav navbar-nav">
<li class="active"><a ng-click="goToFirst()" href="#">First</a></li>
<li><a ng-click="goToPrevious()" href="#">Previous</a></li>
<li><a ng-click="goToNext()" href="#">Next</a></li>
<li><a ng-click="goToLast()" href="#">Last</a></li>
</ul>
</nav>
我有一个页面,其中包含pageNavigator
带页面显示的内容。根据相应按钮(链接)上的用户 click
我正在更新页面。
我将 :page 导航器的指令设为 'docNavigation' 并包含在我的 home
html.
现在我需要,
页面加载时,
我的文档页面应该显示
count
正如我在homeController
中提到的那样,最后的switch
案例应该设置为20
我设置在homeController
.当用户交互时我想更新
homeController
中的count
以更新页面内容。
得到这个的正确方法是什么?
这是我的指令:
"use strict";
angular.module("docNaviDir", [])
.directive("docNavigation", function () {
return {
restrict : "E",
replace : true,
templateUrl : '/views/directiveViews/docNavigation.html',
link : function (scope, element, attr, controller) {
var count = 0;
element.find('a').on('click', function () {
var Id = $(this).prop('id');
switch(Id) {
case 'first':
count = 1; //update to `homeController`
break;
case 'prev':
count -= 1; //update to `homeController`
break;
case 'next':
count += 1; //update to `homeController`
break;
case 'last':
count = scope.totalPages; //get from `homeController`
break;
}
scope.$apply(function () {
count = count;
})
})
}
}
})
我的家庭控制器:
"user strict";
angular.module("ngTenderDocument")
.controller('homeController', function ($scope) {
$scope.count = 0; //pass to directive and update by user
$scope.totalPages = 20; //pass to directive
})
我的看法:
<doc-navigation></doc-navigation> //directive
<h1>This is from home! Now you start to count, count is : {{count}}</h1> //count need to show the appropriate updates here.
我的导航视图:
<nav class="navbar navbar-inverse">
<ul class="nav navbar-nav">
<li class="active"><a id="first" href="#">First</a></li>
<li><a id="prev" href="#">Previous</a></li>
<li><a id="next" href="#">Next</a></li>
<li><a id="last" href="#">Last</a></li>
</ul>
</nav>
使用独立作用域并将计数值从指令属性传递给它。在隔离范围内,您需要提及 scope: { count: '=' },
,它将执行与 count
属性中指定的控制器变量和 directive
计数变量的两种方式绑定。
标记
<doc-navigation count="count"></doc-navigation>
指令
angular.module("docNaviDir", [])
.directive("docNavigation", function () {
return {
restrict : "E",
replace : true,
scope: {
count: '=' //specified two way binding here
},
templateUrl : '/views/directiveViews/docNavigation.html',
link : function (scope, element, attr, controller) {
element.find('a').on('click', function () {
var count = 0;
var Id = $(this).prop('id');
switch(Id) {
case 'first':
count = 1; //update to `homeController`
break;
case 'prev':
count -= 1; //update to `homeController`
break;
case 'next':
count += 1; //update to `homeController`
break;
case 'last':
count = scope.totalPages; //get from `homeController`
break;
}
scope.count = count;
});
}
}
})
我将使用像
这样的对象定义和范围映射$scope.page = {
totalPages: 10,
count: 4
};
然后
app.directive("docNavigation", function () {
return {
restrict: "E",
replace: true,
//use your url
template: '<div>' + '<a data-type="first" href="">first</a>' + '<a data-type="prev" href="">prev</a>' + '<a data-type="next" href="">next</a>' + '<a data-type="last" href="">last</a>' + '</div>',
scope: {
page: '='
},
link: function (scope, element, attr, controller) {
element.find('a').on('click', function () {
//using hard coded ids in a directive is dangerous as there can be other elements with the same id
var type = angular.element(this).attr('data-type');
switch (type) {
case 'first':
scope.page.count = 1; //update to `homeController`
break;
case 'prev':
scope.page.count -= 1; //update to `homeController`
break;
case 'next':
scope.page.count += 1; //update to `homeController`
break;
case 'last':
scope.page.count = scope.page.totalPages; //get from `homeController`
break;
}
scope.$apply(function () {})
})
}
}
});
演示:Fiddle
另一个答案中提供的解决方案是正确的,即您可以将变量传递给您的指令。
我想指出,尽管您混淆了 vanilla 和 AngularJS。在您的指令中,您在 Angular 的意识之外附加了一个点击事件处理程序,这将导致以后出现问题。因此,我建议将您的指令代码更新为:
app.directive("docNavigation", function () {
return {
restrict: "E",
replace: true,
templateUrl: '/views/directiveViews/docNavigation.html',
scope: {
page: '='
},
link: function (scope, element, attr, controller) {
scope.goToPrevious = function(){
scope.page.count -= 1;
};
scope.goToNext = function(){
scope.page.count += 1;
};
scope.goToFirst = function(){
scope.page.count = 1;
};
scope.goToLast = function(){
scope.page.count = scope.page.totalPages;
}
}
}
});
然后将您的模板更新为
<nav class="navbar navbar-inverse">
<ul class="nav navbar-nav">
<li class="active"><a ng-click="goToFirst()" href="#">First</a></li>
<li><a ng-click="goToPrevious()" href="#">Previous</a></li>
<li><a ng-click="goToNext()" href="#">Next</a></li>
<li><a ng-click="goToLast()" href="#">Last</a></li>
</ul>
</nav>