UNPKG

5.43 kBJavaScriptView Raw
1(function ($) {
2 // register namespace
3 $.extend(true, window, {
4 "Slick": {
5 "CellRangeSelector": CellRangeSelector
6 }
7 });
8
9 function CellRangeSelector(options) {
10 var _grid;
11 var _currentlySelectedRange;
12 var _canvas;
13 var _gridOptions;
14 var _$activeCanvas;
15 var _dragging;
16 var _decorator;
17 var _self = this;
18 var _handler = new Slick.EventHandler();
19 var _defaults = {
20 selectionCss: {
21 "border": "2px dashed blue"
22 }
23 };
24
25 // Frozen row & column variables
26 var _rowOffset;
27 var _columnOffset;
28 var _isRightCanvas;
29 var _isBottomCanvas;
30
31 // Scrollings
32 var _scrollTop = 0;
33 var _scrollLeft = 0;
34
35 function init(grid) {
36 options = $.extend(true, {}, _defaults, options);
37 _decorator = options.cellDecorator || new Slick.CellRangeDecorator(grid, options);
38 _grid = grid;
39 _canvas = _grid.getCanvasNode();
40 _gridOptions = _grid.getOptions();
41 _handler
42 .subscribe(_grid.onScroll, handleScroll)
43 .subscribe(_grid.onDragInit, handleDragInit)
44 .subscribe(_grid.onDragStart, handleDragStart)
45 .subscribe(_grid.onDrag, handleDrag)
46 .subscribe(_grid.onDragEnd, handleDragEnd);
47 }
48
49 function destroy() {
50 _handler.unsubscribeAll();
51 _$activeCanvas = null;
52 _canvas = null;
53 if (_decorator && _decorator.destroy) {
54 _decorator.destroy();
55 }
56 }
57
58 function getCellDecorator() {
59 return _decorator;
60 }
61
62 function handleScroll(e, args) {
63 _scrollTop = args.scrollTop;
64 _scrollLeft = args.scrollLeft;
65 }
66
67 function handleDragInit(e, dd) {
68 // Set the active canvas node because the decorator needs to append its
69 // box to the correct canvas
70 _$activeCanvas = $(_grid.getActiveCanvasNode(e));
71
72 var c = _$activeCanvas.offset();
73
74 _rowOffset = 0;
75 _columnOffset = 0;
76 _isBottomCanvas = _$activeCanvas.hasClass('grid-canvas-bottom');
77
78 if (_gridOptions.frozenRow > -1 && _isBottomCanvas) {
79 _rowOffset = (_gridOptions.frozenBottom) ? $('.'+_grid.getUID()+' .grid-canvas-bottom').height() : $('.'+_grid.getUID()+' .grid-canvas-top').height();
80 }
81
82 _isRightCanvas = _$activeCanvas.hasClass('grid-canvas-right');
83
84 if (_gridOptions.frozenColumn > -1 && _isRightCanvas) {
85 _columnOffset = $('.'+_grid.getUID()+' .grid-canvas-left').width();
86 }
87
88 // prevent the grid from cancelling drag'n'drop by default
89 e.stopImmediatePropagation();
90 }
91
92 function handleDragStart(e, dd) {
93 var cell = _grid.getCellFromEvent(e);
94 if (_self.onBeforeCellRangeSelected.notify(cell) !== false) {
95 if (_grid.canCellBeSelected(cell.row, cell.cell)) {
96 _dragging = true;
97 e.stopImmediatePropagation();
98 }
99 }
100 if (!_dragging) {
101 return;
102 }
103
104 _grid.focus();
105
106 var startX = dd.startX - $(_canvas).offset().left;
107 if (_gridOptions.frozenColumn >= 0 && _isRightCanvas) {
108 startX += _scrollLeft;
109 }
110
111 var startY = dd.startY - $(_canvas).offset().top;
112 if (_gridOptions.frozenRow >= 0 && _isBottomCanvas) {
113 startY += _scrollTop;
114 }
115
116 var start = _grid.getCellFromPoint(startX, startY);
117
118 dd.range = { start: start, end: {} };
119 _currentlySelectedRange = dd.range;
120 return _decorator.show(new Slick.Range(start.row, start.cell));
121 }
122
123 function handleDrag(e, dd) {
124 if (!_dragging) {
125 return;
126 }
127 e.stopImmediatePropagation();
128
129 var end = _grid.getCellFromPoint(
130 e.pageX - _$activeCanvas.offset().left + _columnOffset,
131 e.pageY - _$activeCanvas.offset().top + _rowOffset
132 );
133
134 // ... frozen column(s),
135 if ( _gridOptions.frozenColumn >= 0 && (!_isRightCanvas && (end.cell > _gridOptions.frozenColumn)) || (_isRightCanvas && (end.cell <= _gridOptions.frozenColumn)) ) {
136 return;
137 }
138
139 // ... or frozen row(s)
140 if ( _gridOptions.frozenRow >= 0 && (!_isBottomCanvas && (end.row >= _gridOptions.frozenRow)) || (_isBottomCanvas && (end.row < _gridOptions.frozenRow)) ) {
141 return;
142 }
143
144 // ... or regular grid (without any frozen options)
145 if (!_grid.canCellBeSelected(end.row, end.cell)) {
146 return;
147 }
148
149 dd.range.end = end;
150
151 _decorator.show(new Slick.Range(dd.range.start.row, dd.range.start.cell, end.row, end.cell));
152 }
153
154 function handleDragEnd(e, dd) {
155 if (!_dragging) {
156 return;
157 }
158
159 _dragging = false;
160 e.stopImmediatePropagation();
161
162 _decorator.hide();
163 _self.onCellRangeSelected.notify({
164 range: new Slick.Range(
165 dd.range.start.row,
166 dd.range.start.cell,
167 dd.range.end.row,
168 dd.range.end.cell
169 )
170 });
171 }
172
173 function getCurrentRange() {
174 return _currentlySelectedRange;
175 }
176
177 $.extend(this, {
178 "init": init,
179 "destroy": destroy,
180 "pluginName": "CellRangeSelector",
181
182 "getCellDecorator": getCellDecorator,
183 "getCurrentRange": getCurrentRange,
184
185 "onBeforeCellRangeSelected": new Slick.Event(),
186 "onCellRangeSelected": new Slick.Event()
187 });
188 }
189})(jQuery);