diff --git a/packages/app/public/globals.css b/packages/app/public/globals.css index 7388399c01..5a33ec99f6 100644 --- a/packages/app/public/globals.css +++ b/packages/app/public/globals.css @@ -158,6 +158,9 @@ a, a:hover { color: var(--affine-link-color); } +a:visited { + color: var(--affine-link-visited-color); +} input { border: none; diff --git a/packages/app/src/components/Header/index.tsx b/packages/app/src/components/Header/index.tsx index b6eb961fb4..405cd9006a 100644 --- a/packages/app/src/components/Header/index.tsx +++ b/packages/app/src/components/Header/index.tsx @@ -14,7 +14,7 @@ import { useEditor } from '@/components/editor-provider'; import EditorModeSwitch from '@/components/editor-mode-switch'; import { EdgelessIcon, PaperIcon } from '../editor-mode-switch/icons'; import ThemeModeSwitch from '@/components/theme-mode-switch'; -import ContactModal from '@/components/contact-modal'; +import { useModal } from '@/components/global-modal-provider'; const PopoverContent = () => { const { editor, mode, setMode } = useEditor(); @@ -26,7 +26,7 @@ const PopoverContent = () => { }} > {mode === 'page' ? : } - Convert to {mode === 'page' ? 'edgeless' : 'page'} + Convert to {mode === 'page' ? 'Edgeless' : 'Page'} { @@ -42,7 +42,7 @@ const PopoverContent = () => { }} > - Export to markdown + Export to Markdown ); @@ -51,8 +51,7 @@ const PopoverContent = () => { export const Header = () => { const [title, setTitle] = useState(''); const [isHover, setIsHover] = useState(false); - const [showContactModal, setShowContactModal] = useState(false); - + const { contactModalHandler } = useModal(); const { editor } = useEditor(); useEffect(() => { @@ -66,15 +65,11 @@ export const Header = () => { return ( <> - setShowContactModal(false)} - /> { - setShowContactModal(true); + contactModalHandler(true); }} /> diff --git a/packages/app/src/components/Header/styles.ts b/packages/app/src/components/Header/styles.ts index 16ac015e7a..9c529803e8 100644 --- a/packages/app/src/components/Header/styles.ts +++ b/packages/app/src/components/Header/styles.ts @@ -1,13 +1,16 @@ -import { styled } from '@/styles'; +import { displayFlex, styled } from '@/styles'; export const StyledHeader = styled('div')({ height: '60px', width: '100vw', - display: 'flex', - justifyContent: 'space-between', - alignItems: 'center', - position: 'relative', + ...displayFlex('space-between', 'center'), + background: 'var(--affine-page-background)', + transition: 'background-color 0.5s', + position: 'fixed', + left: '0', + top: '0', padding: '0 22px', + zIndex: '10', }); export const StyledTitle = styled('div')({ @@ -19,9 +22,7 @@ export const StyledTitle = styled('div')({ top: 0, margin: 'auto', - display: 'flex', - justifyContent: 'center', - alignItems: 'center', + ...displayFlex('center', 'center'), fontSize: '20px', }); @@ -69,9 +70,7 @@ export const IconButton = styled('div')(({ theme }) => { return { width: '32px', height: '32px', - display: 'flex', - justifyContent: 'center', - alignItems: 'center', + ...displayFlex('center', 'center'), color: theme.colors.iconColor, borderRadius: '5px', ':hover': { diff --git a/packages/app/src/components/contact-modal/bg.png b/packages/app/src/components/contact-modal/bg.png new file mode 100644 index 0000000000..737c8c17c0 Binary files /dev/null and b/packages/app/src/components/contact-modal/bg.png differ diff --git a/packages/app/src/components/contact-modal/icons.tsx b/packages/app/src/components/contact-modal/icons.tsx index d267dbe9c3..aba676278d 100644 --- a/packages/app/src/components/contact-modal/icons.tsx +++ b/packages/app/src/components/contact-modal/icons.tsx @@ -1,55 +1,139 @@ -// export const CloseIcon = () => { -// return ( -// -// -// -// ); -// }; - export const LogoIcon = () => { return ( + + ); +}; +export const DocIcon = () => { + return ( + + ); }; -export const DiscordIcon = (props: any) => { +export const TwitterIcon = () => { return ( - + + + ); +}; + +export const GithubIcon = () => { + return ( + + - - + + ); }; +export const DiscordIcon = (props: any) => { + return ( + + + + + + + + + + + ); +}; + +export const TelegramIcon = () => { + return ( + + + + ); +}; + +export const RedditIcon = () => { + return ( + + + + ); +}; + +export const LinkIcon = () => { + return ( + + + + ); +}; diff --git a/packages/app/src/components/contact-modal/index.tsx b/packages/app/src/components/contact-modal/index.tsx index 2c2d75430d..0b45ec18ba 100644 --- a/packages/app/src/components/contact-modal/index.tsx +++ b/packages/app/src/components/contact-modal/index.tsx @@ -1,18 +1,20 @@ import { createPortal } from 'react-dom'; import Fade from '@mui/material/Fade'; -import GitHubIcon from '@mui/icons-material/GitHub'; -import RedditIcon from '@mui/icons-material/Reddit'; -import TelegramIcon from '@mui/icons-material/Telegram'; -import TwitterIcon from '@mui/icons-material/Twitter'; import CloseIcon from '@mui/icons-material/Close'; - -import { LogoIcon, DiscordIcon } from './icons'; +import { + LogoIcon, + DocIcon, + TwitterIcon, + GithubIcon, + DiscordIcon, + TelegramIcon, + RedditIcon, + LinkIcon, +} from './icons'; import logo from './affine-text-logo.png'; import { StyledModalContainer, StyledModalWrapper, - StyledYellowBall, - StyledBlueBall, StyledBigLink, StyledSmallLink, StyledSubTitle, @@ -29,7 +31,7 @@ import { const linkList = [ { - icon: , + icon: , title: 'Github', link: 'https://github.com/toeverything/AFFiNE', }, @@ -57,12 +59,14 @@ const linkList = [ const rightLinkList = [ { icon: , - title: 'Official Website AFFiNE.pro', + title: 'Official Website ', + subTitle: 'AFFiNE.pro', link: 'https://affine.pro', }, { - icon: , - title: 'Check Our Docs Open Source', + icon: , + title: 'Check Our Docs', + subTitle: 'Open Source', link: 'https://github.com/toeverything/AFFiNE', }, ]; @@ -78,31 +82,31 @@ export const ContactModal = ({ open, onClose }: TransitionsModalProps) => { - - - - 2.0 - live demo + Alpha { onClose(); }} > - + - {rightLinkList.map(({ icon, title, link }) => { + {rightLinkList.map(({ icon, title, subTitle, link }) => { return ( {icon} - {title} +

{title}

+

+ {subTitle} + +

); })} @@ -125,9 +129,7 @@ export const ContactModal = ({ open, onClose }: TransitionsModalProps) => {

- - What is the different from the affine 1.0? - + How is AFFiNE Alpha different?

Copyright © 2022 Toeverything

diff --git a/packages/app/src/components/contact-modal/style.ts b/packages/app/src/components/contact-modal/style.ts index 1527fa6faa..32468d9734 100644 --- a/packages/app/src/components/contact-modal/style.ts +++ b/packages/app/src/components/contact-modal/style.ts @@ -1,5 +1,5 @@ -import { styled } from '@/styles'; - +import { absoluteCenter, displayFlex, styled } from '@/styles'; +import bg from './bg.png'; export const StyledModalContainer = styled('div')(({ theme }) => { return { width: '100vw', @@ -13,10 +13,10 @@ export const StyledModalContainer = styled('div')(({ theme }) => { export const StyledModalWrapper = styled('div')(({ theme }) => { return { - width: '1000px', + width: '860px', height: '626px', - background: theme.colors.popoverBackground, - padding: '0 48px', + backgroundColor: theme.colors.popoverBackground, + backgroundImage: `url(${bg.src})`, borderRadius: '20px', position: 'absolute', left: 0, @@ -27,49 +27,26 @@ export const StyledModalWrapper = styled('div')(({ theme }) => { }; }); -export const StyledYellowBall = styled('div')` - position: absolute; - top: 189px; - left: 186px; - display: block; - width: 122px; - height: 122px; - background-color: #dda82a; - opacity: 0.45; - filter: blur(78px); -`; -export const StyledBlueBall = styled('div')` - content: ''; - position: absolute; - top: 332px; - left: 296px; - display: block; - width: 122px; - height: 122px; - background-color: #4461f2; - filter: blur(78px); -`; - export const StyledBigLink = styled('a')(({ theme }) => { return { - width: '335px', - height: '110px', - marginBottom: '52px', - display: 'flex', - alignItems: 'center', + width: '320px', + height: '100px', + marginBottom: '48px', + paddingLeft: '114px', fontSize: '24px', lineHeight: '36px', - padding: '0 24px', fontWeight: '600', color: theme.colors.textColor, borderRadius: '10px', - + flexDirection: 'column', + ...displayFlex('center'), + position: 'relative', + transition: 'background .15s', ':visited': { color: theme.colors.textColor, }, ':hover': { - color: theme.colors.primaryColor, - background: theme.colors.hoverBackground, + background: 'rgba(68, 97, 242, 0.1)', }, ':last-of-type': { marginBottom: 0, @@ -79,10 +56,30 @@ export const StyledBigLink = styled('a')(({ theme }) => { height: '50px', marginRight: '40px', color: theme.colors.primaryColor, + ...absoluteCenter({ vertical: true, position: { left: '32px' } }), }, p: { - width: '197px', - height: '73px', + width: '100%', + height: '30px', + lineHeight: '30px', + ...displayFlex('flex-start', 'center'), + ':not(:last-of-type)': { + marginBottom: '4px', + }, + ':first-of-type': { + fontSize: '22px', + }, + ':last-of-type': { + fontSize: '20px', + color: theme.colors.primaryColor, + }, + svg: { + width: '15px', + height: '15px', + position: 'static', + transform: 'translate(0,0)', + marginLeft: '5px', + }, }, }; }); @@ -97,6 +94,8 @@ export const StyledSmallLink = styled('a')(({ theme }) => { paddingLeft: '24px', borderRadius: '5px', color: theme.colors.textColor, + transition: 'background .15s, color .15s', + ':visited': { color: theme.colors.textColor, }, @@ -122,25 +121,19 @@ export const StyledSubTitle = styled('div')(({ theme }) => { }); export const StyledLeftContainer = styled('div')({ - // height: '100%', - display: 'flex', flexDirection: 'column', - justifyContent: 'space-between', + ...displayFlex('space-between', 'center'), }); export const StyledRightContainer = styled('div')({ - display: 'flex', flexDirection: 'column', - justifyContent: 'center', - alignItems: 'flex-end', + ...displayFlex('center', 'flex-end'), }); export const StyledContent = styled('div')({ height: '276px', width: '100%', - padding: '0 160px', - display: 'flex', - justifyContent: 'space-between', - alignItems: 'center', + padding: '0 145px', + ...displayFlex('space-between', 'center'), color: '#3A4C5C', marginTop: '100px', }); @@ -149,7 +142,7 @@ export const StyledBackdrop = styled('div')(({ theme }) => { return { width: '100%', height: '100%', background: 'rgba(58, 76, 92, 0.2)' }; }); export const StyledLogo = styled('img')({ - height: '22px', + height: '18px', width: 'auto', }); @@ -158,45 +151,42 @@ export const StyledModalHeader = styled('div')(({ theme }) => { height: '30px', marginTop: '54px', padding: '0 48px', - display: 'flex', - alignItems: 'center', - justifyContent: 'space-between', + ...displayFlex('space-between', 'center'), }; }); export const StyledModalHeaderLeft = styled('div')(({ theme }) => { return { - display: 'flex', - alignItems: 'center', color: theme.colors.primaryColor, - - 'span:first-of-type': { - fontSize: '28px', - lineHeight: 1, - fontWeight: '600', - margin: '0 12px', - }, - 'span:last-of-type': { - height: '26px', + ...displayFlex('flex-end', 'flex-end'), + span: { + height: '20px', border: `1px solid ${theme.colors.primaryColor}`, borderRadius: '10px', - padding: '0 10px', + padding: '0 8px', lineHeight: '26px', - fontSize: '16px', + fontSize: '14px', + marginLeft: '12px', + ...displayFlex('center', 'center'), }, }; }); export const CloseButton = styled('div')(({ theme }) => { return { - width: '24px', - height: '24px', - borderRadius: '5px', + width: '30px', + height: '30px', + borderRadius: '6px', color: theme.colors.iconColor, cursor: 'pointer', + ...displayFlex('center', 'center'), ':hover': { background: theme.colors.hoverBackground, }, + svg: { + width: '20px', + height: '20px', + }, }; }); diff --git a/packages/app/src/components/edgeless-toolbar/icons.tsx b/packages/app/src/components/edgeless-toolbar/icons.tsx new file mode 100644 index 0000000000..aa04207aad --- /dev/null +++ b/packages/app/src/components/edgeless-toolbar/icons.tsx @@ -0,0 +1,151 @@ +export const SelectIcon = () => { + return ( + + + + + + + + + + + ); +}; + +export const TextIcon = () => { + return ( + + + + ); +}; + +export const ShapeIcon = () => { + return ( + + + + ); +}; + +export const PenIcon = () => { + return ( + + + + ); +}; + +export const StickerIcon = () => { + return ( + + + + ); +}; + +export const ConnectorIcon = () => { + return ( + + + + ); +}; + +export const UndoIcon = () => { + return ( + + + + ); +}; + +export const RedoIcon = () => { + return ( + + + + ); +}; diff --git a/packages/app/src/components/edgeless-toolbar/index.tsx b/packages/app/src/components/edgeless-toolbar/index.tsx new file mode 100644 index 0000000000..49762dde84 --- /dev/null +++ b/packages/app/src/components/edgeless-toolbar/index.tsx @@ -0,0 +1,110 @@ +import { + StyledEdgelessToolbar, + StyledToolbarWrapper, + StyledToolbarItem, +} from './style'; +import { + SelectIcon, + TextIcon, + ShapeIcon, + PenIcon, + StickerIcon, + ConnectorIcon, + UndoIcon, + RedoIcon, +} from './icons'; +import { Tooltip } from '@/components/tooltip'; +import Slide from '@mui/material/Slide'; +import { useEditor } from '@/components/editor-provider'; + +const toolbarList1 = [ + { + icon: , + toolTip: 'Select', + onClick: () => {}, + disable: false, + }, + { + icon: , + toolTip: 'Text(coming soon)', + onClick: () => {}, + disable: true, + }, + { + icon: , + toolTip: 'Shape(coming soon)', + onClick: () => {}, + disable: true, + }, + { + icon: , + toolTip: 'Sticker(coming soon)', + onClick: () => {}, + disable: true, + }, + { + icon: , + toolTip: 'Pen(coming soon)', + onClick: () => {}, + disable: true, + }, + + { + icon: , + toolTip: 'Connector(coming soon)', + onClick: () => {}, + disable: true, + }, +]; +const toolbarList2 = [ + { + icon: , + toolTip: 'Undo(coming soon)', + onClick: () => {}, + disable: true, + }, + { + icon: , + toolTip: 'Redo(coming soon)', + onClick: () => {}, + disable: true, + }, +]; +export const EdgelessToolbar = () => { + const { mode } = useEditor(); + return ( + + + + {toolbarList1.map(({ icon, toolTip, onClick, disable }, index) => { + return ( + + + {icon} + + + ); + })} + + + {toolbarList2.map(({ icon, toolTip, onClick, disable }, index) => { + return ( + + + {icon} + + + ); + })} + + + + ); +}; + +export default EdgelessToolbar; diff --git a/packages/app/src/components/edgeless-toolbar/reply.svg b/packages/app/src/components/edgeless-toolbar/reply.svg new file mode 100644 index 0000000000..bfe127a193 --- /dev/null +++ b/packages/app/src/components/edgeless-toolbar/reply.svg @@ -0,0 +1,3 @@ + + + diff --git a/packages/app/src/components/edgeless-toolbar/style.ts b/packages/app/src/components/edgeless-toolbar/style.ts new file mode 100644 index 0000000000..e57a370beb --- /dev/null +++ b/packages/app/src/components/edgeless-toolbar/style.ts @@ -0,0 +1,41 @@ +import { styled, displayFlex, fixedCenter } from '@/styles'; + +export const StyledEdgelessToolbar = styled.div(({ theme }) => ({ + height: '320px', + position: 'fixed', + left: '12px', + top: 0, + bottom: 0, + margin: 'auto', + zIndex: theme.zIndex.modal, +})); + +export const StyledToolbarWrapper = styled.div(({ theme }) => ({ + width: '44px', + borderRadius: '10px', + boxShadow: theme.shadow.modal, + padding: '4px', + background: theme.colors.popoverBackground, + transition: 'background .5s', + marginBottom: '12px', +})); + +export const StyledToolbarItem = styled.div<{ disable: boolean }>( + ({ theme, disable }) => ({ + width: '36px', + height: '36px', + ...displayFlex('center', 'center'), + color: disable ? '#C0C0C0' : theme.colors.iconColor, + cursor: 'pointer', + svg: { + width: '36px', + height: '36px', + }, + ':hover': disable + ? {} + : { + color: theme.colors.primaryColor, + background: theme.colors.hoverBackground, + }, + }) +); diff --git a/packages/app/src/components/editor-mode-switch/style.ts b/packages/app/src/components/editor-mode-switch/style.ts index d882a3a76d..72b0ab3340 100644 --- a/packages/app/src/components/editor-mode-switch/style.ts +++ b/packages/app/src/components/editor-mode-switch/style.ts @@ -1,4 +1,4 @@ -import { keyframes, styled } from '@/styles'; +import { displayFlex, keyframes, styled } from '@/styles'; // @ts-ignore import spring, { toString } from 'css-spring'; import type { ItemStatus } from './type'; @@ -128,9 +128,7 @@ export const StyledIcon = styled('div')<{ ? { width: '36px' } : { width: isLeft ? '44px' : '34px' }; return { - display: 'flex', - justifyContent: 'center', - alignItems: 'center', + ...displayFlex('center', 'center'), flexShrink: '0', ...dynamicStyle, }; diff --git a/packages/app/src/components/faq/index.tsx b/packages/app/src/components/faq/index.tsx index af9d84a2d0..96dddc4b45 100644 --- a/packages/app/src/components/faq/index.tsx +++ b/packages/app/src/components/faq/index.tsx @@ -8,51 +8,17 @@ import { import { CloseIcon, ContactIcon, HelpIcon, KeyboardIcon } from './icons'; import Grow from '@mui/material/Grow'; import { Tooltip } from '../tooltip'; -import ContactModal from '@/components/contact-modal'; -import ShortcutsModal from '@/components/shortcuts-modal'; -const Contact = () => { - const [openModal, setOpenModal] = useState(false); - return ( - <> - setOpenModal(false)} /> - - { - setOpenModal(true); - }} - > - - - - - ); -}; +import { useEditor } from '@/components/editor-provider'; +import { useModal } from '@/components/global-modal-provider'; +import { useTheme } from '@/styles'; -const Shortcuts = () => { - const [openModal, setOpenModal] = useState(false); - return ( - <> - { - setOpenModal(false); - }} - /> - - - { - setOpenModal(true); - }} - > - - - - - ); -}; export const FAQ = () => { const [showContent, setShowContent] = useState(false); + const { mode } = useTheme(); + const { mode: editorMode } = useEditor(); + const { shortcutsModalHandler, contactModalHandler } = useModal(); + const isEdgelessDark = mode === 'dark' && editorMode === 'edgeless'; + return ( <> { > - - + + { + setShowContent(false); + contactModalHandler(true); + }} + > + + + + + { + setShowContent(false); + shortcutsModalHandler(true); + }} + > + + +
- + @@ -83,3 +69,14 @@ export const FAQ = () => { ); }; + +const routesLIst: any = [ + { + path: '/', + children: [ + { + element: , + }, + ], + }, +]; diff --git a/packages/app/src/components/faq/style.ts b/packages/app/src/components/faq/style.ts index f82ed8ccba..e39e6280c5 100644 --- a/packages/app/src/components/faq/style.ts +++ b/packages/app/src/components/faq/style.ts @@ -1,4 +1,4 @@ -import { styled } from '@/styles'; +import { displayFlex, styled } from '@/styles'; export const StyledFAQ = styled('div')(({ theme }) => { return { @@ -10,10 +10,6 @@ export const StyledFAQ = styled('div')(({ theme }) => { bottom: '30px', borderRadius: '50%', zIndex: theme.zIndex.popover, - ':hover': { - backgroundColor: theme.colors.popoverBackground, - color: theme.colors.primaryColor, - }, }; }); export const StyledTransformIcon = styled.div<{ in: boolean }>( @@ -27,35 +23,39 @@ export const StyledTransformIcon = styled.div<{ in: boolean }>( bottom: '0', top: '0', margin: 'auto', - display: 'flex', - justifyContent: 'center', - alignItems: 'center', + ...displayFlex('center', 'center'), opacity: isIn ? 1 : 0, backgroundColor: isIn ? theme.colors.hoverBackground : theme.colors.pageBackground, }) ); -export const StyledIconWrapper = styled('div')(({ theme }) => { - return { - color: theme.colors.iconColor, - marginBottom: '24px', - display: 'flex', - justifyContent: 'center', - alignItems: 'center', - cursor: 'pointer', - backgroundColor: theme.colors.pageBackground, - borderRadius: '50%', - width: '32px', - height: '32px', - transition: 'background-color 0.3s', - position: 'relative', - ':hover': { - color: theme.colors.primaryColor, - backgroundColor: theme.colors.hoverBackground, - }, - }; -}); +export const StyledIconWrapper = styled('div')<{ isEdgelessDark: boolean }>( + ({ theme, isEdgelessDark }) => { + return { + color: isEdgelessDark + ? theme.colors.popoverBackground + : theme.colors.iconColor, + marginBottom: '24px', + ...displayFlex('center', 'center'), + cursor: 'pointer', + backgroundColor: isEdgelessDark + ? 'transparent' + : theme.colors.pageBackground, + borderRadius: '50%', + width: '32px', + height: '32px', + transition: 'background-color 0.3s', + position: 'relative', + ':hover': { + color: isEdgelessDark + ? theme.colors.iconColor + : theme.colors.primaryColor, + backgroundColor: theme.colors.hoverBackground, + }, + }; + } +); export const StyledFAQWrapper = styled('div')(({ theme }) => { return { diff --git a/packages/app/src/components/global-modal-provider.tsx b/packages/app/src/components/global-modal-provider.tsx new file mode 100644 index 0000000000..fe4851f197 --- /dev/null +++ b/packages/app/src/components/global-modal-provider.tsx @@ -0,0 +1,53 @@ +import { createContext, useContext, useState } from 'react'; +import type { PropsWithChildren } from 'react'; +import ShortcutsModal from './shortcuts-modal'; +import ContactModal from '@/components/contact-modal'; + +type ModalContextValue = { + shortcutsModalHandler: (visible: boolean) => void; + contactModalHandler: (visible: boolean) => void; +}; +type ModalContextProps = PropsWithChildren<{}>; + +export const ModalContext = createContext({ + shortcutsModalHandler: () => {}, + contactModalHandler: () => {}, +}); + +export const useModal = () => useContext(ModalContext); + +export const ModalProvider = ({ + children, +}: PropsWithChildren) => { + const [openContactModal, setOpenContactModal] = useState(false); + const [openShortcutsModal, setOpenShortcutsModal] = useState(false); + + return ( + { + setOpenShortcutsModal(visible); + }, + contactModalHandler: visible => { + setOpenContactModal(visible); + }, + }} + > + { + setOpenContactModal(false); + }} + > + { + setOpenShortcutsModal(false); + }} + > + {children} + + ); +}; + +export default ModalProvider; diff --git a/packages/app/src/components/shortcuts-modal/config.ts b/packages/app/src/components/shortcuts-modal/config.ts index 707ff48a20..7a868e3d75 100644 --- a/packages/app/src/components/shortcuts-modal/config.ts +++ b/packages/app/src/components/shortcuts-modal/config.ts @@ -1,21 +1,21 @@ export const macKeyboardShortcuts = { - Undo: 'cmd + Z', - Redo: 'cmd + shift + Z', - Bold: 'cmd + B', - Italic: 'cmd + I', - Underline: 'cmd + U', - Strikethrough: 'cmd + Shit + S', - 'Inline code': ' cmd + E', - Link: 'cmd + K', - 'Body text': 'cmd + Option + 0', - 'Heading 1': 'cmd + Option + 1', - 'Heading 2': 'cmd + Option + 2', - 'Heading 3': 'cmd + Option + 3', - 'Heading 4': 'cmd + Option + 4', - 'Heading 5': 'cmd + Option + 5', - 'Heading 6': 'cmd + Option + 6', + Undo: '⌘ + Z', + Redo: '⌘ + ⇧ + Z', + Bold: '⌘ + B', + Italic: '⌘ + I', + Underline: '⌘ + U', + Strikethrough: '⌘ + ⇧ + S', + 'Inline code': ' ⌘ + E', + Link: '⌘ + K', + 'Body text': '⌘ + ⌥ + 0', + 'Heading 1': '⌘ + ⌥ + 1', + 'Heading 2': '⌘ + ⌥ + 2', + 'Heading 3': '⌘ + ⌥ + 3', + 'Heading 4': '⌘ + ⌥ + 4', + 'Heading 5': '⌘ + ⌥ + 5', + 'Heading 6': '⌘ + ⌥ + 6', 'Increase indent': 'Tab', - 'Reduce indent': 'Shift + Tab', + 'Reduce indent': '⇧ + Tab', }; export const macMarkdownShortcuts = { @@ -24,12 +24,12 @@ export const macMarkdownShortcuts = { Underline: '~Text~', Strikethrough: '~~Text~~', 'Inline code': '`Code`', - 'Heading 1': '# + Space', - 'Heading 2': '## + Space', - 'Heading 3': '### + Space', - 'Heading 4': '#### + Space', - 'Heading 5': '##### + Space', - 'Heading 6': '###### + Space', + 'Heading 1': '# Space', + 'Heading 2': '## Space', + 'Heading 3': '### Space', + 'Heading 4': '#### Space', + 'Heading 5': '##### Space', + 'Heading 6': '###### Space', }; export const windowsKeyboardShortcuts = { @@ -38,7 +38,7 @@ export const windowsKeyboardShortcuts = { Bold: 'Ctrl + B', Italic: 'Ctrl + I', Underline: 'Ctrl + U', - Strikethrough: 'Ctrl + Shit + S', + Strikethrough: 'Ctrl + ⇧ + S', 'Inline code': ' Ctrl + E', Link: 'Ctrl + K', 'Body text': 'Ctrl + Shift + 0', @@ -52,15 +52,15 @@ export const windowsKeyboardShortcuts = { 'Reduce indent': 'Shift + Tab', }; export const winMarkdownShortcuts = { - Bold: '**Text** + Space', - Italic: '*Text* + Space', - Underline: '~Text~ + Space', - Strikethrough: '~~Text~~ + Space', - 'Inline code': '`Code` + Space', - 'Heading 1': '# + Space', - 'Heading 2': '## + Space', - 'Heading 3': '### + Space', - 'Heading 4': '#### + Space', - 'Heading 5': '##### + Space', - 'Heading 6': '###### + Space', + Bold: '**Text** Space', + Italic: '*Text* Space', + Underline: '~Text~ Space', + Strikethrough: '~~Text~~ Space', + 'Inline code': '`Code` Space', + 'Heading 1': '# Space', + 'Heading 2': '## Space', + 'Heading 3': '### Space', + 'Heading 4': '#### Space', + 'Heading 5': '##### Space', + 'Heading 6': '###### Space', }; diff --git a/packages/app/src/components/shortcuts-modal/index.tsx b/packages/app/src/components/shortcuts-modal/index.tsx index 2d079525f7..42559480f8 100644 --- a/packages/app/src/components/shortcuts-modal/index.tsx +++ b/packages/app/src/components/shortcuts-modal/index.tsx @@ -50,7 +50,9 @@ export const ShortcutsModal = ({ open, onClose }: ModalProps) => { - Keyboard shortcuts + + Keyboard Shortcuts + {Object.entries(keyboardShortcuts).map(([title, shortcuts]) => { return ( @@ -59,7 +61,7 @@ export const ShortcutsModal = ({ open, onClose }: ModalProps) => { ); })} - Markdown shortcuts + Markdown Syntax {Object.entries(markdownShortcuts).map(([title, shortcuts]) => { return ( diff --git a/packages/app/src/components/shortcuts-modal/style.ts b/packages/app/src/components/shortcuts-modal/style.ts index e1924b513f..e9a34cf679 100644 --- a/packages/app/src/components/shortcuts-modal/style.ts +++ b/packages/app/src/components/shortcuts-modal/style.ts @@ -1,4 +1,4 @@ -import { styled } from '@/styles'; +import { displayFlex, styled } from '@/styles'; export const StyledShortcutsModal = styled.div(({ theme }) => ({ width: '268px', @@ -6,7 +6,6 @@ export const StyledShortcutsModal = styled.div(({ theme }) => ({ backgroundColor: theme.colors.popoverBackground, boxShadow: theme.shadow.popover, color: theme.colors.popoverColor, - padding: '8px 16px', overflow: 'auto', boxRadius: '10px', position: 'fixed', @@ -20,9 +19,7 @@ export const StyledTitle = styled.div(({ theme }) => ({ color: theme.colors.textColor, fontWeight: '600', fontSize: theme.font.sm, - display: 'flex', - justifyContent: 'center', - alignItems: 'center', + ...displayFlex('center', 'center'), svg: { width: '20px', marginRight: '14px', @@ -35,20 +32,27 @@ export const StyledSubTitle = styled.div(({ theme }) => ({ fontSize: '12px', height: '36px', lineHeight: '36px', + marginTop: '28px', + padding: '0 16px', })); export const StyledModalHeader = styled.div(({ theme }) => ({ - display: 'flex', - justifyContent: 'space-between', - alignItems: 'center', + ...displayFlex('space-between', 'center'), height: '36px', + width: '100%', + padding: '8px 16px 0 16px', + position: 'sticky', + left: '0', + top: '0', + background: 'var(--affine-popover-background)', + + transition: 'background-color 0.5s', })); export const StyledListItem = styled.div(({ theme }) => ({ height: '32px', - display: 'flex', - justifyContent: 'space-between', - alignItems: 'center', + ...displayFlex('space-between', 'center'), fontSize: theme.font.xs, + padding: '0 16px', })); export const CloseButton = styled('div')(({ theme }) => { @@ -58,6 +62,11 @@ export const CloseButton = styled('div')(({ theme }) => { borderRadius: '5px', color: theme.colors.iconColor, cursor: 'pointer', + ...displayFlex('center', 'center'), + svg: { + width: '15px', + height: '15px', + }, ':hover': { background: theme.colors.hoverBackground, }, diff --git a/packages/app/src/components/theme-mode-switch/style.ts b/packages/app/src/components/theme-mode-switch/style.ts index b40f7d3439..7f90930e67 100644 --- a/packages/app/src/components/theme-mode-switch/style.ts +++ b/packages/app/src/components/theme-mode-switch/style.ts @@ -1,4 +1,4 @@ -import { keyframes, styled } from '@/styles'; +import { displayFlex, keyframes, styled } from '@/styles'; import { CSSProperties } from 'react'; // @ts-ignore import spring, { toString } from 'css-spring'; @@ -56,11 +56,9 @@ export const StyledSwitchItem = styled('div')<{ return { width: '32px', height: '32px', - display: 'flex', position: 'absolute', left: '0', - justifyContent: 'center', - alignItems: 'center', + ...displayFlex('center', 'center'), cursor: 'pointer', ...activeStyle, }; diff --git a/packages/app/src/components/tooltip/Tooltip.tsx b/packages/app/src/components/tooltip/Tooltip.tsx index 8b33bb9b35..6fabed3f6d 100644 --- a/packages/app/src/components/tooltip/Tooltip.tsx +++ b/packages/app/src/components/tooltip/Tooltip.tsx @@ -26,11 +26,14 @@ export const placementToContainerDirection: Record< }; const useTooltipStyle = (): CSSProperties => { - const { theme } = useTheme(); + const { theme, mode } = useTheme(); return { boxShadow: '1px 1px 4px rgba(0, 0, 0, 0.14)', padding: '4px 12px', - backgroundColor: theme.colors.primaryColor, + backgroundColor: + mode === 'dark' + ? theme.colors.popoverBackground + : theme.colors.primaryColor, color: '#fff', fontSize: theme.font.xs, }; diff --git a/packages/app/src/pages/_app.tsx b/packages/app/src/pages/_app.tsx index 3aaf96efb7..747669cad0 100644 --- a/packages/app/src/pages/_app.tsx +++ b/packages/app/src/pages/_app.tsx @@ -4,6 +4,7 @@ import '../../public/globals.css'; import '../../public/variable.css'; import './temporary.css'; import { EditorProvider } from '@/components/editor-provider'; +import { ModalProvider } from '@/components/global-modal-provider'; import { Logger } from '@toeverything/pathfinder-logger'; const ThemeProvider = dynamic(() => import('@/styles/themeProvider'), { @@ -15,9 +16,11 @@ function MyApp({ Component, pageProps }: AppProps) { <> - - - + + + + + ); diff --git a/packages/app/src/pages/_document.tsx b/packages/app/src/pages/_document.tsx index 7bc23a3892..d84f7f8604 100644 --- a/packages/app/src/pages/_document.tsx +++ b/packages/app/src/pages/_document.tsx @@ -42,7 +42,12 @@ export default class AppDocument extends Document { render() { return ( - + + +
diff --git a/packages/app/src/pages/affine.tsx b/packages/app/src/pages/affine.tsx index 2d5bbe9b30..5596e2778e 100644 --- a/packages/app/src/pages/affine.tsx +++ b/packages/app/src/pages/affine.tsx @@ -1,12 +1,10 @@ -import { styled } from '@/styles'; +import { displayFlex, styled } from '@/styles'; import { ThemeModeSwitch } from '@/components/theme-mode-switch'; export const StyledHeader = styled('div')({ height: '60px', width: '100vw', - display: 'flex', - justifyContent: 'space-between', - alignItems: 'center', + ...displayFlex('space-between', 'center'), position: 'relative', padding: '0 22px', borderBottom: '1px solid #e5e5e5', diff --git a/packages/app/src/pages/index.tsx b/packages/app/src/pages/index.tsx index 5089d75b1b..628b9f0334 100644 --- a/packages/app/src/pages/index.tsx +++ b/packages/app/src/pages/index.tsx @@ -1,29 +1,28 @@ import type { NextPage } from 'next'; import dynamic from 'next/dynamic'; -import { styled, useTheme } from '@/styles'; +import { styled } from '@/styles'; import { Header } from '@/components/Header'; import { FAQ } from '@/components/faq'; +import EdgelessToolbar from '@/components/edgeless-toolbar'; import '@/components/simple-counter'; const StyledEditorContainer = styled('div')(({ theme }) => { return { - flexGrow: 1, - paddingTop: '78px', + height: 'calc(100vh - 60px)', }; }); const StyledPage = styled('div')(({ theme }) => { return { height: '100vh', - display: 'flex', - flexDirection: 'column', + paddingTop: '60px', backgroundColor: theme.colors.pageBackground, transition: 'background-color .5s', }; }); const DynamicEditor = dynamic(() => import('../components/editor'), { - loading: () =>
Loading...
, + loading: () =>
Loading...
, ssr: false, }); @@ -34,31 +33,8 @@ const Home: NextPage = () => { - {/**/} - {/**/} - {/*

current mode {mode}

*/} - {/* {*/} - {/* changeMode('light');*/} - {/* }}*/} - {/*>*/} - {/* light*/} - {/**/} - {/* {*/} - {/* changeMode('dark');*/} - {/* }}*/} - {/*>*/} - {/* dark*/} - {/**/} - {/* {*/} - {/* changeMode('auto');*/} - {/* }}*/} - {/*>*/} - {/* auto*/} - {/**/} + ); }; diff --git a/packages/app/src/pages/temporary.css b/packages/app/src/pages/temporary.css index de63ef2492..8f93223804 100644 --- a/packages/app/src/pages/temporary.css +++ b/packages/app/src/pages/temporary.css @@ -1,44 +1,23 @@ debug-menu { display: none !important; } -/*.affine-editor-container {*/ -/* height: 100%;*/ -/* padding: 0 !important;*/ -/*}*/ -/*.affine-default-page-block-container {*/ -/* width: 720px;*/ -/* height: 100%;*/ -/* margin: 0 auto;*/ -/*}*/ +.affine-block-children-container.edgeless { + background-color: #fff; +} -/*u {*/ -/* text-decoration: none;*/ -/* border-bottom: 1px solid #4c6275 !important;*/ -/*}*/ -/*u::after {*/ -/* display: none;*/ -/*}*/ +.affine-editor-container { + background: var(--affine-page-background); + transition: background-color 0.5s; + overflow-y: auto !important; + overflow-x: hidden; +} -/*.affine-paragraph-block-container.text {*/ -/* margin-top: 18px !important;*/ -/*}*/ - -/*.affine-default-page-block-title {*/ -/* width: 100%;*/ -/*}*/ -/*s {*/ -/* text-decoration: line-through !important;*/ -/*}*/ - -/*.affine-edgeless-page-block-container {*/ -/* height: 100% !important;*/ -/*}*/ -/*.affine-block-children-container.edgeless {*/ -/* height: 100% !important;*/ -/*}*/ -/*.affine-list-rich-text-wrapper > div {*/ -/* box-sizing: content-box;*/ -/* color: var(--affine-highlight-color);*/ -/* min-width: unset !important;*/ -/* max-width: 26px;*/ -/*}*/ +.affine-default-page-block-title-container { + margin-top: 78px; +} +.affine-default-page-block-container { + min-height: calc(100% - 78px); + height: auto !important; + overflow: hidden; + padding-bottom: 150px !important; +} diff --git a/packages/app/src/styles/helper.ts b/packages/app/src/styles/helper.ts new file mode 100644 index 0000000000..50955a254b --- /dev/null +++ b/packages/app/src/styles/helper.ts @@ -0,0 +1,84 @@ +import type { CSSProperties } from 'react'; + +export const displayFlex = ( + justifyContent: CSSProperties['justifyContent'] = 'unset', + alignItems: CSSProperties['alignContent'] = 'unset', + alignContent: CSSProperties['alignContent'] = 'unset' +): { + display: CSSProperties['display']; + justifyContent: CSSProperties['justifyContent']; + alignItems: CSSProperties['alignContent']; + alignContent: CSSProperties['alignContent']; +} => { + return { + display: 'flex', + justifyContent, + alignItems, + alignContent, + }; +}; + +export const absoluteCenter = ({ + horizontal = false, + vertical = false, + position: { left, right, top, bottom } = {}, +}: { + horizontal?: boolean; + vertical?: boolean; + position?: { + left?: CSSProperties['left']; + right?: CSSProperties['right']; + top?: CSSProperties['top']; + bottom?: CSSProperties['bottom']; + }; +}): { + position: CSSProperties['position']; + left: CSSProperties['left']; + top: CSSProperties['top']; + right: CSSProperties['right']; + bottom: CSSProperties['bottom']; + transform: CSSProperties['transform']; +} => { + return { + position: 'absolute', + left: left ? left : horizontal ? '50%' : 'auto', + top: top ? top : vertical ? '50%' : 'auto', + right: right ? right : horizontal ? 'auto' : 'auto', + bottom: bottom ? bottom : vertical ? 'auto' : 'auto', + transform: `translate(${horizontal ? '-50%' : '0'}, ${ + vertical ? '-50%' : '0' + })`, + }; +}; +export const fixedCenter = ({ + horizontal = false, + vertical = false, + position: { left, right, top, bottom } = {}, +}: { + horizontal?: boolean; + vertical?: boolean; + position?: { + left?: CSSProperties['left']; + right?: CSSProperties['right']; + top?: CSSProperties['top']; + bottom?: CSSProperties['bottom']; + }; +}): { + position: CSSProperties['position']; + left: CSSProperties['left']; + top: CSSProperties['top']; + right: CSSProperties['right']; + bottom: CSSProperties['bottom']; + transform: CSSProperties['transform']; +} => { + return { + position: 'fixed', + left: left ? left : horizontal ? '50%' : 'auto', + top: top ? top : vertical ? '50%' : 'auto', + right: right ? right : horizontal ? 'auto' : 'auto', + bottom: bottom ? bottom : vertical ? 'auto' : 'auto', + transform: `translate(${horizontal ? '-50%' : '0'}, ${ + vertical ? '-50%' : '0' + })`, + }; +}; diff --git a/packages/app/src/styles/index.ts b/packages/app/src/styles/index.ts index e74c167d3c..7c6781815e 100644 --- a/packages/app/src/styles/index.ts +++ b/packages/app/src/styles/index.ts @@ -4,3 +4,4 @@ export * from './styled'; export { ThemeProvider } from './themeProvider'; export { lightTheme, darkTheme } from './theme'; export { useTheme } from './hooks'; +export * from './helper'; diff --git a/packages/app/src/styles/theme.ts b/packages/app/src/styles/theme.ts index fb011861c3..acf8685e34 100644 --- a/packages/app/src/styles/theme.ts +++ b/packages/app/src/styles/theme.ts @@ -29,7 +29,7 @@ export const lightTheme: AffineTheme = { sm: '16px', base: '18px', family: `Avenir Next, ${basicFontFamily}`, - family2: `Roboto Mono, ${basicFontFamily}`, + family2: `Roboto, ${basicFontFamily}`, }, zIndex: { modal: 1000, @@ -55,8 +55,8 @@ export const darkTheme: AffineTheme = { textColor: '#fff', iconColor: '#9096A5', - linkColor: '#6880FF', - linkColor2: '#7D91FF', + linkColor: '#7D91FF', + linkColor2: '#6880FF', linkVisitedColor: '#505FAB', popoverColor: '#A9B1C6', codeColor: '#BDDBFD', @@ -103,6 +103,9 @@ export const globalThemeVariables: ( '--affine-font-sm': theme.font.sm, // small '--affine-font-base': theme.font.base, + '--affine-z-index-modal': theme.zIndex.modal, + '--affine-z-index-popover': theme.zIndex.popover, + '--affine-font-family': theme.font.family, '--affine-font-family2': theme.font.family2, }; diff --git a/packages/app/src/styles/types.ts b/packages/app/src/styles/types.ts index da54956d91..3e70ffc340 100644 --- a/packages/app/src/styles/types.ts +++ b/packages/app/src/styles/types.ts @@ -76,6 +76,9 @@ export interface AffineThemeCSSVariables { '--affine-font-sm': AffineTheme['font']['sm']; // small '--affine-font-base': AffineTheme['font']['base']; + '--affine-z-index-modal': AffineTheme['zIndex']['modal']; + '--affine-z-index-popover': AffineTheme['zIndex']['popover']; + '--affine-font-family': AffineTheme['font']['family']; '--affine-font-family2': AffineTheme['font']['family2']; }