fix(drag-drop): only add top-level drop lists to drop group (#14130)

Currently all drop lists will add themselves to the closest group that is resolved through DI. This can lead to some weird results where a parent list and a list inside it will be grouped automatically. These changes rework the way the group is provided in order to prevent it from bleeding into child lists.
This commit is contained in:
Kristiyan Kostadinov
2018-11-27 16:44:24 +01:00
committed by Jeremy Elbourn
parent d8cd6a788b
commit db7491c8b0
3 changed files with 34 additions and 2 deletions
+28
View File
@@ -26,6 +26,7 @@ import {CdkDragDrop} from './drag-events';
import {moveItemInArray} from './drag-utils';
import {CdkDropList} from './drop-list';
import {CdkDragHandle} from './drag-handle';
import {CdkDropListGroup} from './drop-list-group';
const ITEM_HEIGHT = 25;
const ITEM_WIDTH = 75;
@@ -2218,6 +2219,14 @@ describe('CdkDrag', () => {
expect(fixture.componentInstance.droppedSpy).not.toHaveBeenCalled();
}));
it('should not add child drop lists to the same group as their parents', fakeAsync(() => {
const fixture = createComponent(NestedDropListGroups);
const component = fixture.componentInstance;
fixture.detectChanges();
expect(Array.from(component.group._items)).toEqual([component.listOne, component.listTwo]);
}));
});
});
@@ -2603,6 +2612,25 @@ class ConnectedDropZonesWithSingleItems {
droppedSpy = jasmine.createSpy('dropped spy');
}
@Component({
template: `
<div cdkDropListGroup #group="cdkDropListGroup">
<div cdkDropList #listOne="cdkDropList">
<div cdkDropList #listThree="cdkDropList"></div>
<div cdkDropList #listFour="cdkDropList"></div>
</div>
<div cdkDropList #listTwo="cdkDropList"></div>
</div>
`
})
class NestedDropListGroups {
@ViewChild('group') group: CdkDropListGroup<CdkDropList>;
@ViewChild('listOne') listOne: CdkDropList;
@ViewChild('listTwo') listTwo: CdkDropList;
}
/**
* Component that passes through whatever content is projected into it.
* Used to test having drag elements being projected into a component.
+2 -1
View File
@@ -15,7 +15,8 @@ import {Directive, OnDestroy} from '@angular/core';
* from `cdkDropList`.
*/
@Directive({
selector: '[cdkDropListGroup]'
selector: '[cdkDropListGroup]',
exportAs: 'cdkDropListGroup',
})
export class CdkDropListGroup<T> implements OnDestroy {
/** Drop lists registered inside the group. */
+4 -1
View File
@@ -20,6 +20,7 @@ import {
Optional,
Directive,
ChangeDetectorRef,
SkipSelf,
} from '@angular/core';
import {Directionality} from '@angular/cdk/bidi';
import {CdkDrag} from './drag';
@@ -81,6 +82,8 @@ interface ListPositionCacheEntry {
selector: '[cdkDropList], cdk-drop-list',
exportAs: 'cdkDropList',
providers: [
// Prevent child drop lists from picking up the same group as their parent.
{provide: CdkDropListGroup, useValue: undefined},
{provide: CDK_DROP_LIST_CONTAINER, useExisting: CdkDropList},
],
host: {
@@ -157,7 +160,7 @@ export class CdkDropList<T = any> implements OnInit, OnDestroy {
private _dragDropRegistry: DragDropRegistry<CdkDrag, CdkDropList<T>>,
private _changeDetectorRef: ChangeDetectorRef,
@Optional() private _dir?: Directionality,
@Optional() private _group?: CdkDropListGroup<CdkDropList>) {}
@Optional() @SkipSelf() private _group?: CdkDropListGroup<CdkDropList>) {}
ngOnInit() {
this._dragDropRegistry.registerDropContainer(this);