_RowMapLayer.js 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206
  1. define("dojox/grid/enhanced/plugins/_RowMapLayer", [
  2. "dojo/_base/declare",
  3. "dojo/_base/array",
  4. "dojo/_base/lang",
  5. "./_StoreLayer"
  6. ], function(declare, array, lang, layers){
  7. var _devideToArrays = function(a){
  8. a.sort(function(v1, v2){
  9. return v1 - v2;
  10. });
  11. var arr = [[a[0]]];
  12. for(var i = 1, j = 0; i < a.length; ++i){
  13. if(a[i] == a[i-1] + 1){
  14. arr[j].push(a[i]);
  15. }else{
  16. arr[++j] = [a[i]];
  17. }
  18. }
  19. return arr;
  20. },
  21. hitchIfCan = function(scope, func){
  22. return func ? lang.hitch(scope || lang.global, func) : function(){};
  23. };
  24. return declare("dojox.grid.enhanced.plugins._RowMapLayer", layers._StoreLayer, {
  25. tags: ["reorder"],
  26. constructor: function(grid){
  27. this._map = {};
  28. this._revMap = {};
  29. this.grid = grid;
  30. this._oldOnDelete = grid._onDelete;
  31. var _this = this;
  32. grid._onDelete = function(item){
  33. _this._onDelete(item);
  34. _this._oldOnDelete.call(grid, item);
  35. };
  36. this._oldSort = grid.sort;
  37. grid.sort = function(){
  38. _this.clearMapping();
  39. _this._oldSort.apply(grid, arguments);
  40. };
  41. },
  42. uninitialize: function(){
  43. this.grid._onDelete = this._oldOnDelete;
  44. this.grid.sort = this._oldSort;
  45. },
  46. setMapping: function(mapping){
  47. // summary:
  48. // Remember the row mapping.
  49. // mapping: Object
  50. // keys are original rowIndexes, values are new rowIndexes.
  51. this._store.forEachLayer(function(layer){
  52. if(layer.name() === "rowmap"){
  53. return false;
  54. }else if(layer.onRowMappingChange){
  55. layer.onRowMappingChange(mapping);
  56. }
  57. return true;
  58. }, false);
  59. var from, to, origin, revmap = {};
  60. for(from in mapping){
  61. from = parseInt(from, 10);
  62. to = mapping[from];
  63. if(typeof to == "number"){
  64. if(from in this._revMap){
  65. origin = this._revMap[from];
  66. delete this._revMap[from];
  67. }else{
  68. origin = from;
  69. }
  70. if(origin == to){
  71. delete this._map[origin];
  72. revmap[to] = "eq";
  73. }else{
  74. this._map[origin] = to;
  75. revmap[to] = origin;
  76. }
  77. }
  78. }
  79. for(to in revmap){
  80. if(revmap[to] === "eq"){
  81. delete this._revMap[parseInt(to, 10)];
  82. }else{
  83. this._revMap[parseInt(to, 10)] = revmap[to];
  84. }
  85. }
  86. },
  87. clearMapping: function(){
  88. this._map = {};
  89. this._revMap = {};
  90. },
  91. _onDelete: function(item){
  92. var idx = this.grid._getItemIndex(item, true);
  93. if(idx in this._revMap){
  94. var rowIdxArr = [], r, i, origin = this._revMap[idx];
  95. delete this._map[origin];
  96. delete this._revMap[idx];
  97. for(r in this._revMap){
  98. r = parseInt(r, 10);
  99. if(this._revMap[r] > origin){
  100. --this._revMap[r];
  101. }
  102. }
  103. for(r in this._revMap){
  104. r = parseInt(r, 10);
  105. if(r > idx){
  106. rowIdxArr.push(r);
  107. }
  108. }
  109. rowIdxArr.sort(function(a, b){
  110. return b - a;
  111. });
  112. for(i = rowIdxArr.length - 1; i >= 0; --i){
  113. r = rowIdxArr[i];
  114. this._revMap[r - 1] = this._revMap[r];
  115. delete this._revMap[r];
  116. }
  117. this._map = {};
  118. for(r in this._revMap){
  119. this._map[this._revMap[r]] = r;
  120. }
  121. }
  122. },
  123. _fetch: function(userRequest){
  124. var mapCount = 0, r;
  125. var start = userRequest.start || 0;
  126. for(r in this._revMap){
  127. r = parseInt(r, 10);
  128. if(r >= start){
  129. ++mapCount;
  130. }
  131. }
  132. if(mapCount > 0){
  133. //Row mapping is in use.
  134. var rows = [], i, map = {},
  135. count = userRequest.count > 0 ? userRequest.count : -1;
  136. if(count > 0){
  137. for(i = 0; i < count; ++i){
  138. r = start + i;
  139. r = r in this._revMap ? this._revMap[r] : r;
  140. map[r] = i;
  141. rows.push(r);
  142. }
  143. }else{
  144. //We don't have a count, must create our own.
  145. for(i = 0;; ++i){
  146. r = start + i;
  147. if(r in this._revMap){
  148. --mapCount;
  149. r = this._revMap[r];
  150. }
  151. map[r] = i;
  152. rows.push(r);
  153. if(mapCount <= 0){
  154. break;
  155. }
  156. }
  157. }
  158. this._subFetch(userRequest, this._getRowArrays(rows), 0, [], map, userRequest.onComplete, start, count);
  159. return userRequest;
  160. }else{
  161. //No row mapping at all.
  162. return lang.hitch(this._store, this._originFetch)(userRequest);
  163. }
  164. },
  165. _getRowArrays: function(rows){
  166. return _devideToArrays(rows);
  167. },
  168. _subFetch: function(userRequest, rowArrays, index, result, map, oldOnComplete, start, count){
  169. var arr = rowArrays[index], _this = this;
  170. var urstart = userRequest.start = arr[0];
  171. userRequest.count = arr[arr.length - 1] - arr[0] + 1;
  172. userRequest.onComplete = function(items){
  173. array.forEach(items, function(item, i){
  174. var r = urstart + i;
  175. if(r in map){
  176. result[map[r]] = item;
  177. }
  178. });
  179. if(++index == rowArrays.length){
  180. //mapped rows are all fetched.
  181. if(count > 0){
  182. userRequest.start = start;
  183. userRequest.count = count;
  184. userRequest.onComplete = oldOnComplete;
  185. hitchIfCan(userRequest.scope, oldOnComplete)(result, userRequest);
  186. }else{
  187. userRequest.start = userRequest.start + items.length;
  188. delete userRequest.count;
  189. userRequest.onComplete = function(items){
  190. result = result.concat(items);
  191. userRequest.start = start;
  192. userRequest.onComplete = oldOnComplete;
  193. hitchIfCan(userRequest.scope, oldOnComplete)(result, userRequest);
  194. };
  195. _this.originFetch(userRequest);
  196. }
  197. }else{
  198. _this._subFetch(userRequest, rowArrays, index, result, map, oldOnComplete, start, count);
  199. }
  200. };
  201. _this.originFetch(userRequest);
  202. }
  203. });
  204. });