Skip to content

Commit 58a83af

Browse files
authored
Merge pull request #1628 from adumesny/develop
collision overall Part II - 50% coverage check
2 parents 39373eb + dd1f24b commit 58a83af

File tree

8 files changed

+179
-70
lines changed

8 files changed

+179
-70
lines changed

doc/CHANGES.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -50,9 +50,9 @@ Change log
5050
<!-- END doctoc generated TOC please keep comment here to allow auto update -->
5151
## 3.3.0-dev
5252

53-
- fix [#149](https://github.com/gridstack/gridstack.js/issues/149) [#1094](https://github.com/gridstack/gridstack.js/issues/1094) [#1605](https://github.com/gridstack/gridstack.js/issues/1605) re-write of the **collision code**! you can now swap items of the same size (vertical/horizontal) when grid is full, and is the default in `float:false` (top gravity) as it feels more natural. Could add Alt key for swap vs push behavior later.<br>
54-
Dragging up and down now behave the same (used to require push WAY down past to swap/append). Also much more efficient collision code.<br>
55-
Still TODO: handle mid point of dragged over items rather 50% of row/column and check for the most covered when multiple items collide.
53+
- fix [#149](https://github.com/gridstack/gridstack.js/issues/149) [#1094](https://github.com/gridstack/gridstack.js/issues/1094) [#1605](https://github.com/gridstack/gridstack.js/issues/1605) re-write of the **collision code**! you can now swap items of the same size (vertical/horizontal) when grid is full, and is the default in `float:false` (top gravity) as it feels more natural. Could add Alt key for swap vs push behavior later.
54+
- Dragging up and down now behave the same (used to require push WAY down past to swap/append). Also much more efficient collision code.
55+
- handle mid point of dragged over items (>50%) rather than a new row/column and check for the most covered when multiple items collide.
5656
- fix [1617](https://github.com/gridstack/gridstack.js/issues/1617) FireFox DOM order issue. Thanks [@marcel-necker](https://github.com/marcel-necker)
5757

5858
## 3.3.0 (2021-2-2)

spec/e2e/html/141_1534_swap.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ <h1>Swap collision demo</h1>
3434

3535
let count = 0;
3636
let items = [
37-
{x:0, y:0}, {x:0, y:1}, {x:0, y:2},{x:1, y:0}, {x:1, y:1}, {x:1, y:2},
37+
{x:0, y:0}, {x:0, y:1}, {x:0, y:2},{x:1, y:0}, {x:1, y:1}, {x:1, y:2, h:2, w:2},
3838
{x:5, y:0}, {x:4, y:1, w:3, locked: false, _content: 'locked'}, {x:5, y:2},
3939
{x:7, y:0}, {x:8, y:0}, {x:9, y:0}, {x:7, y:1, w:3}, {x:8, y:2},
4040
{x:11, y:0}, {x:11, y:1, h:2},

spec/gridstack-engine-spec.ts

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -333,23 +333,23 @@ describe('gridstack engine', function() {
333333
});
334334
it('should return true for changed x', function() {
335335
let widget = { x: 1, y: 2, w: 3, h: 4 };
336-
expect(engine.changedPos(widget, 2, 2)).toEqual(true);
336+
expect(engine.changedPosConstrain(widget, {x:2, y:2})).toEqual(true);
337337
});
338338
it('should return true for changed y', function() {
339339
let widget = { x: 1, y: 2, w: 3, h: 4 };
340-
expect(engine.changedPos(widget, 1, 1)).toEqual(true);
340+
expect(engine.changedPosConstrain(widget, {x:1, y:1})).toEqual(true);
341341
});
342342
it('should return true for changed width', function() {
343343
let widget = { x: 1, y: 2, w: 3, h: 4 };
344-
expect(engine.changedPos(widget, 2, 2, 4, 4)).toEqual(true);
344+
expect(engine.changedPosConstrain(widget, {x:2, y:2, w:4, h:4})).toEqual(true);
345345
});
346346
it('should return true for changed height', function() {
347347
let widget = { x: 1, y: 2, w: 3, h: 4 };
348-
expect(engine.changedPos(widget, 1, 2, 3, 3)).toEqual(true);
348+
expect(engine.changedPosConstrain(widget, {x:1, y:2, w:3, h:3})).toEqual(true);
349349
});
350350
it('should return false for unchanged position', function() {
351351
let widget = { x: 1, y: 2, w: 3, h: 4 };
352-
expect(engine.changedPos(widget, 1, 2, 3, 4)).toEqual(false);
352+
expect(engine.changedPosConstrain(widget, {x:1, y:2, w:3, h:4})).toEqual(false);
353353
});
354354
});
355355

@@ -368,17 +368,17 @@ describe('gridstack engine', function() {
368368
engine.addNode(nodes[1])
369369
// add item that moves past locked one
370370
expect(findNode(engine, 1)).toEqual(jasmine.objectContaining({x: 0, y: 1, w: 12, h: 1, locked: true}));
371-
expect(findNode(engine, 2)).toEqual(jasmine.objectContaining({x: 1, y: 2}));
371+
expect(findNode(engine, 2)).toEqual(jasmine.objectContaining({x: 1, y: 2, h: 3, id: 2}));
372372
// prevents moving locked item
373373
let node1 = findNode(engine, 1);
374-
expect(engine.moveNode(node1, 6, 6)).toEqual(false);
374+
expect(engine.moveNode(node1, {x:6, y:6})).toEqual(false);
375375
// but moves regular one (gravity ON)
376376
let node2 = findNode(engine, 2);
377-
expect(engine.moveNode(node2, 6, 6)).toEqual(true);
377+
expect(engine.moveNode(node2, {x:6, y:6})).toEqual(true);
378378
expect(node2).toEqual(jasmine.objectContaining({x: 6, y: 2, w: 2, h: 3}));
379379
// but moves regular one (gravity OFF)
380380
engine.float = true;
381-
expect(engine.moveNode(node2, 7, 6)).toEqual(true);
381+
expect(engine.moveNode(node2, {x:7, y:6})).toEqual(true);
382382
expect(node2).toEqual(jasmine.objectContaining({x: 7, y: 6, w: 2, h: 3}));
383383
});
384384
});

