Upgrade to ExtJS 4.0.0 - Released 04/26/2011
[extjs.git] / docs / source / Sortable.html
diff --git a/docs/source/Sortable.html b/docs/source/Sortable.html
new file mode 100644 (file)
index 0000000..a9f7bf6
--- /dev/null
@@ -0,0 +1,251 @@
+<!DOCTYPE html><html><head><title>Sencha Documentation Project</title><link rel="stylesheet" href="../reset.css" type="text/css"><link rel="stylesheet" href="../prettify.css" type="text/css"><link rel="stylesheet" href="../prettify_sa.css" type="text/css"><script type="text/javascript" src="../prettify.js"></script></head><body onload="prettyPrint()"><pre class="prettyprint"><pre><span id='Ext-util.Sortable'>/**
+</span> * @class Ext.util.Sortable
+
+A mixin which allows a data component to be sorted. This is used by e.g. {@link Ext.data.Store} and {@link Ext.data.TreeStore}.
+
+**NOTE**: This mixin is mainly for internal library use and most users should not need to use it directly. It
+is more likely you will want to use one of the component classes that import this mixin, such as
+{@link Ext.data.Store} or {@link Ext.data.TreeStore}.
+ * @markdown
+ * @docauthor Tommy Maintz &lt;tommy@sencha.com&gt;
+ */
+Ext.define(&quot;Ext.util.Sortable&quot;, {
+<span id='Ext-util.Sortable-property-isSortable'>    /**
+</span>     * @property isSortable
+     * @type Boolean
+     * Flag denoting that this object is sortable. Always true.
+     */
+    isSortable: true,
+    
+<span id='Ext-util.Sortable-property-defaultSortDirection'>    /**
+</span>     * The default sort direction to use if one is not specified (defaults to &quot;ASC&quot;)
+     * @property defaultSortDirection
+     * @type String
+     */
+    defaultSortDirection: &quot;ASC&quot;,
+    
+    requires: [
+        'Ext.util.Sorter'
+    ],
+
+<span id='Ext-util.Sortable-property-sortRoot'>    /**
+</span>     * The property in each item that contains the data to sort. (defaults to null)
+     * @type String
+     */    
+    sortRoot: null,
+    
+<span id='Ext-util.Sortable-method-initSortable'>    /**
+</span>     * Performs initialization of this mixin. Component classes using this mixin should call this method
+     * during their own initialization.
+     */
+    initSortable: function() {
+        var me = this,
+            sorters = me.sorters;
+        
+<span id='Ext-util.Sortable-property-sorters'>        /**
+</span>         * The collection of {@link Ext.util.Sorter Sorters} currently applied to this Store
+         * @property sorters
+         * @type Ext.util.MixedCollection
+         */
+        me.sorters = Ext.create('Ext.util.AbstractMixedCollection', false, function(item) {
+            return item.id || item.property;
+        });
+        
+        if (sorters) {
+            me.sorters.addAll(me.decodeSorters(sorters));
+        }
+    },
+
+<span id='Ext-util.Sortable-method-sort'>    /**
+</span>     * &lt;p&gt;Sorts the data in the Store by one or more of its properties. Example usage:&lt;/p&gt;
+&lt;pre&gt;&lt;code&gt;
+//sort by a single field
+myStore.sort('myField', 'DESC');
+
+//sorting by multiple fields
+myStore.sort([
+    {
+        property : 'age',
+        direction: 'ASC'
+    },
+    {
+        property : 'name',
+        direction: 'DESC'
+    }
+]);
+&lt;/code&gt;&lt;/pre&gt;
+     * &lt;p&gt;Internally, Store converts the passed arguments into an array of {@link Ext.util.Sorter} instances, and delegates the actual
+     * sorting to its internal {@link Ext.util.MixedCollection}.&lt;/p&gt;
+     * &lt;p&gt;When passing a single string argument to sort, Store maintains a ASC/DESC toggler per field, so this code:&lt;/p&gt;
+&lt;pre&gt;&lt;code&gt;
+store.sort('myField');
+store.sort('myField');
+     &lt;/code&gt;&lt;/pre&gt;
+     * &lt;p&gt;Is equivalent to this code, because Store handles the toggling automatically:&lt;/p&gt;
+&lt;pre&gt;&lt;code&gt;
+store.sort('myField', 'ASC');
+store.sort('myField', 'DESC');
+&lt;/code&gt;&lt;/pre&gt;
+     * @param {String|Array} sorters Either a string name of one of the fields in this Store's configured {@link Ext.data.Model Model},
+     * or an Array of sorter configurations.
+     * @param {String} direction The overall direction to sort the data by. Defaults to &quot;ASC&quot;.
+     */
+    sort: function(sorters, direction, where, doSort) {
+        var me = this,
+            sorter, sorterFn,
+            newSorters;
+        
+        if (Ext.isArray(sorters)) {
+            doSort = where;
+            where = direction;
+            newSorters = sorters;
+        }
+        else if (Ext.isObject(sorters)) {
+            doSort = where;
+            where = direction;
+            newSorters = [sorters];
+        }
+        else if (Ext.isString(sorters)) {
+            sorter = me.sorters.get(sorters);
+
+            if (!sorter) {
+                sorter = {
+                    property : sorters,
+                    direction: direction
+                };
+                newSorters = [sorter];
+            }
+            else if (direction === undefined) {
+                sorter.toggle();
+            }
+            else {
+                sorter.setDirection(direction);
+            }
+        }
+        
+        if (newSorters &amp;&amp; newSorters.length) {
+            newSorters = me.decodeSorters(newSorters);
+            if (Ext.isString(where)) {
+                if (where === 'prepend') {
+                    sorters = me.sorters.clone().items;
+                    
+                    me.sorters.clear();
+                    me.sorters.addAll(newSorters);
+                    me.sorters.addAll(sorters);
+                }
+                else {
+                    me.sorters.addAll(newSorters);
+                }
+            }
+            else {
+                me.sorters.clear();
+                me.sorters.addAll(newSorters);
+            }
+            
+            if (doSort !== false) {
+                me.onBeforeSort(newSorters);
+            }
+        }
+        
+        if (doSort !== false) {
+            sorters = me.sorters.items;
+            if (sorters.length) {
+                //construct an amalgamated sorter function which combines all of the Sorters passed
+                sorterFn = function(r1, r2) {
+                    var result = sorters[0].sort(r1, r2),
+                        length = sorters.length,
+                        i;
+
+                        //if we have more than one sorter, OR any additional sorter functions together
+                        for (i = 1; i &lt; length; i++) {
+                            result = result || sorters[i].sort.call(this, r1, r2);
+                        }
+
+                    return result;
+                };
+
+                me.doSort(sorterFn);                
+            }
+        }
+        
+        return sorters;
+    },
+    
+    onBeforeSort: Ext.emptyFn,
+        
+<span id='Ext-util.Sortable-method-decodeSorters'>    /**
+</span>     * @private
+     * Normalizes an array of sorter objects, ensuring that they are all Ext.util.Sorter instances
+     * @param {Array} sorters The sorters array
+     * @return {Array} Array of Ext.util.Sorter objects
+     */
+    decodeSorters: function(sorters) {
+        if (!Ext.isArray(sorters)) {
+            if (sorters === undefined) {
+                sorters = [];
+            } else {
+                sorters = [sorters];
+            }
+        }
+
+        var length = sorters.length,
+            Sorter = Ext.util.Sorter,
+            fields = this.model ? this.model.prototype.fields : null,
+            field,
+            config, i;
+
+        for (i = 0; i &lt; length; i++) {
+            config = sorters[i];
+
+            if (!(config instanceof Sorter)) {
+                if (Ext.isString(config)) {
+                    config = {
+                        property: config
+                    };
+                }
+                
+                Ext.applyIf(config, {
+                    root     : this.sortRoot,
+                    direction: &quot;ASC&quot;
+                });
+
+                //support for 3.x style sorters where a function can be defined as 'fn'
+                if (config.fn) {
+                    config.sorterFn = config.fn;
+                }
+
+                //support a function to be passed as a sorter definition
+                if (typeof config == 'function') {
+                    config = {
+                        sorterFn: config
+                    };
+                }
+
+                // ensure sortType gets pushed on if necessary
+                if (fields &amp;&amp; !config.transform) {
+                    field = fields.get(config.property);
+                    config.transform = field ? field.sortType : undefined;
+                }
+                sorters[i] = Ext.create('Ext.util.Sorter', config);
+            }
+        }
+
+        return sorters;
+    },
+    
+    getSorters: function() {
+        return this.sorters.items;
+    },
+    
+<span id='Ext-util.Sortable-method-getSortState'>    /**
+</span>     * Returns an object describing the current sort state of this Store.
+     * @return {Object} The sort state of the Store. An object with two properties:&lt;ul&gt;
+     * &lt;li&gt;&lt;b&gt;field&lt;/b&gt; : String&lt;p class=&quot;sub-desc&quot;&gt;The name of the field by which the Records are sorted.&lt;/p&gt;&lt;/li&gt;
+     * &lt;li&gt;&lt;b&gt;direction&lt;/b&gt; : String&lt;p class=&quot;sub-desc&quot;&gt;The sort order, 'ASC' or 'DESC' (case-sensitive).&lt;/p&gt;&lt;/li&gt;
+     * &lt;/ul&gt;
+     * See &lt;tt&gt;{@link #sortInfo}&lt;/tt&gt; for additional details.
+     */
+    getSortState : function() {
+        return this.sortInfo;
+    }
+});</pre></pre></body></html>
\ No newline at end of file