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
Popover component won't always close when clicking outside of it #2752
Comments
Hey! You didn't do anything wrong, but in Headless UI we have a few assumptions that worked fine up until now, but one of the assumptions don't work when you use the app router in Next.js. I will dig more into this exact issue soon, but a quick workaround for now to unblock you is that you apply the following diff in the import Navbar from '@components/navbar/navbar'
import './globals.css'
export default function RootLayout({
children,
}: {
children: React.ReactNode
}) {
return (
<html lang="en">
<body className="p-5">
+ <div>
<p className='text-center mb-5 bg-slate-100 rounded-lg'>'body' tag - white background</p>
<Navbar />
{children}
+ </div>
</body>
</html>
)
} |
Hey! Alright so I think for now the way to solve it is to apply the diff I mentioned above. But I also want to give some background information about why this is even necessary in the first place and why "solving" it will very likely break existing code. I am also going to close this issue because I think this workaround is not too bad, but if more people are running into this, and solving it with an additional wrapper is too painful for one reason or another, then I'm more than happen to look into this again. Some context: A few components within Headless UI use different mechanisms for "closing" a component. For example the The click outside behaviour is trickier than you initially expect if you want to use this in real world applications. A typical click outside function listens for a click event, and receives a DOM element (e.g.: a DOM reference to the However, let's imagine that you have a little notification that pops up in the corner of your application because of some action that happened, dismissing that notification will close the popover. This typically happens because:
One solution to this problem could be a Another solution is that we provide a very generic Another very common problem is browser extensions. Imagine you have a This happens because Grammerly injects some elements in either the To solve all of this we made some assumptions. The idea looks like this:
Next, when an outside click happens we check a few things:
We could find other Properly fixing this without this assumption is going to be hard because we don't have control over 3rd party components or browser extensions and therefore we can't really tell if the current element should be closed or not when clicked on a specific DOM node. We could introduce a component like This is all the context I wanted to provide. I hope this makes sense. Going to close the issue right now, but if more people run into this, then I'm more than happy to take another look at how we can solve this. Thanks! |
@RobinMalfait I have the same issue and using a Any advice appreciated! <html
lang="de"
className={clsx(
'h-full scroll-smooth bg-sand antialiased',
inter.variable,
lexend.variable,
)}
>
<body className="flex h-full flex-col">{children}</body>
</html> export default function Home() {
return (
<>
<GTM />
<div>
<Header /> // use client
</div>
<Consent /> // use client
<main>
<Hero /> // use client
<MoreComponents />
</main>
<Footer />
</>
)
} |
Discussed in #2731
Originally posted by FabioDainese September 5, 2023
What package within Headless UI are you using?
@headlessui/react (more specifically the popover component)
What version of that package are you using?
v1.7.17
What browser are you using?
Chrome (v116.0.5845.96), Firefox (v116.0.3), Safari (v16.4.1)
Reproduction URL
https://codesandbox.io/p/sandbox/flamboyant-marco-57cyzh
Describe your issue
The popover component seems to not close every time you click outside of it. To be more specific - you can try on the provided sandbox - only when you click on one of the siblings of the component that uses the popover, it won't work. So, for example, in the provided project if you click on:
<main>
tag is sibling to the<nav>
one, which uses the popover component)<body>
tag is parent of the<nav>
, so all okay)'body' tag - white background
" text: the popover will still be open (i.e. the<p>
tag that contains the text is sibling to the<nav>
one)Now, the temporary "workaround" that kinda fix this issue would be to use a transparent overlay (i.e.
<Popover.Overlay className="fixed inset-0" />
), so basically wherever you click, you would click on the overlay that consequently will close the popover. Now, this is far from optimal though, since if a user would like to click on an hypothetical visible button (placed outside the popover), it would need to click 2 times (one to close the popover by clicking the invisible overlay and the second one to actually trigger the button).So, I'm not sure if this is the intended behavior for the
popover
component - or if I coded something wrong here - but I would like to gently ask you a feedback on it, also to understand which would be the best approach to tackle this issue (if it's not the intended behavior).P.S. the popover used on the provided project is just a simpler copy-paste version of the first example that you can find on the headlessui website
As mentioned by @mattmcegg and @ijrzhong this behavior can be seen on v1.7.15, v1.7.16 and v1.7.17 of the
@headlessui/react
package (on the v1.7.14 all works normal)The text was updated successfully, but these errors were encountered: