如何使指令使用指令属性中指定的控制器?
How to make directive use the controller specified in directive attribute?
所以我有一个指令:
<directive data="user" templateUrl="./user.html" controller="UserController"></directive>
我希望该指令使用“controller”属性中指定的控制器,如上所示。
AngularJS 指令是否可行?或者我应该用其他方式来做,也许用组件?
我的代码目前是这样的:
app.directive('directive', function() {
var controllerName = "UserController"; // i want that to dynamicaly come from attribute
// check if controller extists:
var services = [];
app['_invokeQueue'].forEach(function(value){
services[value[2][0]] = true;
});
if (!services[controllerName]) controllerName = false;
return {
scope: { 'data' : '=' },
link: function (scope) {
Object.assign(scope, scope.data);
},
templateUrl: function(element, attr) {
return attr.templateurl;
},
controller: controllerName
}
});
您可以执行以下操作(不完全按照您的要求 - 它会创建一堆嵌套范围,但应该足够了):
.directive('directive', () => {
scope: { 'data' : '=' },
template: (elem, attrs) => {
return '<div ng-controller="' + attrs.controller + ' as vm"><div ng-include="' + attrs.template + '"></div></div>';
}
});
<directive data="user" templateUrl="./user.html" controller="UserController"></directive>
- 你可以直接使用 $templateCache 而不是 ng-include
- 如果你需要 controller/template/... 是动态的,你需要 observe/watch + dom 操作 + 重新编译东西
好的,所以在分析了 Petr 的回答后,我 post 工作代码 using nested div:
app.directive('directive', function() {
return {
scope: { 'data' : '=' },
link: function (scope) {
// this makes your fields available as {{name}} instead of {{user.name}}:
Object.assign(scope, scope.data);
},
template: function(element, attrs) {
var controllerName = attrs.controller;
var controllerString = controllerName + ' as vm';
// check if controller extists:
var services = [];
app['_invokeQueue'].forEach(function(value){
services[value[2][0]] = true;
})
if (!services[controllerName]) {
return '<div ng-include="\'' + attrs.templateurl + '\'"></div>';
} else {
return '<div ng-controller="' + controllerString + '"><div ng-include="\'' + attrs.templateurl + '\'"></div></div>';
}
}
}
});
所以我有一个指令:
<directive data="user" templateUrl="./user.html" controller="UserController"></directive>
我希望该指令使用“controller”属性中指定的控制器,如上所示。
AngularJS 指令是否可行?或者我应该用其他方式来做,也许用组件?
我的代码目前是这样的:
app.directive('directive', function() {
var controllerName = "UserController"; // i want that to dynamicaly come from attribute
// check if controller extists:
var services = [];
app['_invokeQueue'].forEach(function(value){
services[value[2][0]] = true;
});
if (!services[controllerName]) controllerName = false;
return {
scope: { 'data' : '=' },
link: function (scope) {
Object.assign(scope, scope.data);
},
templateUrl: function(element, attr) {
return attr.templateurl;
},
controller: controllerName
}
});
您可以执行以下操作(不完全按照您的要求 - 它会创建一堆嵌套范围,但应该足够了):
.directive('directive', () => {
scope: { 'data' : '=' },
template: (elem, attrs) => {
return '<div ng-controller="' + attrs.controller + ' as vm"><div ng-include="' + attrs.template + '"></div></div>';
}
});
<directive data="user" templateUrl="./user.html" controller="UserController"></directive>
- 你可以直接使用 $templateCache 而不是 ng-include
- 如果你需要 controller/template/... 是动态的,你需要 observe/watch + dom 操作 + 重新编译东西
好的,所以在分析了 Petr 的回答后,我 post 工作代码 using nested div:
app.directive('directive', function() {
return {
scope: { 'data' : '=' },
link: function (scope) {
// this makes your fields available as {{name}} instead of {{user.name}}:
Object.assign(scope, scope.data);
},
template: function(element, attrs) {
var controllerName = attrs.controller;
var controllerString = controllerName + ' as vm';
// check if controller extists:
var services = [];
app['_invokeQueue'].forEach(function(value){
services[value[2][0]] = true;
})
if (!services[controllerName]) {
return '<div ng-include="\'' + attrs.templateurl + '\'"></div>';
} else {
return '<div ng-controller="' + controllerString + '"><div ng-include="\'' + attrs.templateurl + '\'"></div></div>';
}
}
}
});