source: trunk/web2/addons/job_monarch/js/jobgrid.js @ 588

Last change on this file since 588 was 588, checked in by ramonb, 15 years ago

job_monarch/js/jobgrid.js:

  • correctly clear query filter
File size: 20.9 KB
Line 
1var JobsDataStore;
2var JobsColumnModel;
3var JobListingEditorGrid;
4var JobListingWindow;
5var JobProxy;
6var SearchField;
7var filterButton;
8var myfilters = { };
9var myparams = { };
10var mylimit = 15;
11var ClusterImageArgs = { };
12
13var filterfields = [ "jid", "queue", "name", "owner" ];
14
15var filterMenu = new Ext.menu.Menu({
16    id: 'filterMenu',
17    items: [ new Ext.menu.Item({ text: 'Clear all', handler: clearFilters }) ]
18});
19
20var filterButton = new Ext.MenuButton({
21                        id: 'filtermenuknop',
22                        text: 'Filters',
23                        disabled: true,
24                        menu: filterMenu
25                });
26
27Ext.namespace('Ext.ux');
28
29Ext.ux.PageSizePlugin = function() {
30    Ext.ux.PageSizePlugin.superclass.constructor.call(this, {
31        store: new Ext.data.SimpleStore({
32            fields: ['text', 'value'],
33            data: [['10', 10], ['15', 15], ['20', 20], ['30', 30], ['50', 50], ['100', 100], ['max', 'max' ]]
34        }),
35        mode: 'local',
36        displayField: 'text',
37        valueField: 'value',
38        editable: false,
39        allowBlank: false,
40        triggerAction: 'all',
41        width: 40
42    });
43};
44
45Ext.extend(Ext.ux.PageSizePlugin, Ext.form.ComboBox, {
46    init: function(paging) {
47        paging.on('render', this.onInitView, this);
48    },
49   
50    onInitView: function(paging) {
51        paging.add('-',
52            this,
53            'jobs per page'
54        );
55        this.setValue(paging.pageSize);
56        this.on('select', this.onPageSizeChanged, paging);
57    },
58   
59    onPageSizeChanged: function(combo) {
60        if ( combo.getValue() == 'max' )
61          mylimit = JobsDataStore.getTotalCount();
62        else
63          mylimit = parseInt(combo.getValue());
64        this.pageSize = mylimit;
65        this.doLoad(0);
66    }
67});
68
69Ext.namespace( 'Ext' );
70
71function clearFilters()
72{
73        if( inMyArrayKeys( myfilters, 'query' ) )
74        {
75                SearchField.getEl().dom.value = '';
76                delete SearchField.store.baseParams['query'];
77                delete myfilters['query'];
78                delete myparams['query'];
79        }
80        if( inMyArrayKeys( myfilters, 'host' ) )
81        {
82                delete myfilters['host'];
83                delete myparams['host'];
84        }
85        if( inMyArrayKeys( myfilters, 'jid' ) )
86        {
87                delete myfilters['jid'];
88                delete myparams['jid'];
89        }
90        if( inMyArrayKeys( myfilters, 'queue' ) )
91        {
92                delete myfilters['queue'];
93                delete myparams['queue'];
94        }
95        if( inMyArrayKeys( myfilters, 'owner' ) )
96        {
97                delete myfilters['owner'];
98                delete myparams['owner'];
99        }
100        if( inMyArrayKeys( myfilters, 'status' ) )
101        {
102                delete myfilters['status'];
103                delete myparams['status'];
104        }
105        reloadJobStore();
106}
107
108function makeArrayURL( somearr )
109{
110  filter_url = '';
111  filter_sep = '';
112
113  for( filtername in somearr )
114  {
115    filter_url = filter_url + filter_sep + filtername + '=' + somearr[filtername];
116    filter_sep = '&';
117  }
118
119  return filter_url;
120}
121
122
123function isset( somevar )
124{
125  try
126  {
127    if( eval( somevar ) ) { }
128  }
129  catch( err )
130  {
131    return false;
132  }
133  return true;
134}
135
136function inMyArray( arr, someval )
137{
138  for( arval in arr )
139  {
140    if( arval == someval )
141    {
142      return true;
143    }
144  }
145  return false;
146}
147
148function ArraySize( arr )
149{
150  count = 0;
151
152  for( arkey in arr )
153  {
154    count = count + 1;
155  }
156
157  return count;
158}
159
160function inMyArrayValues( arr, someval )
161{
162  for( arkey in arr )
163  {
164    if( arr[arkey] == someval )
165    {
166      return true;
167    }
168  }
169  return false;
170}
171
172function inMyArrayKeys( arr, someval )
173{
174  for( arkey in arr )
175  {
176    if( arkey == someval )
177    {
178      return true;
179    }
180  }
181  return false;
182}
183
184function joinMyArray( arr1, arr2 )
185{
186  for( arkey in arr2 )
187  {
188    arr1[arkey] = arr2[arkey];
189  }
190
191  return arr1;
192}
193
194function ClusterImageSelectHost( somehost )
195{
196
197  if( !inMyArrayKeys( myfilters, 'host' ) )
198  {
199    myfilters['host'] = somehost;
200  }
201  else
202  {
203    if( myfilters['host'] == somehost )
204    {
205      delete myfilters['host'];
206      delete myparams['host'];
207    }
208    else
209    {
210      myfilters['host'] = somehost;
211    }
212  }
213
214  reloadClusterImage();
215  reloadJobStore();
216
217  return false;
218}
219
220function reloadJobStore()
221{
222  // Respect any other parameters that may have been set outside filters
223  //
224  myparams = joinMyArray( myparams, myfilters );
225
226  // Can't be sure if there are enough pages for new filter: reset to page 1
227  //
228  myparams = joinMyArray( myparams, { start: 0, limit: mylimit } );
229
230  JobsDataStore.reload( { params: myparams } );
231}
232
233function addListener(element, type, expression, bubbling)
234{
235  bubbling = bubbling || false;
236  if(window.addEventListener)
237  { // Standard
238    element.addEventListener(type, expression, bubbling);
239    return true;
240  } 
241  else if(window.attachEvent) 
242  { // IE
243    element.attachEvent('on' + type, expression);
244    return true;
245  } 
246  else 
247    return false;
248}
249
250function makeFilterString()
251{
252  var filter_str = '';
253
254  for( arkey in myfilters )
255  {
256    filter_str = filter_str + ' > ' + myfilters[arkey];
257  }
258
259  return filter_str;
260}
261
262var ImageLoader = function( id, url )
263{
264  this.url = url;
265  this.image = document.getElementById( id );
266  this.loadEvent = null;
267};
268
269ImageLoader.prototype = 
270{
271  load:function()
272  {
273    var url = this.url;
274    var image = this.image;
275    var loadEvent = this.loadEvent;
276    addListener( this.image, 'load', function(e)
277    {
278      if( loadEvent != null )
279      {
280        loadEvent( url, image );
281      }
282    }, false);
283    this.image.src = this.url;
284  },
285  getImage: function()
286  {
287    return this.image;
288  }
289};
290
291function achorJobListing()
292{
293  JobListingWindow.anchorTo( "ClusterImageWindow", "tr-br", [ 0, 10 ] );
294}
295
296function setClusterImagePosition()
297{
298  ci_x = (window.innerWidth - ClusterImageWindow.getSize()['width'] - 20); 
299  ClusterImageWindow.setPosition( ci_x, 10 );
300}
301
302function deselectFilterMenu( menuItem, event )
303{
304  filterValue = menuItem.text;
305
306  if( filterValue == SearchField.getEl().dom.value && inMyArrayKeys( myfilters, 'query' ) )
307  {
308    SearchField.getEl().dom.value = '';
309    delete SearchField.store.baseParams['query'];
310  }
311
312  for( arkey in myfilters )
313  {
314    if( myfilters[arkey] == filterValue )
315    {
316      delete myfilters[arkey];
317      delete myparams[arkey];
318    }
319  }
320  reloadJobStore();
321}
322
323function makeFilterMenu()
324{
325  var filterMenu = new Ext.menu.Menu({
326      id: 'filterMenu',
327      items: [ new Ext.menu.Item({ text: 'Clear all', handler: clearFilters }) ]
328  });
329
330  if( ArraySize( myfilters ) > 0 )
331  {
332    filterMenu.addSeparator();
333  }
334
335  for( arkey in myfilters )
336  {
337    filterMenu.add( new Ext.menu.CheckItem({ text: myfilters[arkey], handler: deselectFilterMenu, checked: true }) );
338  }
339
340  if( filterButton )
341  {
342    filterButton.menu = filterMenu;
343
344    if( ArraySize( myfilters ) > 0 )
345    {
346      filterButton.enable();
347    }
348    else
349    {
350      filterButton.disable();
351    }
352  }
353}
354
355function reloadClusterImage()
356{
357  ClusterImageArgs['view'] = 'big-clusterimage';
358
359  filt_url = makeArrayURL( myfilters );
360  imag_url = makeArrayURL( ClusterImageArgs );
361  img_url = './image.php?' + filt_url + '&' + imag_url;
362
363  var newClusterImage = new ImageLoader( 'clusterimage', img_url );
364  newClusterImage.loadEvent = function( url, image ) 
365    {
366      ClusterImageWindow.getBottomToolbar().clearStatus( { useDefaults:true } );
367      setTimeout( "resizeClusterImage()", 250 );
368      setTimeout( "setClusterImagePosition()", 500 );
369      //setTimeout( "achorJobListing()", 1000 );
370    }
371
372  ClusterImageWindow.getBottomToolbar().showBusy();
373
374  filter_str = 'Nodes' + makeFilterString();
375  ClusterImageWindow.setTitle( filter_str );
376
377  newClusterImage.load();
378}
379
380function resizeClusterImage()
381{
382  var ci_height = document.getElementById( "clusterimage" ).height + ClusterImageWindow.getFrameHeight();
383  var ci_width = document.getElementById( "clusterimage" ).width + ClusterImageWindow.getFrameWidth();
384
385  ClusterImageWindow.setSize( ci_width, ci_height );
386}
387
388Ext.apply(Ext.form.VTypes, {
389        num: function(val, field) {
390
391                if (val) {
392                   var strValidChars = "0123456789";
393                   var blnResult = true;
394
395                   if (val.length == 0) return false;
396
397                   //  test strString consists of valid characters listed above
398                   for (i = 0; i < val.length && blnResult == true; i++)
399                      {
400                      strChar = val.charAt(i);
401                      if (strValidChars.indexOf(strChar) == -1)
402                         {
403                         blnResult = false;
404                         }
405                      }
406                   return blnResult;
407
408                }
409                },
410        numText: 'Must be numeric'
411});
412
413function initJobGrid() {
414
415  Ext.QuickTips.init();
416
417  function jobCellClick(grid, rowIndex, columnIndex, e)
418  {
419    var record = grid.getStore().getAt(rowIndex);  // Get the Record
420    var fieldName = grid.getColumnModel().getDataIndex(columnIndex);
421    var data = record.get(fieldName);
422    var view = grid.getView();
423    var cell = view.getCell( rowIndex, columnIndex );
424    var filter_title = false;
425    var fil_dis = 'filter';
426    var fil_ena = 'filterenabled';
427    var filterName = fieldName;
428
429    if( fieldName == 'owner' || fieldName == 'jid' || fieldName == 'status' || fieldName == 'queue' || fieldName == 'nodes')
430    {
431      if( fieldName == 'nodes' )
432      {
433        filterName = 'host';
434        fil_dis = 'nodesfilter';
435        fil_ena = 'nodesfilterenabled';
436      }
437      if( inMyArrayKeys( myfilters, filterName ) )
438      {
439        Ext.fly(cell).removeClass( fil_ena );
440        Ext.fly(cell).addClass( fil_dis );
441
442        // Remove this filter
443        //
444        delete myfilters[filterName];
445        delete myparams[filterName];
446
447        reloadJobStore();
448        //reloadClusterImage();
449      }
450      else
451      {
452        Ext.fly(cell).removeClass( fil_dis );
453        Ext.fly(cell).addClass( fil_ena );
454
455        if( fieldName == 'nodes' )
456        { // Get the first node (master mom) as node filter
457          new_data = data.split( ',' )[0];
458          data = new_data;
459        }
460
461        // Set filter for selected column to selected cell value
462        //
463        myfilters[filterName] = data;
464
465        reloadJobStore();
466        //reloadClusterImage();
467      }
468      JobListingWindow.setTitle( filter_str );
469      filter_title = true;
470      filter_str = myparams.c + ' Jobs Overview' + makeFilterString();
471    }
472  }
473
474  function jobCellRender( value, metadata, record, rowindex, colindex, store )
475  {
476    var fieldName = JobsColumnModel.getColumnById( colindex ).dataIndex;
477    var fil_dis = 'filter';
478    var fil_ena = 'filterenabled';
479    var filterName = fieldName;
480
481    if( fieldName == 'owner' || fieldName == 'jid' || fieldName == 'status' || fieldName == 'queue' || fieldName == 'nodes' )
482    {
483      if( fieldName == 'nodes' )
484      {
485        fil_dis = 'nodesfilter';
486        fil_ena = 'nodesfilterenabled';
487        filterName = 'host';
488      }
489      if( myfilters[filterName] != null )
490      {
491        metadata.css = fil_ena;
492      }
493      else
494      {
495        metadata.css = fil_dis;
496      }
497    }
498    return value;
499  }
500
501  JobProxy = new Ext.data.HttpProxy({
502                url: 'jobstore.php',
503                method: 'POST'
504            });
505
506
507  JobsDataStore = new Ext.data.Store({
508      id: 'JobsDataStore',
509      proxy: JobProxy,
510      baseParams: { task: "GETJOBS" },
511      reader: new Ext.data.JsonReader({
512        root: 'results',
513        totalProperty: 'total',
514        id: 'id'
515      },[
516        {name: 'jid', type: 'int', mapping: 'jid'},
517        {name: 'status', type: 'string', mapping: 'status'},
518        {name: 'owner', type: 'string', mapping: 'owner'},
519        {name: 'queue', type: 'string', mapping: 'queue'},
520        {name: 'name', type: 'string', mapping: 'name'},
521        {name: 'requested_time', type: 'string', mapping: 'requested_time'},
522        {name: 'requested_memory', type: 'string', mapping: 'requested_memory'},
523        {name: 'ppn', type: 'int', mapping: 'ppn'},
524        {name: 'nodect', type: 'int', mapping: 'nodect'},
525        {name: 'nodes', type: 'string', mapping: 'nodes'},
526        {name: 'queued_timestamp', type: 'string', mapping: 'queued_timestamp'},
527        {name: 'start_timestamp', type: 'string', mapping: 'start_timestamp'},
528        {name: 'runningtime', type: 'string', mapping: 'runningtime'}
529      ]),
530      sortInfo: { field: 'jid', direction: "DESC" },
531      remoteSort: true,
532      listeners:
533        { 
534                'beforeload':
535                {
536                        scope: this,
537                        fn: function()
538                        {
539                                if( SearchField )
540                                {
541                                        search_value = SearchField.getEl().dom.value;
542                                        if( search_value == '' )
543                                        {
544                                                delete SearchField.store.baseParams['query'];
545                                                delete myfilters['query'];
546                                                delete myparams['query'];
547                                        }
548                                        else
549                                        {
550                                                myfilters['query']      = search_value;
551                                        }
552
553                                        makeFilterMenu();
554                                        reloadClusterImage();
555
556                                        filter_str = myparams.c + ' Jobs Overview' + makeFilterString();
557                                        JobListingWindow.setTitle( filter_str );
558                                }
559                        }
560                } //,
561                //'load':
562                //{
563                //      scope: this,
564                //      fn: function()
565                //      {
566                //              if( SearchField )
567                //              {
568                //                      search_value = SearchField.getEl().dom.value;
569
570                //                      if( search_value != '' )
571                //                      {
572                //                              myfilters['query']      = search_value;
573                //                      }
574
575                //                      reloadClusterImage();
576
577                //                      filter_str = myparams.c + ' Jobs Overview' + makeFilterString();
578                //                      JobListingWindow.setTitle( filter_str );
579
580                //                      if( search_value != '' )
581                //                      {
582                //                              delete myfilters['query'];
583                //                      }
584                //              }
585                //      }
586                //}
587        }
588    });
589   
590  var CheckJobs = new Ext.grid.CheckboxSelectionModel();
591
592  JobsColumnModel = new Ext.grid.ColumnModel(
593    [ CheckJobs,
594    {
595        header: '#',
596        tooltip: 'Job id',
597        readOnly: true,
598        dataIndex: 'jid',
599        width: 50,
600        hidden: false,
601        renderer: jobCellRender
602      },{
603        header: 'S',
604        tooltip: 'Job status',
605        readOnly: true,
606        dataIndex: 'status',
607        width: 20,
608        hidden: false,
609        renderer: jobCellRender
610      },{
611        header: 'User',
612        tooltip: 'Owner of job',
613        readOnly: true,
614        dataIndex: 'owner',
615        width: 60,
616        hidden: false,
617        renderer: jobCellRender
618      },{
619        header: 'Queue',
620        tooltip: 'In which queue does this job reside',
621        readOnly: true,
622        dataIndex: 'queue',
623        width: 60,
624        hidden: false,
625        renderer: jobCellRender
626      },{
627        header: 'Name',
628        tooltip: 'Name of job',
629        readOnly: true,
630        dataIndex: 'name',
631        width: 100,
632        hidden: false
633      },{
634        header: 'Requested Time',
635        tooltip: 'Amount of requested time (wallclock)',
636        readOnly: true,
637        dataIndex: 'requested_time',
638        width: 100,
639        hidden: false
640      },{
641        header: 'Requested Memory',
642        tooltip: 'Amount of requested memory',
643        readOnly: true,
644        dataIndex: 'requested_memory',
645        width: 100,
646        hidden: true
647      },{
648        header: 'P',
649        tooltip: 'Number of processors per node (PPN)',
650        readOnly: true,
651        dataIndex: 'ppn',
652        width: 25,
653        hidden: false
654      },{
655        header: 'N',
656        tooltip: 'Number of nodes (hosts)',
657        readOnly: true,
658        dataIndex: 'nodect',
659        width: 25,
660        hidden: false
661      },{
662        header: 'Nodes',
663        readOnly: true,
664        dataIndex: 'nodes',
665        width: 100,
666        hidden: false,
667        renderer: jobCellRender
668      },{
669        header: 'Queued',
670        tooltip: 'At what time did this job enter the queue',
671        readOnly: true,
672        dataIndex: 'queued_timestamp',
673        width: 120,
674        hidden: false
675      },{
676        header: 'Started',
677        tooltip: 'At what time did this job enter the running status',
678        readOnly: true,
679        dataIndex: 'start_timestamp',
680        width: 120,
681        hidden: false
682      },{
683        header: 'Runningtime',
684        tooltip: 'How long has this job been in the running status',
685        readOnly: true,
686        dataIndex: 'runningtime',
687        width: 140,
688        hidden: false
689      }]
690    );
691    JobsColumnModel.defaultSortable= true;
692
693  var win;
694
695  MetricsDataStore = new Ext.data.Store({
696      id: 'MetricsDataStore',
697      proxy: JobProxy,
698      autoLoad: false,
699      baseParams: { task: "GETMETRICS" },
700      reader: new Ext.data.JsonReader({
701        root: 'names',
702        totalProperty: 'total',
703        id: 'id'
704      },[{
705        name: 'ID'
706      },{
707        name: 'name'
708        }])
709  });
710
711  SearchField   = new Ext.app.SearchField({
712                                store: JobsDataStore,
713                                params: {start: 0, limit: mylimit},
714                                width: 200
715                    });
716
717  NodesDataStore = new Ext.data.Store({
718      id: 'NodesDataStore',
719      proxy: JobProxy,
720      autoLoad: false,
721      baseParams: { task: "GETNODES" },
722      reader: new Ext.data.JsonReader({
723        root: 'results',
724        totalProperty: 'total',
725        id: 'id'
726      },[
727        {name: 'c', type: 'string', mapping: 'c'},
728        {name: 'h', type: 'string', mapping: 'h'},
729        {name: 'x', type: 'string', mapping: 'x'},
730        {name: 'v', type: 'string', mapping: 'v'},
731        {name: 'l', type: 'string', mapping: 'l'},
732        {name: 'jr', type: 'string', mapping: 'jr'},
733        {name: 'js', type: 'string', mapping: 'js'}
734      ]),
735      listeners: {
736                'beforeload': {
737                        scope: this,
738                        fn: function() {
739                                        var jids;
740
741                                        var row_records = CheckJobs.getSelections();
742
743                                        for(var i=0; i<row_records.length; i++ )
744                                        {
745                                                rsel = row_records[i];
746                                                if( !jids )
747                                                {
748                                                        jids = rsel.get('jid');
749                                                }
750                                                else
751                                                {
752                                                        jids = jids + ',' + rsel.get('jid');
753                                                }
754                                        }
755                                        NodesDataStore.baseParams.jids  = jids;
756                                        NodesDataStore.baseParams.c     = myparams.c;
757                        }
758                }
759        }
760    });
761
762function ShowGraphs( Button, Event ) {
763   
764    var GraphView = new Ext.DataView({
765        itemSelector: 'thumb',
766        style:'overflow:auto',
767        multiSelect: true,
768        store: NodesDataStore,
769        tpl: new Ext.XTemplate(
770            '<tpl for=".">',
771            '<div class="rrd-float"><img src="../../graph.php?z=small&c={c}&h={h}&l={l}&v={v}&x={x}&r=job&jr={jr}&js={js}" border="0"></div>',
772            '</tpl>'
773        )
774    });
775
776    var images = new Ext.Panel({
777        id:'images',
778        //title:'My Images',
779        region:'center',
780        bodyStyle: 'background: transparent',
781        //margins: '2 2 2 0',
782        layout:'fit',
783        items: GraphView
784    });
785
786        if(!win){
787            win = new Ext.Window({
788                        animateTarget: Button,
789                        width       : 500,
790                        height      : 300,
791                        closeAction :'hide',
792                        collapsible: true,
793                        animCollapse: true,
794                        maximizable: true,
795                        title:  'Node graph details',
796                        layout: 'fit',
797                        tbar:   new Ext.form.ComboBox({
798                                        fieldLabel: 'Metric',
799                                        //hiddenName:'ID',
800                                        store: MetricsDataStore,
801                                        valueField:'name',
802                                        displayField:'name',
803                                        typeAhead: true,
804                                        mode: 'remote',
805                                        triggerAction: 'all',
806                                        emptyText:'Select metric',
807                                        selectOnFocus:true,
808                                        xtype: 'combo',
809                                        width:190,
810                                        listeners: {
811                                                select: function(combo, record, index){
812                                                        var metric = record.data.name;
813                                                        // doe iets
814                                                }
815                                        }
816                                       
817                                }),
818                        items:  [ images ]
819                    });
820        }
821        NodesDataStore.load();
822        win.show(Button);
823}
824
825
826  JobListingEditorGrid =  new Ext.grid.EditorGridPanel({
827      id: 'JobListingEditorGrid',
828      store: JobsDataStore,
829      cm: JobsColumnModel,
830      enableColLock:false,
831      clicksToEdit:1,
832      loadMask: true,
833      selModel: new Ext.grid.RowSelectionModel({singleSelect:false}),
834      stripeRows: true,
835      sm: CheckJobs,
836      bbar: new Ext.PagingToolbar({
837                pageSize: 15,
838                store: JobsDataStore,
839                displayInfo: true,
840                displayMsg: 'Displaying jobs {0} - {1} out of {2} jobs total found.',
841                emptyMsg: 'No jobs found to display',
842                plugins: [new Ext.ux.PageSizePlugin()]
843            }),
844      tbar: [ SearchField,
845                new Ext.Button({
846                                text: 'Show graphs',
847                                tooltip: 'Show node graphs for selected jobs',
848                                iconCls: 'option',
849                                listeners: {
850                                        'click': {
851                                                scope: this,
852                                                fn: ShowGraphs
853                                        }
854                                }
855                        }),
856                filterButton ]
857    });
858
859  ClusterImageWindow = new Ext.Window({
860      id: 'ClusterImageWindow',
861      title: 'Nodes',
862      closable: true,
863      collapsible: true,
864      animCollapse: true,
865      width: 1,
866      height: 1,
867      y: 15,
868      plain: true,
869      shadow: true,
870      resizable: false,
871      shadowOffset: 10,
872      layout: 'fit',
873      bbar: new Ext.StatusBar({
874                defaultText: 'Ready.',
875                id: 'basic-statusbar',
876                defaultIconCls: ''
877        })
878    });
879
880  GraphSummaryWindow = new Ext.Window({
881      id: 'GraphSummaryWindow',
882      title: 'Graph Summary',
883      closable: true,
884      collapsible: true,
885      animCollapse: true,
886      width: 500,
887      height: 400,
888      x: 10,
889      y: 10,
890      plain: true,
891      shadow: true,
892      resizable: true,
893      shadowOffset: 10,
894      layout: 'table',
895      layoutConfig: {
896                columns: 2
897        },
898      defaults:{border: false},
899      items: [{
900        id: 'monarchlogo',
901        cls: 'monarch',
902        bodyStyle: 'background: transparent',
903        html: '<A HREF="https://subtrac.sara.nl/oss/jobmonarch/" TARGET="_blank"><IMG SRC="./jobmonarch.gif" ALT="Job Monarch" BORDER="0"></A>'
904        //colspan: 2
905       },{
906        id: 'summarycount'
907       },{
908        id: 'rjqjgraph'
909       },{
910        id: 'pie',
911        colspan: 2
912       }],
913      bbar: new Ext.StatusBar({
914                defaultText: 'Ready.',
915                id: 'basic-statusbar',
916                defaultIconCls: ''
917        })
918    });
919
920  JobListingWindow = new Ext.Window({
921      id: 'JobListingWindow',
922      title: 'Cluster Jobs Overview',
923      closable:true,
924      collapsible: true,
925      animCollapse: true,
926      maximizable: true,
927      y: 375,
928      width:860,
929      height:445,
930      plain:true,
931      shadow: true,
932      shadowOffset: 10,
933      layout: 'fit',
934      items: JobListingEditorGrid
935    });
936
937  JobListingEditorGrid.addListener( 'cellclick', jobCellClick );
938}
Note: See TracBrowser for help on using the repository browser.