R Claven
R Claven

Reputation: 1210

Angular directive event binding not working

In short, my directive is successfully inserting the proper HTML but the bindings to events are not working. Can anyone suggest why this is happening?

  . . .   directive('rcpRadio', [ function( ) {
        return {
            restrict: 'E',
            link: function (scope, element, attr, ctrl) {
                var label, elementHTML, selection, selectionName;

                    if (typeof(attr) != "undefined" && typeof(attr.label) != "undefined") {
                        label = attr.label;
                    } else {
                        label = "";
                    }
                    if (typeof(attr) != "undefined" && typeof(attr.selection) != "undefined") {
                        selection = attr.selection;
                    } else {
                        selection = "";
                    }
                    if (typeof(attr) != "undefined" && typeof(attr.selectionName) != "undefined") {
                        selectionName = attr.selectionName;
                    } else {
                        selectionName = "";
                    }
                    if (typeof(attr) != "undefined" && typeof(attr.isChecked) != "undefined" && attr.isChecked == "true") {
                        elementHTML = "<div class='switch radius nyes'><input type='radio' value='" + selection + "' name='" + selectionName + "' id='" + selectionName + "_id' checked ><label for='" + selectionName + "'></label><span> " + label + " </span></div>";
                    } else {
                        elementHTML = "<div class='switch radius nyes'><input type='radio' value='" + selection + "' name='" + selectionName + "' id='" + selectionName + "_id'  ><label for='" + selectionName + "'></label><span> " + label + " </span></div>";
                    }


                    element.replaceWith(elementHTML);

                    element.on('click', function(event) {
                    //element.bind('click', function (event) {
                        alert(":CLICK:");
                        console.log("## CLICK! :");
                        console.log(event);
                    });
                    element.bind('mouseover', function() {
                        console.log("## HOVER! :");
                        console.log(event);
                    });
            }
    };
}]);

I really just want to call a function when any change to the inserted HTML is detected.

Any ideas would be much appreciated. I am pulling my hair out!

Update 7/28/2014 4:06

Well, by shifting away from "replaceWith" and instead using :

template: "<div class='switch radius'><input type='radio' value='{{selection}}' name='{{selectionName}}' id='{{selectionName}}_id' checked=''><label for='currentMode'></label><span> {{label}} </span></div>",

With some additions made to scope updates in link like:

$scope.label = attr.label;

Seems to then allow the event binding. So does replaceWith prevent event binding? I am so confused . .

Upvotes: 0

Views: 1073

Answers (1)

Chickenrice
Chickenrice

Reputation: 5727

Actually, you could do the DOM transform in 'compile' function. Try to implement like this:

directive('rcpRadio', [ function( ) {
    return {
        restrict: 'E',
        compile: function(element,attr){
            //transform DOM according to attribute
            var label, elementHTML, selection, selectionName;

            if (typeof(attr) != "undefined" && typeof(attr.label) != "undefined") {
                label = attr.label;
            } else {
                label = "";
            }
            if (typeof(attr) != "undefined" && typeof(attr.selection) != "undefined") {
                selection = attr.selection;
            } else {
                selection = "";
            }
            if (typeof(attr) != "undefined" && typeof(attr.selectionName) != "undefined") {
                selectionName = attr.selectionName;
            } else {
                selectionName = "";
            }
            if (typeof(attr) != "undefined" && typeof(attr.isChecked) != "undefined" && attr.isChecked == "true") {
                elementHTML = "<div class='switch radius nyes'><input type='radio' value='" + selection + "' name='" + selectionName + "' id='" + selectionName + "_id' checked ><label for='" + selectionName + "'></label><span> " + label + " </span></div>";
            } else {
                elementHTML = "<div class='switch radius nyes'><input type='radio' value='" + selection + "' name='" + selectionName + "' id='" + selectionName + "_id'  ><label for='" + selectionName + "'></label><span> " + label + " </span></div>";
            }

            element.replaceWith(elementHTML);

            //return link function

            return function(scope,element,attr){
                element.on('click', function(event) {
                //element.bind('click', function (event) {
                    alert(":CLICK:");
                    console.log("## CLICK! :");
                    console.log(event);
                });
                element.bind('mouseover', function() {
                    console.log("## HOVER! :");
                    console.log(event);
                });
            };
        }
    }
}]);

Here is a jsFiddle DEMO

Upvotes: 1

Related Questions