tags:

views:

2238

answers:

2
+1  Q: 

Extjs Dynamic Grid

Hi,

I'm trying to create a dynamic grid using Extjs. The grid is built and displayed when a click event is fired then an ajax request is sent to the server to fetch the columns, records and records definition a.k.a Store Fields. Each node could have different grid structure and that depends on the level of the node in the tree.

The only way i came up with so far is

        function showGrid(response, request) {                  
        var jsonData = Ext.util.JSON.decode(response.responseText);                 
        var grid = Ext.getCmp('contentGrid'+request.params.owner);

        if(grid) {
            grid.destroy();                                 
        } 

        var store = new Ext.data.ArrayStore({
            id  : 'arrayStore',                 
            fields : jsonData.recordFields,
            autoDestroy : true
        });             

        grid = new Ext.grid.GridPanel({
            defaults: {sortable:true},
            id:'contentGrid'+request.params.owner,
            store: store,        
            columns: jsonData.columns,
            //width:540,
            //height:200,
            loadMask: true
        });         


        store.loadData(jsonData.records);           
        if(Ext.getCmp('tab-'+request.params.owner)) {
            Ext.getCmp('tab-'+request.params.owner).show();
        } else {                
            grid.render('grid-div');
            Ext.getCmp('card-tabs-panel').add({
            id:'tab-'+request.params.owner,
            title: request.params.text,
            iconCls:'silk-tab',
            html:Ext.getDom('grid-div').innerHTML,
            closable:true
            }).show();          
        }
    }

The function above is called when a click event is fired

       'click': function(node) {
            Ext.Ajax.request({
               url: 'showCtn',
               success: function(response, request) {                               
                    alert('Success');                                                   
                    showGrid(response,request);
               },
               failure: function(results, request) {
                    alert('Error');
               },
               params: Ext.urlDecode(node.attributes.options);                                          
        }

The problem i'm getting with this code is that a new grid is displayed each time the showGrid function is called. The end user sees the old grids and the new one. To mitigate this problem, I tried destroying the grid and also removing the grid element on each request, and that seems to solve the problem only that records never get displayed this time.

    if(grid) {
            grid.destroy(true);                                 
        } 

The behavior i'm looking for is to display the result of a grid within a tab and if that tab exists replaced the old grid. Any help is appreciated.

Thank you

+2  A: 

When you are trying to add your grid to the tab like this:

    html:Ext.getDom('grid-div').innerHTML,

Ext is not aware of it being a valid grid component. Instead, you are simply adding HTML markup that just happens to look like a grid, but the TabPanel will not be aware that it is a grid component. Instead you should add the grid itself as the tab (a GridPanel is a Panel and does not need to be nested into a parent panel). You can do so and also apply the needed tab configs like this:

    Ext.getCmp('card-tabs-panel').add(
        Ext.apply(grid, {
            id:'tab-'+request.params.owner,
            title: request.params.text,
            iconCls:'silk-tab',
            closable:true
        });
    }).show();

BTW, constantly creating and destroying grids is not an ideal strategy if you can avoid it. It might be better to simply hide and re-show grids (and reload their data) based on which type of grid is needed if that's possible (assuming the set of grid types is finite).

bmoeskau
Great it works. thank you. As for destroying and recreating the grid each time, I unfortunately can't guarantee a limited number of grids, so i have no choice. BTW Why destroying the grid isn't considered a good strategy ?
ken
The GridPanel is pretty much the heaviest component there is in terms of both markup and memory footprint (aside from maybe a TreePanel with a lot of nodes). If you are not careful (or if Ext has any bugs related to component destruction as they have in the past) this can lead to DOM leaks over time. Also, creating a grid is time-consuming from the user's perspective, so re-creating a grid vs. simply showing a hidden one is a big difference in perceived performance of your app (especially when done often like you are doing). Glad you solved your problem.
bmoeskau
Good to know. I'll try to focus on this more once i get a clear idea if i can control the number of grids that are requested. Maybe have a pool of grids to serve from and limit their numbers.
ken
A: 

Hello,

Your code is very intersting and I am trying to use it for some project. However, I cannot make jsonData.recordFields neither jsonData.columns work as they are the main elements I would like to use.

Can you please help me on this one?

Just to summarize, I have a json file from which I need to extract the fields and data dynamically given it is a valid one (just like you are doing).

Thanks in advance!

Ahmed