feat: replace modal with new design (#4324)
Co-authored-by: Peng Xiao <pengxiao@outlook.com>
This commit is contained in:
@@ -39,7 +39,7 @@
|
|||||||
"@mui/material": "^5.14.7",
|
"@mui/material": "^5.14.7",
|
||||||
"@radix-ui/react-select": "^1.2.2",
|
"@radix-ui/react-select": "^1.2.2",
|
||||||
"@react-hookz/web": "^23.1.0",
|
"@react-hookz/web": "^23.1.0",
|
||||||
"@toeverything/components": "^0.0.34",
|
"@toeverything/components": "^0.0.38",
|
||||||
"async-call-rpc": "^6.3.1",
|
"async-call-rpc": "^6.3.1",
|
||||||
"cmdk": "^0.2.0",
|
"cmdk": "^0.2.0",
|
||||||
"css-spring": "^4.1.0",
|
"css-spring": "^4.1.0",
|
||||||
|
|||||||
@@ -1,14 +1,9 @@
|
|||||||
import {
|
import { Input, toast } from '@affine/component';
|
||||||
Input,
|
|
||||||
Modal,
|
|
||||||
ModalCloseButton,
|
|
||||||
ModalWrapper,
|
|
||||||
toast,
|
|
||||||
} from '@affine/component';
|
|
||||||
import { DebugLogger } from '@affine/debug';
|
import { DebugLogger } from '@affine/debug';
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { HelpIcon } from '@blocksuite/icons';
|
import { HelpIcon } from '@blocksuite/icons';
|
||||||
import { Button } from '@toeverything/components/button';
|
import { Button } from '@toeverything/components/button';
|
||||||
|
import { Modal } from '@toeverything/components/modal';
|
||||||
import { Tooltip } from '@toeverything/components/tooltip';
|
import { Tooltip } from '@toeverything/components/tooltip';
|
||||||
import type {
|
import type {
|
||||||
LoadDBFileResult,
|
LoadDBFileResult,
|
||||||
@@ -386,16 +381,28 @@ export const CreateWorkspaceModal = ({
|
|||||||
/>
|
/>
|
||||||
) : null;
|
) : null;
|
||||||
|
|
||||||
|
const onOpenChange = useCallback(
|
||||||
|
(open: boolean) => {
|
||||||
|
if (!open) {
|
||||||
|
onClose();
|
||||||
|
}
|
||||||
|
},
|
||||||
|
[onClose]
|
||||||
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal open={mode !== false && !!step} onClose={onClose}>
|
<Modal
|
||||||
<ModalWrapper width={560} style={{ padding: '10px' }}>
|
open={mode !== false && !!step}
|
||||||
<div className={style.header}>
|
width={560}
|
||||||
<ModalCloseButton top={6} right={6} onClick={onClose} />
|
onOpenChange={onOpenChange}
|
||||||
</div>
|
contentOptions={{
|
||||||
{nameWorkspaceNode}
|
style: { padding: '10px' },
|
||||||
{setDBLocationNode}
|
}}
|
||||||
{setSyncingModeNode}
|
>
|
||||||
</ModalWrapper>
|
<div className={style.header}></div>
|
||||||
|
{nameWorkspaceNode}
|
||||||
|
{setDBLocationNode}
|
||||||
|
{setSyncingModeNode}
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,33 +1,26 @@
|
|||||||
import { Modal, ModalWrapper } from '@affine/component';
|
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { CloseIcon } from '@blocksuite/icons';
|
import {
|
||||||
import { Button, IconButton } from '@toeverything/components/button';
|
ConfirmModal,
|
||||||
|
type ConfirmModalProps,
|
||||||
|
} from '@toeverything/components/modal';
|
||||||
import { useSetAtom } from 'jotai';
|
import { useSetAtom } from 'jotai';
|
||||||
import { useCallback } from 'react';
|
import { useCallback } from 'react';
|
||||||
|
|
||||||
import { authAtom } from '../../../atoms';
|
import { authAtom } from '../../../atoms';
|
||||||
import { setOnceSignedInEventAtom } from '../../../atoms/event';
|
import { setOnceSignedInEventAtom } from '../../../atoms/event';
|
||||||
import { useCurrentLoginStatus } from '../../../hooks/affine/use-current-login-status';
|
import { useCurrentLoginStatus } from '../../../hooks/affine/use-current-login-status';
|
||||||
import { ButtonContainer, Content, Header, StyleTips, Title } from './style';
|
|
||||||
|
|
||||||
interface EnableAffineCloudModalProps {
|
|
||||||
open: boolean;
|
|
||||||
onConfirm: () => void;
|
|
||||||
onClose: () => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
export const EnableAffineCloudModal = ({
|
export const EnableAffineCloudModal = ({
|
||||||
onConfirm: propsOnConfirm,
|
onConfirm: propsOnConfirm,
|
||||||
open,
|
...props
|
||||||
onClose,
|
}: ConfirmModalProps) => {
|
||||||
}: EnableAffineCloudModalProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
const loginStatus = useCurrentLoginStatus();
|
const loginStatus = useCurrentLoginStatus();
|
||||||
const setAuthAtom = useSetAtom(authAtom);
|
const setAuthAtom = useSetAtom(authAtom);
|
||||||
const setOnceSignedInEvent = useSetAtom(setOnceSignedInEventAtom);
|
const setOnceSignedInEvent = useSetAtom(setOnceSignedInEventAtom);
|
||||||
|
|
||||||
const confirm = useCallback(async () => {
|
const confirm = useCallback(async () => {
|
||||||
return propsOnConfirm();
|
return propsOnConfirm?.();
|
||||||
}, [propsOnConfirm]);
|
}, [propsOnConfirm]);
|
||||||
|
|
||||||
const onConfirm = useCallback(() => {
|
const onConfirm = useCallback(() => {
|
||||||
@@ -39,42 +32,29 @@ export const EnableAffineCloudModal = ({
|
|||||||
setOnceSignedInEvent(confirm);
|
setOnceSignedInEvent(confirm);
|
||||||
}
|
}
|
||||||
if (loginStatus === 'authenticated') {
|
if (loginStatus === 'authenticated') {
|
||||||
return propsOnConfirm();
|
return propsOnConfirm?.();
|
||||||
}
|
}
|
||||||
}, [confirm, loginStatus, propsOnConfirm, setAuthAtom, setOnceSignedInEvent]);
|
}, [confirm, loginStatus, propsOnConfirm, setAuthAtom, setOnceSignedInEvent]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal open={open} onClose={onClose} data-testid="logout-modal">
|
<ConfirmModal
|
||||||
<ModalWrapper width={480}>
|
width={480}
|
||||||
<Header>
|
title={t['Enable AFFiNE Cloud']()}
|
||||||
<Title>{t['Enable AFFiNE Cloud']()}</Title>
|
description={t['Enable AFFiNE Cloud Description']()}
|
||||||
<IconButton onClick={onClose}>
|
cancelText={t['com.affine.enableAffineCloudModal.button.cancel']()}
|
||||||
<CloseIcon />
|
onConfirm={onConfirm}
|
||||||
</IconButton>
|
confirmButtonOptions={{
|
||||||
</Header>
|
type: 'primary',
|
||||||
<Content>
|
['data-testid' as string]: 'confirm-enable-affine-cloud-button',
|
||||||
<StyleTips>{t['Enable AFFiNE Cloud Description']()}</StyleTips>
|
children:
|
||||||
<ButtonContainer>
|
loginStatus === 'authenticated'
|
||||||
<div>
|
? t['Enable']()
|
||||||
<Button onClick={onClose} block>
|
: t['Sign in and Enable'](),
|
||||||
{t['com.affine.enableAffineCloudModal.button.cancel']()}
|
}}
|
||||||
</Button>
|
contentOptions={{
|
||||||
</div>
|
['data-testid' as string]: 'enable-cloud-modal',
|
||||||
<div>
|
}}
|
||||||
<Button
|
{...props}
|
||||||
data-testid="confirm-enable-affine-cloud-button"
|
/>
|
||||||
type="primary"
|
|
||||||
block
|
|
||||||
onClick={onConfirm}
|
|
||||||
>
|
|
||||||
{loginStatus === 'authenticated'
|
|
||||||
? t['Enable']()
|
|
||||||
: t['Sign in and Enable']()}
|
|
||||||
</Button>
|
|
||||||
</div>
|
|
||||||
</ButtonContainer>
|
|
||||||
</Content>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,35 +0,0 @@
|
|||||||
import { styled } from '@affine/component';
|
|
||||||
|
|
||||||
export const Header = styled('div')({
|
|
||||||
display: 'flex',
|
|
||||||
justifyContent: 'space-between',
|
|
||||||
paddingRight: '20px',
|
|
||||||
paddingTop: '20px',
|
|
||||||
paddingLeft: '24px',
|
|
||||||
alignItems: 'center',
|
|
||||||
});
|
|
||||||
|
|
||||||
export const Content = styled('div')({
|
|
||||||
padding: '12px 24px 20px 24px',
|
|
||||||
});
|
|
||||||
|
|
||||||
export const Title = styled('div')({
|
|
||||||
fontSize: 'var(--affine-font-h6)',
|
|
||||||
lineHeight: '26px',
|
|
||||||
fontWeight: 600,
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyleTips = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
userSelect: 'none',
|
|
||||||
marginBottom: '20px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
export const ButtonContainer = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
display: 'flex',
|
|
||||||
justifyContent: 'flex-end',
|
|
||||||
gap: '20px',
|
|
||||||
paddingTop: '20px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
@@ -1,33 +1,24 @@
|
|||||||
import { Input, Modal, ModalCloseButton } from '@affine/component';
|
import { Input } from '@affine/component';
|
||||||
import type { AffineOfficialWorkspace } from '@affine/env/workspace';
|
import type { AffineOfficialWorkspace } from '@affine/env/workspace';
|
||||||
import { WorkspaceFlavour } from '@affine/env/workspace';
|
import { WorkspaceFlavour } from '@affine/env/workspace';
|
||||||
import { Trans } from '@affine/i18n';
|
import { Trans } from '@affine/i18n';
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { Button } from '@toeverything/components/button';
|
import {
|
||||||
|
ConfirmModal,
|
||||||
|
type ConfirmModalProps,
|
||||||
|
} from '@toeverything/components/modal';
|
||||||
import { useBlockSuiteWorkspaceName } from '@toeverything/hooks/use-block-suite-workspace-name';
|
import { useBlockSuiteWorkspaceName } from '@toeverything/hooks/use-block-suite-workspace-name';
|
||||||
import { useState } from 'react';
|
import { useState } from 'react';
|
||||||
|
|
||||||
import {
|
import { StyledInputContent, StyledWorkspaceName } from './style';
|
||||||
StyledButtonContent,
|
|
||||||
StyledInputContent,
|
|
||||||
StyledModalHeader,
|
|
||||||
StyledModalWrapper,
|
|
||||||
StyledTextContent,
|
|
||||||
StyledWorkspaceName,
|
|
||||||
} from './style';
|
|
||||||
|
|
||||||
interface WorkspaceDeleteProps {
|
interface WorkspaceDeleteProps extends ConfirmModalProps {
|
||||||
open: boolean;
|
|
||||||
onClose: () => void;
|
|
||||||
workspace: AffineOfficialWorkspace;
|
workspace: AffineOfficialWorkspace;
|
||||||
onConfirm: () => void;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const WorkspaceDeleteModal = ({
|
export const WorkspaceDeleteModal = ({
|
||||||
open,
|
|
||||||
onClose,
|
|
||||||
onConfirm,
|
|
||||||
workspace,
|
workspace,
|
||||||
|
...props
|
||||||
}: WorkspaceDeleteProps) => {
|
}: WorkspaceDeleteProps) => {
|
||||||
const [workspaceName] = useBlockSuiteWorkspaceName(
|
const [workspaceName] = useBlockSuiteWorkspaceName(
|
||||||
workspace.blockSuiteWorkspace
|
workspace.blockSuiteWorkspace
|
||||||
@@ -37,65 +28,50 @@ export const WorkspaceDeleteModal = ({
|
|||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal open={open} onClose={onClose}>
|
<ConfirmModal
|
||||||
<StyledModalWrapper>
|
title={`${t['com.affine.workspaceDelete.title']()}?`}
|
||||||
<ModalCloseButton onClick={onClose} />
|
cancelText={t['com.affine.workspaceDelete.button.cancel']()}
|
||||||
<StyledModalHeader>
|
confirmButtonOptions={{
|
||||||
{t['com.affine.workspaceDelete.title']()}?
|
type: 'error',
|
||||||
</StyledModalHeader>
|
disabled: !allowDelete,
|
||||||
{workspace.flavour === WorkspaceFlavour.LOCAL ? (
|
['data-testid' as string]: 'delete-workspace-confirm-button',
|
||||||
<StyledTextContent>
|
children: t['com.affine.workspaceDelete.button.delete'](),
|
||||||
<Trans i18nKey="com.affine.workspaceDelete.description">
|
}}
|
||||||
Deleting (
|
{...props}
|
||||||
<StyledWorkspaceName>
|
>
|
||||||
{{ workspace: workspaceName } as any}
|
{workspace.flavour === WorkspaceFlavour.LOCAL ? (
|
||||||
</StyledWorkspaceName>
|
<Trans i18nKey="com.affine.workspaceDelete.description">
|
||||||
) cannot be undone, please proceed with caution. All contents will
|
Deleting (
|
||||||
be lost.
|
<StyledWorkspaceName>
|
||||||
</Trans>
|
{{ workspace: workspaceName } as any}
|
||||||
</StyledTextContent>
|
</StyledWorkspaceName>
|
||||||
) : (
|
) cannot be undone, please proceed with caution. All contents will be
|
||||||
<StyledTextContent>
|
lost.
|
||||||
<Trans i18nKey="com.affine.workspaceDelete.description2">
|
</Trans>
|
||||||
Deleting (
|
) : (
|
||||||
<StyledWorkspaceName>
|
<Trans i18nKey="com.affine.workspaceDelete.description2">
|
||||||
{{ workspace: workspaceName } as any}
|
Deleting (
|
||||||
</StyledWorkspaceName>
|
<StyledWorkspaceName>
|
||||||
) will delete both local and cloud data, this operation cannot be
|
{{ workspace: workspaceName } as any}
|
||||||
undone, please proceed with caution.
|
</StyledWorkspaceName>
|
||||||
</Trans>
|
) will delete both local and cloud data, this operation cannot be
|
||||||
</StyledTextContent>
|
undone, please proceed with caution.
|
||||||
)}
|
</Trans>
|
||||||
<StyledInputContent>
|
)}
|
||||||
<Input
|
<StyledInputContent>
|
||||||
ref={ref => {
|
<Input
|
||||||
if (ref) {
|
ref={ref => {
|
||||||
window.setTimeout(() => ref.focus(), 0);
|
if (ref) {
|
||||||
}
|
window.setTimeout(() => ref.focus(), 0);
|
||||||
}}
|
}
|
||||||
onChange={setDeleteStr}
|
}}
|
||||||
data-testid="delete-workspace-input"
|
onChange={setDeleteStr}
|
||||||
placeholder={t['com.affine.workspaceDelete.placeholder']()}
|
data-testid="delete-workspace-input"
|
||||||
width={315}
|
placeholder={t['com.affine.workspaceDelete.placeholder']()}
|
||||||
height={42}
|
width={315}
|
||||||
/>
|
height={42}
|
||||||
</StyledInputContent>
|
/>
|
||||||
<StyledButtonContent>
|
</StyledInputContent>
|
||||||
<Button onClick={onClose} size="large">
|
</ConfirmModal>
|
||||||
{t['com.affine.workspaceDelete.button.cancel']()}
|
|
||||||
</Button>
|
|
||||||
<Button
|
|
||||||
data-testid="delete-workspace-confirm-button"
|
|
||||||
disabled={!allowDelete}
|
|
||||||
onClick={onConfirm}
|
|
||||||
size="large"
|
|
||||||
type="error"
|
|
||||||
style={{ marginLeft: '24px' }}
|
|
||||||
>
|
|
||||||
{t['com.affine.workspaceDelete.button.delete']()}
|
|
||||||
</Button>
|
|
||||||
</StyledButtonContent>
|
|
||||||
</StyledModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -21,20 +21,6 @@ export const StyledModalHeader = styled('div')(() => {
|
|||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
// export const StyledModalContent = styled('div')(({ theme }) => {});
|
|
||||||
|
|
||||||
export const StyledTextContent = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
margin: 'auto',
|
|
||||||
width: '425px',
|
|
||||||
fontStyle: 'normal',
|
|
||||||
fontWeight: '400',
|
|
||||||
fontSize: '18px',
|
|
||||||
lineHeight: '26px',
|
|
||||||
textAlign: 'left',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledInputContent = styled('div')(() => {
|
export const StyledInputContent = styled('div')(() => {
|
||||||
return {
|
return {
|
||||||
display: 'flex',
|
display: 'flex',
|
||||||
@@ -45,31 +31,8 @@ export const StyledInputContent = styled('div')(() => {
|
|||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
export const StyledButtonContent = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
marginBottom: '42px',
|
|
||||||
display: 'flex',
|
|
||||||
flexDirection: 'row',
|
|
||||||
justifyContent: 'center',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledWorkspaceName = styled('span')(() => {
|
export const StyledWorkspaceName = styled('span')(() => {
|
||||||
return {
|
return {
|
||||||
fontWeight: '600',
|
fontWeight: '600',
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
// export const StyledCancelButton = styled(Button)(({ theme }) => {
|
|
||||||
// return {
|
|
||||||
// width: '100px',
|
|
||||||
// justifyContent: 'center',
|
|
||||||
// };
|
|
||||||
// });
|
|
||||||
|
|
||||||
// export const StyledDeleteButton = styled(Button)(({ theme }) => {
|
|
||||||
// return {
|
|
||||||
// width: '100px',
|
|
||||||
// justifyContent: 'center',
|
|
||||||
// };
|
|
||||||
// });
|
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
import { ConfirmModal } from '@affine/component';
|
|
||||||
import { SettingRow } from '@affine/component/setting-components';
|
import { SettingRow } from '@affine/component/setting-components';
|
||||||
import type { AffineOfficialWorkspace } from '@affine/env/workspace';
|
import type { AffineOfficialWorkspace } from '@affine/env/workspace';
|
||||||
import { WorkspaceFlavour } from '@affine/env/workspace';
|
import { WorkspaceFlavour } from '@affine/env/workspace';
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { ArrowRightSmallIcon } from '@blocksuite/icons';
|
import { ArrowRightSmallIcon } from '@blocksuite/icons';
|
||||||
|
import { ConfirmModal } from '@toeverything/components/modal';
|
||||||
import { useCallback, useState } from 'react';
|
import { useCallback, useState } from 'react';
|
||||||
|
|
||||||
import type { WorkspaceSettingDetailProps } from '../types';
|
import type { WorkspaceSettingDetailProps } from '../types';
|
||||||
@@ -33,10 +33,6 @@ export const DeleteLeaveWorkspace = ({
|
|||||||
}
|
}
|
||||||
}, [isOwner]);
|
}, [isOwner]);
|
||||||
|
|
||||||
const onCloseLeaveModal = useCallback(() => {
|
|
||||||
setShowLeave(false);
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
const onLeaveConfirm = useCallback(() => {
|
const onLeaveConfirm = useCallback(() => {
|
||||||
return onLeaveWorkspace();
|
return onLeaveWorkspace();
|
||||||
}, [onLeaveWorkspace]);
|
}, [onLeaveWorkspace]);
|
||||||
@@ -71,21 +67,21 @@ export const DeleteLeaveWorkspace = ({
|
|||||||
<WorkspaceDeleteModal
|
<WorkspaceDeleteModal
|
||||||
onConfirm={onDeleteConfirm}
|
onConfirm={onDeleteConfirm}
|
||||||
open={showDelete}
|
open={showDelete}
|
||||||
onClose={() => {
|
onOpenChange={setShowDelete}
|
||||||
setShowDelete(false);
|
|
||||||
}}
|
|
||||||
workspace={workspace}
|
workspace={workspace}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
<ConfirmModal
|
<ConfirmModal
|
||||||
open={showLeave}
|
open={showLeave}
|
||||||
|
cancelText={t['com.affine.confirmModal.button.cancel']()}
|
||||||
onConfirm={onLeaveConfirm}
|
onConfirm={onLeaveConfirm}
|
||||||
onCancel={onCloseLeaveModal}
|
onOpenChange={setShowLeave}
|
||||||
onClose={onCloseLeaveModal}
|
|
||||||
title={`${t['com.affine.deleteLeaveWorkspace.leave']()}?`}
|
title={`${t['com.affine.deleteLeaveWorkspace.leave']()}?`}
|
||||||
content={t['com.affine.deleteLeaveWorkspace.leaveDescription']()}
|
description={t['com.affine.deleteLeaveWorkspace.leaveDescription']()}
|
||||||
confirmType="warning"
|
confirmButtonOptions={{
|
||||||
confirmText={t['Leave']()}
|
type: 'warning',
|
||||||
|
children: t['Leave'](),
|
||||||
|
}}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</>
|
</>
|
||||||
|
|||||||
@@ -142,9 +142,7 @@ const PublishPanelLocal = ({
|
|||||||
{runtimeConfig.enableCloud ? (
|
{runtimeConfig.enableCloud ? (
|
||||||
<EnableAffineCloudModal
|
<EnableAffineCloudModal
|
||||||
open={open}
|
open={open}
|
||||||
onClose={() => {
|
onOpenChange={setOpen}
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
onConfirm={() => {
|
onConfirm={() => {
|
||||||
onTransferWorkspace(
|
onTransferWorkspace(
|
||||||
WorkspaceFlavour.LOCAL,
|
WorkspaceFlavour.LOCAL,
|
||||||
@@ -155,12 +153,7 @@ const PublishPanelLocal = ({
|
|||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
<TmpDisableAffineCloudModal
|
<TmpDisableAffineCloudModal open={open} onOpenChange={setOpen} />
|
||||||
open={open}
|
|
||||||
onClose={() => {
|
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
/>
|
|
||||||
)}
|
)}
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -8,12 +8,16 @@ import { guideOnboardingAtom } from '../../atoms/guide';
|
|||||||
export const OnboardingModal = memo(function OnboardingModal() {
|
export const OnboardingModal = memo(function OnboardingModal() {
|
||||||
const [open, setOpen] = useAtom(openOnboardingModalAtom);
|
const [open, setOpen] = useAtom(openOnboardingModalAtom);
|
||||||
const [guideOpen, setShowOnboarding] = useAtom(guideOnboardingAtom);
|
const [guideOpen, setShowOnboarding] = useAtom(guideOnboardingAtom);
|
||||||
const onCloseTourModal = useCallback(() => {
|
const onOpenChange = useCallback(
|
||||||
setShowOnboarding(false);
|
(open: boolean) => {
|
||||||
setOpen(false);
|
if (open) return;
|
||||||
}, [setOpen, setShowOnboarding]);
|
setShowOnboarding(false);
|
||||||
|
setOpen(false);
|
||||||
|
},
|
||||||
|
[setOpen, setShowOnboarding]
|
||||||
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<TourModal open={!open ? guideOpen : open} onClose={onCloseTourModal} />
|
<TourModal open={!open ? guideOpen : open} onOpenChange={onOpenChange} />
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,10 +1,7 @@
|
|||||||
import {
|
import { WorkspaceDetailSkeleton } from '@affine/component/setting-components';
|
||||||
SettingModal as SettingModalBase,
|
|
||||||
type SettingModalProps as SettingModalBaseProps,
|
|
||||||
WorkspaceDetailSkeleton,
|
|
||||||
} from '@affine/component/setting-components';
|
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { ContactWithUsIcon } from '@blocksuite/icons';
|
import { ContactWithUsIcon } from '@blocksuite/icons';
|
||||||
|
import { Modal, type ModalProps } from '@toeverything/components/modal';
|
||||||
import { Suspense, useCallback } from 'react';
|
import { Suspense, useCallback } from 'react';
|
||||||
|
|
||||||
import { useCurrentLoginStatus } from '../../../hooks/affine/use-current-login-status';
|
import { useCurrentLoginStatus } from '../../../hooks/affine/use-current-login-status';
|
||||||
@@ -20,7 +17,7 @@ import { WorkspaceSetting } from './workspace-setting';
|
|||||||
|
|
||||||
type ActiveTab = GeneralSettingKeys | 'workspace' | 'account';
|
type ActiveTab = GeneralSettingKeys | 'workspace' | 'account';
|
||||||
|
|
||||||
export interface SettingProps {
|
export interface SettingProps extends ModalProps {
|
||||||
activeTab: ActiveTab;
|
activeTab: ActiveTab;
|
||||||
workspaceId: string | null;
|
workspaceId: string | null;
|
||||||
onSettingClick: (params: {
|
onSettingClick: (params: {
|
||||||
@@ -29,15 +26,12 @@ export interface SettingProps {
|
|||||||
}) => void;
|
}) => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
type SettingModalProps = SettingModalBaseProps & SettingProps;
|
|
||||||
|
|
||||||
export const SettingModal = ({
|
export const SettingModal = ({
|
||||||
open,
|
|
||||||
setOpen,
|
|
||||||
activeTab = 'appearance',
|
activeTab = 'appearance',
|
||||||
workspaceId = null,
|
workspaceId = null,
|
||||||
onSettingClick,
|
onSettingClick,
|
||||||
}: SettingModalProps) => {
|
...modalProps
|
||||||
|
}: SettingProps) => {
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
const loginStatus = useCurrentLoginStatus();
|
const loginStatus = useCurrentLoginStatus();
|
||||||
|
|
||||||
@@ -66,7 +60,21 @@ export const SettingModal = ({
|
|||||||
}, [onSettingClick]);
|
}, [onSettingClick]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<SettingModalBase open={open} setOpen={setOpen}>
|
<Modal
|
||||||
|
width={1080}
|
||||||
|
height={760}
|
||||||
|
contentOptions={{
|
||||||
|
['data-testid' as string]: 'setting-modal',
|
||||||
|
style: {
|
||||||
|
maxHeight: '85vh',
|
||||||
|
maxWidth: '70vw',
|
||||||
|
padding: 0,
|
||||||
|
overflow: 'hidden',
|
||||||
|
display: 'flex',
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
{...modalProps}
|
||||||
|
>
|
||||||
<SettingSidebar
|
<SettingSidebar
|
||||||
generalSettingList={generalSettingList}
|
generalSettingList={generalSettingList}
|
||||||
onGeneralSettingClick={onGeneralSettingClick}
|
onGeneralSettingClick={onGeneralSettingClick}
|
||||||
@@ -105,6 +113,6 @@ export const SettingModal = ({
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</SettingModalBase>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -30,9 +30,7 @@ export const SharePageModal = ({ workspace, page }: SharePageModalProps) => {
|
|||||||
{workspace.flavour === WorkspaceFlavour.LOCAL ? (
|
{workspace.flavour === WorkspaceFlavour.LOCAL ? (
|
||||||
<EnableAffineCloudModal
|
<EnableAffineCloudModal
|
||||||
open={open}
|
open={open}
|
||||||
onClose={() => {
|
onOpenChange={setOpen}
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
onConfirm={() => {
|
onConfirm={() => {
|
||||||
onTransformWorkspace(
|
onTransformWorkspace(
|
||||||
WorkspaceFlavour.LOCAL,
|
WorkspaceFlavour.LOCAL,
|
||||||
|
|||||||
@@ -1,79 +1,61 @@
|
|||||||
import { Empty, Modal, ModalWrapper } from '@affine/component';
|
import { Empty } from '@affine/component';
|
||||||
import { Trans } from '@affine/i18n';
|
import { Trans } from '@affine/i18n';
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { CloseIcon } from '@blocksuite/icons';
|
import { Modal, type ModalProps } from '@toeverything/components/modal';
|
||||||
import { IconButton } from '@toeverything/components/button';
|
import { useCallback } from 'react';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
Content,
|
|
||||||
ContentTitle,
|
|
||||||
Header,
|
|
||||||
StyleButton,
|
StyleButton,
|
||||||
StyleButtonContainer,
|
StyleButtonContainer,
|
||||||
StyleImage,
|
StyleImage,
|
||||||
StyleTips,
|
StyleTips,
|
||||||
} from './style';
|
} from './style';
|
||||||
|
|
||||||
interface TmpDisableAffineCloudModalProps {
|
export const TmpDisableAffineCloudModal = (props: ModalProps) => {
|
||||||
open: boolean;
|
|
||||||
onClose: () => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
export const TmpDisableAffineCloudModal = ({
|
|
||||||
open,
|
|
||||||
onClose,
|
|
||||||
}: TmpDisableAffineCloudModalProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
|
const onClose = useCallback(() => {
|
||||||
|
props.onOpenChange?.(false);
|
||||||
|
}, [props]);
|
||||||
return (
|
return (
|
||||||
<Modal
|
<Modal
|
||||||
data-testid="disable-affine-cloud-modal"
|
title={t['com.affine.cloudTempDisable.title']()}
|
||||||
open={open}
|
contentOptions={{
|
||||||
onClose={onClose}
|
['data-testid' as string]: 'disable-affine-cloud-modal',
|
||||||
|
}}
|
||||||
|
width={480}
|
||||||
|
{...props}
|
||||||
>
|
>
|
||||||
<ModalWrapper width={480}>
|
<StyleTips>
|
||||||
<Header>
|
<Trans i18nKey="com.affine.cloudTempDisable.description">
|
||||||
<IconButton onClick={onClose}>
|
We are upgrading the AFFiNE Cloud service and it is temporarily
|
||||||
<CloseIcon />
|
unavailable on the client side. If you wish to stay updated on the
|
||||||
</IconButton>
|
progress and be notified on availability, you can fill out the
|
||||||
</Header>
|
<a
|
||||||
<Content>
|
href="https://6dxre9ihosp.typeform.com/to/B8IHwuyy"
|
||||||
<ContentTitle>
|
rel="noreferrer"
|
||||||
{t['com.affine.cloudTempDisable.title']()}
|
target="_blank"
|
||||||
</ContentTitle>
|
style={{
|
||||||
<StyleTips>
|
color: 'var(--affine-link-color)',
|
||||||
<Trans i18nKey="com.affine.cloudTempDisable.description">
|
}}
|
||||||
We are upgrading the AFFiNE Cloud service and it is temporarily
|
>
|
||||||
unavailable on the client side. If you wish to stay updated on the
|
AFFiNE Cloud Signup
|
||||||
progress and be notified on availability, you can fill out the
|
</a>
|
||||||
<a
|
.
|
||||||
href="https://6dxre9ihosp.typeform.com/to/B8IHwuyy"
|
</Trans>
|
||||||
rel="noreferrer"
|
</StyleTips>
|
||||||
target="_blank"
|
<StyleImage>
|
||||||
style={{
|
<Empty
|
||||||
color: 'var(--affine-link-color)',
|
containerStyle={{
|
||||||
}}
|
width: '200px',
|
||||||
>
|
height: '112px',
|
||||||
AFFiNE Cloud Signup
|
}}
|
||||||
</a>
|
/>
|
||||||
.
|
</StyleImage>
|
||||||
</Trans>
|
<StyleButtonContainer>
|
||||||
</StyleTips>
|
<StyleButton type="primary" onClick={onClose}>
|
||||||
<StyleImage>
|
{t['Got it']()}
|
||||||
<Empty
|
</StyleButton>
|
||||||
containerStyle={{
|
</StyleButtonContainer>
|
||||||
width: '200px',
|
|
||||||
height: '112px',
|
|
||||||
}}
|
|
||||||
/>
|
|
||||||
</StyleImage>
|
|
||||||
<StyleButtonContainer>
|
|
||||||
<StyleButton type="primary" onClick={onClose}>
|
|
||||||
{t['Got it']()}
|
|
||||||
</StyleButton>
|
|
||||||
</StyleButtonContainer>
|
|
||||||
</Content>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -16,6 +16,7 @@ export const Content = styled('div')({
|
|||||||
|
|
||||||
export const ContentTitle = styled('h1')(() => {
|
export const ContentTitle = styled('h1')(() => {
|
||||||
return {
|
return {
|
||||||
|
marginTop: 44,
|
||||||
fontSize: 'var(--affine-font-h6)',
|
fontSize: 'var(--affine-font-h6)',
|
||||||
lineHeight: '28px',
|
lineHeight: '28px',
|
||||||
fontWeight: 600,
|
fontWeight: 600,
|
||||||
@@ -24,8 +25,7 @@ export const ContentTitle = styled('h1')(() => {
|
|||||||
|
|
||||||
export const StyleTips = styled('div')(() => {
|
export const StyleTips = styled('div')(() => {
|
||||||
return {
|
return {
|
||||||
userSelect: 'none',
|
margin: '0 0 20px 0',
|
||||||
margin: '20px 0',
|
|
||||||
a: {
|
a: {
|
||||||
color: 'var(--affine-primary-color)',
|
color: 'var(--affine-primary-color)',
|
||||||
},
|
},
|
||||||
@@ -35,7 +35,6 @@ export const StyleTips = styled('div')(() => {
|
|||||||
export const StyleButton = styled(Button)(() => {
|
export const StyleButton = styled(Button)(() => {
|
||||||
return {
|
return {
|
||||||
textAlign: 'center',
|
textAlign: 'center',
|
||||||
margin: '20px 0',
|
|
||||||
borderRadius: '8px',
|
borderRadius: '8px',
|
||||||
backgroundColor: 'var(--affine-primary-color)',
|
backgroundColor: 'var(--affine-primary-color)',
|
||||||
span: {
|
span: {
|
||||||
@@ -46,11 +45,12 @@ export const StyleButton = styled(Button)(() => {
|
|||||||
export const StyleButtonContainer = styled('div')(() => {
|
export const StyleButtonContainer = styled('div')(() => {
|
||||||
return {
|
return {
|
||||||
width: '100%',
|
width: '100%',
|
||||||
|
marginTop: 20,
|
||||||
...displayFlex('flex-end', 'center'),
|
...displayFlex('flex-end', 'center'),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
export const StyleImage = styled('div')(() => {
|
export const StyleImage = styled('div')(() => {
|
||||||
return {
|
return {
|
||||||
width: '100%',
|
...displayFlex('center', 'center'),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,58 +0,0 @@
|
|||||||
import { Modal, ModalWrapper } from '@affine/component';
|
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
|
||||||
import { CloseIcon } from '@blocksuite/icons';
|
|
||||||
import { IconButton } from '@toeverything/components/button';
|
|
||||||
|
|
||||||
import { Content, ContentTitle, Header, StyleButton, StyleTips } from './style';
|
|
||||||
|
|
||||||
export interface TransformWorkspaceToAffineModalProps {
|
|
||||||
open: boolean;
|
|
||||||
onClose: () => void;
|
|
||||||
onConform: () => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
export const TransformWorkspaceToAffineModal = ({
|
|
||||||
open,
|
|
||||||
onClose,
|
|
||||||
onConform,
|
|
||||||
}: TransformWorkspaceToAffineModalProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Modal
|
|
||||||
open={open}
|
|
||||||
onClose={onClose}
|
|
||||||
data-testid="enable-affine-cloud-modal"
|
|
||||||
>
|
|
||||||
<ModalWrapper width={560} height={292}>
|
|
||||||
<Header>
|
|
||||||
<IconButton onClick={onClose}>
|
|
||||||
<CloseIcon />
|
|
||||||
</IconButton>
|
|
||||||
</Header>
|
|
||||||
<Content>
|
|
||||||
<ContentTitle>{t['Enable AFFiNE Cloud']()}?</ContentTitle>
|
|
||||||
<StyleTips>{t['Enable AFFiNE Cloud Description']()}</StyleTips>
|
|
||||||
{/* <StyleTips>{t('Retain cached cloud data')}</StyleTips> */}
|
|
||||||
<div>
|
|
||||||
<StyleButton
|
|
||||||
data-testid="confirm-enable-cloud-button"
|
|
||||||
type="primary"
|
|
||||||
onClick={onConform}
|
|
||||||
>
|
|
||||||
{t['Sign in and Enable']()}
|
|
||||||
</StyleButton>
|
|
||||||
<StyleButton
|
|
||||||
shape="round"
|
|
||||||
onClick={() => {
|
|
||||||
onClose();
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
{t['Not now']()}
|
|
||||||
</StyleButton>
|
|
||||||
</div>
|
|
||||||
</Content>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
@@ -1,41 +0,0 @@
|
|||||||
import { styled } from '@affine/component';
|
|
||||||
import { Button } from '@toeverything/components/button';
|
|
||||||
|
|
||||||
export const Header = styled('div')({
|
|
||||||
height: '44px',
|
|
||||||
display: 'flex',
|
|
||||||
flexDirection: 'row-reverse',
|
|
||||||
paddingRight: '10px',
|
|
||||||
paddingTop: '10px',
|
|
||||||
flexShrink: 0,
|
|
||||||
});
|
|
||||||
|
|
||||||
export const Content = styled('div')({
|
|
||||||
textAlign: 'center',
|
|
||||||
});
|
|
||||||
|
|
||||||
export const ContentTitle = styled('h1')({
|
|
||||||
fontSize: '20px',
|
|
||||||
lineHeight: '28px',
|
|
||||||
fontWeight: 600,
|
|
||||||
textAlign: 'center',
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyleTips = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
userSelect: 'none',
|
|
||||||
width: '400px',
|
|
||||||
margin: 'auto',
|
|
||||||
marginBottom: '32px',
|
|
||||||
marginTop: '12px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyleButton = styled(Button)(() => {
|
|
||||||
return {
|
|
||||||
width: '284px',
|
|
||||||
display: 'block',
|
|
||||||
margin: 'auto',
|
|
||||||
marginTop: '16px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
@@ -225,9 +225,7 @@ export const PageMenu = ({ rename, pageId }: PageMenuProps) => {
|
|||||||
open={openConfirm}
|
open={openConfirm}
|
||||||
title={pageMeta.title}
|
title={pageMeta.title}
|
||||||
onConfirm={handleOnConfirm}
|
onConfirm={handleOnConfirm}
|
||||||
onCancel={() => {
|
onOpenChange={setOpenConfirm}
|
||||||
setOpenConfirm(false);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
</FlexWrapper>
|
</FlexWrapper>
|
||||||
</>
|
</>
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import { Modal, ModalWrapper } from '@affine/component';
|
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
|
import { Modal } from '@toeverything/components/modal';
|
||||||
import { Command } from 'cmdk';
|
import { Command } from 'cmdk';
|
||||||
import { startTransition, Suspense } from 'react';
|
import { startTransition, Suspense } from 'react';
|
||||||
import { useCallback, useEffect, useRef, useState } from 'react';
|
import { useCallback, useEffect, useRef, useState } from 'react';
|
||||||
@@ -75,93 +75,86 @@ export const QuickSearchModal = ({
|
|||||||
return (
|
return (
|
||||||
<Modal
|
<Modal
|
||||||
open={open}
|
open={open}
|
||||||
onClose={handleClose}
|
onOpenChange={setOpen}
|
||||||
wrapperPosition={['top', 'center']}
|
width={608}
|
||||||
data-testid="quickSearch"
|
contentOptions={{
|
||||||
>
|
['data-testid' as string]: 'quickSearch',
|
||||||
<ModalWrapper
|
style: {
|
||||||
width={608}
|
|
||||||
style={{
|
|
||||||
maxHeight: '80vh',
|
maxHeight: '80vh',
|
||||||
minHeight: '412px',
|
minHeight: '412px',
|
||||||
top: '80px',
|
top: '80px',
|
||||||
overflow: 'hidden',
|
overflow: 'hidden',
|
||||||
|
transform: 'translateX(-50%)',
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Command
|
||||||
|
shouldFilter={false}
|
||||||
|
//Handle KeyboardEvent conflicts with blocksuite
|
||||||
|
onKeyDown={(e: React.KeyboardEvent) => {
|
||||||
|
if (
|
||||||
|
e.key === 'ArrowDown' ||
|
||||||
|
e.key === 'ArrowUp' ||
|
||||||
|
e.key === 'ArrowLeft' ||
|
||||||
|
e.key === 'ArrowRight'
|
||||||
|
) {
|
||||||
|
e.stopPropagation();
|
||||||
|
}
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
{/* <NavigationPath
|
<StyledModalHeader>
|
||||||
blockSuiteWorkspace={blockSuiteWorkspace}
|
<SearchInput
|
||||||
onJumpToPage={() => {
|
ref={inputRef}
|
||||||
setOpen(false);
|
onValueChange={value => {
|
||||||
}}
|
setQuery(value);
|
||||||
/> */}
|
}}
|
||||||
<Command
|
onKeyDown={e => {
|
||||||
shouldFilter={false}
|
// Avoid triggering the cmdk onSelect event when the input method is in use
|
||||||
//Handle KeyboardEvent conflicts with blocksuite
|
if (e.nativeEvent.isComposing) {
|
||||||
onKeyDown={(e: React.KeyboardEvent) => {
|
e.stopPropagation();
|
||||||
if (
|
return;
|
||||||
e.key === 'ArrowDown' ||
|
}
|
||||||
e.key === 'ArrowUp' ||
|
}}
|
||||||
e.key === 'ArrowLeft' ||
|
placeholder={t['Quick search placeholder']()}
|
||||||
e.key === 'ArrowRight'
|
/>
|
||||||
) {
|
<StyledShortcut>
|
||||||
e.stopPropagation();
|
{environment.isBrowser && environment.isMacOs
|
||||||
}
|
? '⌘ + K'
|
||||||
}}
|
: 'Ctrl + K'}
|
||||||
>
|
</StyledShortcut>
|
||||||
<StyledModalHeader>
|
</StyledModalHeader>
|
||||||
<SearchInput
|
<StyledModalDivider />
|
||||||
ref={inputRef}
|
<Command.List>
|
||||||
onValueChange={value => {
|
<StyledContent>
|
||||||
setQuery(value);
|
<Suspense
|
||||||
}}
|
fallback={
|
||||||
onKeyDown={e => {
|
<StyledNotFound>
|
||||||
// Avoid triggering the cmdk onSelect event when the input method is in use
|
<span>{t['com.affine.loading']()}</span>
|
||||||
if (e.nativeEvent.isComposing) {
|
</StyledNotFound>
|
||||||
e.stopPropagation();
|
}
|
||||||
return;
|
>
|
||||||
}
|
<Results
|
||||||
}}
|
query={query}
|
||||||
placeholder={t['Quick search placeholder']()}
|
onClose={handleClose}
|
||||||
/>
|
workspace={workspace}
|
||||||
<StyledShortcut>
|
setShowCreatePage={setShowCreatePage}
|
||||||
{environment.isBrowser && environment.isMacOs
|
/>
|
||||||
? '⌘ + K'
|
</Suspense>
|
||||||
: 'Ctrl + K'}
|
</StyledContent>
|
||||||
</StyledShortcut>
|
{showCreatePage ? (
|
||||||
</StyledModalHeader>
|
<>
|
||||||
<StyledModalDivider />
|
<StyledModalDivider />
|
||||||
<Command.List>
|
<StyledModalFooter>
|
||||||
<StyledContent>
|
<Footer
|
||||||
<Suspense
|
|
||||||
fallback={
|
|
||||||
<StyledNotFound>
|
|
||||||
<span>{t['com.affine.loading']()}</span>
|
|
||||||
</StyledNotFound>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Results
|
|
||||||
query={query}
|
query={query}
|
||||||
onClose={handleClose}
|
onClose={handleClose}
|
||||||
workspace={workspace}
|
blockSuiteWorkspace={blockSuiteWorkspace}
|
||||||
setShowCreatePage={setShowCreatePage}
|
|
||||||
/>
|
/>
|
||||||
</Suspense>
|
</StyledModalFooter>
|
||||||
</StyledContent>
|
</>
|
||||||
{showCreatePage ? (
|
) : null}
|
||||||
<>
|
</Command.List>
|
||||||
<StyledModalDivider />
|
</Command>
|
||||||
<StyledModalFooter>
|
|
||||||
<Footer
|
|
||||||
query={query}
|
|
||||||
onClose={handleClose}
|
|
||||||
blockSuiteWorkspace={blockSuiteWorkspace}
|
|
||||||
/>
|
|
||||||
</StyledModalFooter>
|
|
||||||
</>
|
|
||||||
) : null}
|
|
||||||
</Command.List>
|
|
||||||
</Command>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,9 +1,7 @@
|
|||||||
import {
|
import { MuiClickAwayListener, MuiSlide } from '@affine/component';
|
||||||
ModalCloseButton,
|
|
||||||
MuiClickAwayListener,
|
|
||||||
MuiSlide,
|
|
||||||
} from '@affine/component';
|
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
|
import { CloseIcon } from '@blocksuite/icons';
|
||||||
|
import { IconButton } from '@toeverything/components/button';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
type ShortcutsInfo,
|
type ShortcutsInfo,
|
||||||
@@ -14,13 +12,7 @@ import {
|
|||||||
} from '../../../hooks/affine/use-shortcuts';
|
} from '../../../hooks/affine/use-shortcuts';
|
||||||
import { KeyboardIcon } from './icons';
|
import { KeyboardIcon } from './icons';
|
||||||
import * as styles from './style.css';
|
import * as styles from './style.css';
|
||||||
// import {
|
|
||||||
// StyledListItem,
|
|
||||||
// StyledModalHeader,
|
|
||||||
// StyledShortcutsModal,
|
|
||||||
// StyledSubTitle,
|
|
||||||
// StyledTitle,
|
|
||||||
// } from './style';
|
|
||||||
type ModalProps = {
|
type ModalProps = {
|
||||||
open: boolean;
|
open: boolean;
|
||||||
onClose: () => void;
|
onClose: () => void;
|
||||||
@@ -81,12 +73,16 @@ export const ShortcutsModal = ({ open, onClose }: ModalProps) => {
|
|||||||
{t['Shortcuts']()}
|
{t['Shortcuts']()}
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<ModalCloseButton
|
<IconButton
|
||||||
top={6}
|
style={{
|
||||||
right={6}
|
position: 'absolute',
|
||||||
|
right: 6,
|
||||||
|
top: 6,
|
||||||
|
}}
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
onClose();
|
onClose();
|
||||||
}}
|
}}
|
||||||
|
icon={<CloseIcon />}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<ShortcutsPanel shortcutsInfo={generalShortcutsInfo} />
|
<ShortcutsPanel shortcutsInfo={generalShortcutsInfo} />
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
import { Confirm } from '@affine/component';
|
|
||||||
import { WorkspaceSubPath } from '@affine/env/workspace';
|
import { WorkspaceSubPath } from '@affine/env/workspace';
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { assertExists } from '@blocksuite/global/utils';
|
import { assertExists } from '@blocksuite/global/utils';
|
||||||
import { Button } from '@toeverything/components/button';
|
import { Button } from '@toeverything/components/button';
|
||||||
|
import { ConfirmModal } from '@toeverything/components/modal';
|
||||||
import { useBlockSuitePageMeta } from '@toeverything/hooks/use-block-suite-page-meta';
|
import { useBlockSuitePageMeta } from '@toeverything/hooks/use-block-suite-page-meta';
|
||||||
import { currentPageIdAtom } from '@toeverything/infra/atom';
|
import { currentPageIdAtom } from '@toeverything/infra/atom';
|
||||||
import { useAtomValue } from 'jotai';
|
import { useAtomValue } from 'jotai';
|
||||||
@@ -61,23 +61,21 @@ export const TrashButtonGroup = () => {
|
|||||||
{t['com.affine.trashOperation.deletePermanently']()}
|
{t['com.affine.trashOperation.deletePermanently']()}
|
||||||
</Button>
|
</Button>
|
||||||
</div>
|
</div>
|
||||||
<Confirm
|
<ConfirmModal
|
||||||
title={t['com.affine.trashOperation.delete.title']()}
|
title={t['com.affine.trashOperation.delete.title']()}
|
||||||
content={t['com.affine.trashOperation.delete.description']()}
|
cancelText={t['com.affine.confirmModal.button.cancel']()}
|
||||||
confirmText={t['com.affine.trashOperation.delete']()}
|
description={t['com.affine.trashOperation.delete.description']()}
|
||||||
confirmType="error"
|
confirmButtonOptions={{
|
||||||
|
type: 'error',
|
||||||
|
children: t['com.affine.trashOperation.delete'](),
|
||||||
|
}}
|
||||||
open={open}
|
open={open}
|
||||||
onConfirm={useCallback(() => {
|
onConfirm={useCallback(() => {
|
||||||
jumpToSubPath(workspace.id, WorkspaceSubPath.ALL);
|
jumpToSubPath(workspace.id, WorkspaceSubPath.ALL);
|
||||||
blockSuiteWorkspace.removePage(pageId);
|
blockSuiteWorkspace.removePage(pageId);
|
||||||
toast(t['com.affine.toastMessage.permanentlyDeleted']());
|
toast(t['com.affine.toastMessage.permanentlyDeleted']());
|
||||||
}, [blockSuiteWorkspace, jumpToSubPath, pageId, workspace.id, t])}
|
}, [blockSuiteWorkspace, jumpToSubPath, pageId, workspace.id, t])}
|
||||||
onCancel={() => {
|
onOpenChange={setOpen}
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
onClose={() => {
|
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -177,6 +177,7 @@ export const WorkspaceListModal = ({
|
|||||||
const localWorkspaces = workspaces.filter(
|
const localWorkspaces = workspaces.filter(
|
||||||
({ flavour }) => flavour === WorkspaceFlavour.LOCAL
|
({ flavour }) => flavour === WorkspaceFlavour.LOCAL
|
||||||
) as (AffineCloudWorkspace | LocalWorkspace)[];
|
) as (AffineCloudWorkspace | LocalWorkspace)[];
|
||||||
|
// FIXME: replace mui popover
|
||||||
return (
|
return (
|
||||||
<Popover
|
<Popover
|
||||||
sx={{
|
sx={{
|
||||||
@@ -209,6 +210,7 @@ export const WorkspaceListModal = ({
|
|||||||
openModal: true,
|
openModal: true,
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
onClose();
|
||||||
}}
|
}}
|
||||||
data-testid="cloud-signin-button"
|
data-testid="cloud-signin-button"
|
||||||
>
|
>
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import {
|
import {
|
||||||
EditCollectionModel,
|
EditCollectionModal,
|
||||||
useCollectionManager,
|
useCollectionManager,
|
||||||
} from '@affine/component/page-list';
|
} from '@affine/component/page-list';
|
||||||
import type { Collection } from '@affine/env/filter';
|
import type { Collection } from '@affine/env/filter';
|
||||||
@@ -46,12 +46,12 @@ export const AddCollectionButton = ({
|
|||||||
<PlusIcon />
|
<PlusIcon />
|
||||||
</IconButton>
|
</IconButton>
|
||||||
|
|
||||||
<EditCollectionModel
|
<EditCollectionModal
|
||||||
propertiesMeta={workspace.meta.properties}
|
propertiesMeta={workspace.meta.properties}
|
||||||
getPageInfo={getPageInfo}
|
getPageInfo={getPageInfo}
|
||||||
onConfirm={setting.saveCollection}
|
onConfirm={setting.saveCollection}
|
||||||
open={show}
|
open={show}
|
||||||
onClose={() => showUpdateCollection(false)}
|
onOpenChange={showUpdateCollection}
|
||||||
title={t['com.affine.editCollection.saveCollection']()}
|
title={t['com.affine.editCollection.saveCollection']()}
|
||||||
init={defaultCollection}
|
init={defaultCollection}
|
||||||
/>
|
/>
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import { MenuItem as CollectionItem } from '@affine/component/app-sidebar';
|
import { MenuItem as CollectionItem } from '@affine/component/app-sidebar';
|
||||||
import {
|
import {
|
||||||
EditCollectionModel,
|
EditCollectionModal,
|
||||||
useCollectionManager,
|
useCollectionManager,
|
||||||
useSavedCollections,
|
useSavedCollections,
|
||||||
} from '@affine/component/page-list';
|
} from '@affine/component/page-list';
|
||||||
@@ -203,13 +203,13 @@ const CollectionRenderer = ({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Collapsible.Root open={!collapsed}>
|
<Collapsible.Root open={!collapsed}>
|
||||||
<EditCollectionModel
|
<EditCollectionModal
|
||||||
propertiesMeta={workspace.meta.properties}
|
propertiesMeta={workspace.meta.properties}
|
||||||
getPageInfo={getPageInfo}
|
getPageInfo={getPageInfo}
|
||||||
init={collection}
|
init={collection}
|
||||||
onConfirm={setting.saveCollection}
|
onConfirm={setting.saveCollection}
|
||||||
open={show}
|
open={show}
|
||||||
onClose={() => showUpdateCollection(false)}
|
onOpenChange={showUpdateCollection}
|
||||||
/>
|
/>
|
||||||
<CollectionItem
|
<CollectionItem
|
||||||
data-testid="collection-item"
|
data-testid="collection-item"
|
||||||
|
|||||||
@@ -53,14 +53,14 @@ export type RootAppSidebarProps = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const RouteMenuLinkItem = React.forwardRef<
|
const RouteMenuLinkItem = React.forwardRef<
|
||||||
HTMLButtonElement,
|
HTMLDivElement,
|
||||||
{
|
{
|
||||||
currentPath: string; // todo: pass through useRouter?
|
currentPath: string; // todo: pass through useRouter?
|
||||||
path: string;
|
path: string;
|
||||||
icon: ReactElement;
|
icon: ReactElement;
|
||||||
children?: ReactElement;
|
children?: ReactElement;
|
||||||
isDraggedOver?: boolean;
|
isDraggedOver?: boolean;
|
||||||
} & React.HTMLAttributes<HTMLButtonElement>
|
} & React.HTMLAttributes<HTMLDivElement>
|
||||||
>(({ currentPath, path, icon, children, isDraggedOver, ...props }, ref) => {
|
>(({ currentPath, path, icon, children, isDraggedOver, ...props }, ref) => {
|
||||||
// Force active style when a page is dragged over
|
// Force active style when a page is dragged over
|
||||||
const active = isDraggedOver || currentPath === path;
|
const active = isDraggedOver || currentPath === path;
|
||||||
|
|||||||
@@ -86,8 +86,8 @@ export const Setting = () => {
|
|||||||
activeTab={activeTab}
|
activeTab={activeTab}
|
||||||
workspaceId={workspaceId}
|
workspaceId={workspaceId}
|
||||||
onSettingClick={onSettingClick}
|
onSettingClick={onSettingClick}
|
||||||
setOpen={useCallback(
|
onOpenChange={useCallback(
|
||||||
open => {
|
(open: boolean) => {
|
||||||
setOpenSettingModalAtom(prev => ({ ...prev, open }));
|
setOpenSettingModalAtom(prev => ({ ...prev, open }));
|
||||||
},
|
},
|
||||||
[setOpenSettingModalAtom]
|
[setOpenSettingModalAtom]
|
||||||
@@ -147,9 +147,7 @@ export function CurrentWorkspaceModals() {
|
|||||||
<Suspense>
|
<Suspense>
|
||||||
<TmpDisableAffineCloudModal
|
<TmpDisableAffineCloudModal
|
||||||
open={openDisableCloudAlertModal}
|
open={openDisableCloudAlertModal}
|
||||||
onClose={useCallback(() => {
|
onOpenChange={setOpenDisableCloudAlertModal}
|
||||||
setOpenDisableCloudAlertModal(false);
|
|
||||||
}, [setOpenDisableCloudAlertModal])}
|
|
||||||
/>
|
/>
|
||||||
</Suspense>
|
</Suspense>
|
||||||
{environment.isDesktop && (
|
{environment.isDesktop && (
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ export default {
|
|||||||
} satisfies Meta;
|
} satisfies Meta;
|
||||||
|
|
||||||
export const Basic: StoryFn = () => {
|
export const Basic: StoryFn = () => {
|
||||||
return <TourModal open={true} onClose={() => {}} />;
|
return <TourModal open={true} />;
|
||||||
};
|
};
|
||||||
Basic.args = {
|
Basic.args = {
|
||||||
logoSrc: '/imgs/affine-text-logo.png',
|
logoSrc: '/imgs/affine-text-logo.png',
|
||||||
|
|||||||
@@ -136,11 +136,11 @@ export const DisableModal: StoryFn = () => {
|
|||||||
</StyledDisableButton>
|
</StyledDisableButton>
|
||||||
<PublicLinkDisableModal
|
<PublicLinkDisableModal
|
||||||
open={open}
|
open={open}
|
||||||
onConfirmDisable={() => {
|
onConfirm={() => {
|
||||||
toast('Disabled');
|
toast('Disabled');
|
||||||
setOpen(false);
|
setOpen(false);
|
||||||
}}
|
}}
|
||||||
onClose={() => setOpen(false)}
|
onOpenChange={setOpen}
|
||||||
/>
|
/>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ import { Link } from 'react-router-dom';
|
|||||||
|
|
||||||
import * as styles from './index.css';
|
import * as styles from './index.css';
|
||||||
|
|
||||||
export interface MenuItemProps extends React.HTMLAttributes<HTMLButtonElement> {
|
export interface MenuItemProps extends React.HTMLAttributes<HTMLDivElement> {
|
||||||
icon?: React.ReactElement;
|
icon?: React.ReactElement;
|
||||||
active?: boolean;
|
active?: boolean;
|
||||||
disabled?: boolean;
|
disabled?: boolean;
|
||||||
@@ -25,7 +25,7 @@ const stopPropagation: React.MouseEventHandler = e => {
|
|||||||
e.stopPropagation();
|
e.stopPropagation();
|
||||||
};
|
};
|
||||||
|
|
||||||
export const MenuItem = React.forwardRef<HTMLButtonElement, MenuItemProps>(
|
export const MenuItem = React.forwardRef<HTMLDivElement, MenuItemProps>(
|
||||||
(
|
(
|
||||||
{
|
{
|
||||||
onClick,
|
onClick,
|
||||||
@@ -42,7 +42,7 @@ export const MenuItem = React.forwardRef<HTMLButtonElement, MenuItemProps>(
|
|||||||
) => {
|
) => {
|
||||||
const collapsible = onCollapsedChange !== undefined;
|
const collapsible = onCollapsedChange !== undefined;
|
||||||
return (
|
return (
|
||||||
<button
|
<div
|
||||||
ref={ref}
|
ref={ref}
|
||||||
{...props}
|
{...props}
|
||||||
onClick={onClick}
|
onClick={onClick}
|
||||||
@@ -82,22 +82,21 @@ export const MenuItem = React.forwardRef<HTMLButtonElement, MenuItemProps>(
|
|||||||
{postfix}
|
{postfix}
|
||||||
</div>
|
</div>
|
||||||
) : null}
|
) : null}
|
||||||
</button>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
MenuItem.displayName = 'MenuItem';
|
MenuItem.displayName = 'MenuItem';
|
||||||
|
|
||||||
export const MenuLinkItem = React.forwardRef<
|
export const MenuLinkItem = React.forwardRef<HTMLDivElement, MenuLinkItemProps>(
|
||||||
HTMLButtonElement,
|
({ to, ...props }, ref) => {
|
||||||
MenuLinkItemProps
|
return (
|
||||||
>(({ to, ...props }, ref) => {
|
<Link to={to} className={styles.linkItemRoot}>
|
||||||
return (
|
{/* The <a> element rendered by Link does not generate display box due to `display: contents` style */}
|
||||||
<Link to={to} className={styles.linkItemRoot}>
|
{/* Thus ref is passed to MenuItem instead of Link */}
|
||||||
{/* The <a> element rendered by Link does not generate display box due to `display: contents` style */}
|
<MenuItem ref={ref} {...props}></MenuItem>
|
||||||
{/* Thus ref is passed to MenuItem instead of Link */}
|
</Link>
|
||||||
<MenuItem ref={ref} {...props}></MenuItem>
|
);
|
||||||
</Link>
|
}
|
||||||
);
|
);
|
||||||
});
|
|
||||||
MenuLinkItem.displayName = 'MenuLinkItem';
|
MenuLinkItem.displayName = 'MenuLinkItem';
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import clsx from 'clsx';
|
import clsx from 'clsx';
|
||||||
import type { FC } from 'react';
|
import type { FC, HTMLAttributes } from 'react';
|
||||||
|
|
||||||
import { Input, type InputProps } from '../../ui/input';
|
import { Input, type InputProps } from '../../ui/input';
|
||||||
import { authInputWrapper, formHint } from './share.css';
|
import { authInputWrapper, formHint } from './share.css';
|
||||||
@@ -9,6 +9,7 @@ export type AuthInputProps = InputProps & {
|
|||||||
errorHint?: string;
|
errorHint?: string;
|
||||||
withoutHint?: boolean;
|
withoutHint?: boolean;
|
||||||
onEnter?: () => void;
|
onEnter?: () => void;
|
||||||
|
wrapperProps?: HTMLAttributes<HTMLDivElement>;
|
||||||
};
|
};
|
||||||
export const AuthInput: FC<AuthInputProps> = ({
|
export const AuthInput: FC<AuthInputProps> = ({
|
||||||
label,
|
label,
|
||||||
@@ -16,13 +17,15 @@ export const AuthInput: FC<AuthInputProps> = ({
|
|||||||
errorHint,
|
errorHint,
|
||||||
withoutHint = false,
|
withoutHint = false,
|
||||||
onEnter,
|
onEnter,
|
||||||
|
wrapperProps: { className, ...otherWrapperProps } = {},
|
||||||
...inputProps
|
...inputProps
|
||||||
}) => {
|
}) => {
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
className={clsx(authInputWrapper, {
|
className={clsx(authInputWrapper, className, {
|
||||||
'without-hint': withoutHint,
|
'without-hint': withoutHint,
|
||||||
})}
|
})}
|
||||||
|
{...otherWrapperProps}
|
||||||
>
|
>
|
||||||
{label ? <label>{label}</label> : null}
|
{label ? <label>{label}</label> : null}
|
||||||
<Input
|
<Input
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
import { Modal, ModalCloseButton, ModalWrapper } from '@affine/component';
|
import { Modal } from '@toeverything/components/modal';
|
||||||
import type { FC, PropsWithChildren } from 'react';
|
import type { FC, PropsWithChildren } from 'react';
|
||||||
import { useCallback } from 'react';
|
|
||||||
|
|
||||||
export type AuthModalProps = {
|
export type AuthModalProps = {
|
||||||
open: boolean;
|
open: boolean;
|
||||||
@@ -12,32 +11,18 @@ export const AuthModal: FC<PropsWithChildren<AuthModalProps>> = ({
|
|||||||
open,
|
open,
|
||||||
setOpen,
|
setOpen,
|
||||||
}) => {
|
}) => {
|
||||||
const handleClose = useCallback(() => {
|
|
||||||
setOpen(false);
|
|
||||||
}, [setOpen]);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal
|
<Modal
|
||||||
open={open}
|
open={open}
|
||||||
onClose={handleClose}
|
onOpenChange={setOpen}
|
||||||
wrapperPosition={['center', 'center']}
|
width={400}
|
||||||
data-testid="auth-modal"
|
height={468}
|
||||||
|
contentOptions={{
|
||||||
|
['data-testid' as string]: 'auth-modal',
|
||||||
|
style: { padding: '44px 40px 0' },
|
||||||
|
}}
|
||||||
>
|
>
|
||||||
<ModalWrapper
|
{children}
|
||||||
width={1080}
|
|
||||||
height={760}
|
|
||||||
style={{
|
|
||||||
height: '468px',
|
|
||||||
width: '400px',
|
|
||||||
overflow: 'hidden',
|
|
||||||
backgroundColor: 'var(--affine-white)',
|
|
||||||
boxShadow: 'var(--affine-popover-shadow)',
|
|
||||||
padding: '44px 40px 0',
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<ModalCloseButton top={20} right={20} onClick={handleClose} />
|
|
||||||
{children}
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,13 +1,14 @@
|
|||||||
import {
|
import {
|
||||||
|
CloseIcon,
|
||||||
ExportToHtmlIcon,
|
ExportToHtmlIcon,
|
||||||
ExportToMarkdownIcon,
|
ExportToMarkdownIcon,
|
||||||
HelpIcon,
|
HelpIcon,
|
||||||
NewIcon,
|
NewIcon,
|
||||||
NotionIcon,
|
NotionIcon,
|
||||||
} from '@blocksuite/icons';
|
} from '@blocksuite/icons';
|
||||||
|
import { IconButton } from '@toeverything/components/button';
|
||||||
import { Tooltip } from '@toeverything/components/tooltip';
|
import { Tooltip } from '@toeverything/components/tooltip';
|
||||||
|
|
||||||
import { ModalCloseButton } from '../../ui/modal';
|
|
||||||
import { BlockCard } from '../card/block-card';
|
import { BlockCard } from '../card/block-card';
|
||||||
import {
|
import {
|
||||||
importPageBodyStyle,
|
importPageBodyStyle,
|
||||||
@@ -27,7 +28,17 @@ export const ImportPage = ({
|
|||||||
onClose: () => void;
|
onClose: () => void;
|
||||||
}) => (
|
}) => (
|
||||||
<div className={importPageContainerStyle}>
|
<div className={importPageContainerStyle}>
|
||||||
<ModalCloseButton top={6} right={6} onClick={onClose} />
|
<IconButton
|
||||||
|
style={{
|
||||||
|
position: 'absolute',
|
||||||
|
right: 6,
|
||||||
|
top: 6,
|
||||||
|
}}
|
||||||
|
onClick={() => {
|
||||||
|
onClose();
|
||||||
|
}}
|
||||||
|
icon={<CloseIcon />}
|
||||||
|
/>
|
||||||
<div className={importPageBodyStyle}>
|
<div className={importPageBodyStyle}>
|
||||||
<div className="title">Import</div>
|
<div className="title">Import</div>
|
||||||
<span>
|
<span>
|
||||||
|
|||||||
@@ -1,12 +1,10 @@
|
|||||||
import { Permission } from '@affine/graphql';
|
import { Permission } from '@affine/graphql';
|
||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { Button } from '@toeverything/components/button';
|
import { ConfirmModal } from '@toeverything/components/modal';
|
||||||
import { useCallback, useEffect, useState } from 'react';
|
import { useCallback, useEffect, useState } from 'react';
|
||||||
|
|
||||||
import { Modal, ModalCloseButton, ModalWrapper } from '../../ui/modal';
|
|
||||||
import { AuthInput } from '..//auth-components';
|
import { AuthInput } from '..//auth-components';
|
||||||
import { emailRegex } from '..//auth-components/utils';
|
import { emailRegex } from '..//auth-components/utils';
|
||||||
import * as styles from './styles.css';
|
|
||||||
|
|
||||||
export interface InviteModalProps {
|
export interface InviteModalProps {
|
||||||
open: boolean;
|
open: boolean;
|
||||||
@@ -26,10 +24,6 @@ export const InviteModal = ({
|
|||||||
const [permission] = useState(Permission.Write);
|
const [permission] = useState(Permission.Write);
|
||||||
const [isValidEmail, setIsValidEmail] = useState(true);
|
const [isValidEmail, setIsValidEmail] = useState(true);
|
||||||
|
|
||||||
const handleCancel = useCallback(() => {
|
|
||||||
setOpen(false);
|
|
||||||
}, [setOpen]);
|
|
||||||
|
|
||||||
const handleConfirm = useCallback(() => {
|
const handleConfirm = useCallback(() => {
|
||||||
if (!emailRegex.test(inviteEmail)) {
|
if (!emailRegex.test(inviteEmail)) {
|
||||||
setIsValidEmail(false);
|
setIsValidEmail(false);
|
||||||
@@ -51,47 +45,41 @@ export const InviteModal = ({
|
|||||||
}, [open]);
|
}, [open]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal
|
<ConfirmModal
|
||||||
wrapperPosition={['center', 'center']}
|
|
||||||
data-testid="invite-modal"
|
|
||||||
open={open}
|
open={open}
|
||||||
>
|
onOpenChange={setOpen}
|
||||||
<ModalWrapper
|
width={480}
|
||||||
width={480}
|
title={t['Invite Members']()}
|
||||||
height={254}
|
description={t['Invite Members Message']()}
|
||||||
style={{
|
cancelText={t['com.affine.inviteModal.button.cancel']()}
|
||||||
|
contentOptions={{
|
||||||
|
['data-testid' as string]: 'invite-modal',
|
||||||
|
style: {
|
||||||
padding: '20px 26px',
|
padding: '20px 26px',
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
confirmButtonOptions={{
|
||||||
|
loading: isMutating,
|
||||||
|
type: 'primary',
|
||||||
|
['data-testid' as string]: 'confirm-enable-affine-cloud-button',
|
||||||
|
children: t['Invite'](),
|
||||||
|
}}
|
||||||
|
onConfirm={handleConfirm}
|
||||||
|
>
|
||||||
|
{/*TODO: check email & add placeholder*/}
|
||||||
|
<AuthInput
|
||||||
|
disabled={isMutating}
|
||||||
|
placeholder="email@example.com"
|
||||||
|
value={inviteEmail}
|
||||||
|
onChange={setInviteEmail}
|
||||||
|
error={!isValidEmail}
|
||||||
|
errorHint={isValidEmail ? '' : t['com.affine.auth.sign.email.error']()}
|
||||||
|
onEnter={handleConfirm}
|
||||||
|
wrapperProps={{
|
||||||
|
style: { padding: 0 },
|
||||||
}}
|
}}
|
||||||
>
|
size="large"
|
||||||
<ModalCloseButton top={20} right={20} onClick={handleCancel} />
|
/>
|
||||||
|
</ConfirmModal>
|
||||||
<div className={styles.inviteModalTitle}>{t['Invite Members']()}</div>
|
|
||||||
<div className={styles.inviteModalContent}>
|
|
||||||
{t['Invite Members Message']()}
|
|
||||||
{/*TODO: check email & add placeholder*/}
|
|
||||||
<AuthInput
|
|
||||||
disabled={isMutating}
|
|
||||||
placeholder="email@example.com"
|
|
||||||
value={inviteEmail}
|
|
||||||
onChange={setInviteEmail}
|
|
||||||
error={!isValidEmail}
|
|
||||||
errorHint={
|
|
||||||
isValidEmail ? '' : t['com.affine.auth.sign.email.error']()
|
|
||||||
}
|
|
||||||
onEnter={handleConfirm}
|
|
||||||
style={{ marginTop: 20 }}
|
|
||||||
size="large"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div className={styles.inviteModalButtonContainer}>
|
|
||||||
<Button style={{ marginRight: 20 }} onClick={handleCancel}>
|
|
||||||
{t['com.affine.inviteModal.button.cancel']()}
|
|
||||||
</Button>
|
|
||||||
<Button type="primary" onClick={handleConfirm} loading={isMutating}>
|
|
||||||
{t['Invite']()}
|
|
||||||
</Button>
|
|
||||||
</div>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -10,10 +10,11 @@ import {
|
|||||||
} from '@blocksuite/icons';
|
} from '@blocksuite/icons';
|
||||||
import { IconButton } from '@toeverything/components/button';
|
import { IconButton } from '@toeverything/components/button';
|
||||||
import { Menu, MenuIcon, MenuItem } from '@toeverything/components/menu';
|
import { Menu, MenuIcon, MenuItem } from '@toeverything/components/menu';
|
||||||
|
import { ConfirmModal } from '@toeverything/components/modal';
|
||||||
import { Tooltip } from '@toeverything/components/tooltip';
|
import { Tooltip } from '@toeverything/components/tooltip';
|
||||||
import { useState } from 'react';
|
import { useState } from 'react';
|
||||||
|
|
||||||
import { Confirm, FlexWrapper } from '../../..';
|
import { FlexWrapper } from '../../..';
|
||||||
import { DisablePublicSharing, MoveToTrash } from './operation-menu-items';
|
import { DisablePublicSharing, MoveToTrash } from './operation-menu-items';
|
||||||
|
|
||||||
export interface OperationCellProps {
|
export interface OperationCellProps {
|
||||||
@@ -106,19 +107,12 @@ export const OperationCell = ({
|
|||||||
onRemoveToTrash();
|
onRemoveToTrash();
|
||||||
setOpen(false);
|
setOpen(false);
|
||||||
}}
|
}}
|
||||||
onClose={() => {
|
onOpenChange={setOpen}
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
onCancel={() => {
|
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
<DisablePublicSharing.DisablePublicSharingModal
|
<DisablePublicSharing.DisablePublicSharingModal
|
||||||
onConfirmDisable={onDisablePublicSharing}
|
onConfirm={onDisablePublicSharing}
|
||||||
open={openDisableShared}
|
open={openDisableShared}
|
||||||
onClose={() => {
|
onOpenChange={setOpenDisableShared}
|
||||||
setOpenDisableShared(false);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
@@ -161,22 +155,20 @@ export const TrashOperationCell = ({
|
|||||||
<DeletePermanentlyIcon />
|
<DeletePermanentlyIcon />
|
||||||
</IconButton>
|
</IconButton>
|
||||||
</Tooltip>
|
</Tooltip>
|
||||||
<Confirm
|
<ConfirmModal
|
||||||
title={`${t['com.affine.trashOperation.deletePermanently']()}?`}
|
title={`${t['com.affine.trashOperation.deletePermanently']()}?`}
|
||||||
content={t['com.affine.trashOperation.deleteDescription']()}
|
description={t['com.affine.trashOperation.deleteDescription']()}
|
||||||
confirmText={t['com.affine.trashOperation.delete']()}
|
cancelText={t['com.affine.confirmModal.button.cancel']()}
|
||||||
confirmType="error"
|
confirmButtonOptions={{
|
||||||
|
type: 'error',
|
||||||
|
children: t['com.affine.trashOperation.delete'](),
|
||||||
|
}}
|
||||||
open={open}
|
open={open}
|
||||||
|
onOpenChange={setOpen}
|
||||||
onConfirm={() => {
|
onConfirm={() => {
|
||||||
onPermanentlyDeletePage();
|
onPermanentlyDeletePage();
|
||||||
setOpen(false);
|
setOpen(false);
|
||||||
}}
|
}}
|
||||||
onClose={() => {
|
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
onCancel={() => {
|
|
||||||
setOpen(false);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
</FlexWrapper>
|
</FlexWrapper>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -5,9 +5,10 @@ import {
|
|||||||
MenuItem,
|
MenuItem,
|
||||||
type MenuItemProps,
|
type MenuItemProps,
|
||||||
} from '@toeverything/components/menu';
|
} from '@toeverything/components/menu';
|
||||||
|
import {
|
||||||
import type { ConfirmProps } from '../../..';
|
ConfirmModal,
|
||||||
import { Confirm } from '../../..';
|
type ConfirmModalProps,
|
||||||
|
} from '@toeverything/components/modal';
|
||||||
|
|
||||||
export const MoveToTrash = (props: MenuItemProps) => {
|
export const MoveToTrash = (props: MenuItemProps) => {
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
@@ -27,26 +28,29 @@ export const MoveToTrash = (props: MenuItemProps) => {
|
|||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
const ConfirmModal = ({
|
const MoveToTrashConfirm = ({
|
||||||
title,
|
title,
|
||||||
...confirmModalProps
|
...confirmModalProps
|
||||||
}: {
|
}: {
|
||||||
title: string;
|
title: string;
|
||||||
} & ConfirmProps) => {
|
} & ConfirmModalProps) => {
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Confirm
|
<ConfirmModal
|
||||||
title={t['com.affine.moveToTrash.confirmModal.title']()}
|
title={t['com.affine.moveToTrash.confirmModal.title']()}
|
||||||
content={t['com.affine.moveToTrash.confirmModal.description']({
|
description={t['com.affine.moveToTrash.confirmModal.description']({
|
||||||
title: title || 'Untitled',
|
title: title || 'Untitled',
|
||||||
})}
|
})}
|
||||||
confirmButtonTestId="confirm-delete-page"
|
cancelText={t['com.affine.confirmModal.button.cancel']()}
|
||||||
confirmText={t.Delete()}
|
confirmButtonOptions={{
|
||||||
confirmType="error"
|
['data-testid' as string]: 'confirm-delete-page',
|
||||||
|
type: 'error',
|
||||||
|
children: t.Delete(),
|
||||||
|
}}
|
||||||
{...confirmModalProps}
|
{...confirmModalProps}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
MoveToTrash.ConfirmModal = ConfirmModal;
|
MoveToTrash.ConfirmModal = MoveToTrashConfirm;
|
||||||
|
|||||||
@@ -5,14 +5,14 @@ import { ViewLayersIcon } from '@blocksuite/icons';
|
|||||||
import { Button } from '@toeverything/components/button';
|
import { Button } from '@toeverything/components/button';
|
||||||
import { Tooltip } from '@toeverything/components/tooltip';
|
import { Tooltip } from '@toeverything/components/tooltip';
|
||||||
import clsx from 'clsx';
|
import clsx from 'clsx';
|
||||||
import { useCallback, useState } from 'react';
|
import { useState } from 'react';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
type CollectionsAtom,
|
type CollectionsAtom,
|
||||||
useCollectionManager,
|
useCollectionManager,
|
||||||
} from '../use-collection-manager';
|
} from '../use-collection-manager';
|
||||||
import * as styles from './collection-bar.css';
|
import * as styles from './collection-bar.css';
|
||||||
import { EditCollectionModel } from './create-collection';
|
import { EditCollectionModal } from './create-collection';
|
||||||
import { useActions } from './use-action';
|
import { useActions } from './use-action';
|
||||||
|
|
||||||
interface CollectionBarProps {
|
interface CollectionBarProps {
|
||||||
@@ -33,21 +33,20 @@ export const CollectionBar = (props: CollectionBarProps) => {
|
|||||||
setting,
|
setting,
|
||||||
openEdit: () => setOpen(true),
|
openEdit: () => setOpen(true),
|
||||||
});
|
});
|
||||||
const onClose = useCallback(() => setOpen(false), []);
|
|
||||||
|
|
||||||
return !setting.isDefault ? (
|
return !setting.isDefault ? (
|
||||||
<tr style={{ userSelect: 'none' }}>
|
<tr style={{ userSelect: 'none' }}>
|
||||||
<td>
|
<td>
|
||||||
<div className={styles.view}>
|
<div className={styles.view}>
|
||||||
<EditCollectionModel
|
<EditCollectionModal
|
||||||
propertiesMeta={propertiesMeta}
|
propertiesMeta={propertiesMeta}
|
||||||
getPageInfo={getPageInfo}
|
getPageInfo={getPageInfo}
|
||||||
init={collection}
|
init={collection}
|
||||||
open={open}
|
open={open}
|
||||||
onClose={onClose}
|
onOpenChange={setOpen}
|
||||||
// eslint-disable-next-line @typescript-eslint/no-misused-promises
|
// eslint-disable-next-line @typescript-eslint/no-misused-promises
|
||||||
onConfirm={setting.updateCollection}
|
onConfirm={setting.updateCollection}
|
||||||
></EditCollectionModel>
|
/>
|
||||||
<ViewLayersIcon
|
<ViewLayersIcon
|
||||||
style={{
|
style={{
|
||||||
height: 20,
|
height: 20,
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ import { useCallback, useRef, useState } from 'react';
|
|||||||
import { CreateFilterMenu } from '../filter/vars';
|
import { CreateFilterMenu } from '../filter/vars';
|
||||||
import type { useCollectionManager } from '../use-collection-manager';
|
import type { useCollectionManager } from '../use-collection-manager';
|
||||||
import * as styles from './collection-list.css';
|
import * as styles from './collection-list.css';
|
||||||
import { EditCollectionModel } from './create-collection';
|
import { EditCollectionModal } from './create-collection';
|
||||||
import { useActions } from './use-action';
|
import { useActions } from './use-action';
|
||||||
|
|
||||||
const CollectionOption = ({
|
const CollectionOption = ({
|
||||||
@@ -126,14 +126,16 @@ export const CollectionList = ({
|
|||||||
},
|
},
|
||||||
[setting]
|
[setting]
|
||||||
);
|
);
|
||||||
const closeUpdateCollectionModal = useCallback(
|
const closeUpdateCollectionModal = useCallback((open: boolean) => {
|
||||||
() => setCollection(undefined),
|
if (!open) {
|
||||||
[]
|
setCollection(undefined);
|
||||||
);
|
}
|
||||||
|
}, []);
|
||||||
|
|
||||||
const onConfirm = useCallback(
|
const onConfirm = useCallback(
|
||||||
async (view: Collection) => {
|
async (view: Collection) => {
|
||||||
await setting.updateCollection(view);
|
await setting.updateCollection(view);
|
||||||
closeUpdateCollectionModal();
|
closeUpdateCollectionModal(false);
|
||||||
},
|
},
|
||||||
[closeUpdateCollectionModal, setting]
|
[closeUpdateCollectionModal, setting]
|
||||||
);
|
);
|
||||||
@@ -214,14 +216,14 @@ export const CollectionList = ({
|
|||||||
{t['com.affine.filter']()}
|
{t['com.affine.filter']()}
|
||||||
</Button>
|
</Button>
|
||||||
</Menu>
|
</Menu>
|
||||||
<EditCollectionModel
|
<EditCollectionModal
|
||||||
propertiesMeta={propertiesMeta}
|
propertiesMeta={propertiesMeta}
|
||||||
getPageInfo={getPageInfo}
|
getPageInfo={getPageInfo}
|
||||||
init={collection}
|
init={collection}
|
||||||
open={!!collection}
|
open={!!collection}
|
||||||
onClose={closeUpdateCollectionModal}
|
onOpenChange={closeUpdateCollectionModal}
|
||||||
onConfirm={onConfirm}
|
onConfirm={onConfirm}
|
||||||
></EditCollectionModel>
|
/>
|
||||||
</FlexWrapper>
|
</FlexWrapper>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -10,72 +10,69 @@ import {
|
|||||||
} from '@blocksuite/icons';
|
} from '@blocksuite/icons';
|
||||||
import { uuidv4 } from '@blocksuite/store';
|
import { uuidv4 } from '@blocksuite/store';
|
||||||
import { Button } from '@toeverything/components/button';
|
import { Button } from '@toeverything/components/button';
|
||||||
|
import { Modal } from '@toeverything/components/modal';
|
||||||
import { useCallback, useMemo, useState } from 'react';
|
import { useCallback, useMemo, useState } from 'react';
|
||||||
|
|
||||||
import {
|
import { Input, ScrollableContainer } from '../../..';
|
||||||
Input,
|
|
||||||
Modal,
|
|
||||||
ModalCloseButton,
|
|
||||||
ModalWrapper,
|
|
||||||
ScrollableContainer,
|
|
||||||
} from '../../..';
|
|
||||||
import { FilterList } from '../filter';
|
import { FilterList } from '../filter';
|
||||||
import * as styles from './collection-list.css';
|
import * as styles from './collection-list.css';
|
||||||
|
|
||||||
interface EditCollectionModelProps {
|
interface EditCollectionModalProps {
|
||||||
init?: Collection;
|
init?: Collection;
|
||||||
title?: string;
|
title?: string;
|
||||||
open: boolean;
|
open: boolean;
|
||||||
getPageInfo: GetPageInfoById;
|
getPageInfo: GetPageInfoById;
|
||||||
propertiesMeta: PropertiesMeta;
|
propertiesMeta: PropertiesMeta;
|
||||||
onClose: () => void;
|
onOpenChange: (open: boolean) => void;
|
||||||
onConfirm: (view: Collection) => Promise<void>;
|
onConfirm: (view: Collection) => Promise<void>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const EditCollectionModel = ({
|
export const EditCollectionModal = ({
|
||||||
init,
|
init,
|
||||||
onConfirm,
|
onConfirm,
|
||||||
open,
|
open,
|
||||||
onClose,
|
onOpenChange,
|
||||||
getPageInfo,
|
getPageInfo,
|
||||||
propertiesMeta,
|
propertiesMeta,
|
||||||
title,
|
title,
|
||||||
}: EditCollectionModelProps) => {
|
}: EditCollectionModalProps) => {
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
const onConfirmOnCollection = useCallback(
|
const onConfirmOnCollection = useCallback(
|
||||||
(view: Collection) => {
|
(view: Collection) => {
|
||||||
onConfirm(view)
|
onConfirm(view)
|
||||||
.then(() => {
|
.then(() => {
|
||||||
onClose();
|
onOpenChange(false);
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch(err => {
|
||||||
console.error(err);
|
console.error(err);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
[onClose, onConfirm]
|
[onConfirm, onOpenChange]
|
||||||
);
|
);
|
||||||
|
const onCancel = useCallback(() => {
|
||||||
|
onOpenChange(false);
|
||||||
|
}, [onOpenChange]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal open={open} onClose={onClose}>
|
<Modal
|
||||||
<ModalWrapper
|
open={open}
|
||||||
width={600}
|
onOpenChange={onOpenChange}
|
||||||
style={{
|
width={600}
|
||||||
padding: '40px',
|
contentOptions={{
|
||||||
background: 'var(--affine-background-primary-color)',
|
style: { padding: '40px' },
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<ModalCloseButton top={12} right={12} onClick={onClose} />
|
{init ? (
|
||||||
{init ? (
|
<EditCollection
|
||||||
<EditCollection
|
propertiesMeta={propertiesMeta}
|
||||||
propertiesMeta={propertiesMeta}
|
title={title}
|
||||||
title={title}
|
onConfirmText={t['com.affine.editCollection.save']()}
|
||||||
onConfirmText={t['com.affine.editCollection.save']()}
|
init={init}
|
||||||
init={init}
|
getPageInfo={getPageInfo}
|
||||||
getPageInfo={getPageInfo}
|
onCancel={onCancel}
|
||||||
onCancel={onClose}
|
onConfirm={onConfirmOnCollection}
|
||||||
onConfirm={onConfirmOnCollection}
|
/>
|
||||||
/>
|
) : null}
|
||||||
) : null}
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
@@ -301,14 +298,14 @@ export const SaveCollectionButton = ({
|
|||||||
>
|
>
|
||||||
{t['com.affine.editCollection.saveCollection']()}
|
{t['com.affine.editCollection.saveCollection']()}
|
||||||
</Button>
|
</Button>
|
||||||
<EditCollectionModel
|
<EditCollectionModal
|
||||||
title={t['com.affine.editCollection.saveCollection']()}
|
title={t['com.affine.editCollection.saveCollection']()}
|
||||||
propertiesMeta={propertiesMeta}
|
propertiesMeta={propertiesMeta}
|
||||||
init={init}
|
init={init}
|
||||||
onConfirm={onConfirm}
|
onConfirm={onConfirm}
|
||||||
open={show}
|
open={show}
|
||||||
getPageInfo={getPageInfo}
|
getPageInfo={getPageInfo}
|
||||||
onClose={() => changeShow(false)}
|
onOpenChange={changeShow}
|
||||||
/>
|
/>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
export { SettingModal, type SettingModalProps } from './modal';
|
|
||||||
export { SettingHeader } from './setting-header';
|
export { SettingHeader } from './setting-header';
|
||||||
export { SettingRow } from './setting-row';
|
export { SettingRow } from './setting-row';
|
||||||
export * from './storage-progess';
|
export * from './storage-progess';
|
||||||
|
|||||||
@@ -1,43 +0,0 @@
|
|||||||
import { Modal, ModalCloseButton, ModalWrapper } from '@affine/component';
|
|
||||||
import type { PropsWithChildren } from 'react';
|
|
||||||
import { useCallback } from 'react';
|
|
||||||
|
|
||||||
export interface SettingModalProps {
|
|
||||||
open: boolean;
|
|
||||||
setOpen: (value: boolean) => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
export const SettingModal = ({
|
|
||||||
children,
|
|
||||||
open,
|
|
||||||
setOpen,
|
|
||||||
}: PropsWithChildren<SettingModalProps>) => {
|
|
||||||
const handleClose = useCallback(() => {
|
|
||||||
setOpen(false);
|
|
||||||
}, [setOpen]);
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Modal
|
|
||||||
open={open}
|
|
||||||
onClose={handleClose}
|
|
||||||
wrapperPosition={['center', 'center']}
|
|
||||||
data-testid="setting-modal"
|
|
||||||
>
|
|
||||||
<ModalWrapper
|
|
||||||
width={1080}
|
|
||||||
height={760}
|
|
||||||
style={{
|
|
||||||
maxHeight: '85vh',
|
|
||||||
maxWidth: '70vw',
|
|
||||||
overflow: 'hidden',
|
|
||||||
display: 'flex',
|
|
||||||
backgroundColor: 'var(--affine-background-overlay-panel-color)',
|
|
||||||
boxShadow: 'var(--affine-popover-shadow)',
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<ModalCloseButton top={16} right={20} onClick={handleClose} />
|
|
||||||
{children}
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
@@ -1,57 +1,24 @@
|
|||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { CloseIcon } from '@blocksuite/icons';
|
import {
|
||||||
import { Button, IconButton } from '@toeverything/components/button';
|
ConfirmModal,
|
||||||
|
type ConfirmModalProps,
|
||||||
|
} from '@toeverything/components/modal';
|
||||||
|
|
||||||
import { Modal, ModalWrapper } from '../../..';
|
export const PublicLinkDisableModal = (props: ConfirmModalProps) => {
|
||||||
import { ButtonContainer, Content, Header, StyleTips, Title } from './style';
|
|
||||||
|
|
||||||
export type PublicLinkDisableProps = {
|
|
||||||
open: boolean;
|
|
||||||
onConfirmDisable: () => void;
|
|
||||||
onClose: () => void;
|
|
||||||
};
|
|
||||||
|
|
||||||
export const PublicLinkDisableModal = ({
|
|
||||||
open,
|
|
||||||
onConfirmDisable,
|
|
||||||
onClose,
|
|
||||||
}: PublicLinkDisableProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal open={open} onClose={onClose}>
|
<ConfirmModal
|
||||||
<ModalWrapper width={480}>
|
width={480}
|
||||||
<Header>
|
title={t['com.affine.publicLinkDisableModal.title']()}
|
||||||
<Title>{t['com.affine.publicLinkDisableModal.title']()}</Title>
|
description={t['com.affine.publicLinkDisableModal.description']()}
|
||||||
<IconButton onClick={onClose}>
|
cancelText={t['com.affine.publicLinkDisableModal.button.cancel']()}
|
||||||
<CloseIcon />
|
confirmButtonOptions={{
|
||||||
</IconButton>
|
type: 'error',
|
||||||
</Header>
|
['data-testid' as string]: 'confirm-enable-affine-cloud-button',
|
||||||
<Content>
|
children: t['com.affine.publicLinkDisableModal.button.disable'](),
|
||||||
<StyleTips>
|
}}
|
||||||
{t['com.affine.publicLinkDisableModal.description']()}
|
{...props}
|
||||||
</StyleTips>
|
/>
|
||||||
<ButtonContainer>
|
|
||||||
<div>
|
|
||||||
<Button onClick={onClose} block>
|
|
||||||
{t['com.affine.publicLinkDisableModal.button.cancel']()}
|
|
||||||
</Button>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<Button
|
|
||||||
data-testid="confirm-enable-affine-cloud-button"
|
|
||||||
type="error"
|
|
||||||
block
|
|
||||||
onClick={() => {
|
|
||||||
onConfirmDisable();
|
|
||||||
onClose();
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
{t['com.affine.publicLinkDisableModal.button.disable']()}
|
|
||||||
</Button>
|
|
||||||
</div>
|
|
||||||
</ButtonContainer>
|
|
||||||
</Content>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,35 +0,0 @@
|
|||||||
import { styled } from '../../..';
|
|
||||||
|
|
||||||
export const Header = styled('div')({
|
|
||||||
display: 'flex',
|
|
||||||
justifyContent: 'space-between',
|
|
||||||
paddingRight: '20px',
|
|
||||||
paddingTop: '20px',
|
|
||||||
paddingLeft: '24px',
|
|
||||||
alignItems: 'center',
|
|
||||||
});
|
|
||||||
|
|
||||||
export const Content = styled('div')({
|
|
||||||
padding: '12px 24px 20px 24px',
|
|
||||||
});
|
|
||||||
|
|
||||||
export const Title = styled('div')({
|
|
||||||
fontSize: 'var(--affine-font-h6)',
|
|
||||||
lineHeight: '26px',
|
|
||||||
fontWeight: 600,
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyleTips = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
userSelect: 'none',
|
|
||||||
marginBottom: '20px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
export const ButtonContainer = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
display: 'flex',
|
|
||||||
justifyContent: 'flex-end',
|
|
||||||
gap: '20px',
|
|
||||||
paddingTop: '20px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
@@ -208,7 +208,10 @@ export const AffineSharePage = (props: ShareMenuProps) => {
|
|||||||
block
|
block
|
||||||
type="danger"
|
type="danger"
|
||||||
className={styles.menuItemStyle}
|
className={styles.menuItemStyle}
|
||||||
onClick={() => setShowDisable(true)}
|
onSelect={e => {
|
||||||
|
e.preventDefault();
|
||||||
|
setShowDisable(true);
|
||||||
|
}}
|
||||||
>
|
>
|
||||||
<div className={styles.disableSharePage}>
|
<div className={styles.disableSharePage}>
|
||||||
{t['Disable Public Link']()}
|
{t['Disable Public Link']()}
|
||||||
@@ -216,10 +219,8 @@ export const AffineSharePage = (props: ShareMenuProps) => {
|
|||||||
</MenuItem>
|
</MenuItem>
|
||||||
<PublicLinkDisableModal
|
<PublicLinkDisableModal
|
||||||
open={showDisable}
|
open={showDisable}
|
||||||
onConfirmDisable={onDisablePublic}
|
onConfirm={onDisablePublic}
|
||||||
onClose={() => {
|
onOpenChange={setShowDisable}
|
||||||
setShowDisable(false);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
</>
|
</>
|
||||||
) : null}
|
) : null}
|
||||||
@@ -231,7 +232,11 @@ export const SharePage = (props: ShareMenuProps) => {
|
|||||||
if (props.workspace.flavour === WorkspaceFlavour.LOCAL) {
|
if (props.workspace.flavour === WorkspaceFlavour.LOCAL) {
|
||||||
return <LocalSharePage {...props} />;
|
return <LocalSharePage {...props} />;
|
||||||
} else if (props.workspace.flavour === WorkspaceFlavour.AFFINE_CLOUD) {
|
} else if (props.workspace.flavour === WorkspaceFlavour.AFFINE_CLOUD) {
|
||||||
return <AffineSharePage {...props} />;
|
return (
|
||||||
|
<>
|
||||||
|
<AffineSharePage {...props} />
|
||||||
|
</>
|
||||||
|
);
|
||||||
}
|
}
|
||||||
throw new Error('Unreachable');
|
throw new Error('Unreachable');
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -5,7 +5,6 @@ export const modalStyle = style({
|
|||||||
display: 'flex',
|
display: 'flex',
|
||||||
flexDirection: 'column',
|
flexDirection: 'column',
|
||||||
alignItems: 'center',
|
alignItems: 'center',
|
||||||
position: 'relative',
|
|
||||||
backgroundColor: 'var(--affine-background-secondary-color)',
|
backgroundColor: 'var(--affine-background-secondary-color)',
|
||||||
borderRadius: '16px',
|
borderRadius: '16px',
|
||||||
overflow: 'hidden',
|
overflow: 'hidden',
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
||||||
import { ArrowLeftSmallIcon, ArrowRightSmallIcon } from '@blocksuite/icons';
|
import { ArrowLeftSmallIcon, ArrowRightSmallIcon } from '@blocksuite/icons';
|
||||||
|
import { Modal, type ModalProps } from '@toeverything/components/modal';
|
||||||
import clsx from 'clsx';
|
import clsx from 'clsx';
|
||||||
import { useState } from 'react';
|
import { useState } from 'react';
|
||||||
|
|
||||||
import { Modal, ModalCloseButton, ModalWrapper } from '../..';
|
|
||||||
import {
|
import {
|
||||||
arrowStyle,
|
arrowStyle,
|
||||||
buttonDisableStyle,
|
buttonDisableStyle,
|
||||||
@@ -25,140 +25,133 @@ import {
|
|||||||
videoStyle,
|
videoStyle,
|
||||||
} from './index.css';
|
} from './index.css';
|
||||||
|
|
||||||
export interface TourModalProps {
|
export const TourModal = (props: ModalProps) => {
|
||||||
open: boolean;
|
|
||||||
onClose: () => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
export const TourModal = ({ open, onClose }: TourModalProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
const t = useAFFiNEI18N();
|
||||||
const [step, setStep] = useState(-1);
|
const [step, setStep] = useState(-1);
|
||||||
const handleClose = () => {
|
|
||||||
setStep(-1);
|
|
||||||
onClose();
|
|
||||||
};
|
|
||||||
return (
|
return (
|
||||||
<Modal
|
<Modal
|
||||||
open={open}
|
width={545}
|
||||||
onClose={handleClose}
|
contentOptions={{
|
||||||
wrapperPosition={['center', 'center']}
|
['data-testid' as string]: 'onboarding-modal',
|
||||||
hideBackdrop
|
style: {
|
||||||
|
minHeight: '480px',
|
||||||
|
padding: 0,
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
overlayOptions={{
|
||||||
|
style: {
|
||||||
|
background: 'transparent',
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
closeButtonOptions={{
|
||||||
|
// @ts-expect-error - fix upstream type
|
||||||
|
'data-testid': 'onboarding-modal-close-button',
|
||||||
|
}}
|
||||||
|
{...props}
|
||||||
>
|
>
|
||||||
<ModalWrapper
|
<div className={modalStyle}>
|
||||||
width={545}
|
<div className={titleContainerStyle}>
|
||||||
style={{ minHeight: '480px' }}
|
{step !== -1 && (
|
||||||
data-testid="onboarding-modal"
|
|
||||||
>
|
|
||||||
<ModalCloseButton
|
|
||||||
top={6}
|
|
||||||
right={10}
|
|
||||||
onClick={handleClose}
|
|
||||||
data-testid="onboarding-modal-close-button"
|
|
||||||
/>
|
|
||||||
<div className={modalStyle}>
|
|
||||||
<div className={titleContainerStyle}>
|
|
||||||
{step !== -1 && (
|
|
||||||
<div
|
|
||||||
className={clsx(titleStyle, {
|
|
||||||
[slideToRightStyle]: step === 0,
|
|
||||||
[formSlideToLeftStyle]: step === 1,
|
|
||||||
})}
|
|
||||||
>
|
|
||||||
{t['com.affine.onboarding.title2']()}
|
|
||||||
</div>
|
|
||||||
)}
|
|
||||||
<div
|
<div
|
||||||
className={clsx(titleStyle, {
|
className={clsx(titleStyle, {
|
||||||
[slideToLeftStyle]: step === 1,
|
[slideToRightStyle]: step === 0,
|
||||||
[formSlideToRightStyle]: step === 0,
|
[formSlideToLeftStyle]: step === 1,
|
||||||
})}
|
})}
|
||||||
>
|
>
|
||||||
{t['com.affine.onboarding.title1']()}
|
{t['com.affine.onboarding.title2']()}
|
||||||
</div>
|
</div>
|
||||||
|
)}
|
||||||
|
<div
|
||||||
|
className={clsx(titleStyle, {
|
||||||
|
[slideToLeftStyle]: step === 1,
|
||||||
|
[formSlideToRightStyle]: step === 0,
|
||||||
|
})}
|
||||||
|
>
|
||||||
|
{t['com.affine.onboarding.title1']()}
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div className={containerStyle}>
|
<div className={containerStyle}>
|
||||||
<div
|
<div
|
||||||
className={clsx(arrowStyle, { [buttonDisableStyle]: step !== 1 })}
|
className={clsx(arrowStyle, { [buttonDisableStyle]: step !== 1 })}
|
||||||
onClick={() => step === 1 && setStep(0)}
|
onClick={() => step === 1 && setStep(0)}
|
||||||
data-testid="onboarding-modal-pre-button"
|
data-testid="onboarding-modal-pre-button"
|
||||||
>
|
>
|
||||||
<ArrowLeftSmallIcon />
|
<ArrowLeftSmallIcon />
|
||||||
</div>
|
</div>
|
||||||
<div className={videoContainerStyle}>
|
<div className={videoContainerStyle}>
|
||||||
<div className={videoSlideStyle}>
|
<div className={videoSlideStyle}>
|
||||||
{step !== -1 && (
|
{step !== -1 && (
|
||||||
<video
|
|
||||||
autoPlay
|
|
||||||
muted
|
|
||||||
loop
|
|
||||||
className={clsx(videoStyle, {
|
|
||||||
[slideToRightStyle]: step === 0,
|
|
||||||
[formSlideToLeftStyle]: step === 1,
|
|
||||||
})}
|
|
||||||
data-testid="onboarding-modal-editing-video"
|
|
||||||
>
|
|
||||||
<source src="/editingVideo.mp4" type="video/mp4" />
|
|
||||||
<source src="/editingVideo.webm" type="video/webm" />
|
|
||||||
</video>
|
|
||||||
)}
|
|
||||||
<video
|
<video
|
||||||
autoPlay
|
autoPlay
|
||||||
muted
|
muted
|
||||||
loop
|
loop
|
||||||
className={clsx(videoStyle, {
|
className={clsx(videoStyle, {
|
||||||
[slideToLeftStyle]: step === 1,
|
[slideToRightStyle]: step === 0,
|
||||||
[formSlideToRightStyle]: step === 0,
|
[formSlideToLeftStyle]: step === 1,
|
||||||
})}
|
})}
|
||||||
data-testid="onboarding-modal-switch-video"
|
data-testid="onboarding-modal-editing-video"
|
||||||
>
|
>
|
||||||
<source src="/switchVideo.mp4" type="video/mp4" />
|
<source src="/editingVideo.mp4" type="video/mp4" />
|
||||||
<source src="/switchVideo.webm" type="video/webm" />
|
<source src="/editingVideo.webm" type="video/webm" />
|
||||||
</video>
|
</video>
|
||||||
</div>
|
)}
|
||||||
</div>
|
<video
|
||||||
<div
|
autoPlay
|
||||||
className={clsx(arrowStyle, { [buttonDisableStyle]: step === 1 })}
|
muted
|
||||||
onClick={() => setStep(1)}
|
loop
|
||||||
data-testid="onboarding-modal-next-button"
|
className={clsx(videoStyle, {
|
||||||
>
|
[slideToLeftStyle]: step === 1,
|
||||||
<ArrowRightSmallIcon />
|
[formSlideToRightStyle]: step === 0,
|
||||||
|
})}
|
||||||
|
data-testid="onboarding-modal-switch-video"
|
||||||
|
>
|
||||||
|
<source src="/switchVideo.mp4" type="video/mp4" />
|
||||||
|
<source src="/switchVideo.webm" type="video/webm" />
|
||||||
|
</video>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<ul className={tabContainerStyle}>
|
<div
|
||||||
<li
|
className={clsx(arrowStyle, { [buttonDisableStyle]: step === 1 })}
|
||||||
className={clsx(tabStyle, {
|
onClick={() => setStep(1)}
|
||||||
[tabActiveStyle]: step !== 1,
|
data-testid="onboarding-modal-next-button"
|
||||||
})}
|
>
|
||||||
onClick={() => setStep(0)}
|
<ArrowRightSmallIcon />
|
||||||
></li>
|
|
||||||
<li
|
|
||||||
className={clsx(tabStyle, { [tabActiveStyle]: step === 1 })}
|
|
||||||
onClick={() => setStep(1)}
|
|
||||||
></li>
|
|
||||||
</ul>
|
|
||||||
<div className={descriptionContainerStyle}>
|
|
||||||
{step !== -1 && (
|
|
||||||
<div
|
|
||||||
className={clsx(descriptionStyle, {
|
|
||||||
[slideToRightStyle]: step === 0,
|
|
||||||
[formSlideToLeftStyle]: step === 1,
|
|
||||||
})}
|
|
||||||
>
|
|
||||||
{t['com.affine.onboarding.videoDescription2']()}
|
|
||||||
</div>
|
|
||||||
)}
|
|
||||||
<div
|
|
||||||
className={clsx(descriptionStyle, {
|
|
||||||
[slideToLeftStyle]: step === 1,
|
|
||||||
[formSlideToRightStyle]: step === 0,
|
|
||||||
})}
|
|
||||||
>
|
|
||||||
{t['com.affine.onboarding.videoDescription1']()}
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</ModalWrapper>
|
<ul className={tabContainerStyle}>
|
||||||
|
<li
|
||||||
|
className={clsx(tabStyle, {
|
||||||
|
[tabActiveStyle]: step !== 1,
|
||||||
|
})}
|
||||||
|
onClick={() => setStep(0)}
|
||||||
|
></li>
|
||||||
|
<li
|
||||||
|
className={clsx(tabStyle, { [tabActiveStyle]: step === 1 })}
|
||||||
|
onClick={() => setStep(1)}
|
||||||
|
></li>
|
||||||
|
</ul>
|
||||||
|
<div className={descriptionContainerStyle}>
|
||||||
|
{step !== -1 && (
|
||||||
|
<div
|
||||||
|
className={clsx(descriptionStyle, {
|
||||||
|
[slideToRightStyle]: step === 0,
|
||||||
|
[formSlideToLeftStyle]: step === 1,
|
||||||
|
})}
|
||||||
|
>
|
||||||
|
{t['com.affine.onboarding.videoDescription2']()}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
<div
|
||||||
|
className={clsx(descriptionStyle, {
|
||||||
|
[slideToLeftStyle]: step === 1,
|
||||||
|
[formSlideToRightStyle]: step === 0,
|
||||||
|
})}
|
||||||
|
>
|
||||||
|
{t['com.affine.onboarding.videoDescription1']()}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -2,12 +2,10 @@ export * from './components/list-skeleton';
|
|||||||
export * from './styles';
|
export * from './styles';
|
||||||
export * from './ui/breadcrumbs';
|
export * from './ui/breadcrumbs';
|
||||||
export * from './ui/button';
|
export * from './ui/button';
|
||||||
export * from './ui/confirm';
|
|
||||||
export * from './ui/empty';
|
export * from './ui/empty';
|
||||||
export * from './ui/input';
|
export * from './ui/input';
|
||||||
export * from './ui/layout';
|
export * from './ui/layout';
|
||||||
export * from './ui/menu';
|
export * from './ui/menu';
|
||||||
export * from './ui/modal';
|
|
||||||
export * from './ui/mui';
|
export * from './ui/mui';
|
||||||
export * from './ui/popper';
|
export * from './ui/popper';
|
||||||
export * from './ui/scrollbar';
|
export * from './ui/scrollbar';
|
||||||
|
|||||||
@@ -1,110 +0,0 @@
|
|||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
|
||||||
import { Button } from '@toeverything/components/button';
|
|
||||||
import { useCallback, useMemo } from 'react';
|
|
||||||
|
|
||||||
import type { ModalProps } from '../modal';
|
|
||||||
import { Modal, ModalCloseButton } from '../modal';
|
|
||||||
import {
|
|
||||||
StyledColumnButtonWrapper,
|
|
||||||
StyledConfirmContent,
|
|
||||||
StyledConfirmTitle,
|
|
||||||
StyledModalWrapper,
|
|
||||||
StyledRowButtonWrapper,
|
|
||||||
} from './styles';
|
|
||||||
|
|
||||||
export type ConfirmProps = {
|
|
||||||
title?: string;
|
|
||||||
content?: string;
|
|
||||||
confirmText?: string;
|
|
||||||
cancelText?: string;
|
|
||||||
// TODO: Confirm button's color should depend on confirm type
|
|
||||||
confirmType?: 'primary' | 'warning' | 'error';
|
|
||||||
buttonDirection?: 'row' | 'column';
|
|
||||||
onConfirm?: () => void;
|
|
||||||
onCancel?: () => void;
|
|
||||||
cancelButtonTestId?: string;
|
|
||||||
confirmButtonTestId?: string;
|
|
||||||
} & Omit<ModalProps, 'children'>;
|
|
||||||
|
|
||||||
export const Confirm = ({
|
|
||||||
title,
|
|
||||||
content,
|
|
||||||
confirmText,
|
|
||||||
confirmType,
|
|
||||||
onConfirm,
|
|
||||||
onCancel,
|
|
||||||
buttonDirection = 'row',
|
|
||||||
cancelText = 'Cancel',
|
|
||||||
open,
|
|
||||||
cancelButtonTestId = '',
|
|
||||||
confirmButtonTestId = '',
|
|
||||||
}: ConfirmProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
|
||||||
const cancelText_ = useMemo<string>(() => {
|
|
||||||
return cancelText === 'Cancel'
|
|
||||||
? t['com.affine.confirmModal.button.cancel']()
|
|
||||||
: cancelText;
|
|
||||||
}, [cancelText, t]);
|
|
||||||
|
|
||||||
const handleCancel = useCallback(() => {
|
|
||||||
onCancel?.();
|
|
||||||
}, [onCancel]);
|
|
||||||
const handleConfirm = useCallback(() => {
|
|
||||||
onConfirm?.();
|
|
||||||
}, [onConfirm]);
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Modal open={open} disablePortal={false}>
|
|
||||||
<StyledModalWrapper>
|
|
||||||
<ModalCloseButton onClick={handleCancel} />
|
|
||||||
<StyledConfirmTitle>{title}</StyledConfirmTitle>
|
|
||||||
<StyledConfirmContent>{content}</StyledConfirmContent>
|
|
||||||
{buttonDirection === 'row' ? (
|
|
||||||
<StyledRowButtonWrapper>
|
|
||||||
<Button
|
|
||||||
onClick={handleCancel}
|
|
||||||
size="large"
|
|
||||||
style={{ marginRight: '24px' }}
|
|
||||||
data-testid={cancelButtonTestId}
|
|
||||||
>
|
|
||||||
{cancelText_}
|
|
||||||
</Button>
|
|
||||||
<Button
|
|
||||||
type={confirmType}
|
|
||||||
onClick={handleConfirm}
|
|
||||||
size="large"
|
|
||||||
data-testid={confirmButtonTestId}
|
|
||||||
>
|
|
||||||
{confirmText}
|
|
||||||
</Button>
|
|
||||||
</StyledRowButtonWrapper>
|
|
||||||
) : (
|
|
||||||
<StyledColumnButtonWrapper>
|
|
||||||
<Button
|
|
||||||
type={confirmType}
|
|
||||||
onClick={handleConfirm}
|
|
||||||
style={{ width: '284px', height: '38px', textAlign: 'center' }}
|
|
||||||
data-testid={confirmButtonTestId}
|
|
||||||
>
|
|
||||||
{confirmText}
|
|
||||||
</Button>
|
|
||||||
<Button
|
|
||||||
onClick={handleCancel}
|
|
||||||
style={{
|
|
||||||
marginTop: '16px',
|
|
||||||
width: '284px',
|
|
||||||
height: '38px',
|
|
||||||
textAlign: 'center',
|
|
||||||
}}
|
|
||||||
data-testid={cancelButtonTestId}
|
|
||||||
>
|
|
||||||
{cancelText_}
|
|
||||||
</Button>
|
|
||||||
</StyledColumnButtonWrapper>
|
|
||||||
)}
|
|
||||||
</StyledModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
export default Confirm;
|
|
||||||
@@ -1 +0,0 @@
|
|||||||
export * from './confirm';
|
|
||||||
@@ -1,46 +0,0 @@
|
|||||||
import { displayFlex, styled } from '../../styles';
|
|
||||||
import { ModalWrapper } from '../modal';
|
|
||||||
|
|
||||||
export const StyledModalWrapper = styled(ModalWrapper)(() => {
|
|
||||||
return {
|
|
||||||
minWidth: '460px',
|
|
||||||
maxWidth: '560px',
|
|
||||||
maxHeight: '292px',
|
|
||||||
padding: '44px 84px 32px 84px',
|
|
||||||
overflow: 'auto',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledConfirmTitle = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
fontSize: 'var(--affine-font-h6)',
|
|
||||||
fontWeight: 600,
|
|
||||||
textAlign: 'center',
|
|
||||||
lineHeight: '28px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledConfirmContent = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
fontSize: 'var(--affine-font-base)',
|
|
||||||
textAlign: 'center',
|
|
||||||
marginTop: '12px',
|
|
||||||
color: 'var(--affine-text-primary-color)',
|
|
||||||
lineHeight: '26px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledColumnButtonWrapper = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
...displayFlex('center', 'center'),
|
|
||||||
flexDirection: 'column',
|
|
||||||
marginTop: '32px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
export const StyledRowButtonWrapper = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
...displayFlex('center', 'center'),
|
|
||||||
flexDirection: 'row',
|
|
||||||
marginTop: '32px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
@@ -1,72 +0,0 @@
|
|||||||
import { useAFFiNEI18N } from '@affine/i18n/hooks';
|
|
||||||
import { Button, type ButtonType } from '@toeverything/components/button';
|
|
||||||
import { useCallback } from 'react';
|
|
||||||
|
|
||||||
import { Modal, type ModalProps } from './modal';
|
|
||||||
import { ModalCloseButton } from './modal-close-button';
|
|
||||||
import { ModalWrapper } from './modal-wrapper';
|
|
||||||
import {
|
|
||||||
StyledModalContent,
|
|
||||||
StyledModalFooter,
|
|
||||||
StyledModalTitle,
|
|
||||||
} from './styles';
|
|
||||||
|
|
||||||
export interface BaseModalProps
|
|
||||||
extends Omit<ModalProps, 'onClose' | 'children'> {
|
|
||||||
title?: string;
|
|
||||||
content?: string;
|
|
||||||
confirmText?: string;
|
|
||||||
confirmType?: ButtonType;
|
|
||||||
onClose: () => void;
|
|
||||||
onCancel: () => void;
|
|
||||||
onConfirm: () => void;
|
|
||||||
}
|
|
||||||
|
|
||||||
export const ConfirmModal = ({
|
|
||||||
open,
|
|
||||||
onClose,
|
|
||||||
confirmText,
|
|
||||||
confirmType = 'primary',
|
|
||||||
onCancel,
|
|
||||||
onConfirm,
|
|
||||||
title,
|
|
||||||
content,
|
|
||||||
}: BaseModalProps) => {
|
|
||||||
const t = useAFFiNEI18N();
|
|
||||||
|
|
||||||
const handleClose = useCallback(() => {
|
|
||||||
onClose();
|
|
||||||
}, [onClose]);
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Modal
|
|
||||||
open={open}
|
|
||||||
onClose={handleClose}
|
|
||||||
wrapperPosition={['center', 'center']}
|
|
||||||
data-testid="auth-modal"
|
|
||||||
>
|
|
||||||
<ModalWrapper
|
|
||||||
width={480}
|
|
||||||
minHeight={194}
|
|
||||||
style={{
|
|
||||||
overflow: 'hidden',
|
|
||||||
backgroundColor: 'var(--affine-white)',
|
|
||||||
boxShadow: 'var(--affine-popover-shadow)',
|
|
||||||
padding: '20px 24px 0',
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<ModalCloseButton top={22} right={20} onClick={handleClose} />
|
|
||||||
<StyledModalTitle>{title}</StyledModalTitle>
|
|
||||||
<StyledModalContent>{content}</StyledModalContent>
|
|
||||||
<StyledModalFooter>
|
|
||||||
<Button onClick={onCancel} style={{ marginRight: 20 }}>
|
|
||||||
{t['com.affine.confirmModal.button.cancel']()}
|
|
||||||
</Button>
|
|
||||||
<Button type={confirmType} onClick={onConfirm}>
|
|
||||||
{confirmText || t['Confirm']()}
|
|
||||||
</Button>
|
|
||||||
</StyledModalFooter>
|
|
||||||
</ModalWrapper>
|
|
||||||
</Modal>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
@@ -1,8 +0,0 @@
|
|||||||
import Modal from './modal';
|
|
||||||
|
|
||||||
export * from './confirm-modal';
|
|
||||||
export * from './modal';
|
|
||||||
export * from './modal-close-button';
|
|
||||||
export * from './modal-wrapper';
|
|
||||||
|
|
||||||
export default Modal;
|
|
||||||
@@ -1,39 +0,0 @@
|
|||||||
import { CloseIcon } from '@blocksuite/icons';
|
|
||||||
import {
|
|
||||||
IconButton,
|
|
||||||
type IconButtonProps,
|
|
||||||
} from '@toeverything/components/button';
|
|
||||||
import type { HTMLAttributes } from 'react';
|
|
||||||
|
|
||||||
export type ModalCloseButtonProps = {
|
|
||||||
top?: number;
|
|
||||||
right?: number;
|
|
||||||
absolute?: boolean;
|
|
||||||
} & Omit<IconButtonProps, 'children'> &
|
|
||||||
HTMLAttributes<HTMLButtonElement>;
|
|
||||||
|
|
||||||
export const ModalCloseButton = ({
|
|
||||||
absolute = true,
|
|
||||||
right,
|
|
||||||
top,
|
|
||||||
...props
|
|
||||||
}: ModalCloseButtonProps) => {
|
|
||||||
return (
|
|
||||||
<IconButton
|
|
||||||
style={
|
|
||||||
absolute
|
|
||||||
? {
|
|
||||||
position: 'absolute',
|
|
||||||
top: top ?? 24,
|
|
||||||
right: right ?? 40,
|
|
||||||
zIndex: 1,
|
|
||||||
}
|
|
||||||
: {}
|
|
||||||
}
|
|
||||||
data-testid="modal-close-button"
|
|
||||||
{...props}
|
|
||||||
>
|
|
||||||
<CloseIcon />
|
|
||||||
</IconButton>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
@@ -1,22 +0,0 @@
|
|||||||
import type { CSSProperties } from 'react';
|
|
||||||
|
|
||||||
import { styled } from '../../styles';
|
|
||||||
|
|
||||||
export const ModalWrapper = styled('div')<{
|
|
||||||
width?: CSSProperties['width'];
|
|
||||||
height?: CSSProperties['height'];
|
|
||||||
minHeight?: CSSProperties['minHeight'];
|
|
||||||
}>(({ width, height, minHeight }) => {
|
|
||||||
return {
|
|
||||||
width,
|
|
||||||
height,
|
|
||||||
minHeight,
|
|
||||||
backgroundColor: 'var(--affine-background-overlay-panel-color)',
|
|
||||||
boxShadow: 'var(--affine-shadow-3)',
|
|
||||||
borderRadius: '12px',
|
|
||||||
position: 'relative',
|
|
||||||
maxHeight: 'calc(100vh - 32px)',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export default ModalWrapper;
|
|
||||||
@@ -1,59 +0,0 @@
|
|||||||
import type { ModalProps as ModalUnstyledOwnProps } from '@mui/base/Modal';
|
|
||||||
import Fade from '@mui/material/Fade';
|
|
||||||
|
|
||||||
import { StyledBackdrop, StyledModal } from './styles';
|
|
||||||
const Backdrop = ({
|
|
||||||
open,
|
|
||||||
...other
|
|
||||||
}: {
|
|
||||||
open?: boolean;
|
|
||||||
className: string;
|
|
||||||
}) => {
|
|
||||||
return (
|
|
||||||
<Fade in={open}>
|
|
||||||
<StyledBackdrop {...other} />
|
|
||||||
</Fade>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
export type ModalProps = {
|
|
||||||
wrapperPosition?: ['top' | 'bottom' | 'center', 'left' | 'right' | 'center'];
|
|
||||||
} & ModalUnstyledOwnProps;
|
|
||||||
|
|
||||||
const transformConfig = {
|
|
||||||
top: 'flex-start',
|
|
||||||
bottom: 'flex-end',
|
|
||||||
center: 'center',
|
|
||||||
left: 'flex-start',
|
|
||||||
right: 'flex-end',
|
|
||||||
};
|
|
||||||
|
|
||||||
export const Modal = (props: ModalProps) => {
|
|
||||||
const {
|
|
||||||
wrapperPosition = ['center', 'center'],
|
|
||||||
open,
|
|
||||||
children,
|
|
||||||
...otherProps
|
|
||||||
} = props;
|
|
||||||
const [vertical, horizontal] = wrapperPosition;
|
|
||||||
// Fixme: This is a workaround for Mui bug
|
|
||||||
// Refs: https://github.com/mui/material-ui/issues/33748
|
|
||||||
if (!open) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<StyledModal
|
|
||||||
{...otherProps}
|
|
||||||
open={open}
|
|
||||||
slots={{ backdrop: Backdrop }}
|
|
||||||
alignItems={transformConfig[vertical]}
|
|
||||||
justifyContent={transformConfig[horizontal]}
|
|
||||||
disableEnforceFocus
|
|
||||||
>
|
|
||||||
<Fade in={open}>{children}</Fade>
|
|
||||||
</StyledModal>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
export default Modal;
|
|
||||||
@@ -1,65 +0,0 @@
|
|||||||
import { Modal as ModalUnstyled } from '@mui/base/Modal';
|
|
||||||
import type { CSSProperties } from 'react';
|
|
||||||
|
|
||||||
import { styled } from '../../styles';
|
|
||||||
|
|
||||||
export const StyledBackdrop = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
zIndex: '-1',
|
|
||||||
position: 'fixed',
|
|
||||||
right: '0',
|
|
||||||
bottom: '0',
|
|
||||||
top: '0',
|
|
||||||
left: '0',
|
|
||||||
backgroundColor: 'var(--affine-background-modal-color)',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledModal = styled(ModalUnstyled, {
|
|
||||||
shouldForwardProp: prop => {
|
|
||||||
return !['justifyContent', 'alignItems'].includes(prop as string);
|
|
||||||
},
|
|
||||||
})<{
|
|
||||||
alignItems: CSSProperties['alignItems'];
|
|
||||||
justifyContent: CSSProperties['justifyContent'];
|
|
||||||
}>(({ alignItems, justifyContent }) => {
|
|
||||||
return {
|
|
||||||
width: '100vw',
|
|
||||||
height: '100vh',
|
|
||||||
display: 'flex',
|
|
||||||
alignItems,
|
|
||||||
justifyContent,
|
|
||||||
position: 'fixed',
|
|
||||||
left: '0',
|
|
||||||
top: '0',
|
|
||||||
zIndex: 'var(--affine-z-index-modal)',
|
|
||||||
WebkitAppRegion: 'no-drag',
|
|
||||||
'*': {
|
|
||||||
WebkitTapHighlightColor: 'transparent',
|
|
||||||
outline: 'none',
|
|
||||||
},
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledModalFooter = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
marginTop: 40,
|
|
||||||
display: 'flex',
|
|
||||||
justifyContent: 'flex-end',
|
|
||||||
alignItems: 'center',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const StyledModalTitle = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
fontWeight: 600,
|
|
||||||
fontSize: 'var(--affine-font-h-6)',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
export const StyledModalContent = styled('div')(() => {
|
|
||||||
return {
|
|
||||||
fontSize: 'var(--affine-font-base)',
|
|
||||||
lineHeight: '24px',
|
|
||||||
marginTop: '12px',
|
|
||||||
};
|
|
||||||
});
|
|
||||||
@@ -16,7 +16,7 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@affine/component": "workspace:*",
|
"@affine/component": "workspace:*",
|
||||||
"@affine/sdk": "workspace:*",
|
"@affine/sdk": "workspace:*",
|
||||||
"@toeverything/components": "^0.0.34",
|
"@toeverything/components": "^0.0.38",
|
||||||
"idb": "^7.1.1",
|
"idb": "^7.1.1",
|
||||||
"langchain": "^0.0.138",
|
"langchain": "^0.0.138",
|
||||||
"marked": "^7.0.5",
|
"marked": "^7.0.5",
|
||||||
|
|||||||
@@ -18,7 +18,7 @@
|
|||||||
"@affine/component": "workspace:*",
|
"@affine/component": "workspace:*",
|
||||||
"@affine/sdk": "workspace:*",
|
"@affine/sdk": "workspace:*",
|
||||||
"@blocksuite/icons": "^2.1.33",
|
"@blocksuite/icons": "^2.1.33",
|
||||||
"@toeverything/components": "^0.0.34"
|
"@toeverything/components": "^0.0.38"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@affine/plugin-cli": "workspace:*"
|
"@affine/plugin-cli": "workspace:*"
|
||||||
|
|||||||
@@ -17,7 +17,7 @@
|
|||||||
"@affine/component": "workspace:*",
|
"@affine/component": "workspace:*",
|
||||||
"@affine/sdk": "workspace:*",
|
"@affine/sdk": "workspace:*",
|
||||||
"@blocksuite/icons": "^2.1.33",
|
"@blocksuite/icons": "^2.1.33",
|
||||||
"@toeverything/components": "^0.0.34",
|
"@toeverything/components": "^0.0.38",
|
||||||
"@toeverything/theme": "^0.7.15",
|
"@toeverything/theme": "^0.7.15",
|
||||||
"clsx": "^2.0.0",
|
"clsx": "^2.0.0",
|
||||||
"foxact": "^0.2.20",
|
"foxact": "^0.2.20",
|
||||||
|
|||||||
@@ -18,7 +18,7 @@
|
|||||||
"@affine/component": "workspace:*",
|
"@affine/component": "workspace:*",
|
||||||
"@affine/sdk": "workspace:*",
|
"@affine/sdk": "workspace:*",
|
||||||
"@blocksuite/icons": "^2.1.33",
|
"@blocksuite/icons": "^2.1.33",
|
||||||
"@toeverything/components": "^0.0.34"
|
"@toeverything/components": "^0.0.38"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@affine/plugin-cli": "workspace:*",
|
"@affine/plugin-cli": "workspace:*",
|
||||||
|
|||||||
52
yarn.lock
52
yarn.lock
@@ -231,7 +231,7 @@ __metadata:
|
|||||||
"@affine/component": "workspace:*"
|
"@affine/component": "workspace:*"
|
||||||
"@affine/plugin-cli": "workspace:*"
|
"@affine/plugin-cli": "workspace:*"
|
||||||
"@affine/sdk": "workspace:*"
|
"@affine/sdk": "workspace:*"
|
||||||
"@toeverything/components": ^0.0.34
|
"@toeverything/components": ^0.0.38
|
||||||
"@types/marked": ^5.0.1
|
"@types/marked": ^5.0.1
|
||||||
idb: ^7.1.1
|
idb: ^7.1.1
|
||||||
jotai: ^2.4.1
|
jotai: ^2.4.1
|
||||||
@@ -282,7 +282,7 @@ __metadata:
|
|||||||
"@sentry/webpack-plugin": ^2.7.0
|
"@sentry/webpack-plugin": ^2.7.0
|
||||||
"@svgr/webpack": ^8.1.0
|
"@svgr/webpack": ^8.1.0
|
||||||
"@swc/core": ^1.3.81
|
"@swc/core": ^1.3.81
|
||||||
"@toeverything/components": ^0.0.34
|
"@toeverything/components": ^0.0.38
|
||||||
"@types/lodash-es": ^4.17.9
|
"@types/lodash-es": ^4.17.9
|
||||||
"@types/webpack-env": ^1.18.1
|
"@types/webpack-env": ^1.18.1
|
||||||
async-call-rpc: ^6.3.1
|
async-call-rpc: ^6.3.1
|
||||||
@@ -458,7 +458,7 @@ __metadata:
|
|||||||
"@affine/plugin-cli": "workspace:*"
|
"@affine/plugin-cli": "workspace:*"
|
||||||
"@affine/sdk": "workspace:*"
|
"@affine/sdk": "workspace:*"
|
||||||
"@blocksuite/icons": ^2.1.33
|
"@blocksuite/icons": ^2.1.33
|
||||||
"@toeverything/components": ^0.0.34
|
"@toeverything/components": ^0.0.38
|
||||||
languageName: unknown
|
languageName: unknown
|
||||||
linkType: soft
|
linkType: soft
|
||||||
|
|
||||||
@@ -484,7 +484,7 @@ __metadata:
|
|||||||
"@affine/plugin-cli": "workspace:*"
|
"@affine/plugin-cli": "workspace:*"
|
||||||
"@affine/sdk": "workspace:*"
|
"@affine/sdk": "workspace:*"
|
||||||
"@blocksuite/icons": ^2.1.33
|
"@blocksuite/icons": ^2.1.33
|
||||||
"@toeverything/components": ^0.0.34
|
"@toeverything/components": ^0.0.38
|
||||||
"@toeverything/theme": ^0.7.15
|
"@toeverything/theme": ^0.7.15
|
||||||
clsx: ^2.0.0
|
clsx: ^2.0.0
|
||||||
foxact: ^0.2.20
|
foxact: ^0.2.20
|
||||||
@@ -580,7 +580,7 @@ __metadata:
|
|||||||
"@affine/plugin-cli": "workspace:*"
|
"@affine/plugin-cli": "workspace:*"
|
||||||
"@affine/sdk": "workspace:*"
|
"@affine/sdk": "workspace:*"
|
||||||
"@blocksuite/icons": ^2.1.33
|
"@blocksuite/icons": ^2.1.33
|
||||||
"@toeverything/components": ^0.0.34
|
"@toeverything/components": ^0.0.38
|
||||||
jotai: ^2.4.1
|
jotai: ^2.4.1
|
||||||
react: 18.2.0
|
react: 18.2.0
|
||||||
react-dom: 18.2.0
|
react-dom: 18.2.0
|
||||||
@@ -9108,6 +9108,39 @@ __metadata:
|
|||||||
languageName: node
|
languageName: node
|
||||||
linkType: hard
|
linkType: hard
|
||||||
|
|
||||||
|
"@radix-ui/react-dialog@npm:^1.0.4":
|
||||||
|
version: 1.0.4
|
||||||
|
resolution: "@radix-ui/react-dialog@npm:1.0.4"
|
||||||
|
dependencies:
|
||||||
|
"@babel/runtime": ^7.13.10
|
||||||
|
"@radix-ui/primitive": 1.0.1
|
||||||
|
"@radix-ui/react-compose-refs": 1.0.1
|
||||||
|
"@radix-ui/react-context": 1.0.1
|
||||||
|
"@radix-ui/react-dismissable-layer": 1.0.4
|
||||||
|
"@radix-ui/react-focus-guards": 1.0.1
|
||||||
|
"@radix-ui/react-focus-scope": 1.0.3
|
||||||
|
"@radix-ui/react-id": 1.0.1
|
||||||
|
"@radix-ui/react-portal": 1.0.3
|
||||||
|
"@radix-ui/react-presence": 1.0.1
|
||||||
|
"@radix-ui/react-primitive": 1.0.3
|
||||||
|
"@radix-ui/react-slot": 1.0.2
|
||||||
|
"@radix-ui/react-use-controllable-state": 1.0.1
|
||||||
|
aria-hidden: ^1.1.1
|
||||||
|
react-remove-scroll: 2.5.5
|
||||||
|
peerDependencies:
|
||||||
|
"@types/react": "*"
|
||||||
|
"@types/react-dom": "*"
|
||||||
|
react: ^16.8 || ^17.0 || ^18.0
|
||||||
|
react-dom: ^16.8 || ^17.0 || ^18.0
|
||||||
|
peerDependenciesMeta:
|
||||||
|
"@types/react":
|
||||||
|
optional: true
|
||||||
|
"@types/react-dom":
|
||||||
|
optional: true
|
||||||
|
checksum: 01ad549a3685e221628950e6fbec306494170aa3b92cbe00732b1531c16e1cf681138cd4a79d658f4f97d4096676a40d08642090fdea1675d0b7dc78df66d962
|
||||||
|
languageName: node
|
||||||
|
linkType: hard
|
||||||
|
|
||||||
"@radix-ui/react-direction@npm:1.0.0":
|
"@radix-ui/react-direction@npm:1.0.0":
|
||||||
version: 1.0.0
|
version: 1.0.0
|
||||||
resolution: "@radix-ui/react-direction@npm:1.0.0"
|
resolution: "@radix-ui/react-direction@npm:1.0.0"
|
||||||
@@ -12447,11 +12480,12 @@ __metadata:
|
|||||||
languageName: node
|
languageName: node
|
||||||
linkType: hard
|
linkType: hard
|
||||||
|
|
||||||
"@toeverything/components@npm:^0.0.34":
|
"@toeverything/components@npm:^0.0.38":
|
||||||
version: 0.0.34
|
version: 0.0.38
|
||||||
resolution: "@toeverything/components@npm:0.0.34"
|
resolution: "@toeverything/components@npm:0.0.38"
|
||||||
dependencies:
|
dependencies:
|
||||||
"@blocksuite/icons": ^2.1.33
|
"@blocksuite/icons": ^2.1.33
|
||||||
|
"@radix-ui/react-dialog": ^1.0.4
|
||||||
"@radix-ui/react-dropdown-menu": ^2.0.5
|
"@radix-ui/react-dropdown-menu": ^2.0.5
|
||||||
"@radix-ui/react-tooltip": ^1.0.6
|
"@radix-ui/react-tooltip": ^1.0.6
|
||||||
peerDependencies:
|
peerDependencies:
|
||||||
@@ -12459,7 +12493,7 @@ __metadata:
|
|||||||
clsx: ^2
|
clsx: ^2
|
||||||
react: ^18
|
react: ^18
|
||||||
react-dom: ^18
|
react-dom: ^18
|
||||||
checksum: 240fadd8101d92eb2da6700372a2cb87516479999943628c7d422d3cfeb3f330a15096eed470d650d207bd1a132e4115e1277b13d59a6f4994827e231e9cf5f3
|
checksum: 8771f0439be2db0acffa1d6f73a2c49155acf35c5a0538c3391f98f5dfc7961f6e88e48dfc9e5dae2847b3a31a720a58dc79075db024758b74b72bcfe15eadd0
|
||||||
languageName: node
|
languageName: node
|
||||||
linkType: hard
|
linkType: hard
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user