src/gridstack-dd.ts

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
/* eslint-disable @typescript-eslint/no-unused-vars */
99

1010
import { GridStackDDI } from './gridstack-ddi';
11-
import { GridItemHTMLElement, GridStackNode, GridStackElement, DDUIData, DDDragInOpt } from './types';
11+
import { GridItemHTMLElement, GridStackNode, GridStackElement, DDUIData, DDDragInOpt, GridStackPosition } from './types';
1212
import { GridStack } from './gridstack';
1313
import { Utils } from './utils';
1414

@@ -115,7 +115,7 @@ GridStack.prototype._setupAcceptWidget = function(): GridStack {
115115
node.el = this.placeholder; // dom we update while dragging...
116116

117117
this._updateContainerHeight();
118-
} else if (this.engine.moveNodeCheck(node, x, y)) {
118+
} else if (this.engine.moveNodeCheck(node, {x, y})) {
119119
this._updateContainerHeight();
120120
}
121121
};
@@ -381,6 +381,7 @@ GridStack.prototype._prepareDragDropByNode = function(node: GridStackNode): Grid
381381
// set the min/max resize info
382382
cellWidth = this.cellWidth();
383383
cellHeight = this.getCellHeight(true); // force pixels for calculations
384+
this.engine.cacheRects(cellWidth, cellHeight, this.opts.marginTop, this.opts.marginRight, this.opts.marginBottom, this.opts.marginLeft);
384385
let dd = GridStackDD.get()
385386
.resizable(el, 'option', 'minWidth', cellWidth * (node.minW || 1))
386387
.resizable(el, 'option', 'minHeight', cellHeight * (node.minH || 1));
@@ -395,8 +396,8 @@ GridStack.prototype._prepareDragDropByNode = function(node: GridStackNode): Grid
395396
let top = ui.position.top + (ui.position.top > node._lastUiPosition.top ? -this.opts.marginBottom : this.opts.marginTop);
396397
let x = Math.round(left / cellWidth);
397398
let y = Math.round(top / cellHeight);
398-
let w: number;
399-
let h: number;
399+
let w = node.w;
400+
let h = node.h;
400401
let resizing: boolean;
401402

402403
if (event.type === 'drag') {
@@ -433,7 +434,8 @@ GridStack.prototype._prepareDragDropByNode = function(node: GridStackNode): Grid
433434
}
434435
}
435436
if (node.x === x && node.y === y) return; // skip same
436-
if (node._lastTried && node._lastTried.x === x && node._lastTried.y === y) return; // skip one we tried (but failed)
437+
// DON'T skip one we tried as we might have failed because of coverage <50% before
438+
// if (node._lastTried && node._lastTried.x === x && node._lastTried.y === y) return;
437439
} else if (event.type === 'resize') {
438440
if (x < 0) return;
439441
// Scrolling page if needed
@@ -446,8 +448,15 @@ GridStack.prototype._prepareDragDropByNode = function(node: GridStackNode): Grid
446448
}
447449

448450
node._lastTried = {x, y, w, h}; // set as last tried (will nuke if we go there)
449-
if (this.engine.moveNodeCheck(node, x, y, w, h)) {
451+
let rect: GridStackPosition = { // screen pix of the dragged box
452+
x: ui.position.left + this.opts.marginLeft,
453+
y: ui.position.top + this.opts.marginTop,
454+
w: (ui.size ? ui.size.width : node.w * cellWidth) - this.opts.marginLeft - this.opts.marginRight,
455+
h: (ui.size ? ui.size.height : node.h * cellHeight) - this.opts.marginTop - this.opts.marginBottom
456+
};
457+
if (this.engine.moveNodeCheck(node, {x, y, w, h, cellWidth, cellHeight, rect})) {
450458
node._lastUiPosition = ui.position;
459+
this.engine.cacheRects(cellWidth, cellHeight, this.opts.marginTop, this.opts.marginRight, this.opts.marginBottom, this.opts.marginLeft);
451460
delete node._skipDown;
452461
if (resizing && node.subGrid) { (node.subGrid as GridStack).onParentResize(); }
453462
this._updateContainerHeight();

0 commit comments

Comments
 (0)