use*_*530 118 javascript jquery angularjs angularjs-directive
我有一个有自己的控制器的指令.请参阅以下代码:
var popdown = angular.module('xModules',[]);
popdown.directive('popdown', function () {
var PopdownController = function ($scope) {
this.scope = $scope;
}
PopdownController.prototype = {
show:function (message, type) {
this.scope.message = message;
this.scope.type = type;
},
hide:function () {
this.scope.message = '';
this.scope.type = '';
}
}
var linkFn = function (scope, lElement, attrs, controller) {
};
return {
controller: PopdownController,
link: linkFn,
replace: true,
templateUrl: './partials/modules/popdown.html'
}
});
Run Code Online (Sandbox Code Playgroud)
这是一个错误/通知/警告的通知系统.我想要做的是从另一个控制器(而不是指令控制器)调用show该控制器上的函数.当我这样做时,我还希望我的链接功能检测到某些属性已更改并执行一些动画.
这里有一些代码来举例说明我的要求:
var app = angular.module('app', ['RestService']);
app.controller('IndexController', function($scope, RestService) {
var result = RestService.query();
if(result.error) {
popdown.notify(error.message, 'error');
}
});
Run Code Online (Sandbox Code Playgroud)
所以打电话时show开启popdown指令控制器,链接功能也应该被触发,执行动画.我怎么能实现这一目标?
sat*_*run 167
这是一个有趣的问题,我开始考虑如何实现这样的事情.
我想出了这个(小提琴) ;
基本上,我没有尝试从控制器调用指令,而是创建了一个模块来存放所有弹出逻辑:
var PopdownModule = angular.module('Popdown', []);
Run Code Online (Sandbox Code Playgroud)
我在模块中放了两个东西,一个factory用于可以在任何地方注入的API,以及directive用于定义实际popdown元素的行为:
工厂只定义了几个函数success,error并跟踪了几个变量:
PopdownModule.factory('PopdownAPI', function() {
return {
status: null,
message: null,
success: function(msg) {
this.status = 'success';
this.message = msg;
},
error: function(msg) {
this.status = 'error';
this.message = msg;
},
clear: function() {
this.status = null;
this.message = null;
}
}
});
Run Code Online (Sandbox Code Playgroud)
该指令将API注入其控制器,并监视api的更改(为方便起见,我使用bootstrap css):
PopdownModule.directive('popdown', function() {
return {
restrict: 'E',
scope: {},
replace: true,
controller: function($scope, PopdownAPI) {
$scope.show = false;
$scope.api = PopdownAPI;
$scope.$watch('api.status', toggledisplay)
$scope.$watch('api.message', toggledisplay)
$scope.hide = function() {
$scope.show = false;
$scope.api.clear();
};
function toggledisplay() {
$scope.show = !!($scope.api.status && $scope.api.message);
}
},
template: '<div class="alert alert-{{api.status}}" ng-show="show">' +
' <button type="button" class="close" ng-click="hide()">×</button>' +
' {{api.message}}' +
'</div>'
}
})
Run Code Online (Sandbox Code Playgroud)
然后我定义一个app依赖于的模块Popdown:
var app = angular.module('app', ['Popdown']);
app.controller('main', function($scope, PopdownAPI) {
$scope.success = function(msg) { PopdownAPI.success(msg); }
$scope.error = function(msg) { PopdownAPI.error(msg); }
});
Run Code Online (Sandbox Code Playgroud)
HTML看起来像:
<html ng-app="app">
<body ng-controller="main">
<popdown></popdown>
<a class="btn" ng-click="success('I am a success!')">Succeed</a>
<a class="btn" ng-click="error('Alas, I am a failure!')">Fail</a>
</body>
</html>
Run Code Online (Sandbox Code Playgroud)
我不确定它是否完全理想,但它似乎是一种与全局弹出指令建立通信的合理方式.
再次,作为参考,小提琴.
Aro*_*ron 26
您还可以使用事件来触发Popdown.
这是基于satchmorun解决方案的小提琴.它取消了PopdownAPI,而顶级控制器取代$broadcast了范围链中的"成功"和"错误"事件:
$scope.success = function(msg) { $scope.$broadcast('success', msg); };
$scope.error = function(msg) { $scope.$broadcast('error', msg); };
Run Code Online (Sandbox Code Playgroud)
Popdown模块然后为这些事件注册处理函数,例如:
$scope.$on('success', function(event, msg) {
$scope.status = 'success';
$scope.message = msg;
$scope.toggleDisplay();
});
Run Code Online (Sandbox Code Playgroud)
这至少在我看来是一个很好的解耦方案.如果由于某种原因这被认为是糟糕的做法,我会让其他人插话.
lua*_*sus 11
你也可能使该指令的控制器父范围,如ngForm与name属性的作用:http://docs.angularjs.org/api/ng.directive:ngForm
在这里你可以找到一个非常基本的例子如何实现它http://plnkr.co/edit/Ps8OXrfpnePFvvdFgYJf?p=preview
在这个例子中,我使用myDirective了带有$clear方法的专用控制器(一种非常简单的指令公共API).我可以将此控制器发布到父作用域,并在指令外部使用调用此方法.
| 归档时间: |
|
| 查看次数: |
99966 次 |
| 最近记录: |