如何在父指令的按钮单击侦听器中调用child指令中定义的方法。
angular.module('editableDivDirective', [])
.directive("editableDiv", function() {
var directive = {};
directive.restrict = 'E';
directive.replace = 'true';
directive.scope = {};
directive.transclude = 'true';
directive.template =
'<div id="wrapper">' +
'<div required class="text-area" name="search" contenteditable="true" ng-model="formData.text"></div>' +
'<button type="submit" class="btn btn-warning add-button" id="submit" ng-click="createTodo()">Add</button>' +
'</div>';
directive.link = function(scope, element, attrs, controller) {
scope.createTodo = function(){
// do something
// Call child directive setPlaceholderText()
}
};
return directive;
})
.directive("contenteditable", function() {
var directive = {};
directive.require = ['^editableDiv','?ngModel'];
directive.restrict = 'A';
directive.scope = {};
directive.link = function(scope, element, attrs, ctrls) {
var ngModel = ctrls[1];
var editableDivController = ctrls[0];
function setPlaceholderText(){
return element.html("Hello World");
}
return directive;
})
我想在调用parent指令的“scope.createTodo()”时调用child指令setPlaceholderText()。
如何做到这一点。
答案 0 :(得分:3)
在您的父指令
中link: function($scope,$el,$attr) {
$el.find(".thing").on('click',function(event){
$scope.$broadcast('thing', $scope.someData);
});
}
在您的孩子指令
中link: function($scope. $el, $attr) {
$scope.$on('thing',function(event, someData) {
alert('My parent called me with this data: ' + someData);
});
}
答案 1 :(得分:2)
您可以将$事件广播到子范围(如上所述),或者您也可以从子指令向父指令的控制器添加一个函数。
这是一个jsfiddle,其中包含$ broadcast to child指令和使用控制器技术的示例。
angular.module("myApp", [])
.directive("parentDirective", function () {
var directive = {};
directive.restrict = "E";
directive.scope = {};
directive.template = '<div>' +
'<button type="button" ng-click="broadcastDemo()">' +
'Broadcast to child' +
'</button>' +
'<button type="button" ng-click="controllerDemo()">' +
'Use Controller' +
'</button><br /><br />' +
'<child-directive></child-directive>';
//Setup directive controller
directive.controller = function ($scope) {
var ctrl = this;
//Store events for convenience
var events = ctrl.events = {
setPlaceHolderText: "setPlaceHolderTextEvent"
};
$scope.broadcastDemo = function () {
//$broadcast event and optional additional args
$scope.$broadcast(events.setPlaceHolderText, "Additional arg1", "Additional arg2");
};
$scope.controllerDemo = function () {
//do some work
//call the ctrl.setPlaceHolderText added by child
if (ctrl.setPlaceHolderText) {
ctrl.setPlaceHolderText();
}
};
};
return directive;
})
.directive("childDirective", function () {
var directive = {};
directive.restrict = "E";
directive.scope = {};
directive.require = ["^parentDirective", "?ngModel"];
directive.template = '<div></div>';
directive.link = function (scope, elem, attrs, ctrl) {
var parentDirCtrl = ctrl[0];
//allow parent scope(s) to $broadcast event
scope.$on(parentDirCtrl.events.setPlaceHolderText,
function (event, arg1, arg2) {
elem.html("$Broadcast: " + arg1 + " " + arg2);
});
//Add function to parent controller
parentDirCtrl.setPlaceHolderText = function () {
elem.html("Added to parent controller!");
}
};
return directive;
});
如果您有多个childDirectives并且您要将功能添加到父指令控制器,则必须采取预防措施,因为每个额外的子指令都会破坏ctrl.setPlaceHolderText(即只调用一个elem.html)。
bindonce库使用类似于第二种技术的东西,允许子指令将“绑定器”添加到父指令。事件模型可能更适合您的目的,但希望为指令通信提供另一种选择。
答案 2 :(得分:0)
广播不是首选,因为如果有多个子实例甚至父子组合,那么广播将触发全部。