Results 1 to 5 of 5

Thread: Can a Grid Cell span Multiple Rows (Rowspan for Grid Cell)?

  1. #1
    Sencha User
    Join Date
    Apr 2007
    Posts
    38
    Answers
    1
    Vote Rating
    3
      1  

    Default Answered: Can a Grid Cell span Multiple Rows (Rowspan for Grid Cell)?

    Let's say a Grid has the same value in a particular column, like so -

    Normal Grid.jpg


    Would like to show the repeated rows in this fashion -

    Grouped Grid.jpg


    How could this be achieved? Can Row Expander or Grouping View be extended somehow to get this?

    Thanks.

  2. As mentioned, initial pointers given by Condor from this forum thread. This solution was for ExtJs 3.

    After that I got a big hint from bogc in this forum thread.

    Then I just tied everything together!

    Code is below...

    PHP Code:
    <html>
      <
    head>
        <
    meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
        <
    title>Editor Grid with Row Span</title>
        
        <
    link rel='stylesheet' type='text/css' href='http://dev.sencha.com/deploy/ext-4.1.0-gpl/resources/css/ext-all.css' />

        <
    script type='text/javascript' src='http://dev.sencha.com/deploy/ext-4.1.0-gpl/ext-all.js'></script>

        <script type="text/javascript">
          
          Ext.onReady(function(){
            Ext.define('gridstore', {
               extend    : 'Ext.data.Store'

              ,fields    : [
                {name: 'company'}
                 ,{name: 'price', type: 'float'}
                 ,{name: 'change', type: 'float'}
                 ,{name: 'lastChange', type: 'date', dateFormat: 'n/j h:ia'}
                 ,{name: 'industry'}
              ]

              ,data: [
                 { company: '3m Co',                    price: 71.72,  change: 0.12,  lastChange: '4/2 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Alcoa Inc',                  price: 29.01,  change: 0.42,  lastChange: '4/1 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Altria Group Inc',                price: 83.81,  change: 0.28,  lastChange: '4/3 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'American Express Company',            price: 52.55,  change: 0.01,  lastChange: '4/8 12:00am',  industry: 'Finance'      }
                ,{ company: 'American International Group, Inc.',      price: 64.13,  change: 0.31,  lastChange: '4/1 12:00am',  industry: 'Services'    }
                ,{ company: 'AT&amp;T Inc.',                price: 31.61,  change: -0.48,  lastChange: '4/8 12:00am',  industry: 'Services'    }
                ,{ company: 'Boeing Co.',                  price: 75.43,  change: 0.53,  lastChange: '4/8 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Caterpillar Inc.',                price: 67.27,  change: 0.92,  lastChange: '4/1 12:00am',  industry: 'Services'    }
                ,{ company: 'Citigroup, Inc.',                price: 49.37,  change: 0.02,  lastChange: '4/4 12:00am',  industry: 'Finance'      }
                ,{ company: 'E.I. du Pont de Nemours and Company',      price: 40.48,  change: 0.51,  lastChange: '4/1 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Exxon Mobil Corp',                price: 68.1,  change: -0.43,  lastChange: '4/3 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'General Electric Company',            price: 34.14,  change: -0.08,  lastChange: '4/3 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'The Procter &amp; Gamble Company',        price: 61.91,  change: 0.01,  lastChange: '4/1 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'United Technologies Corporation',        price: 63.26,  change: 0.55,  lastChange: '4/1 12:00am',  industry: 'Computer'    }
              ],
            });


            var store = Ext.create('gridstore');
            
            store.sort('industry', 'ASC');

            var celledit  = Ext.create('Ext.grid.plugin.CellEditing', {
              clicksToEdit: 1
            });

            var grid  = Ext.create('Ext.grid.Panel', {
               renderTo  : Ext.getBody()
              ,store    : store
              
              ,plugins: [ celledit ]
              ,viewConfig  : {
                 stripeRows  : false
              }

              ,columnLines  : true

              ,columns  : [
                {
                   header    : "Industry"
                  ,width    : 200
                  ,sortable  : true
                  ,dataIndex  : 'industry'
                  ,editor    : { xtype: 'textfield' }
                  ,renderer  : function (value, meta, record, rowIndex, colIndex, store) {
                    var first = !rowIndex || value !== store.getAt(rowIndex - 1).get('industry'),
                      last = rowIndex >= store.getCount() - 1 || value !== store.getAt(rowIndex + 1).get('industry');

                    if (first) {
                      var i = rowIndex + 1, span = 1;
                      while (i < store.getCount() && value === store.getAt(i).get('industry')) {
                        i++;
                        span++;
                      }
                      var rowHeight = 20, padding = 6,
                        height = (rowHeight * (i - rowIndex) - padding) + 'px';
                      meta.style = 'height:' + height + ';line-height:' + height + ';';
                      meta.tdAttr = 'rowspan = ' + span;
                    }
                    else{
                      meta.tdAttr='style="display:none;"';
                    }
                    return first ? value : '';
                  }
                }
                ,{
                   header    : "Company"
                  ,width    : 300
                  ,sortable  : true
                  ,dataIndex  : 'company'
                  ,editor    : { xtype: 'textfield' }
                }
                ,{
                   header    : "Price"
                  ,width    : 100
                  ,sortable  : true
                  ,renderer  : Ext.util.Format.usMoney
                  ,dataIndex  : 'price'
                }
                ,{
                   header    : "Change"
                  ,width    : 100
                  ,sortable  : true
                  ,dataIndex  : 'change'
                  ,renderer  : Ext.util.Format.usMoney
                  ,editor    : { xtype: 'numberfield' }
                }
                ,{
                   header    : "Last Updated"
                  ,width    : 100
                  ,sortable  : true
                  ,renderer  : Ext.util.Format.dateRenderer('m/d/Y')
                  ,dataIndex  : 'lastChange'
                  ,editor    : { xtype: 'datefield' }
                }
              ]
            });
          });
        
        </script>
        
      </head>

      <body>
      </body>
    </html> 

  3. #2
    Ext JS Premium Member
    Join Date
    Nov 2009
    Location
    St Louis,MO
    Posts
    267
    Answers
    20
    Vote Rating
    18
      0  

    Default

    A grouping grid is designed to handle this situation, though it is visually different from what you have drawn. You would group on company and not show the company collum. Visually it would look like this:


    Boeing
    A-123 12
    A234 11

  4. #3
    Sencha User
    Join Date
    Apr 2007
    Posts
    38
    Answers
    1
    Vote Rating
    3
      0  

    Default

    I know. But that doesn't give the same effect as what I'm looking for. I did find this implementation by Condor for Extjs 3.

    Although, there isn't a ExtJs 4 implementation, I'm trying to create one. The renderer which Condor shows works quite well with Extjs 4.1.1 quite well out of the box. Am still struggling a bit with the styling, though.

    I'll post my solution once I'm done.

  5. #4
    Ext JS Premium Member tvanzoelen's Avatar
    Join Date
    Apr 2008
    Location
    Groningen - Netherlands
    Posts
    1,154
    Answers
    87
    Vote Rating
    34
      0  

  6. #5
    Sencha User
    Join Date
    Apr 2007
    Posts
    38
    Answers
    1
    Vote Rating
    3
      1  

    Default This is how I got it working

    As mentioned, initial pointers given by Condor from this forum thread. This solution was for ExtJs 3.

    After that I got a big hint from bogc in this forum thread.

    Then I just tied everything together!

    Code is below...

    PHP Code:
    <html>
      <
    head>
        <
    meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
        <
    title>Editor Grid with Row Span</title>
        
        <
    link rel='stylesheet' type='text/css' href='http://dev.sencha.com/deploy/ext-4.1.0-gpl/resources/css/ext-all.css' />

        <
    script type='text/javascript' src='http://dev.sencha.com/deploy/ext-4.1.0-gpl/ext-all.js'></script>

        <script type="text/javascript">
          
          Ext.onReady(function(){
            Ext.define('gridstore', {
               extend    : 'Ext.data.Store'

              ,fields    : [
                {name: 'company'}
                 ,{name: 'price', type: 'float'}
                 ,{name: 'change', type: 'float'}
                 ,{name: 'lastChange', type: 'date', dateFormat: 'n/j h:ia'}
                 ,{name: 'industry'}
              ]

              ,data: [
                 { company: '3m Co',                    price: 71.72,  change: 0.12,  lastChange: '4/2 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Alcoa Inc',                  price: 29.01,  change: 0.42,  lastChange: '4/1 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Altria Group Inc',                price: 83.81,  change: 0.28,  lastChange: '4/3 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'American Express Company',            price: 52.55,  change: 0.01,  lastChange: '4/8 12:00am',  industry: 'Finance'      }
                ,{ company: 'American International Group, Inc.',      price: 64.13,  change: 0.31,  lastChange: '4/1 12:00am',  industry: 'Services'    }
                ,{ company: 'AT&amp;T Inc.',                price: 31.61,  change: -0.48,  lastChange: '4/8 12:00am',  industry: 'Services'    }
                ,{ company: 'Boeing Co.',                  price: 75.43,  change: 0.53,  lastChange: '4/8 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Caterpillar Inc.',                price: 67.27,  change: 0.92,  lastChange: '4/1 12:00am',  industry: 'Services'    }
                ,{ company: 'Citigroup, Inc.',                price: 49.37,  change: 0.02,  lastChange: '4/4 12:00am',  industry: 'Finance'      }
                ,{ company: 'E.I. du Pont de Nemours and Company',      price: 40.48,  change: 0.51,  lastChange: '4/1 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'Exxon Mobil Corp',                price: 68.1,  change: -0.43,  lastChange: '4/3 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'General Electric Company',            price: 34.14,  change: -0.08,  lastChange: '4/3 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'The Procter &amp; Gamble Company',        price: 61.91,  change: 0.01,  lastChange: '4/1 12:00am',  industry: 'Manufacturing'  }
                ,{ company: 'United Technologies Corporation',        price: 63.26,  change: 0.55,  lastChange: '4/1 12:00am',  industry: 'Computer'    }
              ],
            });


            var store = Ext.create('gridstore');
            
            store.sort('industry', 'ASC');

            var celledit  = Ext.create('Ext.grid.plugin.CellEditing', {
              clicksToEdit: 1
            });

            var grid  = Ext.create('Ext.grid.Panel', {
               renderTo  : Ext.getBody()
              ,store    : store
              
              ,plugins: [ celledit ]
              ,viewConfig  : {
                 stripeRows  : false
              }

              ,columnLines  : true

              ,columns  : [
                {
                   header    : "Industry"
                  ,width    : 200
                  ,sortable  : true
                  ,dataIndex  : 'industry'
                  ,editor    : { xtype: 'textfield' }
                  ,renderer  : function (value, meta, record, rowIndex, colIndex, store) {
                    var first = !rowIndex || value !== store.getAt(rowIndex - 1).get('industry'),
                      last = rowIndex >= store.getCount() - 1 || value !== store.getAt(rowIndex + 1).get('industry');

                    if (first) {
                      var i = rowIndex + 1, span = 1;
                      while (i < store.getCount() && value === store.getAt(i).get('industry')) {
                        i++;
                        span++;
                      }
                      var rowHeight = 20, padding = 6,
                        height = (rowHeight * (i - rowIndex) - padding) + 'px';
                      meta.style = 'height:' + height + ';line-height:' + height + ';';
                      meta.tdAttr = 'rowspan = ' + span;
                    }
                    else{
                      meta.tdAttr='style="display:none;"';
                    }
                    return first ? value : '';
                  }
                }
                ,{
                   header    : "Company"
                  ,width    : 300
                  ,sortable  : true
                  ,dataIndex  : 'company'
                  ,editor    : { xtype: 'textfield' }
                }
                ,{
                   header    : "Price"
                  ,width    : 100
                  ,sortable  : true
                  ,renderer  : Ext.util.Format.usMoney
                  ,dataIndex  : 'price'
                }
                ,{
                   header    : "Change"
                  ,width    : 100
                  ,sortable  : true
                  ,dataIndex  : 'change'
                  ,renderer  : Ext.util.Format.usMoney
                  ,editor    : { xtype: 'numberfield' }
                }
                ,{
                   header    : "Last Updated"
                  ,width    : 100
                  ,sortable  : true
                  ,renderer  : Ext.util.Format.dateRenderer('m/d/Y')
                  ,dataIndex  : 'lastChange'
                  ,editor    : { xtype: 'datefield' }
                }
              ]
            });
          });
        
        </script>
        
      </head>

      <body>
      </body>
    </html> 

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •