Форк Rambox
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

114 lines
3.6 KiB

/**
* Represents a grouping of items. The grouper works in a similar fashion as the
* `Ext.util.Sorter` except that groups must be able to extract a value by which all items
* in the group can be collected. By default this is derived from the `property` config
* but can be customized using the `groupFn` if necessary.
*
* All items with the same group value compare as equal. If the group values do not compare
* equally, the sort can be controlled further by setting `sortProperty` or `sorterFn`.
*/
Ext.define('Ext.util.Grouper', {
extend: 'Ext.util.Sorter',
isGrouper: true,
config: {
/**
* @cfg {Function} groupFn This function is called for each item in the collection
* to determine the group to which it belongs. By default the `property` value is
* used to group items.
* @cfg {Object} groupFn.item The current item from the collection.
* @cfg {String} groupFn.return The group identifier for the item.
*/
groupFn: null,
/**
* @cfg {String} property The field by which records are grouped. Groups are
* sorted alphabetically by group value as the default. To sort groups by a different
* property, use the {@link #sortProperty} configuration.
*/
/**
* @cfg {String} sortProperty You can set this configuration if you want the groups
* to be sorted on something other then the group string returned by the `groupFn`.
* This serves the same role as `property` on a normal `Ext.util.Sorter`.
*/
sortProperty: null
},
constructor: function(config) {
//<debug>
if (config) {
if (config.getGroupString) {
Ext.Error.raise("Cannot set getGroupString - use groupFn instead");
}
}
//</debug>
this.callParent(arguments);
},
/**
* Returns the value for grouping to be used.
* @param {Ext.data.Model} item The Model instance
* @return {String}
*/
getGroupString: function (item) {
var group = this._groupFn(item);
return (group != null) ? String(group) : '';
},
sortFn: function (item1, item2) {
var me = this,
lhs = me._groupFn(item1),
rhs = me._groupFn(item2),
property = me._sortProperty, // Sorter's sortFn uses "_property"
root = me._root,
sorterFn = me._sorterFn,
transform = me._transform;
// Items with the same groupFn result must be equal... otherwise we sort them
// by sorterFn or sortProperty.
if (lhs === rhs) {
return 0;
}
if (property || sorterFn) {
if (sorterFn) {
return sorterFn.call(this, item1, item2);
}
if (root) {
item1 = item1[root];
item2 = item2[root];
}
lhs = item1[property];
rhs = item2[property];
if (transform) {
lhs = transform(lhs);
rhs = transform(rhs);
}
}
return (lhs > rhs) ? 1 : (lhs < rhs ? -1 : 0);
},
standardGroupFn: function (item) {
var root = this._root;
return (root ? item[root] : item)[this._property];
},
updateSorterFn: function () {
// don't callParent here - we don't want to smash sortFn w/sorterFn
},
updateProperty: function () {
// we don't callParent since that is related to sorterFn smashing sortFn
if (!this.getGroupFn()) {
this.setGroupFn(this.standardGroupFn);
}
}
});