From 487ef35563c63c6cfdc7b50514664daf9a818237 Mon Sep 17 00:00:00 2001 From: Peng Xiao Date: Mon, 3 Apr 2023 13:24:53 +0800 Subject: [PATCH] fix: some minor ui issues (#1783) --- .prettierignore | 2 +- apps/electron/layers/preload/preload.d.ts | 24 ++++------ .../pure/workspace-slider-bar/index.tsx | 25 ++++------ .../pure/workspace-slider-bar/style.ts | 47 +++++++++---------- .../src/hooks/affine/use-sidebar-status.ts | 6 +++ apps/web/src/layouts/index.tsx | 22 +++++++-- apps/web/src/layouts/styles.ts | 25 ++++++---- tests/parallels/layout.spec.ts | 14 +++--- tests/parallels/quick-search.spec.ts | 2 +- tests/parallels/subpage.spec.ts | 2 +- 10 files changed, 90 insertions(+), 79 deletions(-) diff --git a/.prettierignore b/.prettierignore index 11aac20664..1c4786433e 100644 --- a/.prettierignore +++ b/.prettierignore @@ -1,2 +1,2 @@ pnpm-lock.yaml - +apps/electron/layers/preload/preload.d.ts diff --git a/apps/electron/layers/preload/preload.d.ts b/apps/electron/layers/preload/preload.d.ts index e9d3cd6c0b..578259644e 100644 --- a/apps/electron/layers/preload/preload.d.ts +++ b/apps/electron/layers/preload/preload.d.ts @@ -1,16 +1,12 @@ interface Window { - /** - * After analyzing the `exposeInMainWorld` calls, - * `packages/preload/exposedInMainWorld.d.ts` file will be generated. - * It contains all interfaces. - * `packages/preload/exposedInMainWorld.d.ts` file is required for TS is `renderer` - * - * @see https://github.com/cawa-93/dts-for-context-bridge - */ - readonly apis: { - workspaceSync: (id: string) => Promise; - onThemeChange: (theme: string) => Promise; - onSidebarVisibilityChange: (visible: boolean) => Promise; - }; - readonly appInfo: { electron: boolean; isMacOS: boolean }; + /** + * After analyzing the `exposeInMainWorld` calls, + * `packages/preload/exposedInMainWorld.d.ts` file will be generated. + * It contains all interfaces. + * `packages/preload/exposedInMainWorld.d.ts` file is required for TS is `renderer` + * + * @see https://github.com/cawa-93/dts-for-context-bridge + */ + readonly apis: { workspaceSync: (id: string) => Promise; onThemeChange: (theme: string) => Promise; onSidebarVisibilityChange: (visible: boolean) => Promise; }; + readonly appInfo: { electron: boolean; isMacOS: boolean; }; } diff --git a/apps/web/src/components/pure/workspace-slider-bar/index.tsx b/apps/web/src/components/pure/workspace-slider-bar/index.tsx index b7da14955d..b89ccd482a 100644 --- a/apps/web/src/components/pure/workspace-slider-bar/index.tsx +++ b/apps/web/src/components/pure/workspace-slider-bar/index.tsx @@ -8,11 +8,11 @@ import { SettingsIcon, } from '@blocksuite/icons'; import type { Page, PageMeta } from '@blocksuite/store'; -import { useMediaQuery, useTheme } from '@mui/material'; import type React from 'react'; import { useCallback, useEffect } from 'react'; import { + useSidebarFloating, useSidebarResizing, useSidebarStatus, useSidebarWidth, @@ -80,16 +80,11 @@ export const WorkSpaceSliderBar: React.FC = ({ const page = await createPage(); openPage(page.id); }, [createPage, openPage]); - const theme = useTheme(); - const floatingSlider = useMediaQuery(theme.breakpoints.down('md')); + const floatingSlider = useSidebarFloating(); const [sliderWidth, setSliderWidth] = useSidebarWidth(); const [isResizing, setIsResizing] = useSidebarResizing(); const show = isPublicWorkspace ? false : sidebarOpen; - const actualWidth = show - ? floatingSlider - ? 'calc(10vw + 400px)' - : sliderWidth - : 0; + const actualWidth = floatingSlider ? 'calc(10vw + 400px)' : sliderWidth; const onResizeStart = useCallback(() => { let resized = false; function onMouseMove(e: MouseEvent) { @@ -117,13 +112,13 @@ export const WorkSpaceSliderBar: React.FC = ({ }, [sidebarOpen]); return ( <> - - + + { +const macosElectron = environment.isDesktop && environment.isMacOs; + +export const StyledSliderBarWrapper = styled('div')<{ + show: boolean; + floating: boolean; +}>(({ theme, show, floating }) => { return { height: '100%', - width: 'auto', - position: 'relative', + position: 'absolute', 'button, a': { userSelect: 'none', }, + zIndex: theme.zIndex.modal, + transition: 'transform .25s', + transform: show ? 'translateX(0)' : 'translateX(-100%)', + maxWidth: floating ? undefined : 'calc(100vw - 698px)', + background: + !floating && macosElectron ? 'transparent' : theme.colors.hubBackground, + borderRight: '1px solid', + borderColor: theme.colors.borderColor, }; }); -export const StyledSliderBar = styled('div')<{ - resizing: boolean; - show: boolean; - floating: boolean; -}>(({ theme, show, floating, resizing }) => { - const env = getEnvironment(); - const macosElectron = env.isDesktop && env.isMacOs; +export const StyledSliderBar = styled('div')(({ theme }) => { return { whiteSpace: 'nowrap', + width: '100%', height: '100%', - background: - !floating && macosElectron ? 'transparent' : theme.colors.hubBackground, - zIndex: theme.zIndex.modal, - transition: !resizing ? 'width .15s, padding .15s' : '', - padding: show ? '0 4px' : '0', + padding: '0 4px', flexShrink: 0, display: 'flex', flexDirection: 'column', overflow: 'hidden', - position: floating ? 'absolute' : 'relative', - maxWidth: floating ? undefined : 'calc(100vw - 698px)', - borderRight: '1px solid', - borderColor: theme.colors.borderColor, }; }); export const StyledSidebarSwitchWrapper = styled('div')(() => { @@ -43,7 +41,7 @@ export const StyledSidebarSwitchWrapper = styled('div')(() => { height: '52px', flexShrink: 0, padding: '0 16px', - ...displayFlex('flex-end', 'center'), + ...displayFlex(macosElectron ? 'flex-end' : 'flex-start', 'center'), }; }); export const StyledSliderBarInnerWrapper = styled('div')(() => { @@ -92,11 +90,10 @@ export const StyledSliderModalBackground = styled('div')<{ active: boolean }>( transition: 'opacity .15s', pointerEvents: active ? 'auto' : 'none', opacity: active ? 1 : 0, - display: active ? 'block' : 'none', position: 'fixed', top: 0, left: 0, - right: 0, + right: active ? 0 : '100%', bottom: 0, zIndex: theme.zIndex.modal - 1, background: theme.colors.modalBackground, @@ -104,7 +101,7 @@ export const StyledSliderModalBackground = styled('div')<{ active: boolean }>( } ); export const StyledSliderResizer = styled('div')<{ isResizing: boolean }>( - ({ theme }) => { + () => { return { position: 'absolute', top: 0, @@ -113,7 +110,7 @@ export const StyledSliderResizer = styled('div')<{ isResizing: boolean }>( width: '12px', transform: 'translateX(50%)', cursor: 'col-resize', - zIndex: theme.zIndex.modal + 1, + zIndex: 1, userSelect: 'none', ':hover > *': { background: 'rgba(0, 0, 0, 0.1)', diff --git a/apps/web/src/hooks/affine/use-sidebar-status.ts b/apps/web/src/hooks/affine/use-sidebar-status.ts index cce4b10191..8e6bfc4c43 100644 --- a/apps/web/src/hooks/affine/use-sidebar-status.ts +++ b/apps/web/src/hooks/affine/use-sidebar-status.ts @@ -1,4 +1,5 @@ import { atomWithSyncStorage } from '@affine/jotai'; +import { useMediaQuery, useTheme } from '@mui/material'; import { atom, useAtom } from 'jotai'; const sideBarOpenAtom = atomWithSyncStorage('sidebarOpen', true); @@ -13,6 +14,11 @@ export function useSidebarWidth() { return useAtom(sideBarWidthAtom); } +export function useSidebarFloating() { + const theme = useTheme(); + return useMediaQuery(theme.breakpoints.down('md')); +} + export function useSidebarResizing() { return useAtom(sidebarResizingAtom); } diff --git a/apps/web/src/layouts/index.tsx b/apps/web/src/layouts/index.tsx index cf45210935..45381aabd7 100644 --- a/apps/web/src/layouts/index.tsx +++ b/apps/web/src/layouts/index.tsx @@ -26,7 +26,12 @@ import { HelpIsland } from '../components/pure/help-island'; import { PageLoading } from '../components/pure/loading'; import WorkSpaceSliderBar from '../components/pure/workspace-slider-bar'; import { useAffineRefreshAuthToken } from '../hooks/affine/use-affine-refresh-auth-token'; -import { useSidebarResizing } from '../hooks/affine/use-sidebar-status'; +import { + useSidebarFloating, + useSidebarResizing, + useSidebarStatus, + useSidebarWidth, +} from '../hooks/affine/use-sidebar-status'; import { useCurrentPageId } from '../hooks/current/use-current-page-id'; import { useCurrentWorkspace } from '../hooks/current/use-current-workspace'; import { useBlockSuiteWorkspaceHelper } from '../hooks/use-blocksuite-workspace-helper'; @@ -246,14 +251,18 @@ export const WorkspaceLayoutInner: React.FC = ({ setOpenWorkspacesModal(true); }, [setOpenWorkspacesModal]); - const [openQuickSearchModal, setOpenQuickSearchModalAtom] = useAtom( - openQuickSearchModalAtom - ); + const [, setOpenQuickSearchModalAtom] = useAtom(openQuickSearchModalAtom); const handleOpenQuickSearchModal = useCallback(() => { setOpenQuickSearchModalAtom(true); }, [setOpenQuickSearchModalAtom]); const [resizingSidebar] = useSidebarResizing(); const lock = useAtomValue(workspaceLockAtom); + const [sidebarOpen] = useSidebarStatus(); + const sidebarFloating = useSidebarFloating(); + const [sidebarWidth] = useSidebarWidth(); + const paddingLeft = + sidebarFloating || !sidebarOpen ? '0' : `${sidebarWidth}px`; + const [resizing] = useSidebarResizing(); if (lock) { return ; } @@ -275,7 +284,10 @@ export const WorkspaceLayoutInner: React.FC = ({ currentPath={router.asPath.split('?')[0]} paths={isPublicWorkspace ? publicPathGenerator : pathGenerator} /> - + {children} diff --git a/apps/web/src/layouts/styles.ts b/apps/web/src/layouts/styles.ts index 56d292b953..4e021d5aa1 100644 --- a/apps/web/src/layouts/styles.ts +++ b/apps/web/src/layouts/styles.ts @@ -4,6 +4,8 @@ export const StyledPage = styled('div')<{ resizing?: boolean }>( ({ theme, resizing }) => { return { cursor: resizing ? 'col-resize' : 'default', + width: '100%', + position: 'relative', height: '100vh', transition: 'background-color .5s', display: 'flex', @@ -24,21 +26,24 @@ export const StyledWrapper = styled('div')(() => { }; }); -export const MainContainerWrapper = styled('div')(({ theme }) => { - return { - display: 'flex', - flexGrow: 1, - position: 'relative', - maxWidth: '100vw', - overflow: 'auto', - backgroundColor: theme.colors.pageBackground, - }; -}); +export const MainContainerWrapper = styled('div')<{ resizing: boolean }>( + ({ theme, resizing }) => { + return { + display: 'flex', + flexGrow: 1, + position: 'relative', + maxWidth: '100vw', + overflow: 'auto', + transition: resizing ? '' : 'padding-left .25s', + }; + } +); export const MainContainer = styled('div')(({ theme }) => { return { position: 'relative', flexGrow: 1, + backgroundColor: theme.colors.pageBackground, [theme.breakpoints.up('md')]: { minWidth: '686px', }, diff --git a/tests/parallels/layout.spec.ts b/tests/parallels/layout.spec.ts index d0fd6f4c7b..23059115fc 100644 --- a/tests/parallels/layout.spec.ts +++ b/tests/parallels/layout.spec.ts @@ -9,8 +9,8 @@ test.describe('Layout ui', () => { await openHomePage(page); await waitMarkdownImported(page); await page.getByTestId('sliderBar-arrowButton-collapse').click(); - const sliderBarArea = page.getByTestId('sliderBar-inner'); - await expect(sliderBarArea).not.toBeVisible(); + const sliderBarArea = page.getByTestId('sliderBar-root'); + await expect(sliderBarArea).not.toBeInViewport(); }); test('Expand Sidebar', async ({ page }) => { @@ -18,10 +18,10 @@ test.describe('Layout ui', () => { await waitMarkdownImported(page); await page.getByTestId('sliderBar-arrowButton-collapse').click(); const sliderBarArea = page.getByTestId('sliderBar-inner'); - await expect(sliderBarArea).not.toBeVisible(); + await expect(sliderBarArea).not.toBeInViewport(); await page.getByTestId('sliderBar-arrowButton-expand').click(); - await expect(sliderBarArea).toBeVisible(); + await expect(sliderBarArea).toBeInViewport(); }); test('Click resizer can close sidebar', async ({ page }) => { @@ -31,7 +31,7 @@ test.describe('Layout ui', () => { await expect(sliderBarArea).toBeVisible(); await page.getByTestId('sliderBar-resizer').click(); - await expect(sliderBarArea).not.toBeVisible(); + await expect(sliderBarArea).not.toBeInViewport(); }); test('Drag resizer can resize sidebar', async ({ page }) => { @@ -58,7 +58,7 @@ test.describe('Layout ui', () => { const sliderBarModalBackground = page.getByTestId( 'sliderBar-modalBackground' ); - await expect(sliderBarArea).toBeVisible(); + await expect(sliderBarArea).toBeInViewport(); await expect(sliderBarModalBackground).not.toBeVisible(); await page.setViewportSize({ @@ -72,6 +72,6 @@ test.describe('Layout ui', () => { force: true, position: { x: 600, y: 150 }, }); - await expect(sliderBarArea).not.toBeVisible(); + await expect(sliderBarArea).not.toBeInViewport(); }); }); diff --git a/tests/parallels/quick-search.spec.ts b/tests/parallels/quick-search.spec.ts index ae8dcea180..41a77ccfa8 100644 --- a/tests/parallels/quick-search.spec.ts +++ b/tests/parallels/quick-search.spec.ts @@ -181,7 +181,7 @@ test.describe('Novice guidance for quick search', () => { await expect(quickSearchTips).not.toBeVisible(); await page.getByTestId('sliderBar-arrowButton-collapse').click(); const sliderBarArea = page.getByTestId('sliderBar-inner'); - await expect(sliderBarArea).not.toBeVisible(); + await expect(sliderBarArea).not.toBeInViewport(); await expect(quickSearchTips).toBeVisible(); await page.locator('[data-testid=quick-search-got-it]').click(); await expect(quickSearchTips).not.toBeVisible(); diff --git a/tests/parallels/subpage.spec.ts b/tests/parallels/subpage.spec.ts index c4003224df..d2891cdc22 100644 --- a/tests/parallels/subpage.spec.ts +++ b/tests/parallels/subpage.spec.ts @@ -10,6 +10,6 @@ test.describe('subpage', () => { await waitMarkdownImported(page); await page.getByTestId('sliderBar-arrowButton-collapse').click(); const sliderBarArea = page.getByTestId('sliderBar-inner'); - await expect(sliderBarArea).not.toBeVisible(); + await expect(sliderBarArea).not.toBeInViewport(); }); });