✨(front) add LeftPanelContext for mobile panel state
Introduce a context to manage left panel visibility on mobile, integrate it into SimpleLayout and calendar page.
This commit is contained in:
@@ -3,6 +3,7 @@ import { GlobalLayout } from "../global/GlobalLayout";
|
|||||||
import { HeaderRight } from "../header/Header";
|
import { HeaderRight } from "../header/Header";
|
||||||
import { Toaster } from "@/features/ui/components/toaster/Toaster";
|
import { Toaster } from "@/features/ui/components/toaster/Toaster";
|
||||||
import { LeftPanelMobile } from "@/features/layouts/components/left-panel/LeftPanelMobile";
|
import { LeftPanelMobile } from "@/features/layouts/components/left-panel/LeftPanelMobile";
|
||||||
|
import { useLeftPanel } from "../../contexts/LeftPanelContext";
|
||||||
|
|
||||||
export const getSimpleLayout = (page: React.ReactElement) => {
|
export const getSimpleLayout = (page: React.ReactElement) => {
|
||||||
return <SimpleLayout>{page}</SimpleLayout>;
|
return <SimpleLayout>{page}</SimpleLayout>;
|
||||||
@@ -14,12 +15,15 @@ export const getSimpleLayout = (page: React.ReactElement) => {
|
|||||||
* Auth context to the children.
|
* Auth context to the children.
|
||||||
*/
|
*/
|
||||||
export const SimpleLayout = ({ children }: { children: React.ReactNode }) => {
|
export const SimpleLayout = ({ children }: { children: React.ReactNode }) => {
|
||||||
|
const { isLeftPanelOpen, setIsLeftPanelOpen } = useLeftPanel();
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<GlobalLayout>
|
<GlobalLayout>
|
||||||
<MainLayout
|
<MainLayout
|
||||||
enableResize
|
enableResize
|
||||||
hideLeftPanelOnDesktop={true}
|
hideLeftPanelOnDesktop={true}
|
||||||
|
isLeftPanelOpen={isLeftPanelOpen}
|
||||||
|
setIsLeftPanelOpen={setIsLeftPanelOpen}
|
||||||
leftPanelContent={<LeftPanelMobile />}
|
leftPanelContent={<LeftPanelMobile />}
|
||||||
rightHeaderContent={<HeaderRight />}
|
rightHeaderContent={<HeaderRight />}
|
||||||
>
|
>
|
||||||
|
|||||||
@@ -0,0 +1,45 @@
|
|||||||
|
import {
|
||||||
|
createContext,
|
||||||
|
useContext,
|
||||||
|
useMemo,
|
||||||
|
useState,
|
||||||
|
type ReactNode,
|
||||||
|
} from "react";
|
||||||
|
|
||||||
|
interface LeftPanelContextType {
|
||||||
|
isLeftPanelOpen: boolean;
|
||||||
|
setIsLeftPanelOpen: (open: boolean) => void;
|
||||||
|
}
|
||||||
|
|
||||||
|
const LeftPanelContext = createContext<LeftPanelContextType | undefined>(
|
||||||
|
undefined,
|
||||||
|
);
|
||||||
|
|
||||||
|
export const useLeftPanel = () => {
|
||||||
|
const context = useContext(LeftPanelContext);
|
||||||
|
if (!context) {
|
||||||
|
throw new Error(
|
||||||
|
"useLeftPanel must be used within a LeftPanelProvider",
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return context;
|
||||||
|
};
|
||||||
|
|
||||||
|
interface LeftPanelProviderProps {
|
||||||
|
children: ReactNode;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const LeftPanelProvider = ({ children }: LeftPanelProviderProps) => {
|
||||||
|
const [isLeftPanelOpen, setIsLeftPanelOpen] = useState(false);
|
||||||
|
|
||||||
|
const value = useMemo(
|
||||||
|
() => ({ isLeftPanelOpen, setIsLeftPanelOpen }),
|
||||||
|
[isLeftPanelOpen, setIsLeftPanelOpen],
|
||||||
|
);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<LeftPanelContext.Provider value={value}>
|
||||||
|
{children}
|
||||||
|
</LeftPanelContext.Provider>
|
||||||
|
);
|
||||||
|
};
|
||||||
@@ -33,6 +33,7 @@ import {
|
|||||||
} from "@/features/ui/cunningham/useCunninghamTheme";
|
} from "@/features/ui/cunningham/useCunninghamTheme";
|
||||||
import { FeedbackFooterMobile } from "@/features/feedback/Feedback";
|
import { FeedbackFooterMobile } from "@/features/feedback/Feedback";
|
||||||
import { useDynamicFavicon } from "@/features/ui/hooks/useDynamicFavicon";
|
import { useDynamicFavicon } from "@/features/ui/hooks/useDynamicFavicon";
|
||||||
|
import { LeftPanelProvider } from "@/features/layouts/contexts/LeftPanelContext";
|
||||||
|
|
||||||
export type NextPageWithLayout<P = object, IP = P> = NextPage<P, IP> & {
|
export type NextPageWithLayout<P = object, IP = P> = NextPage<P, IP> & {
|
||||||
getLayout?: (page: ReactElement) => ReactNode;
|
getLayout?: (page: ReactElement) => ReactNode;
|
||||||
@@ -134,8 +135,10 @@ const MyAppInner = ({ Component, pageProps }: AppPropsWithLayout) => {
|
|||||||
|
|
||||||
<ConfigProvider>
|
<ConfigProvider>
|
||||||
<AnalyticsProvider>
|
<AnalyticsProvider>
|
||||||
{getLayout(<Component {...pageProps} />)}
|
<LeftPanelProvider>
|
||||||
<FeedbackFooterMobile />
|
{getLayout(<Component {...pageProps} />)}
|
||||||
|
<FeedbackFooterMobile />
|
||||||
|
</LeftPanelProvider>
|
||||||
</AnalyticsProvider>
|
</AnalyticsProvider>
|
||||||
</ConfigProvider>
|
</ConfigProvider>
|
||||||
|
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ import {
|
|||||||
HeaderIcon,
|
HeaderIcon,
|
||||||
HeaderRight,
|
HeaderRight,
|
||||||
} from "@/features/layouts/components/header/Header";
|
} from "@/features/layouts/components/header/Header";
|
||||||
|
import { useLeftPanel } from "@/features/layouts/contexts/LeftPanelContext";
|
||||||
import { SpinnerPage } from "@/features/ui/components/spinner/SpinnerPage";
|
import { SpinnerPage } from "@/features/ui/components/spinner/SpinnerPage";
|
||||||
import { Toaster } from "@/features/ui/components/toaster/Toaster";
|
import { Toaster } from "@/features/ui/components/toaster/Toaster";
|
||||||
import { Scheduler } from "@/features/calendar/components/scheduler/Scheduler";
|
import { Scheduler } from "@/features/calendar/components/scheduler/Scheduler";
|
||||||
@@ -56,7 +57,9 @@ export default function CalendarPage() {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
CalendarPage.getLayout = function getLayout(page: React.ReactElement) {
|
const CalendarLayout = ({ children }: { children: React.ReactNode }) => {
|
||||||
|
const { isLeftPanelOpen, setIsLeftPanelOpen } = useLeftPanel();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<CalendarContextProvider>
|
<CalendarContextProvider>
|
||||||
<div className="calendars__calendar">
|
<div className="calendars__calendar">
|
||||||
@@ -66,11 +69,17 @@ CalendarPage.getLayout = function getLayout(page: React.ReactElement) {
|
|||||||
leftPanelContent={<LeftPanel />}
|
leftPanelContent={<LeftPanel />}
|
||||||
icon={<HeaderIcon />}
|
icon={<HeaderIcon />}
|
||||||
rightHeaderContent={<HeaderRight />}
|
rightHeaderContent={<HeaderRight />}
|
||||||
|
isLeftPanelOpen={isLeftPanelOpen}
|
||||||
|
setIsLeftPanelOpen={setIsLeftPanelOpen}
|
||||||
>
|
>
|
||||||
{page}
|
{children}
|
||||||
</MainLayout>
|
</MainLayout>
|
||||||
</GlobalLayout>
|
</GlobalLayout>
|
||||||
</div>
|
</div>
|
||||||
</CalendarContextProvider>
|
</CalendarContextProvider>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
CalendarPage.getLayout = function getLayout(page: React.ReactElement) {
|
||||||
|
return <CalendarLayout>{page}</CalendarLayout>;
|
||||||
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user