Skip to content
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(value-list, sortable-list): fix nested sorting components #6983

Merged
merged 25 commits into from May 22, 2023

Conversation

driskull
Copy link
Member

@driskull driskull commented May 19, 2023

Related Issue: #6024

Summary

The main problem is:

  • Sortable components set up a Sortable instance on connectedCallback and destroy Sortable on disconnectedCallback.
    • When dragging a Sortable component with another Sortable component inside of it, it triggers the child component's connectedCallback/disconnectedCallback methods which initialize/destroy a Sortable. This causes JS errors and UI problems.
    • When a Sortable instance is being dragged (active), we should prevent connectedCallback/disconnectedCallback from doing anything with the inactive Sortable instances. (not destroy them & recreate them).

Solution:

  • Create an interface for SortableComponent components to follow.
    • Make sure the interface does not destroy other nested sortable instances while dragging.

@driskull driskull changed the title fix(value-list, sortable-list): fix nested sorting components. fix(value-list, sortable-list): fix nested sorting components May 19, 2023
@github-actions github-actions bot added the bug Bug reports for broken functionality. Issues should include a reproduction of the bug. label May 19, 2023
Copy link
Member

@jcfranco jcfranco left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is looking good! 😎 I think we could iterate on it to make the utils more seamless (i.e., unify observing and sorting steps, if possible).

src/demos/sortable-list-nested.html Outdated Show resolved Hide resolved
src/utils/sortableComponent.ts Outdated Show resolved Hide resolved
src/utils/sortableComponent.ts Outdated Show resolved Hide resolved
this.cleanUpDragAndDrop();
this.items = Array.from(this.el.children);
this.setUpDragAndDrop();
this.setUpSorting();
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

setUpSorting handles the preceding logic already.

this.items = Array.from(this.el.children);
this.setUpDragAndDrop();
connectSortableComponent(this);
this.setUpSorting();
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

setUpSorting handles the preceding logic already.

@@ -166,15 +173,16 @@ export class SortableList implements InteractiveComponent {
this.items = Array.from(this.el.children);

handle.activated = true;
handle.setFocus();
focusElement(handle);
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

calls setFocus if applicable to the handle.

this.mutationObserver?.disconnect();
this.cleanUpDragAndDrop();
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

disconnectSortableComponent handles this already.

@@ -220,7 +235,6 @@ export class ValueList<

componentDidLoad(): void {
setComponentLoaded(this);
this.setUpDragAndDrop();
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is better handled in connectedCallback since componentDidLoad is only called once. If a component is removed then the sortable will be destroyed in disconnectedCallback so this is needed here.

requestAnimationFrame(() => focusElement(handle));

if ("activated" in handle) {
handle.activated = true;
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

since handleSelector can be anything we need to do this check. Maybe we shouldn't support a handleSelector if we want to maintain drag consistency thoughout components and require use of a calcite-handle.


const handle = event
.composedPath()
.find((el: HTMLElement) => el.matches(this.handleSelector)) as HTMLElement;
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need to find the handle in the composedPath. This was broken.

@driskull driskull marked this pull request as ready for review May 22, 2023 17:13
@driskull driskull requested a review from a team as a code owner May 22, 2023 17:13
Copy link
Member

@jcfranco jcfranco left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏
🤏🔃🤏🤏🤏🔃🤏🤏🔃🔃🤏🤏🔃🔃🔃🤏🤏🔃🔃🔃🤏🔃🔃🔃🔃🤏🔃🤏
🤏🔃🔃🤏🤏🔃🤏🔃🤏🤏🔃🤏🤏🔃🤏🤏🔃🤏🤏🤏🤏🔃🤏🤏🤏🤏🔃🤏
🤏🔃🤏🔃🤏🔃🤏🔃🤏🤏🔃🤏🤏🔃🤏🤏🔃🤏🤏🤏🤏🔃🔃🔃🤏🤏🔃🤏
🤏🔃🤏🤏🔃🔃🤏🔃🤏🤏🔃🤏🤏🔃🤏🤏🔃🤏🤏🤏🤏🔃🤏🤏🤏🤏🤏🤏
🤏🔃🤏🤏🤏🔃🤏🤏🔃🔃🤏🤏🔃🔃🔃🤏🤏🔃🔃🔃🤏🔃🔃🔃🔃🤏🔃🤏
🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏🤏

@@ -313,31 +327,34 @@ export class ValueList<
this.filteredItems = filteredItems;
};

setUpDragAndDrop(): void {
this.cleanUpDragAndDrop();
setUpSorting(): void {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would this be something we need defined in the interface as well?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It could be but it doesn't need to be. I left it out for now since it wouldn't do anything by being added to the interface.

@driskull driskull added the pr ready for visual snapshots Adding this label will run visual snapshot testing. label May 22, 2023
@driskull driskull merged commit b4bbdf3 into master May 22, 2023
15 checks passed
@driskull driskull deleted the dris0000/sortable-fix branch May 22, 2023 18:14
@github-actions github-actions bot added this to the 2023 May Priorities milestone May 22, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Bug reports for broken functionality. Issues should include a reproduction of the bug. pr ready for visual snapshots Adding this label will run visual snapshot testing.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants