[483] | 1 | define([ |
---|
| 2 | "dojo/_base/array", // array.forEach array.map |
---|
| 3 | "dojo/aspect", |
---|
| 4 | "dojo/_base/declare" |
---|
| 5 | ], function(array, aspect, declare){ |
---|
| 6 | |
---|
| 7 | // module: |
---|
| 8 | // dijit/Destroyable |
---|
| 9 | |
---|
| 10 | return declare("dijit.Destroyable", null, { |
---|
| 11 | // summary: |
---|
| 12 | // Mixin to track handles and release them when instance is destroyed. |
---|
| 13 | // description: |
---|
| 14 | // Call this.own(...) on list of handles (returned from dojo/aspect, dojo/on, |
---|
| 15 | // dojo/Stateful::watch, or any class (including widgets) with a destroyRecursive() or destroy() method. |
---|
| 16 | // Then call destroy() later to destroy this instance and release the resources. |
---|
| 17 | |
---|
| 18 | destroy: function(/*Boolean*/ preserveDom){ |
---|
| 19 | // summary: |
---|
| 20 | // Destroy this class, releasing any resources registered via own(). |
---|
| 21 | this._destroyed = true; |
---|
| 22 | }, |
---|
| 23 | |
---|
| 24 | own: function(){ |
---|
| 25 | // summary: |
---|
| 26 | // Track specified handles and remove/destroy them when this instance is destroyed, unless they were |
---|
| 27 | // already removed/destroyed manually. |
---|
| 28 | // tags: |
---|
| 29 | // protected |
---|
| 30 | // returns: |
---|
| 31 | // The array of specified handles, so you can do for example: |
---|
| 32 | // | var handle = this.own(on(...))[0]; |
---|
| 33 | |
---|
| 34 | array.forEach(arguments, function(handle){ |
---|
| 35 | var destroyMethodName = |
---|
| 36 | "destroyRecursive" in handle ? "destroyRecursive" : // remove "destroyRecursive" for 2.0 |
---|
| 37 | "destroy" in handle ? "destroy" : |
---|
| 38 | "remove"; |
---|
| 39 | |
---|
| 40 | // When this.destroy() is called, destroy handle. Since I'm using aspect.before(), |
---|
| 41 | // the handle will be destroyed before a subclass's destroy() method starts running, before it calls |
---|
| 42 | // this.inherited() or even if it doesn't call this.inherited() at all. If that's an issue, make an |
---|
| 43 | // onDestroy() method and connect to that instead. |
---|
| 44 | var odh = aspect.before(this, "destroy", function(preserveDom){ |
---|
| 45 | handle[destroyMethodName](preserveDom); |
---|
| 46 | }); |
---|
| 47 | |
---|
| 48 | // If handle is destroyed manually before this.destroy() is called, remove the listener set directly above. |
---|
| 49 | var hdh = aspect.after(handle, destroyMethodName, function(){ |
---|
| 50 | odh.remove(); |
---|
| 51 | hdh.remove(); |
---|
| 52 | }, true); |
---|
| 53 | }, this); |
---|
| 54 | |
---|
| 55 | return arguments; // handle |
---|
| 56 | } |
---|
| 57 | }); |
---|
| 58 | }); |
---|