Fed*_*les 197 inheritance angularjs angularjs-controller
在模块中,控制器可以从外部控制器继承属性:
var app = angular.module('angularjs-starter', []);
var ParentCtrl = function ($scope, $location) {
};
app.controller('ChildCtrl', function($scope, $injector) {
$injector.invoke(ParentCtrl, this, {$scope: $scope});
});
Run Code Online (Sandbox Code Playgroud)
示例:死链接:http://blog.omkarpatil.com/2013/02/controller-inheritance-in-angularjs.html
模块内的控制器也可以继承兄弟姐妹吗?
var app = angular.module('angularjs-starter', []);
app.controller('ParentCtrl ', function($scope) {
//I'm the sibling, but want to act as parent
});
app.controller('ChildCtrl', function($scope, $injector) {
$injector.invoke(ParentCtrl, this, {$scope: $scope}); //This does not work
});
Run Code Online (Sandbox Code Playgroud)
第二个代码不起作用,因为$injector.invoke需要一个函数作为第一个参数,并且找不到引用ParentCtrl.
Sal*_*bas 287
是的,它可以但您必须使用该$controller服务来实例化控制器: -
var app = angular.module('angularjs-starter', []);
app.controller('ParentCtrl', function($scope) {
// I'm the sibling, but want to act as parent
});
app.controller('ChildCtrl', function($scope, $controller) {
$controller('ParentCtrl', {$scope: $scope}); //This works
});
Run Code Online (Sandbox Code Playgroud)
IPr*_*ory 19
如果您使用vm控制器语法,这是我的解决方案:
.controller("BaseGenericCtrl", function ($scope) {
var vm = this;
vm.reload = reload;
vm.items = [];
function reload() {
// this function will come from child controller scope - RESTDataService.getItemsA
this.getItems();
}
})
.controller("ChildCtrl", function ($scope, $controller, RESTDataService) {
var vm = this;
vm.getItems = RESTDataService.getItemsA;
angular.extend(vm, $controller('BaseGenericCtrl', {$scope: $scope}));
})
Run Code Online (Sandbox Code Playgroud)
不幸的是,您不能使用$controller.call(vm, 'BaseGenericCtrl'...),将当前上下文传递给closure(for reload())函数,因此只有一个解决方案是使用this内部继承函数来动态更改上下文.
为了回应gmontague在这个答案中提出的问题,我找到了一种使用$ controller()继承控制器的方法,并且仍然使用控制器"as"语法.
首先,在继承调用$ controller()时使用"as"语法:
app.controller('ParentCtrl', function(etc...) {
this.foo = 'bar';
});
app.controller('ChildCtrl', function($scope, $controller, etc...) {
var ctrl = $controller('ParentCtrl as parent', {etc: etc, ...});
angular.extend(this, ctrl);
});
Run Code Online (Sandbox Code Playgroud)
然后,在HTML模板中,如果属性由parent定义,则用于parent.检索从parent继承的属性; 如果由child定义,则使用child.它来检索它.
<div ng-controller="ChildCtrl as child">{{ parent.foo }}</div>
Run Code Online (Sandbox Code Playgroud)
好吧,我以另一种方式做到了这一点.在我的情况下,我想要一个在其他控制器中应用相同功能和属性的功能.我喜欢它,除了参数.这样,你所有的ChildCtrls都需要获得$ location.
var app = angular.module('angularjs-starter', []);
function BaseCtrl ($scope, $location) {
$scope.myProp = 'Foo';
$scope.myMethod = function bar(){ /* do magic */ };
}
app.controller('ChildCtrl', function($scope, $location) {
BaseCtrl.call(this, $scope, $location);
// it works
$scope.myMethod();
});
Run Code Online (Sandbox Code Playgroud)
对于那些想知道的人,您可以使用已接受答案中的方法以相同的方式扩展组件控制器。
使用以下方法:
父组件(扩展自):
/**
* Module definition and dependencies
*/
angular.module('App.Parent', [])
/**
* Component
*/
.component('parent', {
templateUrl: 'parent.html',
controller: 'ParentCtrl',
})
/**
* Controller
*/
.controller('ParentCtrl', function($parentDep) {
//Get controller
const $ctrl = this;
/**
* On init
*/
this.$onInit = function() {
//Do stuff
this.something = true;
};
});
Run Code Online (Sandbox Code Playgroud)
子组件(扩展的那个):
/**
* Module definition and dependencies
*/
angular.module('App.Child', [])
/**
* Component
*/
.component('child', {
templateUrl: 'child.html',
controller: 'ChildCtrl',
})
/**
* Controller
*/
.controller('ChildCtrl', function($controller) {
//Get controllers
const $ctrl = this;
const $base = $controller('ParentCtrl', {});
//NOTE: no need to pass $parentDep in here, it is resolved automatically
//if it's a global service/dependency
//Extend
angular.extend($ctrl, $base);
/**
* On init
*/
this.$onInit = function() {
//Call parent init
$base.$onInit.call(this);
//Do other stuff
this.somethingElse = true;
};
});
Run Code Online (Sandbox Code Playgroud)
诀窍是使用命名控制器,而不是在组件定义中定义它们。
| 归档时间: |
|
| 查看次数: |
85281 次 |
| 最近记录: |