PDA

View Full Version : Problem with Pagination and sorting in a GridPanel



abenomar
24 Jan 2011, 4:49 AM
Hello,

I have a problem with my gridPanel, showing all datas in my store , this is the scenario that I am trying to execute:


Show all datas in my store with a SmartRowSelectionPaging.
I check some rows in the grid (1st page) to do a special work.
After submitting, and doing successfully the action, I go Back to show Datas, normally, I still have the order sorting respected in the first page, but when I go to another page, the sort is removed.

Any suggestions for this problem?

Thank you.

valititi
24 Jan 2011, 5:32 PM
try first to post the code of your grid and pagination...

abenomar
25 Jan 2011, 1:24 AM
try first to post the code of your grid and pagination...

Hello,

This is the code I use for my GridPanel :


var grid = new Ext.grid.GridPanel({
id : 'gridRetificacao',
renderTo: 'column-group-grid',
title: 'Résultats de la recherche',
width: 1000,
height: 600,
store: store,
columns: columns,
sm: checkBoxModel,

viewConfig: {
forceFit: false
},

plugins: [
rowSelectionPaging,
new Ext.ux.grid.ColumnHeaderGroup({
rows: headerRows
})
],
tbar: topPagingToolbar,
bbar: bottomPagingToolbar
});

for the SmartRowSelectingPagination :



/**
* Ext.ux.grid.RowSelectionPaging plugin for Ext.grid.GridPanel A grid plugin
* that preserves row selections across paging / filtering of the store.
*
* @author Joeri Sebrechts
* @date October 21st, 2009
*
* @class Ext.ux.grid.RowSelectionPaging
* @extends Ext.util.Observable
*/
Ext.ns('Ext.ux.grid');
Ext.ux.grid.SmartRowSelectionPaging = function(config) {
Ext.apply(this, config);
};
Ext.extend(Ext.ux.grid.SmartRowSelectionPaging, Ext.util.Observable, {
init : function(grid) {
this.grid = grid;
this.selections = []; // array of selected records
this.selected = {}; // hash mapping record id to selected state

grid.on('render', function() {
// attach an interceptor for the selModel's onRefresh handler
this.grid.view.un('refresh', this.grid.selModel.onRefresh, this.grid.selModel);
this.grid.view.on('refresh', this.onViewRefresh, this);
// add a handler to detect when the user changes the selection
this.grid.selModel.on('rowselect', this.onRowSelect, this);
this.grid.selModel.on('rowdeselect', this.onRowDeselect, this);
// patch selModel to detect selection cleared events
var scope = this;
this.selModelClearSelections = this.grid.selModel.clearSelections;
this.grid.selModel.clearSelections = function(fast) {
scope.selModelClearSelections.call(this, fast);
scope.onSelectionClear();
};
// and replace the default behavior of the "check all"
if (!this.originalSelectAll && (this.grid.selModel.id == 'checker')) {
this.grid.selModel.onHdMouseDown = function(e, t) {
if (t.className == 'x-grid3-hd-checker') {
e.stopEvent();
var hd = Ext.fly(t.parentNode);
var isChecked = hd.hasClass('x-grid3-hd-checker-on');
if (isChecked) {
hd.removeClass('x-grid3-hd-checker-on');
scope.clearSelections();
} else {
hd.addClass('x-grid3-hd-checker-on');
scope.selectAll();
}
}
}
}
}, this);
}, // end init

// private
onViewRefresh : function() {
this.ignoreSelectionChanges = true;
// explicitly refresh the selection model
this.grid.selModel.onRefresh();
// selection changed from view updates, restore full selection
var ds = this.grid.getStore();
var newSel = [];
for ( var i = ds.getCount() - 1; i >= 0; i--) {
if (this.selected[ds.getAt(i).id]) {
newSel.push(i);
}
}
this.grid.selModel.selectRows(newSel, false);
this.ignoreSelectionChanges = false;
}, // end onViewRefresh

// private
onSelectionClear : function() {
if (!this.ignoreSelectionChanges) {
// selection cleared by user
// also called internally when the selection replaces the old
// selection
this.selections = [];
this.selected = {};
}
}, // end onSelectionClear

// private
onRowSelect : function(sm, i, rec) {
if (!this.ignoreSelectionChanges) {
if (!this.selected[rec.id]) {

this.selections.push(rec);

this.selected[rec.id] = true;
}
}

}, // end onRowSelect

// private
onRowDeselect : function(sm, i, rec) {
if (!this.ignoreSelectionChanges) {
if (this.selected[rec.id]) {
for ( var i = this.selections.length - 1; i >= 0; i--) {
if (this.selections[i].id == rec.id) {
this.selections.splice(i, 1);
this.selected[rec.id] = false;
break;
}
}
}
}
}, // end onRowDeselect

/**
* Clears selections across all pages
*/
clearSelections : function() {
this.selections = [];
this.selected = {};
this.onViewRefresh();
}, // end clearSelections

/**
* Returns the selected records for all pages
*
* @return {Array} Array of selected records
*/
getSelections : function() {
return [].concat(this.selections);
}, // end getSelections

/**
* Selects all the rows in the grid, including those on other pages Be very
* careful using this on very large datasets
*/
selectAll : function() {
var ds = this.grid.getStore();
ds.suspendEvents();
ds.load({
params : {
start : 0,
limit : ds.getTotalCount()
},
callback : function() {
this.selections = ds.data.items.slice(0);
this.selected = {};
for ( var i = this.selections.length - 1; i >= 0; i--) {
this.selected[this.selections[i].id] = true;
}
;
ds.resumeEvents();
this.onViewRefresh();
},
scope : this
});

},

/**
* Add factices records to select immediatly the previously selected rows
*/
addSelections: function(ids) {
for (var i = ids.length - 1; i >= 0; i--) {
if (!this.selected[ids[i]])
{
this.selections.push(new Ext.data.Record({id:ids[i]},ids[i]));
}
}
},

/**
* Remove records from the selection
*/
removeSelections: function(ids) {
for (var i = this.selections.length - 1; i >= 0; i--) {
if (ids.indexOf(this.selections[i].id) != -1) {
this.selected[this.selections[i].id] = false;
this.selections.splice(i, 1);
}
}
}

});


