I'm not sure how to accomplish the following in the right way:
Consider, for the sake of example, that I want to create my own custom radio-buttons list directive, something like that:
<my-radio-button-list>
<my-radio-button>
...Some HTML content...
</my-radio-button>
<my-radio-button>
...Some HTML content...
</my-radio-button>
<my-radio-button>
...Some HTML content...
</my-radio-button>
</my-radio-button-list>
Please note - the <my-radio-button>
directive doesn't necessarily use any <input>
elements.
I would like that <my-radio-button>
will have its own internal event listener to track when it was clicked, and I would also like that when a <my-radio-button>
directive was clicked, it will notify the parent <my-radio-button-list>
directive that such event occurred, so the parent directive will change the DOM accordingly - it will deselect the current selected item, and will select the item that was clicked.
What is the correct way to achieve something like this?
The only way I could think of was to create a method on the parent directive's controller which will manipulate the DOM as necessarily (which will get as a parameter the newly selected item), and then to share the parent directive's controller with its children directives (so they can call this method from their click event handlers). However, I know that this approach is wrong, because the controller should never manipulate the DOM.
Thanks!
Using events (not just click events) would be an easy way to do it.
child (my-radio-button) html:
<button ng-click="childController.handleClick()">{{childController.childData.id}}</button>
<span ng-if="parentController.currentSelection.id === childController.childData.id">THERE CAN ONLY BE ONE!!!</span>
child (my-radio-button) controller:
controller.childData = {id: 'child1'};
controller.handleClick = function(){
$scope.$emit('childClicked', childData);
};
parent (my-radio-button-list) html:
<div>
<ng-transclude></ng-transclude>
<div>
parent (my-radio-button-list) controller:
$scope.$on('childClicked', function(childData){
controller.currentSelection = childData;
});