gridx-rails 1.1.0 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (59) hide show
  1. checksums.yaml +8 -8
  2. data/README.md +3 -3
  3. data/app/assets/javascripts/gridx/Grid.js +3 -2
  4. data/app/assets/javascripts/gridx/core/model/cache/_Cache.js +25 -8
  5. data/app/assets/javascripts/gridx/modules/Bar.js +1 -2
  6. data/app/assets/javascripts/gridx/modules/Body.js +15 -7
  7. data/app/assets/javascripts/gridx/modules/CellWidget.js +8 -4
  8. data/app/assets/javascripts/gridx/modules/ColumnLock.js +12 -12
  9. data/app/assets/javascripts/gridx/modules/ColumnResizer.js +9 -10
  10. data/app/assets/javascripts/gridx/modules/Dod.js +1 -0
  11. data/app/assets/javascripts/gridx/modules/Edit.js +18 -15
  12. data/app/assets/javascripts/gridx/modules/Filter.js +7 -3
  13. data/app/assets/javascripts/gridx/modules/Focus.js +45 -36
  14. data/app/assets/javascripts/gridx/modules/GroupHeader.js +2 -1
  15. data/app/assets/javascripts/gridx/modules/HLayout.js +1 -0
  16. data/app/assets/javascripts/gridx/modules/HScroller.js +1 -0
  17. data/app/assets/javascripts/gridx/modules/Header.js +8 -1
  18. data/app/assets/javascripts/gridx/modules/HeaderMenu.js +1 -0
  19. data/app/assets/javascripts/gridx/modules/HeaderRegions.js +2 -1
  20. data/app/assets/javascripts/gridx/modules/IndirectSelect.js +7 -34
  21. data/app/assets/javascripts/gridx/modules/IndirectSelectColumn.js +4 -13
  22. data/app/assets/javascripts/gridx/modules/Menu.js +5 -1
  23. data/app/assets/javascripts/gridx/modules/NavigableCell.js +3 -1
  24. data/app/assets/javascripts/gridx/modules/NestedSort.js +4 -1
  25. data/app/assets/javascripts/gridx/modules/Pagination.js +1 -0
  26. data/app/assets/javascripts/gridx/modules/Persist.js +1 -0
  27. data/app/assets/javascripts/gridx/modules/RowHeader.js +11 -10
  28. data/app/assets/javascripts/gridx/modules/SingleSort.js +1 -0
  29. data/app/assets/javascripts/gridx/modules/SummaryBar.js +1 -0
  30. data/app/assets/javascripts/gridx/modules/ToolBar.js +3 -0
  31. data/app/assets/javascripts/gridx/modules/TouchScroll.js +1 -0
  32. data/app/assets/javascripts/gridx/modules/TouchVScroller.js +28 -5
  33. data/app/assets/javascripts/gridx/modules/Traverse.js +1 -0
  34. data/app/assets/javascripts/gridx/modules/Tree.js +2 -1
  35. data/app/assets/javascripts/gridx/modules/VLayout.js +1 -0
  36. data/app/assets/javascripts/gridx/modules/VScroller.js +22 -11
  37. data/app/assets/javascripts/gridx/modules/View.js +11 -6
  38. data/app/assets/javascripts/gridx/modules/VirtualVScroller.js +8 -4
  39. data/app/assets/javascripts/gridx/modules/dnd/Column.js +3 -4
  40. data/app/assets/javascripts/gridx/modules/dnd/Row.js +3 -4
  41. data/app/assets/javascripts/gridx/modules/dnd/_Dnd.js +1 -0
  42. data/app/assets/javascripts/gridx/modules/extendedSelect/Cell.js +4 -3
  43. data/app/assets/javascripts/gridx/modules/extendedSelect/Column.js +6 -7
  44. data/app/assets/javascripts/gridx/modules/extendedSelect/Row.js +33 -15
  45. data/app/assets/javascripts/gridx/modules/filter/FilterBar.js +9 -7
  46. data/app/assets/javascripts/gridx/modules/filter/FilterDialog.js +1 -1
  47. data/app/assets/javascripts/gridx/modules/filter/FilterPane.js +1 -1
  48. data/app/assets/javascripts/gridx/modules/filter/QuickFilter.js +1 -0
  49. data/app/assets/javascripts/gridx/modules/move/Column.js +2 -1
  50. data/app/assets/javascripts/gridx/modules/move/Row.js +2 -1
  51. data/app/assets/javascripts/gridx/modules/pagination/PaginationBar.js +1 -0
  52. data/app/assets/javascripts/gridx/modules/pagination/PaginationBarDD.js +2 -0
  53. data/app/assets/javascripts/gridx/modules/select/Cell.js +10 -7
  54. data/app/assets/javascripts/gridx/modules/select/Column.js +3 -2
  55. data/app/assets/javascripts/gridx/modules/select/Row.js +27 -13
  56. data/app/assets/javascripts/gridx/support/QuickFilter.js +7 -2
  57. data/lib/gridx-rails/version.rb +1 -1
  58. data/test/dummy/log/test.log +5 -0
  59. metadata +2 -2
