ycs77 / headlessui-float

Easily use Headless UI with Floating UI to position floating elements.
https://headlessui-float.vercel.app
MIT License
351 stars 13 forks source link

Dialog example? #33

Closed WesleyKapow closed 1 year ago

WesleyKapow commented 2 years ago

Use Version

Would it be possible to get an example of how to do a dialog? My main struggle seems to be around headlessui's dialog getting portaled away.

ycs77 commented 1 year ago

Hi @WesleyKapow, I think the Headless UI Float is not made for Dialog (Modal); could you please explain how you intend to use both Dialog and Headless UI Float?

WesleyKapow commented 1 year ago

In the same way it is used for Popover it'd be nice if it could also be used with headless Dialog.

ycs77 commented 1 year ago

@WesleyKapow Can you please describe what kind of function you want to develop that will be used in this way?😅 and provide some sample code or screenshots.

tienle commented 1 year ago

@ycs77 We are in the same situation. Dialog is controlled while Popover is not, so there is a case you may need it to emulate "Popover" with Dialog. Similar to Radix Popover: https://www.radix-ui.com/docs/primitives/components/popover

WesleyKapow commented 1 year ago

https://headlessui-float.vercel.app/vue/other-options.html shows how to use Float with a headless Menu. I'd like to do the same but for a headless Dialog. I need this in order to control the position of a Dialog. For now, I ended up using https://floating-ui.com/ directly to control the position of my headless Dialog.

whitespacecode commented 1 year ago

@WesleyKapow you need to understand menu and popover elements are positioned against a parent element (button or menu-item), that is why you can use float-ui to position the child elements around the parent element. A Dialog or modal is just a popup inside a container. You don't need float-ui to position the dialog.

Vue example for Dialog:

<script setup>
import { ref } from 'vue'
import { Dialog, DialogPanel, DialogTitle, TransitionChild, TransitionRoot } from '@headlessui/vue'

const open = ref(true)
</script>

<template>
  <TransitionRoot as="template" :show="open">
    <Dialog as="div" class="relative z-10" @close="open = false">
      <TransitionChild as="template" enter="ease-out duration-300" enter-from="opacity-0" enter-to="opacity-100" leave="ease-in duration-200" leave-from="opacity-100" leave-to="opacity-0">
        <div class="fixed inset-0 bg-gray-500 bg-opacity-75 transition-opacity" />
      </TransitionChild>

      <div class="fixed inset-0 z-10 overflow-y-auto">
        <div class="flex min-h-full items-end justify-center p-4 text-center sm:items-center sm:p-0">
          <TransitionChild as="template" enter="ease-out duration-300" enter-from="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95" enter-to="opacity-100 translate-y-0 sm:scale-100" leave="ease-in duration-200" leave-from="opacity-100 translate-y-0 sm:scale-100" leave-to="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95">
            <DialogPanel class="relative transform overflow-hidden rounded-lg bg-white px-4 pt-5 pb-4 text-left shadow-xl transition-all sm:my-8 sm:w-full sm:max-w-sm sm:p-6">
                <div class="mt-3 text-center sm:mt-5">
                  <DialogTitle as="h3" class="text-lg font-medium leading-6 text-gray-900">Payment successful</DialogTitle>
                  <div class="mt-2">
                    <p class="text-sm text-gray-500">Lorem ipsum dolor sit amet consectetur adipisicing elit. Consequatur amet labore.</p>
                  </div>
                </div>
              <div class="mt-5 sm:mt-6">
                <button type="button" class="inline-flex w-full justify-center rounded-md border border-transparent bg-indigo-600 px-4 py-2 text-base font-medium text-white shadow-sm hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:ring-offset-2 sm:text-sm" @click="open = false">Go back to dashboard</button>
              </div>
            </DialogPanel>
          </TransitionChild>
        </div>
      </div>
    </Dialog>
  </TransitionRoot>
</template>

Just change the classes to position the dialog. No need for another package when using a Dialog.

ycs77 commented 1 year ago

Ok, I have some ideas to support Dialog, but it will take a while.

WesleyKapow commented 1 year ago

Just an FYI, I did end up using floating-ui directly in this case and not using headlessui-float.

ycs77 commented 1 year ago

Just an FYI, I did end up using floating-ui directly in this case and not using headlessui-float.

Of course, floating-ui can be manipulated more freely than headlessui-float.

ycs77 commented 1 year ago

Now support the dialog in v0.11, can see the docs Dialog mode to use it, open a new issue if you have any problems.

And the demo has the example of dialog.