diff --git a/apps/web/src/adapters/affine/index.tsx b/apps/web/src/adapters/affine/index.tsx index 1581837ad2..fbaa5f898f 100644 --- a/apps/web/src/adapters/affine/index.tsx +++ b/apps/web/src/adapters/affine/index.tsx @@ -34,14 +34,17 @@ import { z } from 'zod'; import { createAffineProviders } from '../../blocksuite'; import { createAffineDownloadProvider } from '../../blocksuite/providers/affine'; -import { WorkspaceSettingDetail } from '../../components/affine/workspace-setting-detail'; -import { BlockSuitePageList } from '../../components/blocksuite/block-suite-page-list'; -import { PageDetailEditor } from '../../components/page-detail-editor'; import { PageLoading } from '../../components/pure/loading'; import { useAffineRefreshAuthToken } from '../../hooks/affine/use-affine-refresh-auth-token'; import { BlockSuiteWorkspace } from '../../shared'; import { affineApis, affineAuth } from '../../shared/apis'; import { toast } from '../../utils'; +import { + BlockSuitePageList, + PageDetailEditor, + WorkspaceHeader, + WorkspaceSettingDetail, +} from '../shared'; import type { WorkspaceAdapter } from '../type'; import { QueryKey } from './fetcher'; @@ -311,6 +314,7 @@ export const AffineAdapter: WorkspaceAdapter = { ); }, + Header: WorkspaceHeader, PageDetail: ({ currentWorkspace, currentPageId, onLoadEditor }) => { const page = currentWorkspace.blockSuiteWorkspace.getPage(currentPageId); if (!page) { diff --git a/apps/web/src/adapters/local/index.tsx b/apps/web/src/adapters/local/index.tsx index da111fa917..c70e16e955 100644 --- a/apps/web/src/adapters/local/index.tsx +++ b/apps/web/src/adapters/local/index.tsx @@ -17,32 +17,16 @@ import { } from '@affine/workspace/type'; import { createEmptyBlockSuiteWorkspace } from '@affine/workspace/utils'; import { nanoid } from '@blocksuite/store'; -import { lazy } from 'react'; +import React from 'react'; +import { + BlockSuitePageList, + PageDetailEditor, + WorkspaceHeader, + WorkspaceSettingDetail, +} from '../shared'; import type { WorkspaceAdapter } from '../type'; -const WorkspaceSettingDetail = lazy(() => - import('../../components/affine/workspace-setting-detail').then( - ({ WorkspaceSettingDetail }) => ({ - default: WorkspaceSettingDetail, - }) - ) -); -const BlockSuitePageList = lazy(() => - import('../../components/blocksuite/block-suite-page-list').then( - ({ BlockSuitePageList }) => ({ - default: BlockSuitePageList, - }) - ) -); -const PageDetailEditor = lazy(() => - import('../../components/page-detail-editor').then( - ({ PageDetailEditor }) => ({ - default: PageDetailEditor, - }) - ) -); - const logger = new DebugLogger('use-create-first-workspace'); export const LocalAdapter: WorkspaceAdapter = { @@ -78,6 +62,7 @@ export const LocalAdapter: WorkspaceAdapter = { }, CRUD, UI: { + Header: WorkspaceHeader, Provider: ({ children }) => { return <>{children}; }, diff --git a/apps/web/src/adapters/shared.ts b/apps/web/src/adapters/shared.ts new file mode 100644 index 0000000000..040becc2d2 --- /dev/null +++ b/apps/web/src/adapters/shared.ts @@ -0,0 +1,27 @@ +import { lazy } from 'react'; + +export const WorkspaceSettingDetail = lazy(() => + import('../components/affine/workspace-setting-detail').then( + ({ WorkspaceSettingDetail }) => ({ + default: WorkspaceSettingDetail, + }) + ) +); +export const BlockSuitePageList = lazy(() => + import('../components/blocksuite/block-suite-page-list').then( + ({ BlockSuitePageList }) => ({ + default: BlockSuitePageList, + }) + ) +); +export const PageDetailEditor = lazy(() => + import('../components/page-detail-editor').then(({ PageDetailEditor }) => ({ + default: PageDetailEditor, + })) +); + +export const WorkspaceHeader = lazy(() => + import('../components/workspace-header').then(({ WorkspaceHeader }) => ({ + default: WorkspaceHeader, + })) +); diff --git a/apps/web/src/adapters/workspace.ts b/apps/web/src/adapters/workspace.ts index fa1d1482fb..cf62dd448f 100644 --- a/apps/web/src/adapters/workspace.ts +++ b/apps/web/src/adapters/workspace.ts @@ -32,6 +32,7 @@ export const WorkspaceAdapters = { // todo: implement this UI: { Provider: unimplemented, + Header: unimplemented, PageDetail: unimplemented, PageList: unimplemented, SettingsDetail: unimplemented, @@ -52,6 +53,7 @@ export const WorkspaceAdapters = { // todo: implement this UI: { Provider: unimplemented, + Header: unimplemented, PageDetail: unimplemented, PageList: unimplemented, SettingsDetail: unimplemented, diff --git a/apps/web/src/components/blocksuite/workspace-header/header-right-items/share-menu.tsx b/apps/web/src/components/blocksuite/workspace-header/header-right-items/share-menu.tsx index 1192231ee4..3d786f0fda 100644 --- a/apps/web/src/components/blocksuite/workspace-header/header-right-items/share-menu.tsx +++ b/apps/web/src/components/blocksuite/workspace-header/header-right-items/share-menu.tsx @@ -5,7 +5,7 @@ import type { AffineLegacyCloudWorkspace, LocalWorkspace, } from '@affine/workspace/type'; -import { WorkspaceFlavour } from '@affine/workspace/type'; +import { WorkspaceFlavour, WorkspaceSubPath } from '@affine/workspace/type'; import type { Page } from '@blocksuite/store'; import { assertEquals } from '@blocksuite/store'; import { useRouter } from 'next/router'; @@ -15,7 +15,6 @@ import { useCallback, useState } from 'react'; import { useToggleWorkspacePublish } from '../../../../hooks/affine/use-toggle-workspace-publish'; import { useOnTransformWorkspace } from '../../../../hooks/root/use-on-transform-workspace'; import { useRouterHelper } from '../../../../hooks/use-router-helper'; -import { WorkspaceSubPath } from '../../../../shared'; import { TransformWorkspaceToAffineModal } from '../../../affine/transform-workspace-to-affine-modal'; import type { BaseHeaderProps } from '../header'; diff --git a/apps/web/src/components/blocksuite/workspace-header/header.tsx b/apps/web/src/components/blocksuite/workspace-header/header.tsx index a19514a4aa..cba8fc1417 100644 --- a/apps/web/src/components/blocksuite/workspace-header/header.tsx +++ b/apps/web/src/components/blocksuite/workspace-header/header.tsx @@ -43,7 +43,6 @@ export type BaseHeaderProps< workspace: Workspace; currentPage: Page | null; isPublic: boolean; - isPreview: boolean; leftSlot?: ReactNode; }; @@ -67,7 +66,6 @@ type HeaderItem = { currentPage: Page | null, status: { isPublic: boolean; - isPreview: boolean; } ) => boolean; }; @@ -81,8 +79,8 @@ const HeaderRightItems: Record = { }, [HeaderRightItemName.SyncUser]: { Component: SyncUser, - availableWhen: (_, currentPage, { isPublic, isPreview }) => { - return !isPublic && !isPreview; + availableWhen: (_, currentPage, { isPublic }) => { + return !isPublic; }, }, [HeaderRightItemName.ShareMenu]: { @@ -105,8 +103,8 @@ const HeaderRightItems: Record = { }, [HeaderRightItemName.EditorOptionMenu]: { Component: EditorOptionMenu, - availableWhen: (_, currentPage, { isPublic, isPreview }) => { - return !isPublic && !isPreview; + availableWhen: (_, currentPage, { isPublic }) => { + return !isPublic; }, }, [HeaderRightItemName.WindowsAppControls]: { @@ -216,7 +214,6 @@ export const Header = forwardRef< ([name, { availableWhen, Component }]) => { if ( availableWhen(props.workspace, props.currentPage, { - isPreview: props.isPreview, isPublic: props.isPublic, }) ) { @@ -224,7 +221,6 @@ export const Header = forwardRef< diff --git a/apps/web/src/components/blocksuite/workspace-header/index.tsx b/apps/web/src/components/blocksuite/workspace-header/index.tsx index a8e5d44361..4dca64673c 100644 --- a/apps/web/src/components/blocksuite/workspace-header/index.tsx +++ b/apps/web/src/components/blocksuite/workspace-header/index.tsx @@ -18,7 +18,7 @@ import * as styles from './styles.css'; export type WorkspaceHeaderProps = BaseHeaderProps; -export const WorkspaceHeader: FC< +export const BlockSuiteEditorHeader: FC< PropsWithChildren & HTMLAttributes > = (props): ReactElement => { const { workspace, currentPage, children, isPublic } = props; @@ -62,4 +62,4 @@ export const WorkspaceHeader: FC< ); }; -WorkspaceHeader.displayName = 'BlockSuiteEditorHeader'; +BlockSuiteEditorHeader.displayName = 'BlockSuiteEditorHeader'; diff --git a/apps/web/src/components/page-detail-editor.tsx b/apps/web/src/components/page-detail-editor.tsx index 9286e8c816..d7bdccabac 100644 --- a/apps/web/src/components/page-detail-editor.tsx +++ b/apps/web/src/components/page-detail-editor.tsx @@ -13,16 +13,13 @@ import { startTransition, useCallback } from 'react'; import { currentEditorAtom, workspacePreferredModeAtom } from '../atoms'; import type { AffineOfficialWorkspace } from '../shared'; import { BlockSuiteEditor as Editor } from './blocksuite/block-suite-editor'; -import { WorkspaceHeader } from './blocksuite/workspace-header'; export type PageDetailEditorProps = { isPublic?: boolean; - isPreview?: boolean; workspace: AffineOfficialWorkspace; pageId: string; onInit: (page: Page, editor: Readonly) => void; onLoad?: (page: Page, editor: EditorContainer) => () => void; - header?: React.ReactNode; }; export const PageDetailEditor: React.FC = ({ @@ -30,9 +27,7 @@ export const PageDetailEditor: React.FC = ({ pageId, onInit, onLoad, - header, isPublic, - isPreview, }) => { const blockSuiteWorkspace = workspace.blockSuiteWorkspace; const page = useBlockSuiteWorkspacePage(blockSuiteWorkspace, pageId); @@ -52,14 +47,6 @@ export const PageDetailEditor: React.FC = ({ {title} - - {header} - ): ReactElement { + const setting = useAllPageSetting(); + const t = useAFFiNEI18N(); + if ('subPath' in currentEntry) { + if (currentEntry.subPath === WorkspaceSubPath.ALL) { + const leftSlot = config.enableAllPageFilter && ( + + ); + const filterContainer = config.enableAllPageFilter && + setting.currentView.filterList.length > 0 && ( +
+
+ + setting.changeView( + { + ...setting.currentView, + filterList, + }, + setting.currentViewIndex + ) + } + /> +
+
+ {setting.currentViewIndex == null ? ( + + ) : ( + + )} +
+
+ ); + + return ( + <> + } + leftSlot={leftSlot} + > + {t['All pages']()} + + {filterContainer} + + ); + } else if (currentEntry.subPath === WorkspaceSubPath.SETTING) { + return ( + } + > + {t['Workspace Settings']()} + + ); + } else if (currentEntry.subPath === WorkspaceSubPath.SHARED) { + return ( + } + > + {t['Shared Pages']()} + + ); + } else if (currentEntry.subPath === WorkspaceSubPath.TRASH) { + return ( + } + > + {t['Trash']()} + + ); + } + } else if ('pageId' in currentEntry) { + const pageId = currentEntry.pageId; + const isPublic = currentWorkspace.flavour === WorkspaceFlavour.PUBLIC; + return ( + + ); + } + return <>; +} diff --git a/apps/web/src/hooks/__tests__/index.spec.tsx b/apps/web/src/hooks/__tests__/index.spec.tsx index c73b0ed4ab..bff431806a 100644 --- a/apps/web/src/hooks/__tests__/index.spec.tsx +++ b/apps/web/src/hooks/__tests__/index.spec.tsx @@ -6,7 +6,7 @@ import 'fake-indexeddb/auto'; import assert from 'node:assert'; import { rootCurrentWorkspaceIdAtom } from '@affine/workspace/atom'; -import { WorkspaceFlavour } from '@affine/workspace/type'; +import { WorkspaceFlavour, WorkspaceSubPath } from '@affine/workspace/type'; import type { PageBlockModel } from '@blocksuite/blocks'; import { __unstableSchemas, AffineSchemas } from '@blocksuite/blocks/models'; import type { Page } from '@blocksuite/store'; @@ -23,7 +23,7 @@ import type React from 'react'; import { beforeAll, beforeEach, describe, expect, test, vi } from 'vitest'; import { workspacesAtom } from '../../atoms'; -import { BlockSuiteWorkspace, WorkspaceSubPath } from '../../shared'; +import { BlockSuiteWorkspace } from '../../shared'; import { currentWorkspaceAtom, useCurrentWorkspace, diff --git a/apps/web/src/hooks/__tests__/use-recent-views.spec.tsx b/apps/web/src/hooks/__tests__/use-recent-views.spec.tsx index 73cf42affc..3de4896cc3 100644 --- a/apps/web/src/hooks/__tests__/use-recent-views.spec.tsx +++ b/apps/web/src/hooks/__tests__/use-recent-views.spec.tsx @@ -6,7 +6,7 @@ import { rootWorkspacesMetadataAtom, } from '@affine/workspace/atom'; import type { LocalWorkspace } from '@affine/workspace/type'; -import { WorkspaceFlavour } from '@affine/workspace/type'; +import { WorkspaceFlavour, WorkspaceSubPath } from '@affine/workspace/type'; import { __unstableSchemas, AffineSchemas } from '@blocksuite/blocks/models'; import type { Page } from '@blocksuite/store'; import { assertExists } from '@blocksuite/store'; @@ -21,7 +21,6 @@ import { beforeAll, beforeEach, describe, expect, test, vi } from 'vitest'; import { LocalAdapter } from '../../adapters/local'; import { workspacesAtom } from '../../atoms'; import { BlockSuiteWorkspace } from '../../shared'; -import { WorkspaceSubPath } from '../../shared'; import { currentWorkspaceAtom, useCurrentWorkspace, diff --git a/apps/web/src/hooks/__tests__/use-router-helper.spec.ts b/apps/web/src/hooks/__tests__/use-router-helper.spec.ts index b457351dca..eaa88113dc 100644 --- a/apps/web/src/hooks/__tests__/use-router-helper.spec.ts +++ b/apps/web/src/hooks/__tests__/use-router-helper.spec.ts @@ -1,13 +1,13 @@ /** * @vitest-environment happy-dom */ +import { WorkspaceSubPath } from '@affine/workspace/type'; import { renderHook } from '@testing-library/react'; import { useRouter } from 'next/router'; import routerMock from 'next-router-mock'; import { createDynamicRouteParser } from 'next-router-mock/dynamic-routes'; import { beforeAll, describe, expect, test } from 'vitest'; -import { WorkspaceSubPath } from '../../shared'; import { RouteLogic, useRouterHelper } from '../use-router-helper'; beforeAll(() => { diff --git a/apps/web/src/hooks/use-router-helper.ts b/apps/web/src/hooks/use-router-helper.ts index 9232e09878..4b991bebd2 100644 --- a/apps/web/src/hooks/use-router-helper.ts +++ b/apps/web/src/hooks/use-router-helper.ts @@ -1,8 +1,7 @@ +import type { WorkspaceSubPath } from '@affine/workspace/type'; import type { NextRouter } from 'next/router'; import { useCallback } from 'react'; -import type { WorkspaceSubPath } from '../shared'; - export const enum RouteLogic { REPLACE = 'replace', PUSH = 'push', diff --git a/apps/web/src/pages/index.tsx b/apps/web/src/pages/index.tsx index 47927e6226..3642e63361 100644 --- a/apps/web/src/pages/index.tsx +++ b/apps/web/src/pages/index.tsx @@ -1,4 +1,5 @@ import { DebugLogger } from '@affine/debug'; +import { WorkspaceSubPath } from '@affine/workspace/type'; import type { NextPage } from 'next'; import { useRouter } from 'next/router'; import { Suspense, useEffect } from 'react'; @@ -6,7 +7,6 @@ import { Suspense, useEffect } from 'react'; import { PageLoading } from '../components/pure/loading'; import { RouteLogic, useRouterHelper } from '../hooks/use-router-helper'; import { useAppHelper, useWorkspaces } from '../hooks/use-workspaces'; -import { WorkspaceSubPath } from '../shared'; const logger = new DebugLogger('index-page'); diff --git a/apps/web/src/pages/invite/[invite-code].tsx b/apps/web/src/pages/invite/[invite-code].tsx index 6880b8d1b4..2ac21af83e 100644 --- a/apps/web/src/pages/invite/[invite-code].tsx +++ b/apps/web/src/pages/invite/[invite-code].tsx @@ -1,6 +1,7 @@ import { displayFlex, styled } from '@affine/component'; import { Button } from '@affine/component'; import type { Permission } from '@affine/workspace/affine/api'; +import { WorkspaceSubPath } from '@affine/workspace/type'; import { SucessfulDuotoneIcon, UnsucessfulDuotoneIcon, @@ -15,7 +16,6 @@ import { QueryKey } from '../../adapters/affine/fetcher'; import { PageLoading } from '../../components/pure/loading'; import { RouteLogic, useRouterHelper } from '../../hooks/use-router-helper'; import type { NextPageWithLayout } from '../../shared'; -import { WorkspaceSubPath } from '../../shared'; const InvitePage: NextPageWithLayout = () => { const router = useRouter(); diff --git a/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx b/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx index df077717b4..7d2f070c61 100644 --- a/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx +++ b/apps/web/src/pages/public-workspace/[workspaceId]/[pageId].tsx @@ -16,6 +16,7 @@ import { publicWorkspaceIdAtom, publicWorkspacePageIdAtom, } from '../../../atoms/public-workspace'; +import { BlockSuiteEditorHeader } from '../../../components/blocksuite/workspace-header'; import { PageDetailEditor } from '../../../components/page-detail-editor'; import { WorkspaceAvatar } from '../../../components/pure/footer'; import { PageLoading } from '../../../components/pure/loading'; @@ -70,6 +71,28 @@ const PublicWorkspaceDetailPageInner = (): ReactElement => { return ( <> + + + + + + {name} + + + + {pageTitle ? pageTitle : t['Untitled']()} + + + + { }; }} onInit={initPage} - header={ - - - - - {name} - - - - {pageTitle ? pageTitle : t['Untitled']()} - - - - } /> ); diff --git a/apps/web/src/pages/workspace/[workspaceId]/[pageId].tsx b/apps/web/src/pages/workspace/[workspaceId]/[pageId].tsx index 25b7bb4c0f..c4a916de5e 100644 --- a/apps/web/src/pages/workspace/[workspaceId]/[pageId].tsx +++ b/apps/web/src/pages/workspace/[workspaceId]/[pageId].tsx @@ -56,13 +56,21 @@ const WorkspaceDetail: React.FC = () => { } }, [currentWorkspace]); - const { PageDetail } = getUIAdapter(currentWorkspace.flavour); + const { PageDetail, Header } = getUIAdapter(currentWorkspace.flavour); return ( - + <> +
+ + ); }; diff --git a/apps/web/src/pages/workspace/[workspaceId]/all.tsx b/apps/web/src/pages/workspace/[workspaceId]/all.tsx index bba554d689..79b56d2c1e 100644 --- a/apps/web/src/pages/workspace/[workspaceId]/all.tsx +++ b/apps/web/src/pages/workspace/[workspaceId]/all.tsx @@ -1,14 +1,7 @@ -import { Button } from '@affine/component'; -import { - FilterList, - SaveViewButton, - useAllPageSetting, - ViewList, -} from '@affine/component/page-list'; -import { config } from '@affine/env'; +import { useAllPageSetting } from '@affine/component/page-list'; import { QueryParamError } from '@affine/env/constant'; import { useAFFiNEI18N } from '@affine/i18n/hooks'; -import { FolderIcon } from '@blocksuite/icons'; +import { WorkspaceSubPath } from '@affine/workspace/type'; import { assertExists } from '@blocksuite/store'; import Head from 'next/head'; import { useRouter } from 'next/router'; @@ -16,7 +9,6 @@ import React, { useCallback } from 'react'; import { getUIAdapter } from '../../../adapters/workspace'; import { PageLoading } from '../../../components/pure/loading'; -import { WorkspaceTitle } from '../../../components/pure/workspace-title'; import { useCurrentWorkspace } from '../../../hooks/current/use-current-workspace'; import { useRouterHelper } from '../../../hooks/use-router-helper'; import { WorkspaceLayout } from '../../../layouts/workspace-layout'; @@ -45,56 +37,19 @@ const AllPage: NextPageWithLayout = () => { if (typeof router.query.workspaceId !== 'string') { throw new QueryParamError('workspaceId', router.query.workspaceId); } - const leftSlot = config.enableAllPageFilter && ( - - ); - const filterContainer = config.enableAllPageFilter && - setting.currentView.filterList.length > 0 && ( -
-
- - setting.changeView( - { - ...setting.currentView, - filterList, - }, - setting.currentViewIndex - ) - } - /> -
-
- {setting.currentViewIndex == null ? ( - - ) : ( - - )} -
-
- ); - const { PageList } = getUIAdapter(currentWorkspace.flavour); + const { PageList, Header } = getUIAdapter(currentWorkspace.flavour); return ( <> {t['All pages']()} - AFFiNE - } - leftSlot={leftSlot} - > - {t['All pages']()} - - {filterContainer} +
{ } else if (settingPanelValues.indexOf(currentTab as SettingPanel) === -1) { return ; } - const { SettingsDetail } = getUIAdapter(currentWorkspace.flavour); + const { SettingsDetail, Header } = getUIAdapter(currentWorkspace.flavour); return ( <> {t['Settings']()} - AFFiNE - } - > - {t['Workspace Settings']()} - +
{ const router = useRouter(); const { jumpToPage } = useRouterHelper(router); @@ -34,20 +33,18 @@ const SharedPages: NextPageWithLayout = () => { } const blockSuiteWorkspace = currentWorkspace.blockSuiteWorkspace; assertExists(blockSuiteWorkspace); + const { Header } = getUIAdapter(currentWorkspace.flavour); return ( <> {t['Shared Pages']()} - AFFiNE - } - > - {t['Shared Pages']()} - +
{ // todo(himself65): refactor to plugin const blockSuiteWorkspace = currentWorkspace.blockSuiteWorkspace; assertExists(blockSuiteWorkspace); + const { Header } = getUIAdapter(currentWorkspace.flavour); return ( <> {t['Trash']()} - AFFiNE - } - > - {t['Trash']()} - +
import('../components/pure/workspace-list-modal').then(module => ({ diff --git a/apps/web/src/shared/index.ts b/apps/web/src/shared/index.ts index 4a5c669ae7..feb715cdfc 100644 --- a/apps/web/src/shared/index.ts +++ b/apps/web/src/shared/index.ts @@ -4,6 +4,7 @@ import type { } from '@affine/workspace/type'; import type { AffinePublicWorkspace } from '@affine/workspace/type'; import type { WorkspaceRegistry } from '@affine/workspace/type'; +import { WorkspaceSubPath } from '@affine/workspace/type'; import { Workspace as BlockSuiteWorkspace } from '@blocksuite/store'; import type { NextPage } from 'next'; import type { ReactElement, ReactNode } from 'react'; @@ -24,13 +25,6 @@ export type NextPageWithLayout

, IP = P> = NextPage< getLayout?: (page: ReactElement) => ReactNode; }; -export const enum WorkspaceSubPath { - ALL = 'all', - SETTING = 'setting', - TRASH = 'trash', - SHARED = 'shared', -} - export const WorkspaceSubPathName = { [WorkspaceSubPath.ALL]: 'All Pages', [WorkspaceSubPath.SETTING]: 'Settings', diff --git a/packages/workspace/src/type.ts b/packages/workspace/src/type.ts index 6a983844e0..5e72905ee5 100644 --- a/packages/workspace/src/type.ts +++ b/packages/workspace/src/type.ts @@ -10,6 +10,13 @@ import type { FC, PropsWithChildren } from 'react'; export type JotaiStore = ReturnType; +export const enum WorkspaceSubPath { + ALL = 'all', + SETTING = 'setting', + TRASH = 'trash', + SHARED = 'shared', +} + export type BaseProvider = { flavour: string; @@ -168,6 +175,17 @@ type UIBaseProps = { currentWorkspace: WorkspaceRegistry[Flavour]; }; +export type WorkspaceHeaderProps = + UIBaseProps & { + currentEntry: + | { + subPath: WorkspaceSubPath; + } + | { + pageId: string; + }; + }; + type SettingProps = UIBaseProps & { currentTab: SettingPanel; @@ -196,6 +214,7 @@ type PageListProps<_Flavour extends keyof WorkspaceRegistry> = { }; export interface WorkspaceUISchema { + Header: FC>; PageDetail: FC>; PageList: FC>; SettingsDetail: FC>;