@headlessui/react#Dialog TypeScript Examples
The following examples show how to use
@headlessui/react#Dialog.
You can vote up the ones you like or vote down the ones you don't like,
and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: Modal.tsx From Meshtastic with GNU General Public License v3.0 | 6 votes |
Modal = ({ open, onClose, children }: ModalProps): JSX.Element => {
return (
<AnimatePresence initial={false} exitBeforeEnter={true}>
<Dialog
as="div"
className="fixed inset-0 z-10 overflow-y-auto"
open={open}
onClose={onClose}
>
<div className="min-h-screen px-0.5 text-center md:px-4">
<motion.div
initial={{ opacity: 0 }}
animate={{ opacity: 1 }}
exit={{ opacity: 0 }}
>
<Dialog.Overlay className="fixed inset-0 backdrop-blur-md" />
</motion.div>
<span
className="inline-block h-screen align-middle"
aria-hidden="true"
>
​
</span>
<div className="inline-block w-full transform text-left align-middle transition-all 2xl:max-w-7xl">
<div className="group relative">
<div className="animate-tilt absolute -inset-0.5 rotate-2 rounded-lg bg-accent shadow-md transition duration-1000 group-hover:opacity-100 group-hover:duration-200"></div>
<div className="relative flex flex-col overflow-hidden rounded-2xl bg-base shadow-md md:aspect-[2/1] md:flex-row md:bg-primary">
{children}
</div>
</div>
</div>
</div>
</Dialog>
</AnimatePresence>
);
}
Example #2
Source File: Modal.tsx From pali-wallet with MIT License | 6 votes |
DefaultModal = ({
buttonText = 'Ok',
description = '',
onClose,
show,
title = '',
}: IDefaultModal) => (
<Modal show={show} onClose={onClose}>
<div className="inline-block align-middle my-8 p-6 w-full max-w-md text-center font-poppins bg-bkg-4 rounded-2xl shadow-xl overflow-hidden transform transition-all">
<Dialog.Title
as="h3"
className="pb-4 pt-2 text-brand-white text-lg font-medium leading-6 border-b border-dashed border-gray-600"
>
{title}
</Dialog.Title>
<div className="mt-2">
<p className="text-white text-sm">{description}</p>
</div>
<div className="mt-4">
<button
type="button"
className="inline-flex justify-center px-10 py-2 hover:text-bkg-4 text-brand-white text-sm font-medium hover:bg-button-popuphover bg-transparent border border-brand-white rounded-full focus:outline-none transition-all duration-200 focus-visible:ring-2 focus-visible:ring-brand-royalblue focus-visible:ring-offset-2"
onClick={onClose}
id="got-it-btn"
>
{buttonText}
</button>
</div>
</div>
</Modal>
)
Example #3
Source File: MobileFilters.tsx From po8klasie with GNU General Public License v3.0 | 6 votes |
MobileFilters: FC<MobileFiltersProps> = ({ onFiltersChange, filtersValues}) => {
let [isOpen, setIsOpen] = useState(false)
const { searchView } = useProjectConfig();
const { filters: filtersConfig } = searchView as SearchViewConfig;
return (
<>
<button
className="rounded-xl border border-light px-3 py-1 mx-2 flex items-center md:hidden"
onClick={() => setIsOpen(!isOpen)}>
<BiFilterAlt className="mr-2" />
Filtry
</button>
<Dialog open={isOpen} onClose={() => setIsOpen(false)}>
<Dialog.Panel className="top-0 left-0 h-full w-full fixed z-40 bg-appBg pt-navbarHeight">
<div className="flex items-center justify-end">
<button className="p-2" onClick={() => setIsOpen(false)}>
<FiX className="text-xl" />
</button>
</div>
{filtersConfig.map(({ options, key, component, displayInRowOnMobile }) => {
const FilterComponent = mobileFiltersComponents[component as keyof typeof mobileFiltersComponents];
if (displayInRowOnMobile) return null;
return (
<FilterComponent
options={options}
onChange={onFiltersChange(key)}
value={filtersValues[key]}
/>
);
})}
</Dialog.Panel>
</Dialog>
</>
)
}
Example #4
Source File: Modal.tsx From pali-wallet with MIT License | 5 votes |
Modal = ({
children,
className = '',
onClose,
show = true,
}: IModal) => (
<Transition appear show={show} as={Fragment}>
<Dialog
as="div"
className={`fixed z-10 inset-0 overflow-y-auto ${className}`}
onClose={onClose ?? (() => {})}
>
<div
onClick={() => console.log('inside onClick')}
className="fixed z-0 -inset-0 w-full bg-brand-black bg-opacity-50 transition-all duration-300 ease-in-out"
/>
<div className="px-4 min-h-screen text-center">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0" />
</Transition.Child>
<span className="inline-block align-middle h-screen" aria-hidden="true">
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
{children}
</Transition.Child>
</div>
</Dialog>
</Transition>
)
Example #5
Source File: index.tsx From interbtc-ui with Apache License 2.0 | 5 votes |
Sidebar = ({ className, children }: Props): JSX.Element => {
const [sidebarOpen, setSidebarOpen] = React.useState(false);
const handleClose = () => {
setSidebarOpen(false);
};
const handleOpen = () => {
setSidebarOpen(true);
};
return (
<div className={clsx('h-screen', 'flex', 'overflow-hidden', className)}>
<Transition.Root show={sidebarOpen} as={React.Fragment}>
<Dialog
as='div'
static
className={clsx('fixed', 'inset-0', 'flex', 'z-40', ON_SMALL_SCREEN_CLASS_NAME)}
open={sidebarOpen}
onClose={setSidebarOpen}
>
<Transition.Child
as={React.Fragment}
enter={clsx('transition-opacity', 'ease-linear', 'duration-300')}
enterFrom='opacity-0'
enterTo='opacity-100'
leave={clsx('transition-opacity', 'ease-linear', 'duration-300')}
leaveFrom='opacity-100'
leaveTo='opacity-0'
>
<Dialog.Overlay className={clsx('fixed', 'inset-0', 'bg-interlayHaiti-400', 'bg-opacity-75')} />
</Transition.Child>
<Transition.Child
as={React.Fragment}
enter={clsx('transition', 'ease-in-out', 'duration-300', 'transform')}
enterFrom='-translate-x-full'
enterTo='translate-x-0'
leave={clsx('transition', 'ease-in-out', 'duration-300', 'transform')}
leaveFrom='translate-x-0'
leaveTo='-translate-x-full'
>
<SidebarContent onSmallScreen onClose={handleClose} />
</Transition.Child>
<div className={clsx('flex-shrink-0', 'w-14')} />
</Dialog>
</Transition.Root>
<div className={clsx('hidden', 'md:flex', 'md:flex-shrink-0')}>
<div className={clsx('flex', 'flex-col', 'w-64')}>
<SidebarContent onClose={handleClose} />
</div>
</div>
<div className={clsx('flex', 'flex-col', 'w-0', 'flex-1', 'overflow-hidden')}>
<div className={clsx(ON_SMALL_SCREEN_CLASS_NAME, 'pl-1', 'pt-1', 'sm:pl-3', 'sm:pt-3')}>
<OpenButton onClick={handleOpen} />
</div>
<main className={clsx('flex-1', 'relative', 'z-0', 'overflow-y-auto', 'focus:outline-none')}>{children}</main>
</div>
</div>
);
}
Example #6
Source File: index.tsx From interbtc-ui with Apache License 2.0 | 5 votes |
InterlayModal = ({ open = false, onClose, children, initialFocus }: Props): JSX.Element => {
return (
<Transition appear show={open} as={React.Fragment}>
<Dialog
className={clsx('fixed', 'inset-0', 'z-interlayModal', 'overflow-y-auto')}
open={open}
onClose={onClose}
initialFocus={initialFocus}
>
<div className={clsx('px-4', 'text-center')}>
<Transition.Child
as={React.Fragment}
enter='ease-out duration-300'
enterFrom='opacity-0'
enterTo='opacity-100'
leave='ease-in duration-200'
leaveFrom='opacity-100'
leaveTo='opacity-0'
>
<Dialog.Overlay
className={clsx('absolute', 'inset-0', 'bg-black', 'bg-opacity-30', 'transition-opacity')}
/>
</Transition.Child>
{/* MEMO: this element is to trick the browser into centering the modal contents. */}
<span className={clsx('hidden', 'sm:inline-block', 'sm:align-middle', 'sm:h-screen')} aria-hidden='true'>
​
</span>
<Transition.Child
as={React.Fragment}
enter='ease-out duration-300'
enterFrom='opacity-0 scale-95'
enterTo='opacity-100 scale-100'
leave='ease-in duration-200'
leaveFrom='opacity-100 scale-100'
leaveTo='opacity-0 scale-95'
>
{children}
</Transition.Child>
</div>
</Dialog>
</Transition>
);
}
Example #7
Source File: index.tsx From interbtc-ui with Apache License 2.0 | 5 votes |
InterlayModalTitle = (props: InterlayModalTitleProps): JSX.Element => <Dialog.Title {...props} />
Example #8
Source File: index.tsx From polkabtc-ui with Apache License 2.0 | 5 votes |
InterlayModalTitle = (props: PropsOf<typeof Dialog.Title>): JSX.Element => (
<Dialog.Title {...props} />
)
Example #9
Source File: index.tsx From polkabtc-ui with Apache License 2.0 | 5 votes |
InterlayModal = ({
open = false,
onClose,
children,
initialFocus
}: Props): JSX.Element => {
return (
<Dialog
className={clsx(
'fixed',
'inset-0',
'z-interlayModal',
'overflow-y-auto'
)}
open={open}
onClose={onClose}
initialFocus={initialFocus}>
<div
className={clsx(
'px-4',
'text-center'
)}>
<Dialog.Overlay
className={clsx(
'absolute',
'inset-0',
'bg-black',
'bg-opacity-30',
'transition-opacity'
)} />
{/* MEMO: this element is to trick the browser into centering the modal contents. */}
<span
className={clsx(
'hidden',
'sm:inline-block',
'sm:align-middle',
'sm:h-screen'
)}
aria-hidden='true'>
​
</span>
{children}
</div>
</Dialog>
);
}
Example #10
Source File: ModalBase.tsx From contracts-ui with GNU General Public License v3.0 | 5 votes |
ModalBase = ({ isOpen, setIsOpen, title, children }: ModalProps) => {
function closeModal() {
setIsOpen(false);
}
return (
<>
<Transition appear show={isOpen} as={Fragment}>
<Dialog as="div" className="fixed inset-0 z-99 overflow-y-auto " onClose={closeModal}>
<div className="min-h-screen px-4 text-center">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-black dark:opacity-70 opacity-10" />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span className="inline-block h-screen align-middle" aria-hidden="true">
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="inline-block w-full max-w-lg my-8 overflow-hidden text-left align-middle transition-all transform opacity-100 dark:bg-gray-900 bg-white shadow-xl rounded-xl">
<div className="flex justify-between border-b dark:border-gray-800 border-gray-200">
<Dialog.Title
as="h3"
className="text-lg font-bold leading-6 p-6 dark:text-gray-300 text-gray-600"
>
{title}
</Dialog.Title>
<XIcon
className="w-4 h-4 mx-6 mt-7 text-gray-500 cursor-pointer"
aria-hidden="true"
onClick={closeModal}
/>
</div>
<div className="px-6">{children}</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
</>
);
}
Example #11
Source File: Modal.tsx From pali-wallet with MIT License | 5 votes |
ErrorModal = ({
buttonText = 'Ok',
description = '',
log,
onClose,
show,
title = '',
}: IErrorModal) => (
<Modal className="max-w-2xl" show={show} onClose={onClose}>
<div className="inline-block align-middle my-8 p-6 w-full max-w-2xl text-center font-poppins bg-bkg-3 border border-bkg-3 rounded-2xl shadow-xl overflow-hidden transform transition-all">
<Dialog.Title
as="h3"
className="text-brand-white text-lg font-medium leading-6"
>
{title}
</Dialog.Title>
<div className="mt-4">
<p className="text-gray-300 text-sm">{description}</p>
</div>
<p className="my-4 text-button-primary text-sm">
Error description:
{log}
</p>
<div className="flex gap-x-8 items-center justify-between mt-8">
<button
type="button"
className="inline-flex justify-center py-2 w-40 text-brand-white text-sm font-medium bg-button-secondary border border-button-secondary rounded-full focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-royalblue focus-visible:ring-offset-2"
onClick={onClose}
>
{buttonText}
</button>
<button
type="button"
className="inline-flex justify-center py-2 w-40 text-brand-white text-sm font-medium bg-button-primary hover:bg-opacity-70 border border-button-primary rounded-full focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-royalblue focus-visible:ring-offset-2"
onClick={() =>
window.open(
`mailto:[email protected]?subject="Pali Error Report: Token creation"&body=${log}`
)
}
>
Report
</button>
</div>
</div>
</Modal>
)
Example #12
Source File: modal.tsx From website with Apache License 2.0 | 5 votes |
export function Modal({isOpen, ...props}: Props) {
const close = () => {
props.setIsOpen(false);
};
return (
<Transition appear as={Fragment} show={isOpen}>
<Dialog
as="div"
className="overflow-y-auto fixed inset-0 z-10"
initialFocus={props.focusRef}
onClose={close}
>
<div className="px-4 min-h-screen text-center">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-black/30 dark:bg-black/80 backdrop-blur-md" />
</Transition.Child>
<span
className="inline-block h-screen align-middle"
aria-hidden="true"
>
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="inline-block overflow-hidden relative z-10 p-6 my-8 w-full max-w-xl text-left align-middle bg-white dark:bg-gray-800 rounded-2xl shadow-xl transition-all">
<div className="relative">
<Dialog.Title as="h3" className="text-lg font-medium leading-6">
{props.title}
</Dialog.Title>
<div className="absolute top-0 right-0 text-xl">
<button
type="button"
className="leading-none"
onClick={close}
>
×
</button>
</div>
</div>
{props.description && (
<div className="mt-2">
<p className="text-sm text-gray-100">{props.description}</p>
</div>
)}
<div className="mt-4">{props.children}</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
);
}
Example #13
Source File: about.tsx From vignette-web with MIT License | 4 votes |
OpenSource: NextPage<pageProps> = ({
contributors,
commits,
netReceived,
pullRequests,
openIssues,
totalPaid,
balance,
}) => {
const { t } = useTranslation(`about`)
const [isOpen, setIsOpen] = useState(false)
return (
<>
<SEO title={t(`page-title`)} />
<Nav />
<Container className="pt-8 lg:pt-16" id="content">
<div className="z-20 mx-auto px-2 pb-8 lg:max-w-7xl ">
<h1 className="lg:text-0xl bg-gradient-to-br from-[#005BEA] to-[#00C6FB] bg-clip-text text-4xl font-bold text-transparent xxs:text-5xl lg:text-9xl">
{t(`title1`)} <br />
{t(`title2`)}
</h1>
<p className="my-4 mb-8 mt-8 text-lg sm:px-2 sm:text-xl lg:mb-20 lg:text-2xl">
{t(`hero-p`)}
</p>
<Container offset={10} noMargin fadeIn>
<div className="mx-auto flex flex-wrap gap-8 pb-16 text-center">
<div className="mx-auto text-xl">
<div className="mb-1 text-6xl font-bold">{commits}</div>
{t(`commits`)}
<BiGitPullRequest
className="mx-auto mt-2 fill-pinkRed"
size={40}
/>
</div>
<div className="mx-auto text-xl">
<div className="mb-1 text-6xl font-bold">{pullRequests}</div>
{t(`pull-requests`)}
<BiGitPullRequest
className="mx-auto mt-2 fill-pinkRed"
size={40}
/>
</div>
<div className="mx-auto text-xl">
<div className="mb-1 text-6xl font-bold">{openIssues}</div>
{t(`open-issues`)}
<BiGitPullRequest
className="mx-auto mt-2 fill-pinkRed"
size={40}
/>
</div>
</div>
<div className="w-full text-center">
<a
href="https://github.com/vignetteapp"
className="button mx-auto "
>
{t(`visit-github-button`)}
</a>
</div>
</Container>
</div>
<Container fadeIn noMargin className="mt-32 text-center ">
<Image src={repoIcon} alt="" quality={100} width={72} height={72} />
<h2 className="mt-8 text-2xl font-bold lg:text-3xl">
{t(`section1-title`)}
</h2>
<div className=" mx-auto mt-6 flex max-w-6xl flex-wrap justify-center gap-4 px-0 lg:p-8 ">
{contributors.map((user) => (
<Link
passHref
key={user.login}
href={`https://github.com/${user.login}`}
>
<a className="p-4">
<div className="mx-auto">
<Image
width={64}
height={64}
className="rounded-full"
src={user.profile}
alt=""
/>
</div>
</a>
</Link>
))}
</div>
<p className="mx-auto mt-8 text-xs leading-snug text-gray-700 dark:text-gray-300 sm:max-w-md sm:text-sm">
{t(`section1-p`)}
</p>
<p className="mt-4 text-xs text-gray-800 dark:text-gray-200 ">
{t(`updates-daily-text`)}
</p>
</Container>
<Container>
<div className="mt-14 text-center lg:mt-28">
<div className="inline-flex overflow-hidden rounded-2xl drop-shadow-xl">
<Image
alt=""
src={VignettePadding}
width={64}
height={64}
quality={100}
/>
</div>
<h2 className="mt-3 text-2xl font-semibold">
{t(`section2-title`)}
</h2>
<p className="mx-auto mt-2 max-w-md">{t(`section2-p`)}</p>
</div>
<div className="mx-auto mt-10 flex flex-wrap justify-center gap-4 lg:max-w-5xl ">
{teamMembers.map((m: Member) => (
<a
href={m.url}
key={m.name}
className=" my-2 mx-2 text-center lg:mx-8"
>
<div className="inline-flex overflow-hidden rounded-full ">
<Image
alt=""
className=""
src={m.avatar}
width={64}
height={64}
/>
</div>
<h4 className=" my-1 font-medium capitalize">{m.name}</h4>
<p className="max-w-[9em] text-xs">{m.role}</p>
</a>
))}
</div>
</Container>
<Container className="mt-12 text-center">
<Image src={donationImage} width={400} height={400} alt="" />
<h1 className="text-3xl font-bold"> {t(`section3-title`)}</h1>
<p className="mx-auto mt-2 mb-2 max-w-[34em]">{t(`section3-p`)}</p>
<button
onClick={() => setIsOpen(true)}
className="font-semibold text-pinkRed hover:underline"
>
{t(`gives-back-button`)}
</button>
<Transition appear show={isOpen} as={Fragment}>
<Dialog
as="div"
className="fixed inset-0 z-10 overflow-y-auto"
onClose={() => setIsOpen(false)}
>
<div className="min-h-screen px-4 text-center">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0" />
</Transition.Child>
<Dialog.Overlay className="fixed inset-0 bg-black/20 backdrop-blur-sm dark:bg-neutral-900/80 " />
{/* This element is to trick the browser into centering the modal contents. */}
<span
className="inline-block h-screen align-middle"
aria-hidden="true"
>
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="prose-md prose my-8 inline-block w-full max-w-2xl transform overflow-hidden rounded-2xl bg-white px-6 py-4 text-left align-middle shadow-xl transition-all dark:prose-invert dark:bg-black">
<Dialog.Title
as="h3"
className="text-lg font-medium leading-6 "
>
{t(`gives-back-button`)}
</Dialog.Title>
<div className="mt-2">
<ReactMarkdown>{t(`gives-back-p`)}</ReactMarkdown>
</div>
<div className="mt-6">
<button
type="button"
className="button-small inline-flex justify-center border border-transparent bg-pinkRed px-4 py-2 text-sm font-medium text-white hover:bg-[#ff2277] focus:outline-none focus-visible:ring-2 focus-visible:ring-blue-500 focus-visible:ring-offset-2 dark:bg-pinkRed"
onClick={() => setIsOpen(false)}
>
{t(`got-it-button`)}
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
<div className="mx-auto my-10 flex w-full max-w-5xl flex-wrap justify-center gap-6 text-lg lg:gap-20 lg:text-xl ">
<div className="w-40 md:w-52">
<h3 className="mb-1 text-3xl font-bold lg:text-5xl">
${netReceived}
</h3>
{t(`earned`)}
</div>
<div className="w-40 md:w-52">
<h3 className="mb-1 text-3xl font-bold lg:text-5xl">
${balance}
</h3>
{t(`balance`)}
</div>
<div className="w-52">
<h3 className="mb-1 text-3xl font-bold lg:text-5xl">
${totalPaid}
</h3>
{t(`paid`)}
</div>
</div>
<a className="button">{t(`support-us-button`)}</a>
</Container>
</Container>
<Footer />
</>
)
}
Example #14
Source File: ConnectWallet.tsx From pali-wallet with MIT License | 4 votes |
ConnectWallet = () => {
const { accounts, trustedApps } = useStore();
const accountController = getController().wallet.account;
const connectedAccount = accountController.getConnectedAccount();
const [accountId, setAccountId] = useState<number>(-1);
const [isInTrustedList, setIsInTrustedList] = useState<boolean>(false);
const [openExtraConfirmation, setOpenExtraConfirmation] =
useState<boolean>(false);
const handleSelectAccount = (id: number) => {
if (connectedAccount && id === connectedAccount.id) {
return;
}
setAccountId(id);
};
useEffect(() => {
const trustedApp = trustedApps.includes(getHost(''));
setIsInTrustedList(trustedApp);
});
return (
<Layout canGoBack={false} title="CONNECT WITH">
<div className="flex flex-col items-center justify-center w-full">
<h1 className="mt-4 text-sm">PALI WALLET</h1>
{accounts ? (
<ul className="scrollbar-styled flex flex-col gap-4 mt-4 px-8 w-full h-64 overflow-auto">
{Object.values(accounts).map((acc: any) => (
<li
className={`${
connectedAccount && acc.id === connectedAccount.id
? 'cursor-not-allowed bg-opacity-50 border-brand-royalblue'
: 'cursor-pointer hover:bg-bkg-4 border-brand-royalblue'
} border border-solid rounded-lg px-2 py-4 text-xs bg-bkg-2 flex justify-between items-center transition-all duration-200`}
key={acc.id}
onClick={() => handleSelectAccount(acc.id)}
>
<p>{acc.label}</p>
<div className="flex gap-3 items-center justify-center">
<small>{ellipsis(acc.address.main)}</small>
<div
className={`${
acc.id === accountId
? 'bg-warning-success'
: 'bg-brand-graylight'
} w-3 h-3 rounded-full border border-brand-royalblue`}
/>
</div>
</li>
))}
</ul>
) : (
<div>
<Icon name="loading" className="w-4 text-brand-graylight" />
</div>
)}
<small className="mb-8 text-center text-brand-royalblue text-sm">
Only connect with sites you trust.{' '}
<a href="https://docs.syscoin.org/">Learn more.</a>
</small>
<div className="absolute bottom-10 flex gap-3 items-center justify-between w-full max-w-xs md:max-w-2xl">
<SecondaryButton type="button" action onClick={() => window.close()}>
Cancel
</SecondaryButton>
<PrimaryButton
type="button"
action
disabled={accountId === -1}
onClick={
!isInTrustedList ? () => setOpenExtraConfirmation(true) : () => {}
}
>
{accountId > -1 ? 'Confirm' : 'Next'}
</PrimaryButton>
</div>
<Modal
show={openExtraConfirmation}
onClose={() => setOpenExtraConfirmation(false)}
>
<div className="inline-block align-middle my-8 p-6 w-full max-w-2xl text-center font-poppins bg-bkg-4 border border-brand-royalblue rounded-2xl shadow-xl overflow-hidden transform transition-all">
<Dialog.Title
as="h3"
className="flex gap-3 items-center justify-center text-brand-white text-lg font-medium leading-6"
>
<Icon name="warning" className="mb-2 text-brand-white" />
<p>Not trusted site detected</p>
</Dialog.Title>
<div className="mt-4">
<p className="text-brand-white text-sm">
This site is not on our trusted list. Are you sure you want to
connect?
</p>
</div>
<div className="flex gap-5 items-center justify-between mt-8">
<SecondaryButton
action
width="32"
type="button"
onClick={() => window.close()}
>
Cancel
</SecondaryButton>
<PrimaryButton action width="32" type="button" onClick={() => {}}>
Confirm
</PrimaryButton>
</div>
</div>
</Modal>
</div>
</Layout>
);
}
Example #15
Source File: ConnectedSites.tsx From pali-wallet with MIT License | 4 votes |
ConnectedSites = (): any => {
const { navigate } = useUtils();
const { activeAccount } = useStore();
const [selected, setSelected] = useState<string>('');
const disconnectSite = (id: any) => {
browser.runtime.sendMessage({
type: 'RESET_CONNECTION_INFO',
target: 'background',
id,
url: selected,
});
setSelected('');
};
return (
<Layout title="CONNECTED SITES">
<p className="m-4 max-w-xs text-white text-xs md:max-w-md">
{`${activeAccount?.label} is not connected to any sites. To connect to a SYS platform site, find the connect button on their site.`}
</p>
<div className="flex flex-col items-center justify-center w-full">
{/* {activeAccount?.connectedTo &&
activeAccount.connectedTo.map((url: string) => (
<ul
key={url}
className="scrollbar-styled px-4 py-2 w-full h-80 overflow-auto"
>
<li className="flex items-center justify-between my-2 py-3 w-full text-xs border-b border-dashed border-gray-500">
<p>{formatUrl(url, 25)}</p>
<IconButton onClick={() => setSelected(url)}>
<Icon name="edit" wrapperClassname="w-4" />
</IconButton>
</li>
</ul>
))} */}
{selected && (
<Transition appear show={selected !== ''} as={Fragment}>
<Dialog
as="div"
className="fixed z-10 inset-0 text-center overflow-y-auto"
onClose={() => setSelected('')}
>
<div className="fixed z-0 -inset-0 w-full bg-brand-black bg-opacity-50 transition-all duration-300 ease-in-out" />
<div className="px-4 min-h-screen">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0" />
</Transition.Child>
<span
className="inline-block align-middle h-screen"
aria-hidden="true"
>
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="inline-block align-middle my-8 py-6 w-full max-w-2xl text-left font-poppins bg-bkg-2 rounded-2xl shadow-xl overflow-hidden transform transition-all">
<Dialog.Title
as="h3"
className="pb-3 text-center text-brand-white text-lg font-medium leading-6 border-b border-dashed border-brand-white"
>
Edit connection
</Dialog.Title>
<div className="my-4">
<p className="m-3 text-brand-white text-sm">
Delete connected site:
</p>
<div className="flex items-center justify-between m-3 text-brand-white">
<p>{formatUrl(selected, 20)}</p>
<IconButton
onClick={() => disconnectSite(activeAccount?.id)}
>
<Icon name="delete" />
</IconButton>
</div>
<div className="p-4 bg-bkg-1">
<p className="mb-3 text-brand-white">Permissions</p>
<div className="flex items-center justify-between">
<p className="text-brand-white text-xs">
{activeAccount?.label}
</p>
<p className="text-brand-white text-xs">
{ellipsis(activeAccount?.address)}
</p>
</div>
<p className="mt-4 pt-3 text-brand-white border-t border-dashed border-brand-white opacity-60 cursor-not-allowed">
<input type="checkbox" />
<span className="mb-1 ml-3">
View the addresses of your permitted accounts
</span>
</p>
</div>
</div>
<div className="mt-4 text-center">
<button
type="button"
className="transparent inline-flex justify-center px-12 py-2 hover:text-bkg-4 text-brand-white text-sm font-medium hover:bg-white bg-repeat border border-white rounded-full focus:outline-none focus-visible:ring-2 focus-visible:ring-brand-royalblue focus-visible:ring-offset-2"
onClick={() => setSelected('')}
>
Close
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
)}
<div className="absolute bottom-12 md:static">
<SecondaryButton type="button" onClick={() => navigate('/home')}>
Close
</SecondaryButton>
</div>
</div>
</Layout>
);
}
Example #16
Source File: BlogNav.tsx From vignette-web with MIT License | 4 votes |
Nav: React.FC = () => {
const { t } = useTranslation([`nav`, `common`])
const [isOpen, setIsOpen] = useState<boolean>(false)
const toggleMenu = () => (isOpen ? setIsOpen(false) : setIsOpen(true))
const [mounted, setMounted] = useState(false)
const { resolvedTheme, setTheme } = useTheme()
const router = useRouter()
// A flag to know when the page has mounted so the theme can be accessed
useEffect(() => setMounted(true), [])
return (
<>
{` `}
<a
href="#content"
className="text-md absolute -top-7 z-50 ml-3 -translate-y-12 transform rounded-md border border-gray-300 bg-white px-3 py-2 tracking-tight outline-none transition-transform duration-100 focus:translate-y-12 dark:border-neutral-700 dark:bg-black lg:ml-8"
>
Skip to content
</a>
{` `}
<div className="relative z-30 mx-auto flex w-full max-w-7xl items-center justify-between bg-transparent py-6 px-4 sm:px-8 lg:px-4 ">
<div className="flex items-center">
<Link href="/blog" passHref>
<a className="text-lg font-bold lg:text-xl">
{t(`blog:nav-title`)}
</a>
</Link>
</div>
<div className=" mx-4 ml-auto hidden items-center gap-4 sm:flex ">
<MyListbox router={router} />
<button
className="outline-none"
onClick={() =>
setTheme(resolvedTheme === `dark` ? `light` : `dark`)
}
>
{mounted ? (
resolvedTheme == `dark` ? (
<BsSunFill size={18} />
) : (
<BsMoonFill size={18} />
)
) : (
<div className="w-[18px]" />
)}
</button>
<Link href="https://github.com/vignetteapp" passHref>
<a className="outline-none">
<AiFillGithub size={24} />
</a>
</Link>
<Link href="https://twitter.com/vignette_org" passHref>
<a className="outline-none">
<AiOutlineTwitter size={24} />
</a>
</Link>
<button className="rounded-full bg-pinkRed px-8 py-1 font-semibold text-white ">
{t(`download`)}
</button>
</div>
<div className="flex items-center lg:hidden">
<button className="" onClick={toggleMenu}>
<GiHamburgerMenu size="28" className="fill-neutral-100" />
</button>
<Transition appear show={isOpen} as={Fragment}>
<Dialog
open={isOpen}
onClose={() => setIsOpen(false)}
className="fixed inset-0 z-50 lg:hidden"
>
<Transition.Child
as={Fragment}
enter="ease-out duration-100"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-75"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-black/20 backdrop-blur-sm dark:bg-neutral-900/80 " />
</Transition.Child>
<Transition.Child
as={Fragment}
enter="ease-out duration-100"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-75"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="dark:highlight-white/5 fixed top-4 right-4 w-full max-w-xs rounded-lg bg-white p-6 text-base font-semibold text-gray-900 shadow-lg dark:bg-neutral-900 dark:text-gray-300">
<button
onClick={() => setIsOpen(false)}
className="absolute top-5 right-5 flex h-8 w-8 items-center justify-center text-gray-500 hover:text-gray-600 dark:text-gray-200 dark:hover:text-gray-100"
>
<span className="sr-only">Close navigation</span>
<svg
viewBox="0 0 10 10"
className="h-2.5 w-2.5 overflow-visible"
aria-hidden="true"
>
<path
d="M0 0L10 10M10 0L0 10"
fill="none"
stroke="currentColor"
strokeWidth="2"
strokeLinecap="round"
></path>
</svg>
</button>
<ul className="space-y-6">
<li>
<Link href="/">
<a>{t(`nav:home`)}</a>
</Link>
</li>
<li>
<Link href="/features">
<a>{t(`nav:features`)}</a>
</Link>
</li>
<li>
<Link href="/about">
<a>{t(`nav:about`)}</a>
</Link>
</li>
<li>
<Link href="/blog">
<a>{t(`nav:blog`)}</a>
</Link>
</li>
<li>
<Link href="/contact">
<a>{t(`nav:contact`)}</a>
</Link>
</li>
<li>
<MyListbox router={router} />
</li>
</ul>
<div className="mt-6 border-t border-gray-200 pt-6 dark:border-gray-200/10">
<button
aria-label="Toggle Dark Mode"
type="button"
className="general-ring-state flex w-full items-center justify-center rounded-full bg-gray-200 py-3 dark:bg-neutral-700"
onClick={() =>
setTheme(resolvedTheme === `dark` ? `light` : `dark`)
}
>
{mounted && (
<>
<div>
{resolvedTheme === `dark` ? (
<BsSunFill size={18} />
) : (
<BsMoonFill size={18} />
)}
</div>
{resolvedTheme === `dark` ? (
<p className="ml-3 font-semibold">
{t(`common:switch-theme-light`)}
</p>
) : (
<p className="ml-3 font-semibold">
{t(`common:switch-theme-dark`)}
</p>
)}
</>
)}
</button>
</div>
</div>
</Transition.Child>
</Dialog>
</Transition>
</div>
</div>
</>
)
}
Example #17
Source File: Nav.tsx From vignette-web with MIT License | 4 votes |
Nav: React.FC = () => {
const { t } = useTranslation([`nav`, `common`])
const [isOpen, setIsOpen] = useState<boolean>(false)
const toggleMenu = () => (isOpen ? setIsOpen(false) : setIsOpen(true))
const [mounted, setMounted] = useState(false)
const { resolvedTheme, setTheme } = useTheme()
const router = useRouter()
// A flag to know when the page has mounted so the theme can be accessed
useEffect(() => setMounted(true), [])
return (
<>
<a
href="#content"
className="text-md absolute -top-7 z-50 ml-3 -translate-y-12 transform rounded-md border border-gray-300 bg-white px-3 py-2 tracking-tight outline-none transition-transform duration-100 focus:translate-y-12 dark:border-neutral-700 dark:bg-black lg:ml-8"
>
Skip to content
</a>
<div className="mx-auto flex w-full max-w-7xl items-center justify-between bg-transparent py-6 px-4 sm:px-8 lg:px-4 ">
<div className="flex items-center">
<Link href="/" passHref>
<a>
<Logo />
</a>
</Link>
<div className="mx-8 hidden gap-8 text-sm lg:flex lg:text-base">
<Link href="/features">{t(`nav:features`)}</Link>
<Link href="/about">{t(`nav:about`)}</Link>
<Link href="/plugins">{t(`nav:plugins`)}</Link>
<Link href="/blog">{t(`nav:blog`)}</Link>
</div>
</div>
<div className=" mx-4 ml-auto hidden items-center gap-4 sm:flex ">
<MyListbox router={router} />
<button
className="outline-none"
onClick={() =>
setTheme(resolvedTheme === `dark` ? `light` : `dark`)
}
>
{mounted ? (
resolvedTheme == `dark` ? (
<BsSunFill size={18} />
) : (
<BsMoonFill size={18} />
)
) : (
<div className="w-[18px]" />
)}
</button>
<Link href="https://github.com/vignetteapp" passHref>
<a className="outline-none">
<AiFillGithub size={24} />
</a>
</Link>
<Link href="https://twitter.com/vignette_org" passHref>
<a className="outline-none">
<AiOutlineTwitter size={24} />
</a>
</Link>
<button className="rounded-full bg-pinkRed px-8 py-1 font-semibold text-white ">
{t(`download`)}
</button>
</div>
<div className="flex items-center lg:hidden">
<button className="" onClick={toggleMenu}>
<GiHamburgerMenu
size="28"
className="fill-primary dark:fill-neutral-100"
/>
</button>
<Transition appear show={isOpen} as={Fragment}>
<Dialog
open={isOpen}
onClose={() => setIsOpen(false)}
className="fixed inset-0 z-50 lg:hidden"
>
<Transition.Child
as={Fragment}
enter="ease-out duration-100"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-75"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-black/20 backdrop-blur-sm dark:bg-neutral-900/80 " />
</Transition.Child>
<Transition.Child
as={Fragment}
enter="ease-out duration-100"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-75"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="dark:highlight-white/5 fixed top-4 right-4 w-full max-w-xs rounded-lg bg-white p-6 text-base font-semibold text-gray-900 shadow-lg dark:bg-neutral-900 dark:text-gray-300">
<button
onClick={() => setIsOpen(false)}
className="absolute top-5 right-5 flex h-8 w-8 items-center justify-center text-gray-500 hover:text-gray-600 dark:text-gray-200 dark:hover:text-gray-100"
>
<span className="sr-only">Close navigation</span>
<svg
viewBox="0 0 10 10"
className="h-2.5 w-2.5 overflow-visible"
aria-hidden="true"
>
<path
d="M0 0L10 10M10 0L0 10"
fill="none"
stroke="currentColor"
strokeWidth="2"
strokeLinecap="round"
></path>
</svg>
</button>
<ul className="space-y-6">
<li>
<Link href="/">
<a>{t(`nav:home`)}</a>
</Link>
</li>
<li>
<Link href="/features">
<a>{t(`nav:features`)}</a>
</Link>
</li>
<li>
<Link href="/about">
<a>{t(`nav:about`)}</a>
</Link>
</li>
<li>
<Link href="/blog">
<a>{t(`nav:blog`)}</a>
</Link>
</li>
<li>
<Link href="/contact">
<a>{t(`nav:contact`)}</a>
</Link>
</li>
<li>
<MyListbox router={router} />
</li>
</ul>
<div className="mt-6 border-t border-gray-200 pt-6 dark:border-gray-200/10">
<button
aria-label="Toggle Dark Mode"
type="button"
className="general-ring-state flex w-full items-center justify-center rounded-full bg-gray-200 py-3 dark:bg-neutral-700"
onClick={() =>
setTheme(resolvedTheme === `dark` ? `light` : `dark`)
}
>
{mounted && (
<>
<div>
{resolvedTheme === `dark` ? (
<BsSunFill size={18} />
) : (
<BsMoonFill size={18} />
)}
</div>
{resolvedTheme === `dark` ? (
<p className="ml-3 font-semibold">
{t(`common:switch-theme-light`)}
</p>
) : (
<p className="ml-3 font-semibold">
{t(`common:switch-theme-dark`)}
</p>
)}
</>
)}
</button>
</div>
</div>
</Transition.Child>
</Dialog>
</Transition>
</div>
</div>
</>
)
}
Example #18
Source File: code.tsx From pagely with MIT License | 4 votes |
Page = () => {
const router = useRouter();
const { data } = useClerkSWR<ghSites>(
`/api/getSiteData/github/?siteId=${router.query.siteId}`
);
const [css, setCss] = useState<string>(data?.customCss);
const [head, setHead] = useState<string>(data?.customHead);
let [isOpen, setIsOpen] = useState(false);
const [isLoading, setIsLoading] = useState(false);
const urlWithSession = useUserWithSession('/api/updateSiteData/github/code');
function closeModal() {
setIsOpen(false);
}
function openModal() {
setIsOpen(true);
}
useEffect(() => {
window.addEventListener('keydown', (e) => {
if (e.metaKey && e.key === 's') {
e.preventDefault();
document.getElementById('update-custom-code-btn').click();
}
});
}, []);
return (
<div>
<div>
<GitHubSiteLayout activeTab='code'>
<h1 className='text-4xl font-extrabold'>Code Injection</h1>
<p className='mt-4 text-gray-800 font-base'>
{data?.siteName || 'Just a second...'}
</p>
<div className='my-3'>
<button
onClick={openModal}
className='px-2 py-1 text-green-600 border border-green-500 rounded shadow bg-green-50 hover:bg-green-100 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-green-200'>
Open styling tools
</button>
</div>
<div className='mt-8'>
<p className='my-3 font-mono text-xl font-bold text-gray-500'>{`<style>`}</p>
<TextareaAutosize
spellCheck={false}
value={css}
onChange={(e) => setCss(e.target.value)}
className='w-[70vw] py-5 font-mono border text-sm min-h-[100px] border-gray-600 rounded-md shadow-sm block text-gray-500 focus:outline-none focus:border-gray-700 focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-gray-500'
onKeyDown={(e) => handleHotkeys(e)}
/>
<p className='my-3 font-mono text-xl font-bold text-gray-500'>{`</style>`}</p>
</div>
<hr className='my-10 text-gray-300' />
<div className='mt-8'>
<p className='my-3 font-mono text-xl font-bold text-gray-500'>{`<head>`}</p>
<TextareaAutosize
spellCheck={false}
value={head}
onChange={(e) => setHead(e.target.value)}
className='w-[70vw] py-5 font-mono border text-sm min-h-[100px] border-gray-600 rounded-md shadow-sm block text-gray-500 focus:outline-none focus:border-gray-700 focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-gray-500'
/>
<p className='my-3 font-mono text-xl font-bold text-gray-500'>{`</head>`}</p>
<div className='my-10'>
<button
id='update-custom-code-btn'
onClick={() => {
setIsLoading(true);
axios
.post(urlWithSession, {
customCss: css,
customHead: head,
siteId: data.id,
})
.then((res) => {
console.log(res);
toast.success('Successfully updated site code.', {
duration: 5000,
});
setIsLoading(false);
});
}}
className={`h-10 px-3 mb-10 bg-gray-800 rounded shadow-md text-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-800 hover:bg-gray-700 ${
isLoading && 'opacity-50 cursor-wait'
}`}>
Update Custom Code
</button>
<p className='mt-3 text-base text-gray-600'>
You can press <b>Cmd + S</b> to save the code too ✌️
</p>
</div>
</div>
</GitHubSiteLayout>
<Transition appear show={isOpen} as={Fragment}>
<Dialog
as='div'
className='fixed inset-0 z-10 overflow-y-auto'
onClose={closeModal}>
<div className='min-h-screen px-4 text-center'>
<Transition.Child
as={Fragment}
enter='ease-out duration-300'
enterFrom='opacity-0'
enterTo='opacity-100'
leave='ease-in duration-200'
leaveFrom='opacity-100'
leaveTo='opacity-0'>
<Dialog.Overlay className='fixed inset-0 backdrop-filter backdrop-blur-sm bg-white/40' />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span
className='inline-block h-screen align-middle'
aria-hidden='true'>
​
</span>
<Transition.Child
as={Fragment}
enter='ease-out duration-300'
enterFrom='opacity-0 scale-95'
enterTo='opacity-100 scale-100'
leave='ease-in duration-200'
leaveFrom='opacity-100 scale-100'
leaveTo='opacity-0 scale-95'>
<div className='inline-block w-full max-w-3xl p-6 my-8 overflow-hidden text-left align-middle transition-all transform bg-white border rounded-md shadow-xl border-gray-500/40'>
<Dialog.Title
as='h3'
className='text-lg font-medium leading-6 text-gray-900'>
CSS Utilities ?
</Dialog.Title>
<div className='mt-2 mb-10'>
<p className='text-sm text-gray-500'>
A tiny set of utilities to help you style your app and
make it look great. Many more utilities are coming soon.
</p>
<hr className='w-full mx-auto my-5 text-gray-200' />
<Utility />
</div>
<div className='mt-4'>
<button
type='button'
className='inline-flex justify-center px-4 py-1 text-sm font-medium text-blue-900 bg-blue-100 border border-blue-500 rounded-md hover:bg-blue-200 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-blue-500'
onClick={openModal}>
Thanks!
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
</div>
</div>
);
}
Example #19
Source File: SettingsModal.tsx From ide with Mozilla Public License 2.0 | 4 votes |
SettingsModal = ({
isOpen,
onClose,
}: SettingsDialogProps): JSX.Element => {
const {
settings: realWorkspaceSettings,
setSettings: setRealWorkspaceSettings,
} = useSettings();
const userRef = useAtomValue(authenticatedUserRefAtom);
const dirtyRef = useRef<boolean>(false);
const [workspaceSettings, setWorkspaceSettings] = useReducer(
(prev: WorkspaceSettings, next: Partial<WorkspaceSettings>) => {
return {
...prev,
...next,
};
},
realWorkspaceSettings
);
const [userPermission] = useAtom(actualUserPermissionAtom);
const [name, setName] = useState<string>('');
const [editorMode, setEditorMode] = useState<EditorMode>('Normal');
const [tabSize, setTabSize] = useState<number>(4);
const [lightMode, setLightMode] = useState<boolean>(false);
const [userSettings, setUserSettings] = useAtom(
userSettingsAtomWithPersistence
);
const [tab, setTab] = useState<typeof tabs[number]['id']>('workspace');
const [actualDisplayName, setDisplayName] = useAtom(displayNameAtom);
useEffect(() => {
if (isOpen) {
setWorkspaceSettings(realWorkspaceSettings);
setName(actualDisplayName);
setEditorMode(userSettings.editorMode);
setTabSize(userSettings.tabSize);
setLightMode(userSettings.lightMode);
dirtyRef.current = false;
setTab('workspace');
}
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [isOpen]);
const closeWithoutSaving = () => {
if (dirtyRef.current) {
if (
confirm('Are you sure you want to exit without saving your changes?')
) {
onClose();
}
} else {
onClose();
}
};
const saveAndClose = async () => {
if (!name) {
alert('User Name cannot be empty. Fix before saving.');
return;
}
let settingsToSet: Partial<WorkspaceSettings> = workspaceSettings;
{
// update has no effect if you try to overwrite creation time
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const { creationTime, ...toKeep } = settingsToSet;
settingsToSet = toKeep;
}
if (userPermission === 'READ_WRITE') {
// update has no effect if you try to overwrite default permission
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const { defaultPermission, ...toKeep } = settingsToSet;
settingsToSet = toKeep;
}
setRealWorkspaceSettings(settingsToSet);
setUserSettings({ editorMode, tabSize, lightMode });
if (name !== actualDisplayName) {
setDisplayName(name);
userRef?.child('name').set(name);
}
onClose();
};
const onChange = (data: Partial<WorkspaceSettings>): void => {
dirtyRef.current = true;
setWorkspaceSettings(data);
};
return (
<Transition.Root show={isOpen} as={Fragment}>
<Dialog
as="div"
static
className="fixed z-10 inset-0 overflow-y-auto"
open={isOpen}
onClose={() => closeWithoutSaving()}
>
<div className="flex items-end justify-center min-h-full pt-4 pb-20 text-center sm:block sm:p-0">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-black bg-opacity-75 transition-opacity" />
</Transition.Child>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
enterTo="opacity-100 translate-y-0 sm:scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 translate-y-0 sm:scale-100"
leaveTo="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
>
<div className="inline-block bg-white md:rounded-lg text-left overflow-hidden shadow-xl transform transition-all sm:my-8 sm:max-w-2xl w-full">
<div className="px-4 sm:px-6 pt-4 pb-2">
<Dialog.Title
as="h3"
className="text-lg leading-6 font-medium text-gray-900 text-center"
>
Settings
</Dialog.Title>
</div>
<div>
<div className="border-b border-gray-200">
<nav className="-mb-px flex">
{tabs.map(settingTab => (
<button
className={classNames(
tab === settingTab.id
? 'border-indigo-500 text-indigo-600'
: 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300',
'w-1/2 group flex items-center justify-center py-3 px-1 border-b-2 font-medium text-sm focus:outline-none'
)}
onClick={() => setTab(settingTab.id)}
key={settingTab.id}
>
<settingTab.icon
className={classNames(
tab === settingTab.id
? 'text-indigo-500'
: 'text-gray-400 group-hover:text-gray-500',
'-ml-0.5 mr-2 h-5 w-5'
)}
/>
{settingTab.label}
</button>
))}
</nav>
</div>
</div>
<div className="p-4 sm:p-6 space-y-6">
{tab === 'user' && (
<UserSettings
name={name || ''}
onNameChange={name => {
setName(name);
dirtyRef.current = true;
}}
editorMode={editorMode}
onEditorModeChange={mode => {
setEditorMode(mode);
dirtyRef.current = true;
}}
tabSize={tabSize}
onTabSizeChange={size => {
setTabSize(size);
dirtyRef.current = true;
}}
lightMode={lightMode}
onLightModeChange={lightMode => {
setLightMode(lightMode);
dirtyRef.current = true;
}}
/>
)}
{tab === 'workspace' && (
<WorkspaceSettingsUI
workspaceSettings={workspaceSettings}
onWorkspaceSettingsChange={onChange}
userPermission={userPermission || 'READ'}
/>
)}
{tab === 'judge' && (
<JudgeSettings
workspaceSettings={workspaceSettings}
onWorkspaceSettingsChange={onChange}
userPermission={userPermission || 'READ'}
/>
)}
<div className="flex items-center space-x-4">
<button
type="button"
className="inline-flex items-center px-4 py-2 border border-gray-300 shadow-sm text-sm font-medium rounded-md text-gray-700 bg-white hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
onClick={() => closeWithoutSaving()}
>
Cancel
</button>
<button
type="button"
className="inline-flex justify-center py-2 px-4 border border-transparent rounded-md shadow-sm text-sm font-medium text-white bg-indigo-600 hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
onClick={() => saveAndClose()}
>
Save
</button>
{tab == 'judge' && (
<button
type="button"
className="inline-flex items-center px-4 py-2 border border-gray-300 shadow-sm text-sm font-medium rounded-md text-gray-700 bg-white hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
onClick={() => {
onChange({
problem: undefined,
});
}}
>
Clear
</button>
)}
</div>
{tab === 'user' && (
<>
<hr className="border-gray-200" />
<SignInSettings />
</>
)}
</div>
<div className="absolute top-0 right-0 pt-4 pr-4">
<button
type="button"
className="bg-white rounded-md text-gray-400 hover:text-gray-500 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
onClick={() => closeWithoutSaving()}
>
<span className="sr-only">Close</span>
<XIcon className="h-6 w-6" aria-hidden="true" />
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition.Root>
);
}
Example #20
Source File: ConfirmOverrideModal.tsx From ide with Mozilla Public License 2.0 | 4 votes |
ConfirmOverrideModal = (): JSX.Element => {
const [confirmOverrideDataCallback, setConfirmOverrideDataCallback] = useAtom(
confirmOverrideDataCallbackAtom
);
return (
<Transition.Root show={!!confirmOverrideDataCallback} as={Fragment}>
<Dialog
as="div"
open={!!confirmOverrideDataCallback}
className="fixed z-10 inset-0 overflow-y-auto"
onClose={() => setConfirmOverrideDataCallback(null)}
>
<div className="flex items-end justify-center min-h-screen pt-4 px-4 pb-20 text-center sm:block sm:p-0">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-gray-500 bg-opacity-75 transition-opacity" />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span
className="hidden sm:inline-block sm:align-middle sm:h-screen"
aria-hidden="true"
>
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
enterTo="opacity-100 translate-y-0 sm:scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 translate-y-0 sm:scale-100"
leaveTo="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
>
<div className="inline-block align-bottom bg-white rounded-lg px-4 pt-5 pb-4 text-left overflow-hidden shadow-xl transform transition-all sm:my-8 sm:align-middle sm:max-w-lg sm:w-full sm:p-6">
<div className="sm:flex sm:items-start">
<div className="mx-auto flex-shrink-0 flex items-center justify-center h-12 w-12 rounded-full bg-red-100 sm:mx-0 sm:h-10 sm:w-10">
<ExclamationIcon
className="h-6 w-6 text-red-600"
aria-hidden="true"
/>
</div>
<div className="mt-3 text-center sm:mt-0 sm:ml-4 sm:text-left">
<Dialog.Title
as="h3"
className="text-lg leading-6 font-medium text-gray-900"
>
Override Local Data?
</Dialog.Title>
<div className="mt-2">
<p className="text-sm text-gray-500">
Your local data will be overwritten by your server data.
Are you sure you want to proceed?
</p>
</div>
</div>
</div>
<div className="mt-5 sm:mt-4 sm:flex sm:flex-row-reverse">
<button
type="button"
className="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm"
onClick={() =>
confirmOverrideDataCallback!().then(() =>
setConfirmOverrideDataCallback(null)
)
}
>
Override Data
</button>
<button
type="button"
className="mt-3 w-full inline-flex justify-center rounded-md border border-gray-300 shadow-sm px-4 py-2 bg-white text-base font-medium text-gray-700 hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 sm:mt-0 sm:w-auto sm:text-sm"
onClick={() => setConfirmOverrideDataCallback(null)}
>
Cancel
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition.Root>
);
}
Example #21
Source File: view-hours.tsx From cpinitiative with Mozilla Public License 2.0 | 4 votes |
export default function ViewHours() {
const { data: session } = useSession()
const [viewAddHoursForm, setViewAddHoursForm] = React.useState(false)
// add conditional fetching for useSWR so that it doesn't fetch when the user isn't signed in
const { data, error } = useSWR(session ? "/api/getHours" : null, SWR_FETCHER)
// console.log(data, error)
return (
<Layout>
<SEO
title="View Volunteer Hours"
description="Volunteer hour portal for CPInitiative"
/>
<div className="flex flex-col w-full h-full items-center px-4">
<Header />
{session && (
<div className="w-full max-w-4xl pt-24">
<div className="w-full mt-4 mb-10">
<div className="grid w-full grid-rows-6 grid-cols-none md:grid-rows-2 md:grid-cols-1 md:grid-flow-col gap-3">
<div className="row-span-3 bg-white p-3 flex flex-col rounded-md shadow-lg text-5xl font-extrabold">
<h1 className="m-auto text-purple-900 underline text-center">
{session?.user?.name}
</h1>
<h3 className="mx-auto mb-6 text-purple-800 text-sm">
Email: {session?.user?.email}
</h3>
</div>
<div className="flex bg-white flex-col px-3 py-5 col-span-2 row-span-2 rounded-lg shadow-lg">
{data ? (
<p className="text-purple-800 font-semibold text-3xl m-auto">
<b>{Math.round(data?.totalHours * 100) / 100}</b> hours
volunteered
</p>
) : (
// spinner
<div className="flex items-center justify-center ">
<div className="w-16 h-16 border-b-2 border-gray-900 rounded-full animate-spin"></div>
</div>
)}
</div>
<button
type="button"
disabled={!data}
onClick={() => setViewAddHoursForm(true)}
className="flex cursor-pointer px-3 shadow-lg rounded-lg row-span-1 col-span-1 bg-gradient-to-r from-purple-600 to-indigo-600 hover:from-purple-700 hover:to-indigo-700 disabled:saturate-50"
>
<p className="text-white text-base font-medium m-auto">
Add Volunteer Hours
</p>
</button>
<button
type="button"
onClick={() => signOut()}
className="flex cursor-pointer p-3 shadow-lg rounded-lg row-span-1 col-span-1 bg-gradient-to-r from-purple-600 to-indigo-600 hover:from-purple-700 hover:to-indigo-700"
>
<p className="text-white text-base font-medium m-auto">
Sign out
</p>
</button>
</div>
</div>
{/* <div>
<div className="w-full flex flex-col md:flex-row justify-between">
<div>
<button
onClick={() => setViewAddHoursForm(true)}
className="inline-flex px-4 py-2 border border-transparent text-base font-medium rounded-md shadow-sm text-white bg-gradient-to-r from-purple-600 to-indigo-600 hover:from-purple-700 hover:to-indigo-700"
>
Add Volunteer Hours
</button>
<button
onClick={() => signOut()}
className="inline-flex px-4 ml-4 py-2 border border-transparent text-base font-medium rounded-md shadow-sm text-white bg-gradient-to-r from-purple-600 to-indigo-600 hover:from-purple-700 hover:to-indigo-700"
>
Sign out
</button>
</div>
</div>
</div> */}
<VolunteerHourHistory data={data} />
{viewAddHoursForm && (
<>
<div className="flex fixed items-end justify-center min-h-screen pt-4 px-4 pb-20 text-center sm:block sm:p-0" />
<div
className="fixed inset-0 bg-gray-500 bg-opacity-75 transition-opacity"
aria-hidden="true"
></div>
</>
)}
<Transition appear show={viewAddHoursForm} as={Fragment}>
<Dialog
as="div"
className="fixed inset-0 z-10 pt-10 overflow-auto"
onClose={() => setViewAddHoursForm(false)}
>
<div className="min-h-screen px-4 text-center">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0" />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span
className="inline-block h-screen align-middle"
aria-hidden="true"
>
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="inline-block w-full max-w-5xl p-6 mt-8 overflow-hidden text-left align-middle transition-all transform bg-white shadow-xl rounded-2xl">
<Dialog.Title
as="h3"
className="text-lg font-medium leading-6 text-gray-900"
>
Add your hours
</Dialog.Title>
<AddVolunteerHoursForm
onClose={() => setViewAddHoursForm(false)}
data={data}
/>
{/* <div className="">
<button
type="button"
className="inline-flex justify-center px-4 py-2 text-sm font-medium text-blue-900 bg-blue-100 border border-transparent rounded-md hover:bg-blue-200 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-blue-500"
onClick={() => setViewAddHoursForm(false)}
>
Close
</button>
</div> */}
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
</div>
)}
{!session && (
<div className="w-full max-w-7xl pt-24">
<div className="w-full flex flex-row justify-between my-6">
<h1 className="text-4xl font-semibold">
You're not signed in.{" "}
<button
type="button"
onClick={() => signIn("google")}
className="text-blue-400 cursor-pointer underline"
>
Sign in?
</button>
</h1>
</div>
</div>
)}
</div>
</Layout>
)
}
Example #22
Source File: EventDetailsSlideOut.tsx From platform with MIT License | 4 votes |
export default function EventDetailsSlideOut(props: any) {
const { slideState, user, setIsSlideOutOpen } = props;
const { open, eventDetails } = slideState;
function selectImage(type) {
if (type?.includes("junior")) {
return JuniorRapidPlay;
}
switch (type) {
case "congress":
return OpenCongress;
case "rapidplay":
return OpenRapidPlay;
default:
return OpenCongress;
}
}
// TODO: add address information to event details:
function addressLookup(name) {
if (name?.includes("IGS")) {
return "Ilkley Grammar School, Armitage Hall, LS29 8TH";
}
if (name?.includes("Festival")) {
return "King's Hall & Winter Garden, Station Road, Ilkley, LS29 8HB";
}
return "Unit 8, Crescent Court, Ilkely, LS29 8DE";
}
return (
<Transition.Root show={open} as={Fragment}>
<Dialog
as="div"
static
className="fixed inset-10 top-10 z-50"
open={open}
onClose={() =>
setIsSlideOutOpen((state) => ({ ...state, open: false }))
}
>
<div className="absolute inset-0 overflow-hidden">
<Dialog.Overlay className="absolute inset-0" />
<div className="fixed inset-y-0 right-0 pl-2 max-w-full flex sm:pl-2">
<Transition.Child
as={Fragment}
enter="transform transition ease-in-out duration-500 sm:duration-700"
enterFrom="translate-x-full"
enterTo="translate-x-0"
leave="transform transition ease-in-out duration-500 sm:duration-700"
leaveFrom="translate-x-0"
leaveTo="translate-x-full"
>
<div className="w-screen max-w-md">
<div className="h-full flex flex-col bg-white shadow-xl overflow-y-scroll mr-2 sm:mr-0">
<div className="px-4 py-6 sm:px-6">
<div className="flex items-start justify-between">
<h2
id="slide-over-heading"
className="text-2xl tracking-tight leading-10 font-extrabold text-gray-900 sm:text-3xl sm:leading-none"
>
{eventDetails.name || eventDetails.type?.name}
</h2>
<div className="ml-3 h-7 flex items-center">
<button
autoFocus={false}
className="bg-white z-50 rounded-md text-gray-400 hover:text-gray-500 focus:ring-2 focus:ring-teal-500"
onClick={() =>
setIsSlideOutOpen((state) => ({
...state,
open: false,
}))
}
>
<span className="sr-only">Close panel</span>
<XIcon
className="h-6 w-6 border-none"
aria-hidden="true"
/>
</button>
</div>
</div>
</div>
<div className="mb-4">
<div className="pb-1 sm:pb-6">
<div>
<div
className={classNames(
eventDetails.type?.color === "blue"
? "border-blue-brand"
: borderColor600[eventDetails.type?.color],
"border-4 relative h-52 rounded-md"
)}
>
<img
className="border-gray-200 border-4 absolute h-full w-full object-cover "
src={selectImage(eventDetails.type?.eventType)}
alt="Playing Hall"
/>
</div>
</div>
</div>
<div className="px-2 pt-2 pb-5 sm:px-0 sm:pt-0">
<dl className="space-y-4 px-2 sm:px-6 sm:space-y-4">
<div>
<dt className="text-sm font-medium text-teal-700 sm:w-40 sm:flex-shrink-0">
<i className="fas fa-info-square text-gray-900 mr-1"></i>{" "}
Description
</dt>
<dd className="mt-1 text-sm text-gray-900 sm:col-span-2">
<p>
{eventDetails.description
? eventDetails.description
: eventDetails.type?.description}
</p>
</dd>
</div>
<div>
<dt className="text-sm font-medium text-teal-700 sm:w-40 sm:flex-shrink-0">
<i className="fad fa-map-pin text-gray-900 mr-1"></i>{" "}
Location
</dt>
<dd className="mt-1 text-sm text-gray-900 sm:col-span-2">
{addressLookup(eventDetails?.name)}
</dd>
</div>
<div>
<dt className="text-sm font-medium text-teal-700 sm:w-40 sm:flex-shrink-0">
<i className="fad fa-chess-clock text-gray-900 mr-1"></i>{" "}
Time Control
</dt>
<dd className="mt-1 text-sm text-gray-900 sm:col-span-2">
{eventDetails.type?.timeControl}
</dd>
</div>
<div>
<dt className="text-sm font-medium text-teal-700 sm:w-40 sm:flex-shrink-0">
<i className="fad fa-calendar-alt text-gray-900 mr-1"></i>{" "}
Date
</dt>
<dd className="mt-1 text-sm text-gray-900 sm:col-span-2">
{prettyDate(
eventDetails.startDate,
eventDetails.endDate
)}
</dd>
</div>
<div>
{eventDetails.entries?.items.length > 0 && (
<>
<dt className="text-sm font-medium text-teal-700 sm:w-40 sm:flex-shrink-0">
<i className="fad fa-users mr-1 text-gray-900"></i>{" "}
Entries{" "}
<span className="text-gray-500 text-xs">{`( ${eventDetails.entries?.items.length} )`}</span>
</dt>
<dd className="mt-1 text-sm text-gray-900 sm:col-span-2">
<EntriesTable
user={user}
eventDetails={eventDetails}
/>
</dd>
</>
)}
</div>
</dl>
</div>
<div className="px-4 sm:flex sm:items-end sm:px-6 mb-2">
<div className="sm:flex-1">
<div className="mt-5 flex flex-wrap space-y-3 sm:space-y-0 sm:space-x-3">
<button
onClick={() =>
setIsSlideOutOpen((state) => ({
...state,
open: false,
}))
}
type="button"
className="inline-flex items-center px-4 py-2 border border-gray-300 rounded-md shadow-sm text-sm font-medium text-gray-700 bg-white hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
>
Close
</button>
</div>
</div>
</div>
<div className="text-right mr-2 -mt-10">
<QuickSearch tag="events" />
</div>
</div>
</div>
</div>
</Transition.Child>
</div>
</div>
</Dialog>
</Transition.Root>
);
}
Example #23
Source File: BetaSlideOut.tsx From platform with MIT License | 4 votes |
export default function BetaSlideOut(props) {
const { slideState, setIsSlideOutOpen } = props;
const { open } = slideState;
const mailToSupport = () => {
const userAgent = window.navigator.userAgent
return `mailto:[email protected]?subject=Support%20Issue&Body=%0D%0A// ---- DO NOT DELETE ----//%0D%0A Device: ${userAgent} %0D%0A// ---- THANK YOU ----//%0D%0A%0D%0A`
}
return (
<Transition.Root show={open} as={Fragment}>
<Dialog
as="div"
static
className="fixed inset-10 top-10 z-50"
open={open}
onClose={() =>
setIsSlideOutOpen((state) => ({ ...state, open: false }))
}
>
<div className="absolute inset-0 overflow-hidden">
<Dialog.Overlay className="absolute inset-0" />
<div className="fixed inset-y-0 right-0 pl-2 max-w-full flex sm:pl-2">
<Transition.Child
as={Fragment}
enter="transform transition ease-in-out duration-500 sm:duration-700"
enterFrom="translate-x-full"
enterTo="translate-x-0"
leave="transform transition ease-in-out duration-500 sm:duration-700"
leaveFrom="translate-x-0"
leaveTo="translate-x-full"
>
<div className="w-screen max-w-md">
<div className="h-full flex flex-col bg-white shadow-xl overflow-y-scroll mr-2 sm:mr-0">
<div className="px-4 py-6 sm:px-6">
<div className="flex items-start justify-between">
<h2
id="slide-over-heading"
className="text-2xl m-auto tracking-tight leading-10 font-extrabold text-blue-500 sm:text-3xl sm:leading-none"
>
<span className="text-gray-400 text-sm font-normal">It can only get </span>Beta ...
</h2>
<div className="ml-3 h-7 flex items-center">
<button
className="bg-white z-100 rounded-md text-gray-400 hover:text-gray-500 focus:ring-2 focus:ring-teal-500"
onClick={() =>
setIsSlideOutOpen((state) => ({
...state,
open: false,
}))
}
>
<span className="sr-only">Close panel</span>
<XIcon
className="h-6 w-6 border-none"
aria-hidden="true"
/>
</button>
</div>
</div>
</div>
<div>
<div className="text-center">
<h3 className="mt-2 text-sm font-medium text-gray-900 mb-4">
We prioritise our efforts on most popular devices.
</h3>
<p className="mt-1 text-sm text-gray-500 px-6 mb-4">
Unfortunately this means not everyone's experience is optimal. ?
</p>
<img src={Devices} alt="device stats" className="h-128 m-auto" />
<h3 className="mt-2 text-sm font-medium text-gray-900">
Spotted an issue?
</h3>
<p className="mt-1 text-sm text-gray-500">
Send us a quick screenshot and we'll get right on it!
</p>
<div className="mt-6">
<a href={mailToSupport()}
className="inline-flex items-center px-4 py-2 border border-transparent shadow-sm text-sm font-medium rounded-md text-white bg-teal-600 hover:bg-teal-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-teal-500"
>
<PlusIcon
className="-ml-1 mr-2 h-5 w-5"
aria-hidden="true"
/>
Raise Issue
</a>
</div>
</div>
<div className="px-4 sm:flex sm:items-end sm:px-6 mb-2">
<div className="sm:flex-1">
<div className="mt-5 flex flex-wrap space-y-3 sm:space-y-0 sm:space-x-3">
<button
onClick={() =>
setIsSlideOutOpen((state) => ({
...state,
open: false,
}))
}
type="button"
className="w-full text-center items-center px-4 py-2 border border-gray-300 rounded-md shadow-sm text-sm font-medium text-gray-700 bg-white hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-teal-500"
>
Close
</button>
</div>
</div>
</div>
</div>
</div>
</div>
</Transition.Child>
</div>
</div>
</Dialog>
</Transition.Root>
);
}
Example #24
Source File: PaymentCompleteModal.tsx From platform with MIT License | 4 votes |
export default function PaymentCompleteModal(props) {
const { open, setOpen } = props;
const cancelButtonRef = useRef();
return (
<Transition.Root show={open} as={Fragment}>
<Dialog
as="div"
static
className="fixed z-10 inset-0 overflow-y-auto"
initialFocus={cancelButtonRef}
open={open}
onClose={setOpen}
>
<div className="flex items-end justify-center min-h-screen pt-4 px-4 pb-20 text-center sm:block sm:p-0">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-gray-500 bg-opacity-75 transition-opacity" />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span
className="hidden sm:inline-block sm:align-middle sm:h-screen"
aria-hidden="true"
>
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
enterTo="opacity-100 translate-y-0 sm:scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 translate-y-0 sm:scale-100"
leaveTo="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
>
<div className="inline-block align-bottom bg-white rounded-lg px-4 pt-5 pb-4 text-left overflow-hidden shadow-xl transform transition-all sm:my-8 sm:align-middle sm:max-w-lg sm:w-full sm:p-6">
<div>
<div className="mx-auto flex items-center justify-center h-12 w-12 rounded-full bg-green-100">
<CheckIcon
className="h-6 w-6 text-green-600"
aria-hidden="true"
/>
</div>
<div className="mt-3 text-center sm:mt-5">
<Dialog.Title
as="h3"
className="text-lg leading-6 font-medium text-gray-900"
>
Payment successful
</Dialog.Title>
<div className="mt-2">
<p className="text-sm text-gray-500">
You have now been registered!
</p>
<p className="text-sm text-gray-500">
Your name will appear in <span>yellow</span> in our
entries list.
</p>
</div>
</div>
</div>
<div className="mt-5 sm:mt-6">
<button
type="button"
className="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-teal-600 text-base font-medium text-white hover:bg-teal-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-teal-500 sm:col-start-2 sm:text-sm"
onClick={() => setOpen(false)}
>
Great!
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition.Root>
);
}
Example #25
Source File: modal.tsx From arkadiko with GNU General Public License v3.0 | 4 votes |
export function Modal({
open,
children,
title,
icon,
closeModal,
buttonText,
buttonAction,
buttonDisabled,
initialFocus,
}: Props) {
const actionButtonRef = useRef(null);
return (
<Transition.Root show={open} as={Fragment}>
<Dialog
as="div"
className="fixed inset-0 z-50 overflow-y-auto"
initialFocus={initialFocus}
onClose={closeModal}
>
<div className="flex items-end justify-center min-h-screen px-4 pt-4 pb-20 text-center sm:block sm:p-0">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 transition-opacity bg-gray-500 bg-opacity-75 dark:bg-zinc-600 dark:bg-opacity-80" />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span className="hidden sm:inline-block sm:align-middle sm:h-screen" aria-hidden="true">
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
enterTo="opacity-100 translate-y-0 sm:scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 translate-y-0 sm:scale-100"
leaveTo="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
>
<div className="inline-block px-4 pt-5 pb-4 overflow-hidden text-left align-bottom transition-all transform bg-white rounded-lg shadow-xl dark:bg-zinc-800 sm:my-8 sm:align-middle sm:max-w-lg sm:w-full sm:p-6">
<div className="absolute top-0 right-0 hidden pt-4 pr-4 sm:block">
<button
type="button"
className="text-gray-400 bg-white rounded-md dark:bg-zinc-800 hover:text-gray-500 dark:hover:text-zinc-400 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
onClick={closeModal}
>
<span className="sr-only">Close</span>
<StyledIcon as="XIcon" solid={false} size={6} />
</button>
</div>
<div>
{icon ? (
<div className="flex items-center justify-center mx-auto rounded-full">
{icon}
</div>
) : null}
<div className="mt-3 sm:mt-5">
<Dialog.Title
as="h3"
className="text-lg leading-6 text-center text-gray-900 dark:text-zinc-100 font-headings"
>
{title}
</Dialog.Title>
<div className="mt-2">{children}</div>
</div>
</div>
<div className="mt-5 sm:mt-6 sm:grid sm:grid-cols-2 sm:gap-3 sm:grid-flow-row-dense">
<button
type="button"
className="inline-flex justify-center w-full px-4 py-2 text-base font-medium text-white bg-indigo-600 border border-transparent rounded-md shadow-sm hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 sm:col-start-2 sm:text-sm disabled:bg-gray-100 disabled:text-gray-500 disabled:cursor-not-allowed"
disabled={buttonDisabled}
onClick={buttonAction}
ref={actionButtonRef}
>
{buttonText}
</button>
<button
type="button"
className="inline-flex justify-center w-full px-4 py-2 mt-3 text-base font-medium text-gray-700 bg-white border border-gray-300 rounded-md shadow-sm hover:bg-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500 sm:mt-0 sm:col-start-1 sm:text-sm"
onClick={closeModal}
>
Cancel
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition.Root>
);
}
Example #26
Source File: tx-sidebar.tsx From arkadiko with GNU General Public License v3.0 | 4 votes |
TxSidebar = ({ showSidebar, setShowSidebar }) => {
const address = useSTXAddress();
const [isLoading, setIsLoading] = useState(true);
const [transactions, setTransactions] = useState<JSX.Element[]>();
const [pendingTransactions, setPendingTransactions] = useState<JSX.Element[]>();
const [networks, setNetworks] = useState([]);
const [selectedNetworkKey, setSelectedNetworkKey] = useState(
JSON.parse(localStorage.getItem('arkadiko-stacks-node') || JSON.stringify(DEFAULT_NETWORKS[0]))
.key
);
const selectedNetwork = networks.find(network => network.key === selectedNetworkKey);
const [networkName, setNetworkName] = useState('');
const [networkAddress, setNetworkAddress] = useState('');
const [networkKey, setNetworkKey] = useState('');
const onInputChange = (event: { target: { name: any; value: any } }) => {
const value = event.target.value;
if (event.target.name === 'networkName') {
setNetworkName(value);
} else if (event.target.name === 'networkAddress') {
setNetworkAddress(value);
} else if (event.target.name === 'networkKey') {
setNetworkKey(value);
}
};
const addNewNetwork = () => {
const networks = JSON.parse(localStorage.getItem('arkadiko-stacks-nodes') || '[]');
const network = {
name: networkName,
url: networkAddress,
key: networkKey,
};
networks.push(network);
localStorage.setItem('arkadiko-stacks-nodes', JSON.stringify(networks));
setSelectedNetworkKey(network);
};
useEffect(() => {
const network = JSON.parse(localStorage.getItem('arkadiko-stacks-node')) || networks[0];
if (showSidebar && selectedNetwork['url'] != network['url']) {
localStorage.setItem('arkadiko-stacks-node', JSON.stringify(selectedNetwork));
window.location.reload();
}
}, [selectedNetwork]);
useEffect(() => {
let mounted = true;
const fetchTransactions = async () => {
if (mounted && address) {
setIsLoading(true);
const txs = await getAccountTransactions(address || '', CONTRACT_ADDRESS || '');
let index = 0;
const txMap = txs.map((tx: ContractCallTransaction) => {
let status = 'error';
if (tx.tx_status === 'success') {
status = 'success';
} else if (tx.tx_status === 'pending') {
status = 'pending';
}
index += 1;
return <ContractTransaction key={index} transaction={tx} status={status} />;
});
setTransactions(txMap);
const pending = await getPendingTransactions(address || '', CONTRACT_ADDRESS || '');
const pendingMap = pending.map((tx: MempoolContractCallTransaction) => {
index += 1;
return <ContractTransaction key={index} transaction={tx} status="pending" />;
});
setPendingTransactions(pendingMap);
setIsLoading(false);
}
};
const setAllNetworks = () => {
const addedNetworks = JSON.parse(localStorage.getItem('arkadiko-stacks-nodes') || '[]');
setNetworks(DEFAULT_NETWORKS.concat(addedNetworks));
};
setAllNetworks();
if (showSidebar) {
fetchTransactions();
}
return () => {
mounted = false;
};
}, [showSidebar]);
return (
<Transition show={showSidebar} as={Fragment}>
<Dialog
as="div"
className="fixed inset-0 z-50 overflow-hidden"
onClose={() => {
setShowSidebar(false);
}}
>
<div className="absolute inset-0 overflow-hidden">
<Transition.Child
as={Fragment}
enter="ease-in-out duration-500"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in-out duration-500"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="absolute inset-0 transition-opacity bg-gray-700 bg-opacity-50" />
</Transition.Child>
<div className="fixed inset-y-0 right-0 flex max-w-full pl-10">
<Transition.Child
as={Fragment}
enter="transform transition ease-in-out duration-500 sm:duration-700"
enterFrom="translate-x-full"
enterTo="translate-x-0"
leave="transform transition ease-in-out duration-500 sm:duration-700"
leaveFrom="translate-x-0"
leaveTo="translate-x-full"
>
<div className="w-screen max-w-md">
<div className="flex flex-col h-full overflow-y-scroll bg-white shadow-xl dark:bg-zinc-800">
<div className="px-4 py-6 bg-indigo-700 sm:px-6">
<div className="flex items-start justify-between">
<Dialog.Title className="text-lg text-white font-headings">
Network Settings
</Dialog.Title>
<div className="flex items-center ml-3 h-7">
<button
type="button"
className="text-indigo-200 bg-indigo-700 rounded-md hover:text-white focus:outline-none focus:ring-2 focus:ring-white"
onClick={() => {
setShowSidebar(false);
}}
>
<span className="sr-only">Close panel</span>
<StyledIcon as="XIcon" size={6} solid={false} />
</button>
</div>
</div>
<div className="mt-1">
<p className="text-sm text-indigo-300">Switch between networks easily</p>
</div>
</div>
<div className="relative px-4 my-6 sm:px-6">
<div className="relative w-72">
<Listbox value={selectedNetworkKey} onChange={setSelectedNetworkKey}>
<Listbox.Button className="relative w-full py-2 pl-3 pr-10 text-left bg-white border border-gray-300 rounded-md shadow-sm cursor-default focus:outline-none focus:ring-1 focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm dark:bg-zinc-900 dark:border-zinc-800">
<span className="block truncate dark:text-zinc-50">
{selectedNetwork?.name}
</span>
<span className="absolute inset-y-0 right-0 flex items-center pr-2 pointer-events-none">
<StyledIcon as="SelectorIcon" size={5} className="text-gray-400" />
</span>
</Listbox.Button>
<Transition
as={Fragment}
leave="transition ease-in duration-100"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Listbox.Options className="absolute right-0 w-full py-1 mt-1 overflow-auto text-base bg-white rounded-md shadow-lg dark:text-zinc-50 dark:bg-zinc-900 max-h-56 ring-1 ring-black ring-opacity-5 focus:outline-none sm:text-sm">
{networks.map(network => (
<Listbox.Option
key={network.key}
value={network.key}
className={({ active }) =>
`${active ? 'text-white bg-indigo-600' : 'text-gray-900'}
cursor-default select-none relative py-2 pl-10 pr-4`
}
>
{({ selected, active }) => (
<div>
<span
className={`${
selected ? 'font-semibold' : 'font-normal'
} block truncate dark:text-zinc-50`}
>
{network.name} ({network.url})
</span>
{selected ? (
<span
className={`${active ? 'text-white' : 'text-indigo-600'}
absolute inset-y-0 left-0 flex items-center pl-3`}
>
<StyledIcon as="CheckIcon" size={5} />
</span>
) : null}
</div>
)}
</Listbox.Option>
))}
</Listbox.Options>
</Transition>
</Listbox>
</div>
<Disclosure>
{() => (
<>
<Disclosure.Button className="flex items-center px-3 py-2 mt-4 text-sm font-medium leading-4 text-white bg-indigo-600 border border-transparent rounded-md shadow-sm hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500">
<span>Add a network</span>
</Disclosure.Button>
<Disclosure.Panel className="p-4 mt-4 text-sm text-gray-700 bg-gray-100 rounded-md dark:bg-zinc-700 dark:text-zinc-100">
Use this form to add a new instance of the Stacks Blockchain API. Make
sure you review and trust the host before you add it.
<form className="mt-4">
<div className="flex flex-col">
<label
htmlFor="name"
className="block text-sm font-medium text-gray-500 dark:text-gray-300"
>
Name
</label>
<div className="flex mt-1 rounded-md shadow-sm">
<input
value={networkName}
onChange={onInputChange}
type="text"
name="networkName"
id="networkName"
className="flex-1 block w-full min-w-0 text-black border-gray-300 rounded-md focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm"
/>
</div>
</div>
<div className="flex flex-col mt-3">
<label
htmlFor="address"
className="block text-sm font-medium text-gray-500 dark:text-gray-300"
>
Address (include https://)
</label>
<div className="flex mt-1 rounded-md shadow-sm">
<input
value={networkAddress}
onChange={onInputChange}
type="text"
name="networkAddress"
id="networkAddress"
className="flex-1 block w-full min-w-0 text-black border-gray-300 rounded-md focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm"
/>
</div>
</div>
<div className="flex flex-col mt-3">
<label
htmlFor="key"
className="block text-sm font-medium text-gray-500 dark:text-gray-300"
>
Key
</label>
<div className="flex mt-1 rounded-md shadow-sm">
<input
value={networkKey}
onChange={onInputChange}
type="text"
name="networkKey"
id="networkKey"
className="flex-1 block w-full min-w-0 text-black border-gray-300 rounded-md focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm"
/>
</div>
</div>
<button
onClick={() => addNewNetwork()}
className="flex items-center px-3 py-2 mt-5 text-sm font-medium leading-4 text-white bg-indigo-600 border border-transparent rounded-md shadow-sm hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500"
>
Add network
</button>
</form>
</Disclosure.Panel>
</>
)}
</Disclosure>
</div>
<div className="px-4 py-6 mt-6 bg-indigo-700 sm:px-6">
<div className="flex items-start justify-between">
<Dialog.Title className="text-lg text-white font-headings">
Transaction History
</Dialog.Title>
</div>
<div className="mt-1">
<p className="text-sm text-indigo-300">
Your pending and confirmed transactions.
</p>
</div>
</div>
{isLoading ? (
<div className="relative flex-1 px-4 mt-6 sm:px-6">
<ul className="divide-y divide-gray-200 dark:divide-zinc-700">
<li className="py-4">
<div className="flex flex-col space-y-3">
<Placeholder width={Placeholder.width.FULL} />
<Placeholder width={Placeholder.width.THIRD} />
<Placeholder width={Placeholder.width.HALF} />
</div>
</li>
<li className="py-4">
<div className="flex flex-col space-y-3">
<Placeholder width={Placeholder.width.FULL} />
<Placeholder width={Placeholder.width.THIRD} />
<Placeholder width={Placeholder.width.HALF} />
</div>
</li>
</ul>
</div>
) : (
<div className="relative flex-1 px-4 mt-6 sm:px-6">
<ul className="divide-y divide-gray-200 dark:divide-zinc-700">
{pendingTransactions}
{transactions}
</ul>
</div>
)}
</div>
</div>
</Transition.Child>
</div>
</div>
</Dialog>
</Transition>
);
}
Example #27
Source File: sidebar.tsx From arkadiko with GNU General Public License v3.0 | 4 votes |
Sidebar: React.FC = ({ children }) => {
const [sidebarOpen, setSidebarOpen] = useState(false);
let location = useLocation();
const [navigation, updateNavigation] = useState([
{ name: 'Dashboard', href: '/', icon: TrendingUpIcon, current: true },
{ name: 'Balances', href: '/balances', icon: ScaleIcon, current: false },
])
useEffect(() => {
updateNavigation(navigation => [
...navigation.map((item, index) => item.href.toLowerCase() === location.pathname
? { ...item, current: true, key: index }
: { ...item, current: false, key: index }),
])
}, [location])
return (
<div>
<Transition.Root show={sidebarOpen} as={Fragment}>
<Dialog as="div" className="fixed inset-0 z-40 flex md:hidden" onClose={setSidebarOpen}>
<Transition.Child
as={Fragment}
enter="transition-opacity ease-linear duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="transition-opacity ease-linear duration-300"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0 bg-gray-600 bg-opacity-75" />
</Transition.Child>
<Transition.Child
as={Fragment}
enter="transition ease-in-out duration-300 transform"
enterFrom="-translate-x-full"
enterTo="translate-x-0"
leave="transition ease-in-out duration-300 transform"
leaveFrom="translate-x-0"
leaveTo="-translate-x-full"
>
<div className="relative flex flex-col flex-1 w-full max-w-xs bg-gray-800">
<Transition.Child
as={Fragment}
enter="ease-in-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in-out duration-300"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<div className="absolute top-0 right-0 pt-2 -mr-12">
<button
type="button"
className="flex items-center justify-center w-10 h-10 ml-1 rounded-full focus:outline-none focus:ring-2 focus:ring-inset focus:ring-white"
onClick={() => setSidebarOpen(false)}
>
<span className="sr-only">Close sidebar</span>
<XIcon className="w-6 h-6 text-white" aria-hidden="true" />
</button>
</div>
</Transition.Child>
<div className="flex-1 h-0 pt-5 pb-4 overflow-y-auto">
<RouterLink className="flex items-center shrink-0 px-4" to="/">
<svg className="w-auto h-6 text-white lg:block sm:h-8" viewBox="0 0 60 46" xmlns="http://www.w3.org/2000/svg"><path fill="currentColor" d="M19.03 1.54A2.68 2.68 0 0121.46 0h11.48c.95 0 1.82.49 2.3 1.29L59.62 41.6c.5.82.5 1.84.03 2.66a2.69 2.69 0 01-2.33 1.34h-12a2.7 2.7 0 01-1.9-.77 31.32 31.32 0 00-16.15-8.17c-6.8-1.09-14.81.4-22.7 8.17a2.71 2.71 0 01-3.42.3 2.62 2.62 0 01-.9-3.28L19.02 1.54zm7.1 3.75L46.86 40.3h5.74L31.42 5.3h-5.29zm10.89 28.89L21.75 8.37 9.55 34.55a29.17 29.17 0 0118.58-3.1c3.2.5 6.2 1.5 8.89 2.73z" /></svg>
<span className="inline-block ml-2 text-xl font-bold text-white align-middle font-headings">Arkadiko</span>
<span className="ml-1 text-lg font-semibold tracking-widest text-indigo-400 uppercase">Analytics</span>
</RouterLink>
<nav className="px-4 mt-5 space-y-1">
{navigation.map((item) => (
<a
key={item.name}
href={item.href}
className={classNames(
item.current ? 'bg-gray-900 text-white' : 'text-gray-300 hover:bg-gray-700 hover:text-white',
'group flex items-center px-2 py-2 text-base font-medium rounded-md'
)}
>
<item.icon
className={classNames(
item.current ? 'text-gray-300' : 'text-gray-400 group-hover:text-gray-300',
'mr-4 shrink-0 h-6 w-6'
)}
aria-hidden="true"
/>
{item.name}
</a>
))}
</nav>
</div>
{/* Ability to connect wallet for the user to check their own portfolio data/balances/etc. */}
{/* <div className="flex shrink-0 p-4 bg-gray-700">
<a href="#" className="shrink-0 block group">
<div className="flex items-center">
<div className="flex items-center justify-center w-12 h-12 bg-gray-800 rounded-full">
<UserIcon className="shrink-0 w-6 h-6 text-gray-300" aria-hidden="true" />
</div>
<div className="ml-3">
<p className="text-base font-medium text-white">SPM45...ZVY56</p>
<p className="text-sm font-medium text-gray-400 group-hover:text-gray-300">Your data</p>
</div>
</div>
</a>
</div> */}
</div>
</Transition.Child>
<div className="shrink-0 w-14">{/* Force sidebar to shrink to fit close icon */}</div>
</Dialog>
</Transition.Root>
{/* Static sidebar for desktop */}
<div className="hidden md:flex md:w-64 md:flex-col md:fixed md:inset-y-0">
{/* Sidebar component, swap this element with another sidebar if you like */}
<div className="flex flex-col flex-1 min-h-0 bg-gray-800">
<div className="flex flex-col flex-1 pt-5 pb-4 overflow-y-auto">
<RouterLink className="flex items-center shrink-0 px-4" to="/">
<svg className="w-auto h-8 text-white lg:block sm:h-8" viewBox="0 0 60 46" xmlns="http://www.w3.org/2000/svg"><path fill="currentColor" d="M19.03 1.54A2.68 2.68 0 0121.46 0h11.48c.95 0 1.82.49 2.3 1.29L59.62 41.6c.5.82.5 1.84.03 2.66a2.69 2.69 0 01-2.33 1.34h-12a2.7 2.7 0 01-1.9-.77 31.32 31.32 0 00-16.15-8.17c-6.8-1.09-14.81.4-22.7 8.17a2.71 2.71 0 01-3.42.3 2.62 2.62 0 01-.9-3.28L19.02 1.54zm7.1 3.75L46.86 40.3h5.74L31.42 5.3h-5.29zm10.89 28.89L21.75 8.37 9.55 34.55a29.17 29.17 0 0118.58-3.1c3.2.5 6.2 1.5 8.89 2.73z" /></svg>
<div className="flex flex-col">
<div className="ml-4 text-lg font-bold leading-none text-white align-middle font-headings">Arkadiko</div>
<div className="ml-4 mt-0.5 text-base font-semibold leading-none tracking-widest text-indigo-400 uppercase">Analytics</div>
</div>
</RouterLink>
<nav className="flex-1 px-4 mt-5 space-y-1">
{navigation.map((item) => (
<a
key={item.name}
href={item.href}
className={classNames(
item.current ? 'bg-gray-900 text-white' : 'text-gray-300 hover:bg-gray-700 hover:text-white',
'group flex items-center px-2 py-2 text-sm font-medium rounded-md'
)}
>
<item.icon
className={classNames(
item.current ? 'text-gray-300' : 'text-gray-400 group-hover:text-gray-300',
'mr-3 shrink-0 h-6 w-6'
)}
aria-hidden="true"
/>
{item.name}
</a>
))}
</nav>
</div>
{/* Ability to connect wallet for the user to check their own portfolio data/balances/etc. */}
{/* <div className="flex shrink-0 p-4 bg-gray-700">
<a href="#" className="shrink-0 block w-full group">
<div className="flex items-center">
<div className="flex items-center justify-center w-12 h-12 bg-gray-800 rounded-full">
<UserIcon className="shrink-0 w-6 h-6 text-gray-300" aria-hidden="true" />
</div>
<div className="ml-3">
<p className="text-base font-medium text-white">SPM45...ZVY56</p>
<p className="text-sm font-medium text-gray-400 group-hover:text-gray-300">Your data</p>
</div>
</div>
</a>
</div> */}
</div>
</div>
<div className="flex flex-col flex-1 md:pl-64">
<div className="sticky top-0 z-10 pt-1 pl-1 bg-gray-100 md:hidden sm:pl-3 sm:pt-3">
<button
type="button"
className="-ml-0.5 -mt-0.5 h-12 w-12 inline-flex items-center justify-center rounded-md text-gray-500 hover:text-gray-900 focus:outline-none focus:ring-2 focus:ring-inset focus:ring-indigo-500"
onClick={() => setSidebarOpen(true)}
>
<span className="sr-only">Open sidebar</span>
<MenuIcon className="w-6 h-6" aria-hidden="true" />
</button>
</div>
<main className="flex-1">
<div className="py-6">
{children}
</div>
</main>
</div>
</div>
);
}
Example #28
Source File: signin.tsx From thvu-blog with MIT License | 4 votes |
export default function SignIn({
providers,
}: {
providers: Awaited<ReturnType<typeof getProviders>>;
}) {
const [isOpen, setIsOpen] = useState(false);
const router = useRouter();
useEffect(() => {
if (router.query.error) {
setIsOpen(true);
}
}, [router]);
return (
<>
<PageSEO
title={`Sign In - ${siteMetadata.author}`}
description={`Sign In - ${siteMetadata.author}`}
/>
<div className="pt-6 pb-4 space-y-2 md:space-y-5">
<PageTitle>Sign In</PageTitle>
</div>
<div className="flex flex-col items-center space-y-2 justify-items-center xl:space-y-0">
<div className="p-8 prose dark:prose-dark max-w-none">
<div className="flex flex-col items-center justify-between gap-4">
<p className="text-center sm:text-left">Sign in with one of these providers:</p>
{providers &&
Object.values(providers).map((provider) => {
return <LoginButton key={provider.id} provider={provider} />;
})}
<p className="text-center sm:text-left">
Authentication built with ? using{" "}
<CustomLink href="https://next-auth.js.org/">NextAuth.js</CustomLink>
</p>
</div>
</div>
</div>
<Transition appear show={isOpen} as={Fragment}>
<Dialog
as="div"
className="fixed inset-0 z-10 overflow-y-auto"
onClose={() => setIsOpen(false)}
>
<div className="min-h-screen px-4 text-center">
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0"
enterTo="opacity-100"
leave="ease-in duration-200"
leaveFrom="opacity-100"
leaveTo="opacity-0"
>
<Dialog.Overlay className="fixed inset-0" />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span className="inline-block h-screen align-middle" aria-hidden="true">
​
</span>
<Transition.Child
as={Fragment}
enter="ease-out duration-300"
enterFrom="opacity-0 scale-95"
enterTo="opacity-100 scale-100"
leave="ease-in duration-200"
leaveFrom="opacity-100 scale-100"
leaveTo="opacity-0 scale-95"
>
<div className="inline-block w-full max-w-md p-6 my-8 overflow-hidden text-left align-middle transition-all transform bg-white shadow-xl rounded-2xl">
<Dialog.Title as="h3" className="text-lg font-medium leading-6 text-gray-900">
Problem signing in
</Dialog.Title>
<div className="mt-2">
<p className="text-sm text-gray-500">
An unexpected problem occurred while I'm trying to log you in. Please try with
another providers.
</p>
</div>
<div className="mt-4">
<button
type="button"
className="inline-flex justify-center px-4 py-2 text-sm font-medium border border-transparent rounded-md text-success-900 bg-success-100 hover:bg-success-200 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-success-500"
onClick={() => setIsOpen(false)}
>
OK
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
</>
);
}
Example #29
Source File: settings.tsx From pagely with MIT License | 4 votes |
Page = () => {
const router = useRouter();
const { data } = useClerkSWR<notionSites>(
`/api/getSiteData/notion/?siteId=${router.query.notionId}`
);
const urlWithSession = useUserWithSession(
'/api/updateSiteData/notion/showcase'
);
const deleteUrlWithSession = useUserWithSession('/api/deleteSite/notion');
const [enabled, setEnabled] = useState(data?.inShowcase);
const [isLoading, setIsLoading] = useState(false);
const [isOpen, setIsOpen] = useState(false);
function closeModal() {
setIsOpen(false);
}
function openModal() {
setIsOpen(true);
}
return (
<div>
<div>
<SidebarLayout activeTab='settings'>
<h1 className='text-4xl font-extrabold'>Settings</h1>
<p className='mt-4 text-gray-800 font-base'>
{data?.siteName || 'Just a second...'}
</p>
<div className='mt-8'>
<h2 className='text-2xl font-bold'>Showcase Settings</h2>
<div className='flex items-center my-5'>
<span className='inline-block mr-2'>
I prefer not to display{' '}
<strong title={data?.siteName}>
{truncate(data?.siteName, {
length: 15,
})}
</strong>{' '}
in showcase
</span>
<Switch
checked={enabled}
onChange={setEnabled}
style={{ zoom: 0.5 }}
className={`${enabled ? 'bg-gray-900' : 'bg-gray-700'}
relative inline-flex flex-shrink-0 h-[38px] w-[74px] border-2 border-transparent rounded-full cursor-pointer transition-colors ease-in-out duration-200 focus:outline-none focus-visible:ring-2 focus-visible:ring-white focus-visible:ring-opacity-75`}>
<span className='sr-only'>Use setting</span>
<span
aria-hidden='true'
className={`${enabled ? 'translate-x-9' : 'translate-x-0'}
pointer-events-none inline-block h-[34px] w-[34px] rounded-full bg-white shadow-lg transform ring-0 transition ease-in-out duration-200`}
/>
</Switch>
<span className='inline-block ml-2'>
Display{' '}
<strong title={data?.siteName}>
{truncate(data?.siteName, {
length: 15,
})}
</strong>{' '}
in{' '}
<Link href='/showcase'>
<a className='text-blue-500 hover:underline'>Showcase</a>
</Link>
</span>
</div>
<button
onClick={() => {
setIsLoading(true);
axios
.post(urlWithSession, {
inShowcase: enabled,
siteId: data.id,
})
.then((res) => {
console.log(res);
toast.success(
enabled
? `Yay ?, ${data?.siteName} will be displayed in showcase soon.`
: `${data?.siteName} will be removed showcase soon.`,
{
duration: 5000,
}
);
setIsLoading(false);
});
}}
className={`h-10 px-3 mb-10 bg-gray-800 rounded shadow-md text-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-800 hover:bg-gray-700 ${
isLoading && 'opacity-50 cursor-wait'
}`}>
Update Showcase Settings
</button>
</div>
<hr className='w-[70vw] my-3 text-gray-200' />
<div className='mt-8'>
<h2 className='text-2xl font-bold'>Password protection</h2>
{data?.isPasswordProtected ? (
<div>
<div className='flex items-center my-5'>
<span className='inline-block'>
<strong>{data?.siteName}</strong> has already been password
protected
</span>
</div>
<button className='h-10 px-3 mb-10 bg-gray-800 rounded shadow-md text-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-800 hover:bg-gray-700'>
<a
href='https://staticshield.vercel.app/dashboard'
target='_blank'
rel='noopener noreferrer'>
View details
</a>
</button>
</div>
) : (
<div>
<div className='flex items-center my-5'>
<span className='inline-block'>
Password protect <strong>{data?.siteName}</strong>
</span>
</div>
<button
onClick={() => {
window.open(
`https://staticshield.vercel.app/new/?name=${data?.siteName}&desc=${data?.siteDesc}&url=${data?.subdomain}.pagely.site&id=${data?.id}`,
'_blank'
);
}}
className={`mb-10 h-10 inline-flex items-center px-3 bg-gray-800 rounded shadow-md text-gray-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-800 hover:bg-gray-700`}>
Password protect{' '}
<strong className='mx-1'>{data?.siteName}</strong> with{' '}
<span className='inline-flex !items-center justify-center p-1 mx-1 bg-white rounded'>
<Image
src='/staticshield.png'
alt=''
width='20'
height='20'
// className='block mt-2'
/>
</span>
StaticShield
</button>
</div>
)}
</div>
<hr className='w-[70vw] my-3 text-gray-200' />
<div className='mt-8'>
<h2 className='text-2xl font-bold text-red-500'>Danger Zone</h2>
<div className='mt-5'>
<button
onClick={openModal}
className='h-10 px-3 mb-10 bg-red-600 rounded shadow-md text-red-50 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-800 hover:bg-red-400'>
{/* <button className='px-2 py-1 text-red-600 border border-red-500 rounded shadow bg-red-50 hover:bg-red-100 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-red-200'> */}
Delete <strong>{data?.siteName}</strong>
</button>
</div>
</div>
</SidebarLayout>
<Transition appear show={isOpen} as={Fragment}>
<Dialog
as='div'
className='fixed inset-0 z-10 overflow-y-auto'
onClose={closeModal}>
<div className='min-h-screen px-4 text-center'>
<Transition.Child
as={Fragment}
enter='ease-out duration-300'
enterFrom='opacity-0'
enterTo='opacity-100'
leave='ease-in duration-200'
leaveFrom='opacity-100'
leaveTo='opacity-0'>
<Dialog.Overlay className='fixed inset-0 backdrop-filter backdrop-blur-sm bg-white/40' />
</Transition.Child>
{/* This element is to trick the browser into centering the modal contents. */}
<span
className='inline-block h-screen align-middle'
aria-hidden='true'>
​
</span>
<Transition.Child
as={Fragment}
enter='ease-out duration-300'
enterFrom='opacity-0 scale-95'
enterTo='opacity-100 scale-100'
leave='ease-in duration-200'
leaveFrom='opacity-100 scale-100'
leaveTo='opacity-0 scale-95'>
<div className='inline-block w-full max-w-lg p-6 my-8 overflow-hidden text-left align-middle transition-all transform bg-white border rounded-md shadow-xl border-gray-500/40'>
<Dialog.Title
as='h3'
className='text-lg font-medium leading-6 text-red-700'>
Are you sure that you want to delete{' '}
<strong>{data?.siteName}</strong>?
</Dialog.Title>
<div className='mt-2 mb-10'>
<p className='text-sm text-gray-500'>
Proceed with caution. This action cannot be reversed.
</p>
</div>
<div className='mt-4'>
<button
type='button'
className='inline-flex justify-center px-4 py-1 mr-2 text-sm font-medium text-blue-900 bg-blue-100 border border-blue-500 rounded-md hover:bg-blue-200 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-blue-500'
onClick={closeModal}>
Cancel
</button>
<button
type='button'
className='inline-flex justify-center px-4 py-1 text-sm font-medium text-red-900 bg-red-100 border border-red-500 rounded-md hover:bg-red-200 focus:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-red-500'
onClick={() => {
axios
.post(deleteUrlWithSession, {
siteId: data?.id,
})
.then((res) => {
if (res.data.success) {
toast.success('Site deleted successfully', {
duration: 2000,
});
setTimeout(() => {
router.push('/dashboard');
}, 2000);
} else {
toast.error('Site deletion failed');
}
});
}}>
Delete
</button>
</div>
</div>
</Transition.Child>
</div>
</Dialog>
</Transition>
</div>
</div>
);
}