Skip to content

Dispatch CloseWatcher's cancel event for popovers also #11275

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

Open
keithamus opened this issue Apr 30, 2025 · 4 comments
Open

Dispatch CloseWatcher's cancel event for popovers also #11275

keithamus opened this issue Apr 30, 2025 · 4 comments
Labels
addition/proposal New features or enhancements topic: close watchers topic: popover The popover attribute and friends

Comments

@keithamus
Copy link
Contributor

What problem are you trying to solve?

In openui/open-ui#1206 @thdoan points out that a popover doesn't dispatch a cancel event. @lukewarlow points out that - despite popover using the CloseWatcher infrastructure - the cancel behaviour is a no-op. This creates a bit of an inconsistency because closing a <dialog> will dispatch cancel, beforetoggle, close, toggle - but closing a <dialog popover> will dispatch beforetoggle, close, toggle.

The cancel event itself is useful in ways that the others aren't - it can (sometimes) be cancelled, which allows the developer to stop something being closed if, for example, there are unsaved changes inside the popover.

What solutions exist today?

Any workarounds are tricky and delicate. One could re-open the popover on the close event (but this triggers refocus and alters the popover stack). Or one could trap the Escape key (but then the other CloseWatcher gestures will still work). So there's not a super robust solution here.

How would you solve it?

I think for popovers to dispatch the cancel event from CloseWatcher, and make it cancelable, based on the CloseWatcher event's cancelable state, this would swiftly and accurately solve the issue at hand.

Anything else?

Mozilla would be supportive of this change - it seems low complexity and high reward. If I can get perhaps word from @mfreed7 or @domenic or @josepharhar, and/or @annevk or @nt1m, I'll get to making the necessary changes.

@keithamus keithamus added addition/proposal New features or enhancements topic: close watchers topic: popover The popover attribute and friends labels Apr 30, 2025
@lukewarlow
Copy link
Member

lukewarlow commented Apr 30, 2025

I think this probably makes sense and is on the surface quite trivial. Some questions:

Was there reasoning in the beginning that explains why this wasn't included?

Does light dismiss of a popover trigger this behaviour?

Do popovers need a similar function to requestClose which fires cancel? (Or possibly an argument to hidePopover which triggers cancel as well as close)? (How would this work with command buttons?)

@mfreed7
Copy link
Contributor

mfreed7 commented Apr 30, 2025

Are you suggesting that any time a popover closes, it'll fire a (cancellable) cancel event? If so, I'm fairly against this change. We very explicitly made the beforetoggle event for closing transitions not cancellable, to avoid all kinds of foot-guns. E.g. when a stack of popovers is being closed, e.g. because a new popover is being shown, you shouldn't be able to cancel the closing of one of the popovers in the middle of the stack. If you could, you'd be left in a really weird state. Adding a cancel event would seem to open that door back up. A worse foot-gun: an ancestor popover in the popover stack gets removed from the DOM. If you can cancel the hiding of its descendant popovers, then the popover stack has a "hole" in it, breaking all of the "ancestor popover" algorithms for example.

If you're instead suggesting we add something like popover.requestClose() which first fires cancel before doing anything else, I think that'd be less invasive and much less of a foot-gun. I also don't really see the benefit, other than being parallel to dialog. Maybe that's enough reason to do it though?

As always, I'm open to being convinced. But I just wanted to comment on the history of how we got non-cancellable hidePopover().

@lukewarlow
Copy link
Member

Okay that gives the context that I knew existed but I couldn't think of. In that case it's at the very least not as simple.

I guess you could make it sometimes cancellable in certain simpler cases but it would probably be difficult to get right.

Something like you can cancel a closure for an explicitly closed popover but not for any side effect closures (opening another or removing from document) or something.

@lukewarlow
Copy link
Member

Given the above concerns I'm leaning towards rejecting this as an idea, without concrete use cases that can't be solved another way (e.g. using dialog directly)?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
addition/proposal New features or enhancements topic: close watchers topic: popover The popover attribute and friends
Development

No branches or pull requests

3 participants