-
Notifications
You must be signed in to change notification settings - Fork 6.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fix(drag-drop): error when dragging items inside transplanted views with OnPush change detection #18356
fix(drag-drop): error when dragging items inside transplanted views with OnPush change detection #18356
Conversation
…ith OnPush change detection This is a bit of an edge case, but nevertheless it's something that can happen. The way the dragging sequence works is that the drop list keeps track of its items via `ContentChildren` and it registers itself with them once they're picked up by the `QueryList`. If an item doesn't have a container when the drag sequence is started, it is considered a "standalone" drag. This becomes a problem with transplanted views (e.g. ones created by `cdk-table`) that use OnPush where we could end up in a situation where the items aren't picked up during the first pass, but when the user starts dragging, we trigger change detection and the `QueryList` is updated, but at that point it's too late, because we've already started the dragging sequence with a different set of information. These changes work around the issue by assigning the container manually again through the drag directive. A couple of notes: * This is a second iteration of the fix. I went with this approach, because it doesn't require hacky timeouts and triggering change detection again. See the origin approach here: angular@22afc37 * It's difficult to capture this in a test, because we'd have to duplicate half of the logic from `CdkTable` and we might still not be able to get the same change detection timing due to `TestBed`. Fixes angular#18341.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
Confirmed in cl/293831687 that this fixes #15948. |
This is a bit of an edge case, but nevertheless it's something that can happen. The way the dragging sequence works is that the drop list keeps track of its items via `ContentChildren` and it registers itself with them once they're picked up by the `QueryList`. If an item doesn't have a container when the drag sequence is started, it is considered a "standalone" drag. This becomes a problem with transplanted views (e.g. ones created by `cdk-table`) that use OnPush where we could end up in a situation where the items aren't picked up during the first pass, but when the user starts dragging, we trigger change detection and the `QueryList` is updated, but at that point it's too late, because we've already started the dragging sequence with a different set of information. These changes work around the issue by assigning the container manually again through the drag directive. A couple of notes: * This is a second iteration of the fix. I went with this approach, because it doesn't require hacky timeouts and triggering change detection again. See the origin approach here: 22afc37 * It's difficult to capture this in a test, because we'd have to duplicate half of the logic from `CdkTable` and we might still not be able to get the same change detection timing due to `TestBed`. Fixes #18341.
This issue has been automatically locked due to inactivity. Read more about our automatic conversation locking policy. This action has been performed automatically by a bot. |
This is a bit of an edge case, but nevertheless it's something that can happen. The way the dragging sequence works is that the drop list keeps track of its items via
ContentChildren
and it registers itself with them once they're picked up by theQueryList
. If an item doesn't have a container when the drag sequence is started, it is considered a "standalone" drag.This becomes a problem with transplanted views (e.g. ones created by
cdk-table
) that use OnPush where we could end up in a situation where the items aren't picked up during the first pass, but when the user starts dragging, we trigger change detection and theQueryList
is updated, but at that point it's too late, because we've already started the dragging sequence with a different set of information.These changes work around the issue by assigning the container manually again through the drag directive.
A couple of notes:
CdkTable
and we might still not be able to get the same change detection timing due toTestBed
.Fixes #18341.