mirror of
https://github.com/responsively-org/responsively-app
synced 2024-11-10 06:44:13 +00:00
Merge pull request #1163 from responsively-org/dropdown-overflow-fix
Dropdown flyout is rendered via portal
This commit is contained in:
commit
8f3ade46ad
4 changed files with 113 additions and 59 deletions
|
@ -104,6 +104,7 @@
|
|||
},
|
||||
"dependencies": {
|
||||
"@fontsource/lato": "^5.0.17",
|
||||
"@headlessui-float/react": "^0.12.0",
|
||||
"@headlessui/react": "^1.7.4",
|
||||
"@iconify/react": "^3.2.2",
|
||||
"@reduxjs/toolkit": "^1.9.5",
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
import { Menu, Transition } from '@headlessui/react';
|
||||
import { Float } from '@headlessui-float/react';
|
||||
import { Icon } from '@iconify/react';
|
||||
import cx from 'classnames';
|
||||
import { Fragment } from 'react';
|
||||
|
@ -23,66 +24,66 @@ interface Props {
|
|||
|
||||
export function DropDown({ label, options, className }: Props) {
|
||||
return (
|
||||
<div className="text-right">
|
||||
<Menu as="div" className={`relative inline-block text-left ${className}`}>
|
||||
<div>
|
||||
<div className="relative text-right">
|
||||
<Menu as="div" className={`inline-block text-left ${className}`}>
|
||||
<Float placement="bottom-end" flip portal>
|
||||
<Menu.Button className="inline-flex w-full justify-center gap-1 rounded-md bg-opacity-20 p-2 text-sm font-medium hover:bg-slate-300 hover:bg-opacity-30 focus:outline-none focus-visible:ring-2 focus-visible:ring-white focus-visible:ring-opacity-75 dark:hover:bg-slate-700">
|
||||
{label}
|
||||
<Icon icon="mdi:chevron-down" />
|
||||
</Menu.Button>
|
||||
</div>
|
||||
<Transition
|
||||
as={Fragment}
|
||||
enter="transition ease-out duration-100"
|
||||
enterFrom="transform opacity-0 scale-95"
|
||||
enterTo="transform opacity-100 scale-100"
|
||||
leave="transition ease-in duration-75"
|
||||
leaveFrom="transform opacity-100 scale-100"
|
||||
leaveTo="transform opacity-0 scale-95"
|
||||
>
|
||||
<Menu.Items className="absolute right-0 z-50 mt-2 w-fit origin-top-right divide-y divide-slate-100 rounded-md bg-slate-100 shadow-lg ring-1 ring-black ring-opacity-5 focus:outline-none dark:bg-slate-900">
|
||||
<div className="px-1 py-1 ">
|
||||
{options.map((option, idx) => {
|
||||
if (option.type === 'separator') {
|
||||
<Transition
|
||||
as={Fragment}
|
||||
enter="transition ease-out duration-100"
|
||||
enterFrom="transform opacity-0 scale-95"
|
||||
enterTo="transform opacity-100 scale-100"
|
||||
leave="transition ease-in duration-75"
|
||||
leaveFrom="transform opacity-100 scale-100"
|
||||
leaveTo="transform opacity-0 scale-95"
|
||||
>
|
||||
<Menu.Items className="z-50 mt-2 w-fit origin-top-right divide-y divide-slate-100 rounded-md bg-slate-100 shadow-lg ring-1 ring-black ring-opacity-5 focus:outline-none dark:bg-slate-900">
|
||||
<div className="px-1 py-1 ">
|
||||
{options.map((option, idx) => {
|
||||
if (option.type === 'separator') {
|
||||
return (
|
||||
<div
|
||||
className="m-1 border-t-[1px] border-t-slate-500"
|
||||
// eslint-disable-next-line react/no-array-index-key
|
||||
key={`divider-${idx}`}
|
||||
/>
|
||||
);
|
||||
}
|
||||
return (
|
||||
<div
|
||||
className="m-1 border-t-[1px] border-t-slate-500"
|
||||
// eslint-disable-next-line react/no-array-index-key
|
||||
key={`divider-${idx}`}
|
||||
/>
|
||||
// eslint-disable-next-line react/no-array-index-key
|
||||
<Menu.Item key={idx.toString()}>
|
||||
{({ active }) =>
|
||||
option.onClick !== null ? (
|
||||
<button
|
||||
className={cx(
|
||||
'group flex w-full items-center rounded-md px-2 py-2 text-sm',
|
||||
{ 'bg-slate-200 dark:bg-slate-800': active }
|
||||
)}
|
||||
type="button"
|
||||
onClick={option.onClick}
|
||||
>
|
||||
{option.label}
|
||||
</button>
|
||||
) : (
|
||||
<div
|
||||
className={cx(
|
||||
'group mt-2 flex w-full items-center rounded-md px-2'
|
||||
)}
|
||||
>
|
||||
{option.label}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
</Menu.Item>
|
||||
);
|
||||
}
|
||||
return (
|
||||
// eslint-disable-next-line react/no-array-index-key
|
||||
<Menu.Item key={idx.toString()}>
|
||||
{({ active }) =>
|
||||
option.onClick !== null ? (
|
||||
<button
|
||||
className={cx(
|
||||
'group flex w-full items-center rounded-md px-2 py-2 text-sm',
|
||||
{ 'bg-slate-200 dark:bg-slate-800': active }
|
||||
)}
|
||||
type="button"
|
||||
onClick={option.onClick}
|
||||
>
|
||||
{option.label}
|
||||
</button>
|
||||
) : (
|
||||
<div
|
||||
className={cx(
|
||||
'group mt-2 flex w-full items-center rounded-md px-2'
|
||||
)}
|
||||
>
|
||||
{option.label}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
</Menu.Item>
|
||||
);
|
||||
})}
|
||||
</div>
|
||||
</Menu.Items>
|
||||
</Transition>
|
||||
})}
|
||||
</div>
|
||||
</Menu.Items>
|
||||
</Transition>
|
||||
</Float>
|
||||
</Menu>
|
||||
</div>
|
||||
);
|
||||
|
|
|
@ -6,6 +6,12 @@ const ThemeProvider = ({ children }: { children: React.ReactNode }) => {
|
|||
const darkMode = useSelector(selectDarkMode);
|
||||
|
||||
useEffect(() => {
|
||||
const body = document.querySelector('body');
|
||||
'bg-slate-200 text-light-normal dark:bg-slate-800 dark:text-dark-normal'
|
||||
.split(' ')
|
||||
.forEach((className) => {
|
||||
body?.classList.add(className);
|
||||
});
|
||||
if (darkMode) {
|
||||
document.documentElement.classList.add('dark');
|
||||
} else {
|
||||
|
@ -13,11 +19,7 @@ const ThemeProvider = ({ children }: { children: React.ReactNode }) => {
|
|||
}
|
||||
}, [darkMode]);
|
||||
|
||||
return (
|
||||
<div className="min-w-screen min-h-screen bg-slate-200 text-light-normal dark:bg-slate-800 dark:text-dark-normal">
|
||||
{children}
|
||||
</div>
|
||||
);
|
||||
return <div className="min-w-screen min-h-screen">{children}</div>;
|
||||
};
|
||||
|
||||
export default ThemeProvider;
|
||||
|
|
|
@ -1381,6 +1381,42 @@
|
|||
resolved "https://registry.yarnpkg.com/@eslint/js/-/js-8.36.0.tgz#9837f768c03a1e4a30bd304a64fb8844f0e72efe"
|
||||
integrity sha512-lxJ9R5ygVm8ZWgYdUweoq5ownDlJ4upvoWmO4eLxBYHdMo+vZ/Rx0EN6MbKWDJOSUGrqJy2Gt+Dyv/VKml0fjg==
|
||||
|
||||
"@floating-ui/core@^1.3.0", "@floating-ui/core@^1.4.2":
|
||||
version "1.5.0"
|
||||
resolved "https://registry.yarnpkg.com/@floating-ui/core/-/core-1.5.0.tgz#5c05c60d5ae2d05101c3021c1a2a350ddc027f8c"
|
||||
integrity sha512-kK1h4m36DQ0UHGj5Ah4db7R0rHemTqqO0QLvUqi1/mUUp3LuAWbWxdxSIf/XsnH9VS6rRVPLJCncjRzUvyCLXg==
|
||||
dependencies:
|
||||
"@floating-ui/utils" "^0.1.3"
|
||||
|
||||
"@floating-ui/dom@^1.3.0", "@floating-ui/dom@^1.5.1":
|
||||
version "1.5.3"
|
||||
resolved "https://registry.yarnpkg.com/@floating-ui/dom/-/dom-1.5.3.tgz#54e50efcb432c06c23cd33de2b575102005436fa"
|
||||
integrity sha512-ClAbQnEqJAKCJOEbbLo5IUlZHkNszqhuxS4fHAVxRPXPya6Ysf2G8KypnYcOTpx6I8xcgF9bbHb6g/2KpbV8qA==
|
||||
dependencies:
|
||||
"@floating-ui/core" "^1.4.2"
|
||||
"@floating-ui/utils" "^0.1.3"
|
||||
|
||||
"@floating-ui/react-dom@^2.0.3":
|
||||
version "2.0.4"
|
||||
resolved "https://registry.yarnpkg.com/@floating-ui/react-dom/-/react-dom-2.0.4.tgz#b076fafbdfeb881e1d86ae748b7ff95150e9f3ec"
|
||||
integrity sha512-CF8k2rgKeh/49UrnIBs4BdxPUV6vize/Db1d/YbCLyp9GiVZ0BEwf5AiDSxJRCr6yOkGqTFHtmrULxkEfYZ7dQ==
|
||||
dependencies:
|
||||
"@floating-ui/dom" "^1.5.1"
|
||||
|
||||
"@floating-ui/react@^0.26.0":
|
||||
version "0.26.2"
|
||||
resolved "https://registry.yarnpkg.com/@floating-ui/react/-/react-0.26.2.tgz#1a548f0f9aae64a742c868ae36aa620d15dec728"
|
||||
integrity sha512-ocpz3MxYoZlgsASiVFayiTnKukR8QZDQUMqxMdF0YFLbu8lw/IL6AHKLROI8SOpp6CxpUGPh9Q4a03eBAVEZNQ==
|
||||
dependencies:
|
||||
"@floating-ui/react-dom" "^2.0.3"
|
||||
"@floating-ui/utils" "^0.1.5"
|
||||
tabbable "^6.0.1"
|
||||
|
||||
"@floating-ui/utils@^0.1.3", "@floating-ui/utils@^0.1.5":
|
||||
version "0.1.6"
|
||||
resolved "https://registry.yarnpkg.com/@floating-ui/utils/-/utils-0.1.6.tgz#22958c042e10b67463997bd6ea7115fe28cbcaf9"
|
||||
integrity sha512-OfX7E2oUDYxtBvsuS4e/jSn4Q9Qb6DzgeYtsAdkPZ47znpoNsMgZw0+tVijiv3uGNR6dgNlty6r9rzIzHjtd/A==
|
||||
|
||||
"@fontsource/lato@^5.0.17":
|
||||
version "5.0.17"
|
||||
resolved "https://registry.yarnpkg.com/@fontsource/lato/-/lato-5.0.17.tgz#7c75c443da1e3ae203ed1977b6455bb15c62c106"
|
||||
|
@ -1399,6 +1435,15 @@
|
|||
normalize-path "^2.0.1"
|
||||
through2 "^2.0.3"
|
||||
|
||||
"@headlessui-float/react@^0.12.0":
|
||||
version "0.12.0"
|
||||
resolved "https://registry.yarnpkg.com/@headlessui-float/react/-/react-0.12.0.tgz#092ef8ee39a87526895f314fe8e4765e2e077cda"
|
||||
integrity sha512-/oikFriS8t5nirJnRlHrvltrGx0PwhGUsUFNxxyfLOC/wNGX8k5kvNy+XCmSXBJ3fCYsSHYaDsPLct3lWDMXuw==
|
||||
dependencies:
|
||||
"@floating-ui/core" "^1.3.0"
|
||||
"@floating-ui/dom" "^1.3.0"
|
||||
"@floating-ui/react" "^0.26.0"
|
||||
|
||||
"@headlessui/react@^1.7.4":
|
||||
version "1.7.4"
|
||||
resolved "https://registry.yarnpkg.com/@headlessui/react/-/react-1.7.4.tgz#ba7f50fda20667276ee84fcd4c2a459aa26187e3"
|
||||
|
@ -12960,6 +13005,11 @@ synckit@^0.8.4:
|
|||
"@pkgr/utils" "^2.3.1"
|
||||
tslib "^2.4.0"
|
||||
|
||||
tabbable@^6.0.1:
|
||||
version "6.2.0"
|
||||
resolved "https://registry.yarnpkg.com/tabbable/-/tabbable-6.2.0.tgz#732fb62bc0175cfcec257330be187dcfba1f3b97"
|
||||
integrity sha512-Cat63mxsVJlzYvN51JmVXIgNoUokrIaT2zLclCXjRd8boZ0004U4KCs/sToJ75C6sdlByWxpYnb5Boif1VSFew==
|
||||
|
||||
tailwindcss@^3.1.4:
|
||||
version "3.2.1"
|
||||
resolved "https://registry.yarnpkg.com/tailwindcss/-/tailwindcss-3.2.1.tgz#1bd828fff3172489962357f8d531c184080a6786"
|
||||
|
|
Loading…
Reference in a new issue