armensg90 armensg90 - 11 months ago 87
AngularJS Question

Destroy controller scope and all related events and memory on state change

I'm using ngHandsontable inside a tabbed ui-router app. The first time I load a tab (state/route) and the tables are rendered (i have 5-10 tables in 1 view) the performance is excellent. However, once I navigate away from this view into other views (that may or may not have more handsontables), the repsonsiveness of the tables is massively declined. Can't tell what the issue is but I'm thinking maybe the watch variables are not being cleaned? events? memory?

This is how I'm using it (with the jquery masonry plugin to stack the tables)

The snippet below is the template of the


<div class="row">
<div class="col-md-12">
<div masonry>
<div class="masonry-brick" ng-repeat="(title, group) in instrumentGroups | orderObjectBy:'sortOrder'" style="" column-width="230">
<div class="instrument-group">

<hot-table settings="{colHeaders: colHeaders, className: 'htCenter', contextMenu: ['row_above', 'row_below', 'remove_row'], afterChange: hot.afterChange, afterRender: hot.afterRender}" row-headers="false" min-spare-rows="minSpareRows" datarows="group.nodes" >
<hot-column data="nodeTitle" title="group.title" width="110" colspan="2" type="grayedOut" read-only></hot-column>
<hot-column data="quote" type="'numeric'" width="70" format="group.format"></hot-column>
<hot-column data="isIncluded" title="'Use'" width="50" type="'checkbox'" width="50" checked-template="true" unchecked-template="false"></hot-column>


So I'm doing a bit of digging and Looking at the "Event Listeners" in the chrome dev tool on the table elements and I can see that when I toggle between the tabs and the tables are re-drawn, the number of these scroll and visibltychange events double and triples... is this expected?

Screenshot of events that get duplicated

this is after a few toggles between states:

enter image description here

How can I make sure that all these listeners (and presumably other variables, memory etc) gets destroyed when I toggle between states in ui-router?

Answer Source

This was reported as ngHandsonTable Issue#157 .

Memory leak when hotTable's parent scope is destroyed.

Hi, I often use the directive inside controllers whoose scope is later destroyed. I'm not an expert but it seems that, in this case, the elements are not properly removed from the DOM which causes a memory leak. I discovered that, in the vanilla handsontable code, you can call the .destroy() method on a hot instance to remove it from the DOM so I added

element.on("$destroy", function() { scope.hotInstance.destroy(); });

at the end of hotTable's "compile" (line 584), which fixed the memory leak.

I don't know if this could break other parts of your code but I just wanted to let you know there's potential problem here.