开发者

ExtJS: Reload datastore without redrawing grid

(E开发者_如何转开发xtJS 3.3.1)

How can I save the scroll position of a grid after I call grid.store.reload()?


I managed to fix it like this:

this.store = new Ext.data.Store({
    listeners:{
        'load':function (store, records, options) {
            var restoreScroll = function(scrollState){
                grid.getView().restoreScroll(scrollState);
            };
            if (grid.view && grid.view.scroller){
                _.delay(restoreScroll, 10,grid.getView().getScrollState());
            }
        }
    }, ...
}

As you can see, I use _.delay (of the underscore.js framework). It's just like a setTimeout.

A more optimized version, not using the the function 'restoreScroll' didn't work out. I think that the view is changed when restoreScroll is called. I had to take 10 miliseconds. 1 was not enough. As stated by others, ext.js uses a lot of defer-calls.


That's two different questions.

First, to reload a store without redrawing the grid, use store.suspendEvents(), then call store.resumeEvents() in the load callback.

Restoring scroll position after refresh is a bit more tricky, particularly since ExtJS makes excessive use of setTimeouts and defers in Firefox. Try saving the scroll state using var state = view.getScrollState(), then restore it with view.restoreScroll.defer(1, state)


Finally I found this section in the extjs grid faq. This snipped does not directly run in webkit-browsers. You have to add a timeout and call the restore part a little moment later. 100ms helped me out here. This is what I have now:

grid.getView().on('beforerefresh', function(view) {
  view.scrollTop = view.scroller.dom.scrollTop;
  view.scrollHeight = view.scroller.dom.scrollHeight;
});

grid.getView().on('refresh', function(view) {
    setTimeout(function () {
        view.scroller.dom.scrollTop = view.scrollTop + (view.scrollTop == 0 ? 0 : view.scroller.dom.scrollHeight - view.scrollHeight);
    }, 100);
});

Runs in IE8, Chrome9, Firefox3.6

Does not in Opera 11

This solution has one drawback: Without activly telling the view not to restore the scroll position it is also restored if you goto next page by the paginator.

I think sencha should integrate this feature as a option, because it is a deep integration to tell the view of a grid to restore the position if a store reloads the same position of a datasource and not to do so if changes to the baseparams are made... or so.


listeners: {
                beforerefresh: function(v) {
                    v.hide();
                },
                refresh: function(v) {
                    v.show();
                }
            }

worked for me (add in view config)


This post recently helped me find that the view maintains the control over the scrollState. I was able to view.saveScrollState() then defer view.restoreScrollState() with a timeOut. The longer the timeout the more jarring the return is, so be aware that you want the minimum amount of timeOut for the view to refresh / render. What was missing from earlier posts was that the view has a "saveScrollState" where it stores scroll position internally.

view.saveScrollState();
//do some things here
setTimeout(function(){
   view.restoreScrollState();
},1);
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