AngularJS Removing old $ watchers when recompiling dynamic html

I have an AngularJS app that dynamically used to build pages (fetching XML from the server and reading those XML pages or forms) for XML that we have to build on multiple pages, all related to each other and can be negative through Next. "Previous".

to realize what we have,

<div>
   <form name="myController.mainForm" novalidate>
      <div my-dynamic="myController.dynamicHtml"></div>
   </form>
</div>

      

herer myDynamic is a directive that touches the generated html and when we need to navigate to another page we create a new HTML for that page and assign it myController.dynamicHtml

and in this Directive I have something like this,

link: function postLink(scope, element, attrs) {
    scope.$watch(attrs.myDynamic, function (html) {
        element.html(html);
        $compile(element.contents())(scope);
    });
}

      

Each page now has a number of input controls (or directives), and each has multiple bindings that add to the number of watchers.

I noticed that if I negative go to another page, observers on previous pages will not be destroyed until my dynamic directive is removed from scope.

What do I need to do to ensure that the clock on the previous page is destroyed when we compile the HTML again.

+3


source to share


2 answers


Every time the service $compile

binds something to a scope, it adds observers. That is why the directive, such as ng-repeat

, ng-switch

, ng-view

, ng-include

and ng-if

all create a new child domain. They refer to the child area and destroy that area when the compiled DOM is destroyed. Use the area. $ New and area. $ Destroy .

link: function postLink(scope, element, attrs) {
    var newScope;
    scope.$watch(attrs.myDynamic, function (html) {
        if (newScope) {
            newScope.$destroy();
        };
        element.empty();
        if (html) {
            element.html(html);
            newScope = scope.$new()
            $compile(element.contents())(newScope);
        };
    });
}

      



This creates and destroys the child area on changes.

+4


source


You can disable anything by assigning a variable to the clock:

var dynamicWatcher = scope.$watch(attrs.myDynamic, function (html) {
    element.html(html);
    $compile(element.contents())(scope);

    dynamicWatcher(); // unwatch
});

      



See documentation for return type:

Returns () function
Returns the deregistration function for this listener.

+1


source







All Articles