@@ -11,6 +11,7 @@ define([
11
11
  /*=====
12
12
  var Filter = declare(_Module, {
13
13
  // summary:
14
+ // module name: filter.
14
15
  // This module makes it possible for user to set arbitrary filter condition to grid.
15
16
 
16
17
  serverMode: false,
@@ -53,7 +54,7 @@ define([
53
54
  }
54
55
  });
55
56
 
56
- Filter.__FilterExpressionTools = {
57
+ Filter.__FilterExpressionTools = declare([], {
57
58
  // summary:
58
59
  // A filter expression is just a function returning TRUE/FALSE.
59
60
  // Here provides a set of useful expression tools to help construct complicated filter expressions for grid.
@@ -243,7 +244,7 @@ define([
243
244
  // return: Function
244
245
  // A filter expression.
245
246
  }
246
- };
247
+ });
247
248
 
248
249
  return Filter;
249
250
  =====*/
@@ -256,6 +257,9 @@ define([
256
257
 
257
258
  constructor: function(){
258
259
  this.setFilter(this.arg('preCondition'), 1);
260
+ this.aspect(this.grid.model, 'setStore', function(){
261
+ this._checker = null;
262
+ });
259
263
  },
260
264
 
261
265
  serverMode: false,
@@ -324,7 +328,7 @@ define([
324
328
  d.setFullYear(2000);
325
329
  return d.getTime();
326
330
  default: //string
327
- return d === null || d === undefined ? '' : String(d);
331
+ return (d === null || d === undefined) ? '' : String(d);
328
332
  }
329
333
  }
330
334
 
@@ -13,6 +13,7 @@ define([
13
13
  /*=====
14
14
  var Focus = declare(_Module, {
15
15
  // summary
16
+ // module name: focus.
16
17
  // This module controls the TAB sequence of all the UI modules.
17
18
  // But this module is (or at least can be) a non-UI module, because it does not handle the actual focus job.
18
19
 
@@ -162,7 +163,9 @@ define([
162
163
 
163
164
  return declare(_Module, {
164
165
  name: 'focus',
165
-
166
+
167
+ enabled: !has('ios') && !has('android'),
168
+
166
169
  constructor: function(){
167
170
  var t = this,
168
171
  g = t.grid;
@@ -360,7 +363,7 @@ define([
360
363
  _stackIdx: 0,
361
364
 
362
365
  _onTabDown: function(evt){
363
- if(evt.keyCode === keys.TAB){
366
+ if(this.arg('enabled') && evt.keyCode === keys.TAB){
364
367
  this.tab(evt.shiftKey ? -1 : 1, evt);
365
368
  }
366
369
  },
@@ -371,54 +374,60 @@ define([
371
374
  dn = t.grid.domNode,
372
375
  n = evt.target,
373
376
  currentArea = t._areas[t.currentArea()];
374
- while(n && n !== dn){
375
- i = array.indexOf(t._focusNodes, n);
376
- if(i >= 0){
377
- stack = t._tabQueue[i].stack;
378
- for(j = 0; j < stack.length; ++j){
379
- area = t._areas[stack[j]];
380
- if(area.onFocus(evt)){
381
- if(currentArea && currentArea.name !== area.name){
382
- currentArea.onBlur(evt);
383
- t.onBlurArea(currentArea.name);
377
+ if(t.arg('enabled')){
378
+ while(n && n !== dn){
379
+ i = array.indexOf(t._focusNodes, n);
380
+ if(i >= 0){
381
+ stack = t._tabQueue[i].stack;
382
+ for(j = 0; j < stack.length; ++j){
383
+ area = t._areas[stack[j]];
384
+ if(area.onFocus(evt)){
385
+ if(currentArea && currentArea.name !== area.name){
386
+ currentArea.onBlur(evt);
387
+ t.onBlurArea(currentArea.name);
388
+ }
389
+ t.onFocusArea(area.name);
390
+ t._queueIdx = i;
391
+ t._stackIdx = j;
392
+ return;
384
393
  }
385
- t.onFocusArea(area.name);
386
- t._queueIdx = i;
387
- t._stackIdx = j;
388
- return;
389
394
  }
395
+ return;
390
396
  }
391
- return;
397
+ n = n.parentNode;
398
+ }
399
+ if(n == dn && currentArea){
400
+ t._doBlur(evt, currentArea);
392
401
  }
393
- n = n.parentNode;
394
- }
395
- if(n == dn && currentArea){
396
- t._doBlur(evt, currentArea);
397
402
  }
398
403
  },
399
404
 
400
405
  _focus: function(evt){
401
406
  var t = this;
402
- if(t._tabingOut){
403
- t._tabingOut = 0;
404
- }else if(evt.target == t.grid.domNode){
405
- t._queueIdx = -1;
406
- t.tab(1);
407
- }else if(evt.target === t.grid.lastFocusNode){
408
- t._queueIdx = t._tabQueue.length;
409
- t.tab(-1);
407
+ if(t.arg('enabled')){
408
+ if(t._tabingOut){
409
+ t._tabingOut = 0;
410
+ }else if(evt.target == t.grid.domNode){
411
+ t._queueIdx = -1;
412
+ t.tab(1);
413
+ }else if(evt.target === t.grid.lastFocusNode){
414
+ t._queueIdx = t._tabQueue.length;
415
+ t.tab(-1);
416
+ }
410
417
  }
411
418
  },
412
419
 
413
420
  _doBlur: function(evt, area){
414
421
  var t = this;
415
- if(!area && t.currentArea()){
416
- area = t._areas[t.currentArea()];
417
- }
418
- if(area){
419
- area.onBlur(evt);
420
- t.onBlurArea(area.name);
421
- t._updateCurrentArea();
422
+ if(t.arg('enabled')){
423
+ if(!area && t.currentArea()){
424
+ area = t._areas[t.currentArea()];
425
+ }
426
+ if(area){
427
+ area.onBlur(evt);
428
+ t.onBlurArea(area.name);
429
+ t._updateCurrentArea();
430
+ }
422
431
  }
423
432
  },
424
433
 
@@ -14,6 +14,7 @@ define([
14
14
  /*=====
15
15
  var GroupHeader = declare(Header, {
16
16
  // summary:
17
+ // module name: header.
17
18
  // The header UI of grid. This implementation supports header groups (also called "column groups").
18
19
  // This module is not compatible with IE7 and below.
19
20
  // This module is not compatible with ColumnLock and HiddenColumns.
@@ -409,7 +410,7 @@ define([
409
410
  _onKeyDown: function(evt){
410
411
  var t = this, g = t.grid, col,
411
412
  node = t._curNode;
412
- if(!evt.ctrlKey && !evt.altKey &&
413
+ if(!g._isCtrlKey(evt) && !evt.altKey &&
413
414
  (evt.keyCode == keys.LEFT_ARROW || evt.keyCode == keys.RIGHT_ARROW)){
414
415
  //Prevent scrolling the whole page.
415
416
  g.focus.stopEvent(evt);
@@ -10,6 +10,7 @@ define([
10
10
  /*=====
11
11
  return declare(_Module, {
12
12
  // summary:
13
+ // module name: hLayout.
13
14
  // This module manages the horizontal layout of all grid UI parts.
14
15
  // description:
15
16
  // When a user creates a grid with a given width, it means the width of the whole grid,
@@ -11,6 +11,7 @@ define([
11
11
  /*=====
12
12
  return declare(_Module, {
13
13
  // summary:
14
+ // module name: hScroller.
14
15
  // This module provides basic horizontal scrolling for grid
15
16
 
16
17
  scrollToColumn: function(colId){
@@ -22,6 +22,7 @@ define([
22
22
 
23
23
  return declare(_Module, {
24
24
  // summary:
25
+ // module name: header.
25
26
  // The header UI of grid
26
27
  // description:
27
28
  // This module is in charge of the rendering of the grid header. But it should not manage column width,
@@ -105,6 +106,12 @@ define([
105
106
  });
106
107
  t.aspect(g, 'onHeaderCellMouseOut', function(){
107
108
  g.vLayout.reLayout();
109
+ //When mouse leave a very narrow nested sorting header, sometimes this reLayout happens before the header height change.
110
+ //So set a timeout to ensure this gets relayout.
111
+ //FIXME: need investigate why
112
+ setTimeout(function(){
113
+ g.vLayout.reLayout();
114
+ }, 0);
108
115
  });
109
116
  t._initFocus();
110
117
  },
@@ -273,7 +280,7 @@ define([
273
280
  var t = this, g = t.grid, col,
274
281
  dir = g.isLeftToRight() ? 1 : -1,
275
282
  delta = evt.keyCode == keys.LEFT_ARROW ? -dir : dir;
276
- if(t._focusHeaderId && !evt.ctrlKey && !evt.altKey &&
283
+ if(t._focusHeaderId && !g._isCtrlKey(evt) && !evt.altKey &&
277
284
  (evt.keyCode == keys.LEFT_ARROW || evt.keyCode == keys.RIGHT_ARROW)){
278
285
  //Prevent scrolling the whole page.
279
286
  g.focus.stopEvent(evt);
@@ -12,6 +12,7 @@ define([
12
12
  /*=====
13
13
  var HeaderMenu = declare(_Module, {
14
14
  // summary:
15
+ // module name: headerMenu.
15
16
  // Add a dropdown menu button on header cell.
16
17
  // description:
17
18
  // Add a dropdown menu button on the header of any column that has a "menu" defined in structure.
@@ -14,6 +14,7 @@ define([
14
14
  /*=====
15
15
  return declare(_Module, {
16
16
  // summary:
17
+ // module name: headerRegions.
17
18
  // This module makes it easy to add custom contents to column header.
18
19
  // Other modules such as NestedSort or HeaderMenu can be based upon this module.
19
20
 
@@ -172,7 +173,7 @@ declare(_Module, {
172
173
  },
173
174
 
174
175
  _onKey: function(e){
175
- if(!e.ctrlKey && !e.shiftKey && !e.altKey){
176
+ if(!this.grid._isCtrlKey(e) && !e.shiftKey && !e.altKey){
176
177
  var ltr = this.grid.isLeftToRight(),
177
178
  nextKey = ltr ? keys.RIGHT_ARROW : keys.LEFT_ARROW,
178
179
  prevKey = ltr ? keys.LEFT_ARROW : keys.RIGHT_ARROW;
@@ -16,6 +16,7 @@ define([
16
16
  /*=====
17
17
  return declare(_Module, {
18
18
  // summary:
19
+ // module name: indirectSelect.
19
20
  // This module shows a checkbox(or radiobutton) on the row header when row selection is used.
20
21
  // description:
21
22
  // This module depends on "rowHeader" and "selectRow" modules.
@@ -49,24 +50,11 @@ define([
49
50
  [sr,'onHighlightChange', '_onHighlightChange' ],
50
51
  [sr,'clear', '_onClear' ],
51
52
  [sr, 'onSelectionChange', '_onSelectionChange'],
52
- [g, 'onRowMouseOver', '_onMouseOver'],
53
- [g, 'onRowMouseOut', '_onMouseOut'],
53
+ [g.body, 'onRender', '_onSelectionChange'],
54
54
  [g, 'onRowKeyDown', '_onKeyDown'],
55
55
  [g, 'onHeaderKeyDown', '_onKeyDown'],
56
- g.filter && [g.filter, 'onFilter', '_onSelectionChange'],
57
- //FIX ME, may have performance issue
58
- g.pagination && [g.pagination, 'setPageSize', '_onSelectionChange'],
59
- g.pagination && [g.pagination, 'gotoPage', '_onSelectionChange'],
60
- focus && [focus, 'onFocusArea', function(name){
61
- if(name == 'rowHeader'){
62
- t._onMouseOver();
63
- }
64
- }],
65
- focus && [focus, 'onBlurArea', function(name){
66
- if(name == 'rowHeader'){
67
- t._onMouseOut();
68
- }
69
- }]);
56
+ g.filter && [g.filter, 'onFilter', '_onSelectionChange']);
57
+ g.select.row.holdingCtrl = true;
70
58
  if(sr.selectByIndex && t.arg('all')){
71
59
  t._allSelected = {};
72
60
  rowHeader.headerProvider = lang.hitch(t, t._createSelectAllBox);
@@ -165,21 +153,6 @@ define([
165
153
  node.firstChild.innerHTML = selected ? '&#10003;' : partial ? '&#9646;' : '&#9744;';
166
154
  }
167
155
  },
168
-
169
- _onMouseOver: function(){
170
- var sr = this.grid.select.row;
171
- if(!sr.holdingCtrl){
172
- this._holdingCtrl = false;
173
- sr.holdingCtrl = true;
174
- }
175
- },
176
-
177
- _onMouseOut: function(){
178
- if(this.hasOwnProperty('_holdingCtrl')){
179
- this.grid.select.row.holdingCtrl = false;
180
- delete this._holdingCtrl;
181
- }
182
- },
183
156
 
184
157
  _getDijitClass: function(){
185
158
  return this._isSingle() ? 'dijitRadio' : 'dijitCheckBox';
@@ -199,7 +172,7 @@ define([
199
172
  ]([0, g.view.visualCount - 1]);
200
173
  },
201
174
 
202
- _onSelectionChange: function(selected){
175
+ _onSelectionChange: function(){
203
176
  var t = this, d,
204
177
  g = t.grid,
205
178
  allSelected,
@@ -208,7 +181,7 @@ define([
208
181
  start = view.rootStart,
209
182
  count = view.rootCount;
210
183
  if(g.select.row.selectByIndex && t.arg('all')){
211
- var selectedRoot = array.filter((lang.isArray(selected) && selected) || g.select.row.getSelected(), function(id){
184
+ var selectedRoot = array.filter(g.select.row.getSelected(), function(id){
212
185
  return !model.parentId(id);
213
186
  });
214
187
  var unselectableRows = g.select.row._getUnselectableRows();
@@ -276,7 +249,7 @@ define([
276
249
  },
277
250
  _onKeyDown: function(evt){
278
251
  // CTRL - A
279
- if(evt.keyCode == 65 && evt.ctrlKey && !evt.shiftKey){
252
+ if(evt.keyCode == 65 && this.grid._isCtrlKey(evt) && !evt.shiftKey){
280
253
  if(!this._allSelected[this._getPageId()]){
281
254
  this._onSelectAll();
282
255
  }
@@ -62,14 +62,14 @@ define([
62
62
  declaredWidth: w,
63
63
  width: w
64
64
  };
65
+ sr.holdingCtrl = true;
65
66
  t.batchConnect(
66
67
  [g, 'setColumns', '_onSetColumns'],
67
68
  [sr, 'onHighlightChange', '_onHighlightChange' ],
68
69
  [sr, 'onSelectionChange', '_onSelectionChange'],
69
70
  [sr, 'clear', '_onClear'],
71
+ [g.body, 'onRender', '_onSelectionChange'],
70
72
  g.filter && [g.filter, 'onFilter', '_onSelectionChange'],
71
- g.pagination && [g.pagination, 'setPageSize', '_onSelectionChange'],
72
- g.pagination && [g.pagination, 'gotoPage', '_onSelectionChange'],
73
73
  [g.body, 'onMoveToCell', function(r, c, e){
74
74
  var evt = {
75
75
  columnId: indirectSelectColumnId
@@ -80,7 +80,6 @@ define([
80
80
  t._onMouseOut();
81
81
  }
82
82
  }],
83
- [g.body, 'onRender', '_updateSelectAll'],
84
83
  [g, 'onCellMouseOver', '_onMouseOver'],
85
84
  [g, 'onCellMouseOut', '_onMouseOut']);
86
85
  t._onSetColumns();
@@ -200,10 +199,6 @@ define([
200
199
  this._triggerOnCell = false;
201
200
  sr.triggerOnCell = true;
202
201
  }
203
- if(!sr.arg('holdingCtrl')){
204
- this._holdingCtrl = false;
205
- sr.holdingCtrl = true;
206
- }
207
202
  }else{
208
203
  this._onMouseOut();
209
204
  }
@@ -215,10 +210,6 @@ define([
215
210
  sr.triggerOnCell = false;
216
211
  delete this._triggerOnCell;
217
212
  }
218
- if(this.hasOwnProperty('_holdingCtrl')){
219
- sr.holdingCtrl = false;
220
- delete this._holdingCtrl;
221
- }
222
213
  },
223
214
 
224
215
  _onSelectAll: function(){
@@ -230,7 +221,7 @@ define([
230
221
  ]([0, g.view.visualCount - 1]);
231
222
  },
232
223
 
233
- _onSelectionChange: function(selected){
224
+ _onSelectionChange: function(){
234
225
  var t = this, d,
235
226
  g = t.grid,
236
227
  allSelected,
@@ -239,7 +230,7 @@ define([
239
230
  start = view.rootStart,
240
231
  count = view.rootCount;
241
232
  if(g.select.row.selectByIndex && t.arg('all')){
242
- var selectedRoot = array.filter((lang.isArray(selected) && selected )|| g.select.row.getSelected(), function(id){
233
+ var selectedRoot = array.filter(g.select.row.getSelected(), function(id){
243
234
  return !model.treePath(id).pop();
244
235
  });
245
236
  var unselectableRows = g.select.row._getUnselectableRows();
@@ -11,7 +11,11 @@ define([
11
11
 
12
12
  /*=====
13
13
  var Menu = declare(_Module, {
14
- // context: __MenuContext
14
+ // summary:
15
+ // module name: menu.
16
+ // Manage context menu for grid.
17
+
18
+ // context: [readonly] __MenuContext
15
19
  // An object representing the current context when user triggers a context menu.
16
20
  // This property is updated everytime a menu of grid is popped up.
17
21
  // Users can refer to this in their menu action handlers by grid.menu.context.
@@ -11,6 +11,7 @@ define([
11
11
  /*=====
12
12
  return declare(_Module, {
13
13
  // summary:
14
+ // module name: navigableCell.
14
15
  // This module allow the elements in grid cell be focusable.
15
16
  // description:
16
17
  // When focus is on a cell, press F2 to focus the first focusable element in that cell.
@@ -85,7 +86,8 @@ define([
85
86
  colIndex = g._columnsById[t._focusColId].index,
86
87
  dir = step > 0 ? 1 : -1,
87
88
  checker = function(r, c){
88
- return t._isNavigable(g._columns[c].id);
89
+ //If there's no decorator, we assume there's no focusable elements in this column
90
+ return t._isNavigable(g._columns[c].id) && g._columns[c].decorator;
89
91
  };
90
92
  body._nextCell(rowIndex, colIndex, dir, checker).then(function(obj){
91
93
  t._focusColId = g._columns[obj.c].id;
@@ -18,6 +18,7 @@ define([
18
18
  /*=====
19
19
  return declare(_Module, {
20
20
  // summary:
21
+ // module name: sort.
21
22
  // Sort multiple columns in a nested way.
22
23
 
23
24
  getSortData: function(){
@@ -208,7 +209,9 @@ define([
208
209
  nls = t._nls,
209
210
  g = t.grid,
210
211
  dn = g.domNode,
211
- sortData = t._sortData;
212
+ sortData = array.filter(t._sortData, function(s){
213
+ return g._columnsById[s.colId];
214
+ });
212
215
  removeClass(dn, 'gridxSingleSorted');
213
216
  removeClass(dn, 'gridxNestedSorted');
214
217
  if(sortData.length == 1){