pl-fe: modals style changes

Signed-off-by: nicole mikołajczyk <git@mkljczk.pl>
This commit is contained in:
nicole mikołajczyk
2025-11-25 19:52:59 +01:00
parent 770f5e30ae
commit 8e6446ef82
14 changed files with 105 additions and 52 deletions

View File

@ -13,17 +13,6 @@ const messages = defineMessages({
confirm: { id: 'confirmations.delete.confirm', defaultMessage: 'Delete' },
});
const widths = {
xs: 'max-w-xs',
sm: 'max-w-sm',
md: 'max-w-base',
lg: 'max-w-lg',
xl: 'max-w-xl',
'2xl': 'max-w-2xl',
'3xl': 'max-w-3xl',
'4xl': 'max-w-4xl',
};
interface IModal {
/** Callback when the modal is cancelled. */
cancelAction?: () => void;
@ -41,8 +30,6 @@ interface IModal {
confirmationText?: React.ReactNode;
/** Confirmation button theme. */
confirmationTheme?: ButtonThemes;
/** Whether to use full width style for confirmation button. */
confirmationFullWidth?: boolean;
/** Callback when the modal is closed. */
onClose?: () => void;
/** Callback when the secondary action is chosen. */
@ -54,7 +41,6 @@ interface IModal {
skipFocus?: boolean;
/** Title text for the modal. */
title?: React.ReactNode;
width?: keyof typeof widths;
children?: React.ReactNode;
className?: string;
onBack?: () => void;
@ -71,14 +57,12 @@ const Modal = React.forwardRef<HTMLDivElement, IModal>(({
confirmationDisabled,
confirmationText,
confirmationTheme,
confirmationFullWidth,
onClose,
secondaryAction,
secondaryDisabled = false,
secondaryText,
skipFocus = false,
title,
width = 'xl',
className,
onBack,
}, ref) => {
@ -100,50 +84,43 @@ const Modal = React.forwardRef<HTMLDivElement, IModal>(({
<div
ref={ref}
data-testid='modal'
className={clsx(className, 'pointer-events-auto relative mx-auto flex max-h-[90vh] w-full flex-col overflow-auto rounded-2xl bg-white text-start align-middle text-gray-900 shadow-xl transition-all ease-in-out black:bg-black dark:bg-primary-900 dark:text-gray-100 md:max-h-[80vh]', widths[width], {
'bottom-0': !firstRender,
'no-reduce-motion:-bottom-32': firstRender,
})}
className={clsx('⁂-modal', {
'⁂-modal--first-render': firstRender,
'⁂-modal--close-position-left': closePosition === 'left',
}, className)}
>
{title && (
<div className='sticky top-0 z-10 bg-white/75 p-6 pb-2 backdrop-blur backdrop-saturate-200 black:bg-black/75 dark:bg-primary-900/75'>
<div
className={clsx('flex w-full items-center gap-2', {
'flex-row-reverse': closePosition === 'left',
})}
>
<div className='⁂-modal__title'>
<div>
{onBack && (
<IconButton
src={require('@phosphor-icons/core/regular/arrow-left.svg')}
title={intl.formatMessage(messages.back)}
onClick={onBack}
className='text-gray-500 hover:text-gray-700 dark:text-gray-300 dark:hover:text-gray-200 rtl:rotate-180'
/>
)}
<h3 className='grow text-lg font-bold leading-6 text-gray-900 dark:text-white'>
{title}
</h3>
<h3>{title}</h3>
{onClose && (
<IconButton
src={closeIcon}
title={intl.formatMessage(messages.close)}
onClick={onClose}
className='text-gray-500 hover:text-gray-700 dark:text-gray-300 dark:hover:text-gray-200 rtl:rotate-180'
/>
)}
</div>
</div>
)}
<div className={clsx('p-6', { 'pt-0': title })}>
<div className='w-full'>
<div className='⁂-modal__body'>
<div className='⁂-modal__children'>
{children}
</div>
{confirmationAction && (
<HStack className='mt-5' justifyContent='between' data-testid='modal-actions'>
<div className={clsx({ 'grow': !confirmationFullWidth })}>
<div className='grow'>
{cancelAction && (
<Button
theme='tertiary'
@ -154,7 +131,7 @@ const Modal = React.forwardRef<HTMLDivElement, IModal>(({
)}
</div>
<HStack space={2} className={clsx({ 'grow': confirmationFullWidth })}>
<HStack space={2}>
{secondaryAction && (
<Button
theme='secondary'
@ -170,7 +147,6 @@ const Modal = React.forwardRef<HTMLDivElement, IModal>(({
onClick={confirmationAction}
disabled={confirmationDisabled}
ref={buttonRef}
block={confirmationFullWidth}
>
{confirmationText}
</Button>

View File

@ -9,7 +9,7 @@ import type { BaseModalProps } from 'pl-fe/features/ui/components/modal-root';
const CryptoDonateModal: React.FC<BaseModalProps & ICryptoAddress> = ({ onClose, ...props }) => {
return (
<Modal onClose={onClose} width='xs'>
<Modal onClose={onClose} className='⁂-crypto-donate-map-modal'>
<DetailedCryptoAddress {...props} />
</Modal>
);

View File

@ -62,7 +62,7 @@ const EventMapModal: React.FC<BaseModalProps & EventMapModalProps> = ({ onClose,
<Modal
title={<FormattedMessage id='column.event_map' defaultMessage='Event location' />}
onClose={onClickClose}
width='2xl'
className='⁂-event-map-modal'
>
<Stack alignItems='center' space={6}>
<div className='h-96 w-full' id='event-map' />

View File

@ -158,7 +158,7 @@ const HotkeysModal: React.FC<BaseModalProps> = ({ onClose }) => {
<Modal
title={<FormattedMessage id='keyboard_shortcuts.heading' defaultMessage='Keyboard shortcuts' />}
onClose={() => onClose('HOTKEYS')}
width='4xl'
className='⁂-hotkey-modal'
>
<div className='flex flex-col text-xs lg:flex-row'>
{columns.map((column, i) => (

View File

@ -88,7 +88,6 @@ const CreateGroupModal: React.FC<BaseModalProps> = ({ onClose }) => {
confirmationAction={handleNextStep}
confirmationText={confirmationText}
confirmationDisabled={isSubmitting}
confirmationFullWidth
onClose={handleClose}
>
<Stack space={2}>

View File

@ -1,4 +1,5 @@
@use 'mixins';
@use 'variables';
.-accordion {
border-radius: 0.5rem;
@ -11,7 +12,7 @@
justify-content: space-between;
padding: 0.75rem 1rem;
font-weight: 600;
&__actions {
display: flex;
align-items: center;
@ -243,7 +244,7 @@ a.⁂-list-item,
padding: 0.5rem 1rem;
color: white;
@apply bg-primary-600/80 backdrop-blur-md backdrop-saturate-200 transition-transform hover:scale-105 hover:bg-primary-700/80 active:scale-100;
.-icon svg {
width: 1rem;
height: 1rem;
@ -296,3 +297,57 @@ a.⁂-list-item,
div[data-viewport-type="window"]:has(.-empty-message) {
position: initial!important;
}
.-modal {
@apply pointer-events-auto relative mx-auto flex w-full flex-col overflow-auto rounded-2xl bg-white text-start align-middle text-gray-900 shadow-xl transition-all ease-in-out black:bg-black dark:bg-primary-900 dark:text-gray-100;
max-height: calc(min(90vh, 100dvh));
max-width: 36rem;
@media (min-width: variables.$breakpoint-md) {
max-height: calc(min(80vh, 100dvh));
}
&--first-render {
@apply no-reduce-motion:-bottom-32;
}
&:not(&--first-render) {
@apply bottom-0;
}
&__title {
@apply sticky top-0 z-10 bg-white/75 p-6 pb-2 backdrop-blur backdrop-saturate-200 black:bg-black/75 dark:bg-primary-900/75;
> div {
@apply flex w-full items-center gap-2;
}
h3 {
@apply grow text-lg font-bold leading-6 text-gray-900 dark:text-white;
}
.-icon-button {
@apply text-gray-500 hover:text-gray-700 dark:text-gray-300 dark:hover:text-gray-200 rtl:rotate-180;
}
}
&--close-position-left &__title > div {
@apply flex-row-reverse;
}
&__body {
@apply p-6;
}
:has(.-modal__title) &__body {
@apply pt-0;
}
&__children {
@apply w-full;
}
&__actions {
@apply flex justify-between mt-5;
}
}

View File

@ -162,7 +162,7 @@
button {
@apply absolute inset-y-0 right-0 flex cursor-pointer items-center px-2 rtl:left-0 rtl:right-auto;
svg {
@apply size-5 text-gray-600;
}

View File

@ -11,4 +11,8 @@
width: 1rem;
height: 1rem;
}
}
.-event-map-modal {
max-width: 42rem;
}

View File

@ -1,5 +1,6 @@
@use 'components';
@use 'layout';
@use 'modals';
@use 'accounts';
@use 'statuses';
@use 'timelines';

View File

@ -31,7 +31,7 @@ body {
.-dropdown-navigation {
@apply fixed bottom-[60px] left-2 z-[1000] flex max-h-[calc(100dvh-68px)] w-full max-w-xs flex-1 origin-bottom-left flex-col overflow-hidden rounded-xl bg-white/90 shadow-lg backdrop-blur-md backdrop-saturate-200 ease-in-out black:bg-black/80 no-reduce-motion:transition-transform dark:border dark:border-gray-800 dark:bg-primary-900/90 dark:shadow-none rtl:right-2 rtl:origin-bottom-right no-reduce-motion:scale-0;
&__overlay {
@apply fixed inset-0 cursor-default bg-gray-500 black:bg-gray-900 no-reduce-motion:transition-opacity dark:bg-gray-700;
}
@ -246,6 +246,8 @@ body {
&--visible {
@apply fixed left-0 top-0 z-[100] size-full overflow-y-auto overflow-x-hidden transition-opacity ease-in-out;
width: 100%;
height: 100dvh;
}
&--revealed {
@ -257,7 +259,8 @@ body {
}
&__modal {
@apply my-2 mx-auto relative pointer-events-none flex items-center min-h-[calc(100%-3.5rem)];
@apply mx-auto relative pointer-events-none flex items-center;
min-height: calc(min(100vh - 3.5rem, 100dvh));
}
&[data-modal-type='DROPDOWN_MENU'] &__overlay {
@ -272,7 +275,9 @@ body {
}
&:not([data-modal-type='MEDIA']) &__modal {
padding: 1rem;
display: flex;
height: 100%;
padding: 0 1rem;
@apply md:p-0;
}
}
@ -306,7 +311,7 @@ body {
@apply md:grid md:max-w-7xl md:grid-cols-12 xl:max-w-[1440px];
}
}
&__container {
display: flex;
min-height: 100vh;

View File

@ -1,3 +1,5 @@
@use 'variables';
@mixin text($family: sans, $size: md, $theme: default, $tracking: normal, $transform: normal, $truncate: false, $weight: normal, $align: none) {
@if $family == sans {
font-family: var(--font-sans);
@ -104,18 +106,18 @@
@if $size == md {
padding: 1rem;
@media (width >= 581px) {
@media (min-width: variables.$breakpoint-sm) {
border-radius: 0.75rem;
}
} @else if $size == lg {
padding: 1rem;
@media (width >= 581px) {
@media (min-width: variables.$breakpoint-sm) {
padding: 1.5rem;
border-radius: 0.75rem;
}
} @else if $size == xl {
padding: 1rem;
@media (width >= 581px) {
@media (min-width: variables.$breakpoint-sm) {
padding: 2.5rem;
border-radius: 1.5rem;
}

View File

@ -0,0 +1,7 @@
.-crypto-donate-modal {
@apply max-w-sm;
}
.-hotkey-modal {
@apply max-w-4xl;
}

View File

@ -24,7 +24,7 @@
&--active {
@apply bg-primary-100 dark:border-primary-500 dark:bg-primary-500 dark:ring-2 dark:ring-primary-300 black:border-primary-600 black:bg-primary-600;
&:not(:disabled) {
@apply hover:bg-primary-200 hover:dark:border-primary-300 hover:dark:bg-primary-300 hover:black:bg-primary-500;
}
@ -65,7 +65,7 @@
&__button {
@apply -m-1 flex items-center rounded-full p-2 rtl:space-x-reverse transition-all duration-200 focus:outline-none focus:ring-2 focus:ring-primary-500 focus:ring-offset-2 dark:ring-offset-0 text-gray-600 hover:text-gray-800 dark:hover:text-white bg-transparent hover:bg-primary-100 dark:hover:bg-primary-800 black:hover:bg-gray-800;
&:not(:disabled) {
@apply hover:text-gray-600 dark:hover:text-white;
}

View File

@ -0,0 +1,4 @@
$breakpoint-sm: 581px;
$breakpoint-md: 768px;
$breakpoint-lg: 976px;
$breakpoint-xl: 1280px;