for the ColumnHeader :


/*!
* Ext JS Library 3.2.1
* Copyright(c) 2006-2010 Ext JS, Inc.
* [email protected]
* http://www.extjs.com/license
*/
Ext.ns('Ext.ux.grid');

Ext.ux.grid.ColumnHeaderGroup = Ext.extend(Ext.util.Observable, {

constructor: function(config){
// this.config = config;
if (!config)
config = {};

this.prefix = 'id_';
this.items = {};
this.idProperty = config.idProperty || 'id';
},

init: function(grid){
//Ext.applyIf(grid.colModel, this.config);
//Ext.apply(grid.getView(), this.viewConfig);
this.grid = grid;
this.view = grid.getView();
this.store = null;
this.sm = grid.getSelectionModel();
this.sm.on('rowselect', this.onSelect, this);
this.sm.on('rowdeselect', this.onDeselect, this);
this.view.on('refresh', this.reConfigure, this);
},

viewConfig: {
initTemplates: function(){
this.constructor.prototype.initTemplates.apply(this, arguments);
var ts = this.templates || {};
if(!ts.gcell){
ts.gcell = new Ext.XTemplate('<td class="x-grid3-hd x-grid3-gcell x-grid3-td-{id} ux-grid-hd-group-row-{row} {cls}" style="{style}">', '<div {tooltip} class="x-grid3-hd-inner x-grid3-hd-{id}" unselectable="on" style="{istyle}">', this.grid.enableHdMenu ? '<a class="x-grid3-hd-btn" href="#"></a>' : '', '{value}</div></td>');
}
this.templates = ts;
this.hrowRe = new RegExp("ux-grid-hd-group-row-(\\d+)", "");
},

renderHeaders: function(){
var ts = this.templates, headers = [], cm = this.cm, rows = cm.rows, tstyle = 'width:' + this.getTotalWidth() + ';';

for(var row = 0, rlen = rows.length; row < rlen; row++){
var r = rows[row], cells = [];
for(var i = 0, gcol = 0, len = r.length; i < len; i++){
var group = r[i];
group.colspan = group.colspan || 1;
var id = this.getColumnId(group.dataIndex ? cm.findColumnIndex(group.dataIndex) : gcol), gs = Ext.ux.grid.ColumnHeaderGroup.prototype.getGroupStyle.call(this, group, gcol);
cells[i] = ts.gcell.apply({
cls: 'ux-grid-hd-group-cell',
id: id,
row: row,
style: 'width:' + gs.width + ';' + (gs.hidden ? 'display:none;' : '') + (group.align ? 'text-align:' + group.align + ';' : ''),
tooltip: group.tooltip ? (Ext.QuickTips.isEnabled() ? 'ext:qtip' : 'title') + '="' + group.tooltip + '"' : '',
istyle: group.align == 'right' ? 'padding-right:16px' : '',
btn: this.grid.enableHdMenu && group.header,
value: group.header || '&nbsp;'
});
gcol += group.colspan;
}
headers[row] = ts.header.apply({
tstyle: tstyle,
cells: cells.join('')
});
}
headers.push(this.constructor.prototype.renderHeaders.apply(this, arguments));
return headers.join('');
},

onColumnWidthUpdated: function(){
this.constructor.prototype.onColumnWidthUpdated.apply(this, arguments);
Ext.ux.grid.ColumnHeaderGroup.prototype.updateGroupStyles.call(this);
},

onAllColumnWidthsUpdated: function(){
this.constructor.prototype.onAllColumnWidthsUpdated.apply(this, arguments);
Ext.ux.grid.ColumnHeaderGroup.prototype.updateGroupStyles.call(this);
},

onColumnHiddenUpdated: function(){
this.constructor.prototype.onColumnHiddenUpdated.apply(this, arguments);
Ext.ux.grid.ColumnHeaderGroup.prototype.updateGroupStyles.call(this);
},

getHeaderCell: function(index){
return this.mainHd.query(this.cellSelector)[index];
},

findHeaderCell: function(el){
return el ? this.fly(el).findParent('td.x-grid3-hd', this.cellSelectorDepth) : false;
},

findHeaderIndex: function(el){
var cell = this.findHeaderCell(el);
return cell ? this.getCellIndex(cell) : false;
},

updateSortIcon: function(col, dir){
var sc = this.sortClasses, hds = this.mainHd.select(this.cellSelector).removeClass(sc);
hds.item(col).addClass(sc[dir == "DESC" ? 1 : 0]);
},

handleHdDown: function(e, t){
var el = Ext.get(t);
if(el.hasClass('x-grid3-hd-btn')){
e.stopEvent();
var hd = this.findHeaderCell(t);
Ext.fly(hd).addClass('x-grid3-hd-menu-open');
var index = this.getCellIndex(hd);
this.hdCtxIndex = index;
var ms = this.hmenu.items, cm = this.cm;
ms.get('asc').setDisabled(!cm.isSortable(index));
ms.get('desc').setDisabled(!cm.isSortable(index));
this.hmenu.on('hide', function(){
Ext.fly(hd).removeClass('x-grid3-hd-menu-open');
}, this, {
single: true
});
this.hmenu.show(t, 'tl-bl?');
}else if(el.hasClass('ux-grid-hd-group-cell') || Ext.fly(t).up('.ux-grid-hd-group-cell')){
e.stopEvent();
}
},

handleHdMove: function(e, t){
var hd = this.findHeaderCell(this.activeHdRef);
if(hd && !this.headersDisabled && !Ext.fly(hd).hasClass('ux-grid-hd-group-cell')){
var hw = this.splitHandleWidth || 5, r = this.activeHdRegion, x = e.getPageX(), ss = hd.style, cur = '';
if(this.grid.enableColumnResize !== false){
if(x - r.left <= hw && this.cm.isResizable(this.activeHdIndex - 1)){
cur = Ext.isAir ? 'move' : Ext.isWebKit ? 'e-resize' : 'col-resize'; // col-resize
// not
// always
// supported
}else if(r.right - x <= (!this.activeHdBtn ? hw : 2) && this.cm.isResizable(this.activeHdIndex)){
cur = Ext.isAir ? 'move' : Ext.isWebKit ? 'w-resize' : 'col-resize';
}
}
ss.cursor = cur;
}
},

handleHdOver: function(e, t){
var hd = this.findHeaderCell(t);
if(hd && !this.headersDisabled){
this.activeHdRef = t;
this.activeHdIndex = this.getCellIndex(hd);
var fly = this.fly(hd);
this.activeHdRegion = fly.getRegion();
if(!(this.cm.isMenuDisabled(this.activeHdIndex) || fly.hasClass('ux-grid-hd-group-cell'))){
fly.addClass('x-grid3-hd-over');
this.activeHdBtn = fly.child('.x-grid3-hd-btn');
if(this.activeHdBtn){
this.activeHdBtn.dom.style.height = (hd.firstChild.offsetHeight - 1) + 'px';
}
}
}
},

handleHdOut: function(e, t){
var hd = this.findHeaderCell(t);
if(hd && (!Ext.isIE || !e.within(hd, true))){
this.activeHdRef = null;
this.fly(hd).removeClass('x-grid3-hd-over');
hd.style.cursor = '';
}
},

handleHdMenuClick: function(item){
var index = this.hdCtxIndex, cm = this.cm, ds = this.ds, id = item.getItemId();
switch(id){
case 'asc':
ds.sort(cm.getDataIndex(index), 'ASC');
break;
case 'desc':
ds.sort(cm.getDataIndex(index), 'DESC');
break;
default:
if(id.substr(0, 5) == 'group'){
var i = id.split('-'), row = parseInt(i[1], 10), col = parseInt(i[2], 10), r = this.cm.rows[row], group, gcol = 0;
for(var i = 0, len = r.length; i < len; i++){
group = r[i];
if(col >= gcol && col < gcol + group.colspan){
break;
}
gcol += group.colspan;
}
if(item.checked){
var max = cm.getColumnsBy(this.isHideableColumn, this).length;
for(var i = gcol, len = gcol + group.colspan; i < len; i++){
if(!cm.isHidden(i)){
max--;
}
}
if(max < 1){
this.onDenyColumnHide();
return false;
}
}
for(var i = gcol, len = gcol + group.colspan; i < len; i++){
if(cm.config[i].fixed !== true && cm.config[i].hideable !== false){
cm.setHidden(i, item.checked);
}
}
}else{
index = cm.getIndexById(id.substr(4));
if(index != -1){
if(item.checked && cm.getColumnsBy(this.isHideableColumn, this).length <= 1){
this.onDenyColumnHide();
return false;
}
cm.setHidden(index, item.checked);
}
}
item.checked = !item.checked;
if(item.menu){
var updateChildren = function(menu){
menu.items.each(function(childItem){
if(!childItem.disabled){
childItem.setChecked(item.checked, false);
if(childItem.menu){
updateChildren(childItem.menu);
}
}
});
}
updateChildren(item.menu);
}
var parentMenu = item, parentItem;
while(parentMenu = parentMenu.parentMenu){
if(!parentMenu.parentMenu || !(parentItem = parentMenu.parentMenu.items.get(parentMenu.getItemId())) || !parentItem.setChecked){
break;
}
var checked = parentMenu.items.findIndexBy(function(m){
return m.checked;
}) >= 0;
parentItem.setChecked(checked, true);
}
item.checked = !item.checked;
}
return true;
},

beforeColMenuShow: function(){
var cm = this.cm, rows = this.cm.rows;
this.colMenu.removeAll();
for(var col = 0, clen = cm.getColumnCount(); col < clen; col++){
var menu = this.colMenu, title = cm.getColumnHeader(col), text = [];
if(cm.config[col].fixed !== true && cm.config[col].hideable !== false){
for(var row = 0, rlen = rows.length; row < rlen; row++){
var r = rows[row], group, gcol = 0;
for(var i = 0, len = r.length; i < len; i++){
group = r[i];
if(col >= gcol && col < gcol + group.colspan){
break;
}
gcol += group.colspan;
}
if(group && group.header){
if(cm.hierarchicalColMenu){
var gid = 'group-' + row + '-' + gcol;
var item = menu.items.item(gid);
var submenu = item ? item.menu : null;
if(!submenu){
submenu = new Ext.menu.Menu({
itemId: gid
});
submenu.on("itemclick", this.handleHdMenuClick, this);
var checked = false, disabled = true;
for(var c = gcol, lc = gcol + group.colspan; c < lc; c++){
if(!cm.isHidden(c)){
checked = true;
}
if(cm.config[c].hideable !== false){
disabled = false;
}
}
menu.add({
itemId: gid,
text: group.header,
menu: submenu,
hideOnClick: false,
checked: checked,
disabled: disabled
});
}
menu = submenu;
}else{
text.push(group.header);
}
}
}
text.push(title);
menu.add(new Ext.menu.CheckItem({
itemId: "col-" + cm.getColumnId(col),
text: text.join(' '),
checked: !cm.isHidden(col),
hideOnClick: false,
disabled: cm.config[col].hideable === false
}));
}
}
},

renderUI: function(){
this.constructor.prototype.renderUI.apply(this, arguments);
Ext.apply(this.columnDrop, Ext.ux.grid.ColumnHeaderGroup.prototype.columnDropConfig);
Ext.apply(this.splitZone, Ext.ux.grid.ColumnHeaderGroup.prototype.splitZoneConfig);
}
},

splitZoneConfig: {
allowHeaderDrag: function(e){
return !e.getTarget(null, null, true).hasClass('ux-grid-hd-group-cell');
}
},

columnDropConfig: {
getTargetFromEvent: function(e){
var t = Ext.lib.Event.getTarget(e);
return this.view.findHeaderCell(t);
},

positionIndicator: function(h, n, e){
var data = Ext.ux.grid.ColumnHeaderGroup.prototype.getDragDropData.call(this, h, n, e);
if(data === false){
return false;
}
var px = data.px + this.proxyOffsets[0];
this.proxyTop.setLeftTop(px, data.r.top + this.proxyOffsets[1]);
this.proxyTop.show();
this.proxyBottom.setLeftTop(px, data.r.bottom);
this.proxyBottom.show();
return data.pt;
},

onNodeDrop: function(n, dd, e, data){
var h = data.header;
if(h != n){
var d = Ext.ux.grid.ColumnHeaderGroup.prototype.getDragDropData.call(this, h, n, e);
if(d === false){
return false;
}
var cm = this.grid.colModel, right = d.oldIndex < d.newIndex, rows = cm.rows;
for(var row = d.row, rlen = rows.length; row < rlen; row++){
var r = rows[row], len = r.length, fromIx = 0, span = 1, toIx = len;
for(var i = 0, gcol = 0; i < len; i++){
var group = r[i];
if(d.oldIndex >= gcol && d.oldIndex < gcol + group.colspan){
fromIx = i;
}
if(d.oldIndex + d.colspan - 1 >= gcol && d.oldIndex + d.colspan - 1 < gcol + group.colspan){
span = i - fromIx + 1;
}
if(d.newIndex >= gcol && d.newIndex < gcol + group.colspan){
toIx = i;
}
gcol += group.colspan;
}
var groups = r.splice(fromIx, span);
rows[row] = r.splice(0, toIx - (right ? span : 0)).concat(groups).concat(r);
}
for(var c = 0; c < d.colspan; c++){
var oldIx = d.oldIndex + (right ? 0 : c), newIx = d.newIndex + (right ? -1 : c);
cm.moveColumn(oldIx, newIx);
this.grid.fireEvent("columnmove", oldIx, newIx);
}
return true;
}
return false;
}
},

getGroupStyle: function(group, gcol){
var width = 0, hidden = true;
for(var i = gcol, len = gcol + group.colspan; i < len; i++){
if(!this.cm.isHidden(i)){
var cw = this.cm.getColumnWidth(i);
if(typeof cw == 'number'){
width += cw;
}
hidden = false;
}
}
return {
width: (Ext.isBorderBox || (Ext.isWebKit && !Ext.isSafari2) ? width : Math.max(width - this.borderWidth, 0)) + 'px',
hidden: hidden
};
},

updateGroupStyles: function(col){
var tables = this.mainHd.query('.x-grid3-header-offset > table'), tw = this.getTotalWidth(), rows = this.cm.rows;
for(var row = 0; row < tables.length; row++){
tables[row].style.width = tw;
if(row < rows.length){
var cells = tables[row].firstChild.firstChild.childNodes;
for(var i = 0, gcol = 0; i < cells.length; i++){
var group = rows[row][i];
if((typeof col != 'number') || (col >= gcol && col < gcol + group.colspan)){
var gs = Ext.ux.grid.ColumnHeaderGroup.prototype.getGroupStyle.call(this, group, gcol);
cells[i].style.width = gs.width;
cells[i].style.display = gs.hidden ? 'none' : '';
}
gcol += group.colspan;
}
}
}
},

getGroupRowIndex: function(el){
if(el){
var m = el.className.match(this.hrowRe);
if(m && m[1]){
return parseInt(m[1], 10);
}
}
return this.cm.rows.length;
},

getGroupSpan: function(row, col){
if(row < 0){
return {
col: 0,
colspan: this.cm.getColumnCount()
};
}
var r = this.cm.rows[row];
if(r){
for(var i = 0, gcol = 0, len = r.length; i < len; i++){
var group = r[i];
if(col >= gcol && col < gcol + group.colspan){
return {
col: gcol,
colspan: group.colspan
};
}
gcol += group.colspan;
}
return {
col: gcol,
colspan: 0
};
}
return {
col: col,
colspan: 1
};
},

getDragDropData: function(h, n, e){
if(h.parentNode != n.parentNode){
return false;
}
var cm = this.grid.colModel, x = Ext.lib.Event.getPageX(e), r = Ext.lib.Dom.getRegion(n.firstChild), px, pt;
if((r.right - x) <= (r.right - r.left) / 2){
px = r.right + this.view.borderWidth;
pt = "after";
}else{
px = r.left;
pt = "before";
}
var oldIndex = this.view.getCellIndex(h), newIndex = this.view.getCellIndex(n);
if(cm.isFixed(newIndex)){
return false;
}
var row = Ext.ux.grid.ColumnHeaderGroup.prototype.getGroupRowIndex.call(this.view, h),
oldGroup = Ext.ux.grid.ColumnHeaderGroup.prototype.getGroupSpan.call(this.view, row, oldIndex),
newGroup = Ext.ux.grid.ColumnHeaderGroup.prototype.getGroupSpan.call(this.view, row, newIndex),
oldIndex = oldGroup.col;
newIndex = newGroup.col + (pt == "after" ? newGroup.colspan : 0);
if(newIndex >= oldGroup.col && newIndex <= oldGroup.col + oldGroup.colspan){
return false;
}
var parentGroup = Ext.ux.grid.ColumnHeaderGroup.prototype.getGroupSpan.call(this.view, row - 1, oldIndex);
if(newIndex < parentGroup.col || newIndex > parentGroup.col + parentGroup.colspan){
return false;
}
return {
r: r,
px: px,
pt: pt,
row: row,
oldIndex: oldIndex,
newIndex: newIndex,
colspan: oldGroup.colspan
};
},

//ajoutés pour regler le probleme de sorting et pagination
reConfigure: function() {
this.store = this.grid.getStore();
this.store.on('clear', this.onClear, this);
this.store.on('datachanged', this.restoreState, this);
},

onSelect: function(sm, idx, rec)
{
this.items[this.getId(rec)] = true;
},

onDeselect: function(sm, idx, rec)
{
delete this.items[this.getId(rec)];
},

restoreState: function()
{
if (this.store != null) {
var i = 0;
var sel = [];
this.store.each(function(rec)
{
var id = this.getId(rec);
if (this.items[id] === true)
sel.push(i);

++i;
}, this);
if (sel.length > 0)
this.sm.selectRows(sel);
}
},

onClear: function()
{
var sel = [];
this.items = {};
},

getId: function(rec)
{
return rec.get(this.idProperty);
}

});

Thanks.