generalopinion
generalopinion

Reputation: 1437

Modify the template of a directive to access the same scope as the directive that created it

AngularJs newbie here. First off, I'm probably going about this all wrong so please feel free to offer up any advice about my approach on this one. What I am attempting to do is to have an element directive that applies a template. Here's the initial directive myDirective.

directives.directive('myDirective', [function() {

    var template = "<button type='button' class='btn btn-default' my-other-directive={{model}}>CLICK ME</button>";

    function link(scope, element, attrs) {

    };

    return {
        restrict: 'E',
        link: link,
        scope: {
            model: '@'
        },
        template: template
    };
}]);

It's referenced in my HTML like so.

<my-Directive model="ThisVaries"></my-Directive>

Here's 'myOtherDirective'

directives.directive('myOtherDirective', [function() {

    function link(scope, element, attrs) {

       var attr = attrs.myOtherDirective;

       element.bind('click', function() {
           scope.$parent.$parent.data.contact[attr].splice(0, 1); // need the index of the item
       });
    };

    return {
        restrict: 'A',
        link: link
    };
}]);

Basically, this is a contact form in which a user will click the button and it will remove the item from the controllers scope.data.contact[variable][index]. I was able to get the attr variable passed in to access the grandparents' scope.data variable but the model doesn't update when I click the button.

I just started working with directives yesterday and I'm pretty sure that this isn't the right way to do this. Any assistance will be helpful.

The controller in my controller.js file holds the $scope.data property which is the controller for the entire html partial.

Upvotes: 0

Views: 29

Answers (1)

Ryan
Ryan

Reputation: 2460

Angular achieves its magical two-way bindings by executing everything inside of a $digest cycle, but when events happen outside of something already being executed by angular (such as a click event triggered by your element.bind('click') you will need to manually instruct it to go back inside a $digest cycle by running it with scope.$apply.

Applied to your example:

directives.directive('myOtherDirective', [function() {

    function link(scope, element, attrs) {

        var attr = attrs.myOtherDirective;

        element.bind('click', function() {
            scope.$apply(function() {
              scope.$parent.$parent.data.contact[attr].splice({0, 1}); // need the index of the item
            })
        });
    };

    return {
        restrict: 'A',
        link: link
    };
}]);

Upvotes: 1

Related Questions