tailwindlabs / headlessui

Completely unstyled, fully accessible UI components, designed to integrate beautifully with Tailwind CSS.
https://headlessui.com
MIT License
25.81k stars 1.07k forks source link

[Dialog] `DialogPanel` with framer motion and `as` prop #3410

Closed knoefel closed 1 month ago

knoefel commented 1 month ago

What package within Headless UI are you using?

@headlessui/react

What version of that package are you using?

v2.1.2

What browser are you using?

Chrome

Describe your issue

Since updating to at least 2.1.0 there is an TS and render error when using the Dialog component with framer motion. The last working version was 2.0.4. I'm using the as prop to pass the motion.div to the DialogPanel.

<DialogPanel
  as={motion.div}
  key="panel"
  initial="initial"
  animate="animate"
  exit="exit"
  transition={{ duration: 0.2 }}
>

TS error message:

Screenshot 2024-08-02 at 22 21 36

Somehow the transition prop is used for the DialogPanel and not for framer's motion.div. So additionally to the TS error i get this error when rendering the modal:

Screenshot 2024-08-02 at 22 18 50

Please note that i'm not using the Transition component that headlessui provides.

RobinMalfait commented 1 month ago

Hey!

This is a side effect and a downside of how the as prop works. Wrote more about it here for more information: https://github.com/tailwindlabs/headlessui/issues/3333#issuecomment-2200138474

The TL;DR is that the transition prop is used by both the DialogPanel and framer motion so from the usage it's not clear which one you want. To solve if, you can split it up:

<DialogPanel as={Fragment}>
  <motion.div     
    key="panel"
    initial="initial"
    animate="animate"
    exit="exit"
    transition={{ duration: 0.2 }}>
    …
  </motion.div>
</DialogPanel >

Hope this helps!

knoefel commented 1 month ago

@RobinMalfait Thanks a lot for the explanation and solution!!