diff --git a/src/frontend/apps/impress/src/features/docs/doc-editor/stores/index.ts b/src/frontend/apps/impress/src/features/docs/doc-editor/stores/index.ts index 499405d49..ccb837296 100644 --- a/src/frontend/apps/impress/src/features/docs/doc-editor/stores/index.ts +++ b/src/frontend/apps/impress/src/features/docs/doc-editor/stores/index.ts @@ -1,3 +1,2 @@ export * from './useEditorStore'; export * from './useHeadingStore'; -export * from './usePanelEditorStore'; diff --git a/src/frontend/apps/impress/src/features/docs/doc-editor/stores/usePanelEditorStore.tsx b/src/frontend/apps/impress/src/features/docs/doc-editor/stores/usePanelEditorStore.tsx deleted file mode 100644 index 64833d03d..000000000 --- a/src/frontend/apps/impress/src/features/docs/doc-editor/stores/usePanelEditorStore.tsx +++ /dev/null @@ -1,19 +0,0 @@ -import { create } from 'zustand'; - -export interface UsePanelEditorStore { - isPanelOpen: boolean; - setIsPanelOpen: (isOpen: boolean) => void; - isPanelTableContentOpen: boolean; - setIsPanelTableContentOpen: (isOpen: boolean) => void; -} - -export const usePanelEditorStore = create((set) => ({ - isPanelOpen: false, - isPanelTableContentOpen: true, - setIsPanelTableContentOpen: (isPanelTableContentOpen) => { - set(() => ({ isPanelTableContentOpen })); - }, - setIsPanelOpen: (isPanelOpen) => { - set(() => ({ isPanelOpen })); - }, -})); diff --git a/src/frontend/apps/impress/src/features/docs/doc-export/utils_print.ts b/src/frontend/apps/impress/src/features/docs/doc-export/utils_print.ts index a19d92c54..82a5ef65c 100644 --- a/src/frontend/apps/impress/src/features/docs/doc-export/utils_print.ts +++ b/src/frontend/apps/impress/src/features/docs/doc-export/utils_print.ts @@ -24,6 +24,7 @@ const PRINT_ONLY_CONTENT_CSS = ` .--docs--table-content, .--docs--doc-footer, .--docs--footer, + .--docs--right-panel, footer, [role="contentinfo"], div[data-is-empty-and-focused="true"], diff --git a/src/frontend/apps/impress/src/features/docs/doc-header/components/FloatingBar.tsx b/src/frontend/apps/impress/src/features/docs/doc-header/components/FloatingBar.tsx index 62208e246..45a94108e 100644 --- a/src/frontend/apps/impress/src/features/docs/doc-header/components/FloatingBar.tsx +++ b/src/frontend/apps/impress/src/features/docs/doc-header/components/FloatingBar.tsx @@ -4,6 +4,7 @@ import { css } from 'styled-components'; import { Box } from '@/components'; import { useCunninghamTheme } from '@/cunningham/useCunninghamTheme'; import { LeftPanelCollapseButton } from '@/features/left-panel'; +import { RightPanelCollapseButton } from '@/features/right-panel/components/RightPanelCollapseButton'; import { useResponsiveStore } from '@/stores'; /** @@ -22,19 +23,15 @@ export const FloatingBar = () => { const sm = spacingsTokens['sm']; return css` position: sticky; - top: calc(-${base}); + top: 0; left: 0; right: 0; - width: calc(100% + ${base} + ${base}); + width: 100%; min-height: 64px; padding: ${sm}; - margin-left: calc(-${base}); - margin-right: calc(-${base}); margin-top: calc(-${base}); z-index: 21; // Under editor select box but above other elements (e.g., doc title, suggestion menu) - display: flex; align-items: flex-start; - justify-content: flex-start; isolation: isolate; &::before { @@ -64,17 +61,16 @@ export const FloatingBar = () => { `; }, [spacingsTokens]); - if (!isDesktop) { - return null; - } - return ( - + {isDesktop ? : } + ); }; diff --git a/src/frontend/apps/impress/src/features/right-panel/components/RightPanel.tsx b/src/frontend/apps/impress/src/features/right-panel/components/RightPanel.tsx new file mode 100644 index 000000000..34f0b2000 --- /dev/null +++ b/src/frontend/apps/impress/src/features/right-panel/components/RightPanel.tsx @@ -0,0 +1,52 @@ +import { useTranslation } from 'react-i18next'; +import { css } from 'styled-components'; + +import { Box } from '@/components'; +import { useDocStore, useProviderStore } from '@/features/docs/doc-management'; +import { HEADER_HEIGHT } from '@/features/header'; +import { useResponsiveStore } from '@/stores'; + +import { useRightPanelStore } from './useRightPanelStore'; + +export const RightPanel = () => { + const { t } = useTranslation(); + const { currentDoc: doc } = useDocStore(); + const { _, isPanelOpen } = useRightPanelStore(); + const { isMobile } = useResponsiveStore(); + const { provider, isReady } = useProviderStore(); + const isProviderReady = + isReady && provider && provider?.configuration.name === doc?.id; + + if (!doc || !isProviderReady) { + return null; + } + + return ( + + ); +}; diff --git a/src/frontend/apps/impress/src/features/right-panel/components/RightPanelCollapseButton.tsx b/src/frontend/apps/impress/src/features/right-panel/components/RightPanelCollapseButton.tsx new file mode 100644 index 000000000..025a5e55a --- /dev/null +++ b/src/frontend/apps/impress/src/features/right-panel/components/RightPanelCollapseButton.tsx @@ -0,0 +1,42 @@ +import { Button } from '@gouvfr-lasuite/cunningham-react'; +import { useTranslation } from 'react-i18next'; +import { css } from 'styled-components'; + +import CommentsIcon from '@/assets/icons/ui-kit/bubble-text.svg'; +import { Card } from '@/components'; + +import { useRightPanelStore } from './useRightPanelStore'; + +export const RightPanelCollapseButton = () => { + const { t } = useTranslation(); + const { isPanelOpen, togglePanel } = useRightPanelStore(); + + const ariaLabel = isPanelOpen + ? t('Hide the right side panel') + : t('Show the right side panel'); + + return ( + + + + ); +}; diff --git a/src/frontend/apps/impress/src/features/right-panel/components/useRightPanelStore.tsx b/src/frontend/apps/impress/src/features/right-panel/components/useRightPanelStore.tsx new file mode 100644 index 000000000..74638b918 --- /dev/null +++ b/src/frontend/apps/impress/src/features/right-panel/components/useRightPanelStore.tsx @@ -0,0 +1,17 @@ +import { create } from 'zustand'; + +export interface UseRightPanelStore { + isPanelOpen: boolean; + setIsPanelOpen: (isOpen: boolean) => void; + togglePanel: () => void; +} + +export const useRightPanelStore = create((set) => ({ + isPanelOpen: false, + setIsPanelOpen: (isPanelOpen) => { + set(() => ({ isPanelOpen })); + }, + togglePanel: () => { + set((state) => ({ isPanelOpen: !state.isPanelOpen })); + }, +})); diff --git a/src/frontend/apps/impress/src/layouts/MainLayout.tsx b/src/frontend/apps/impress/src/layouts/MainLayout.tsx index 273c3ae02..750408bf3 100644 --- a/src/frontend/apps/impress/src/layouts/MainLayout.tsx +++ b/src/frontend/apps/impress/src/layouts/MainLayout.tsx @@ -2,10 +2,11 @@ import { PropsWithChildren } from 'react'; import { useTranslation } from 'react-i18next'; import { css } from 'styled-components'; -import { Box } from '@/components'; +import { Box, BoxProps } from '@/components'; import { Header } from '@/features/header'; import { HEADER_HEIGHT } from '@/features/header/conf'; import { LeftPanel, ResizableLeftPanel } from '@/features/left-panel'; +import { RightPanel } from '@/features/right-panel/components/RightPanel'; import { DocEditorSkeleton, Skeleton } from '@/features/skeletons'; import { useResponsiveStore } from '@/stores'; @@ -43,20 +44,29 @@ export function MainLayout({ export interface MainLayoutContentProps { backgroundColor: 'white' | 'grey'; - enableResizablePanel?: boolean; + enableResizablePanel: boolean; } export function MainLayoutContent({ children, backgroundColor, - enableResizablePanel = false, + enableResizablePanel, }: PropsWithChildren) { const { isDesktop } = useResponsiveStore(); if (enableResizablePanel) { return ( }> - {children} + + + {children} + + + ); } @@ -86,10 +96,15 @@ export function MainLayoutContent({ ); } +type MainContentProps = BoxProps & { + backgroundColor: 'white' | 'grey'; +}; + const MainContent = ({ children, backgroundColor, -}: PropsWithChildren) => { + ...props +}: PropsWithChildren) => { const { isDesktop } = useResponsiveStore(); const { t } = useTranslation(); @@ -106,9 +121,7 @@ const MainContent = ({ $width="100%" $height={`calc(100dvh - ${HEADER_HEIGHT}px)`} $position="relative" - $padding={{ - all: isDesktop ? 'base' : '0', - }} + $padding={isDesktop ? 'base' : '0'} $background={ currentBackgroundColor === 'white' ? 'var(--c--contextuals--background--surface--primary)' @@ -118,6 +131,7 @@ const MainContent = ({ overflow-y: auto; overflow-x: clip; `} + {...props} >