WIP: sidebar overlay component.

This commit is contained in:
a.bouhuolia
2021-08-01 22:11:44 +02:00
parent 44edc990ae
commit 9dbd128236
13 changed files with 277 additions and 56 deletions

View File

@@ -48,7 +48,7 @@ function App({ locale }) {
<div className="App">
<Router history={history}>
<Switch>
<Route path={'/auth'} component={Authentication} />
{/* <Route path={'/auth'} component={Authentication} /> */}
<Route path={'/'}>
<PrivateRoute component={DashboardPrivatePages} />
</Route>

View File

@@ -17,6 +17,8 @@ import DrawersContainer from 'components/DrawersContainer';
* Dashboard page.
*/
export default function Dashboard() {
const dashboardContentRef = React.createRef();
return (
<DashboardProvider>
<Switch>
@@ -29,8 +31,8 @@ export default function Dashboard() {
<Route path="/">
<DashboardSplitPane>
<Sidebar />
<DashboardContent />
<Sidebar dashboardContentRef={dashboardContentRef} />
<DashboardContent ref={dashboardContentRef} />
</DashboardSplitPane>
</Route>
</Switch>

View File

@@ -5,14 +5,14 @@ import DashboardContentRoute from 'components/Dashboard/DashboardContentRoute';
import DashboardFooter from 'components/Dashboard/DashboardFooter';
import DashboardErrorBoundary from './DashboardErrorBoundary';
export default function () {
export default React.forwardRef(({}, ref) => {
return (
<ErrorBoundary FallbackComponent={DashboardErrorBoundary}>
<div className="dashboard-content" id="dashboard">
<div className="dashboard-content" id="dashboard" ref={ref}>
<DashboardTopbar />
<DashboardContentRoute />
<DashboardFooter />
</div>
</ErrorBoundary>
);
}
});

View File

@@ -17,16 +17,16 @@ export default function DashboardPrivatePages() {
return (
<PrivatePagesProvider>
<Switch>
<Route path={'/setup'}>
{/* <Route path={'/setup'}>
<EnsureOrganizationIsNotReady>
<SetupWizardPage />
</EnsureOrganizationIsNotReady>
</Route>
</Route> */}
<Route path='/'>
<EnsureOrganizationIsReady>
{/* <EnsureOrganizationIsReady> */}
<Dashboard />
</EnsureOrganizationIsReady>
{/* </EnsureOrganizationIsReady> */}
</Route>
</Switch>
</PrivatePagesProvider>

View File

@@ -7,10 +7,10 @@ import { useCurrentOrganization } from '../../hooks/query/organization';
*/
export function PrivatePagesProvider({ children }) {
// Fetches the current user's organization.
const { isLoading } = useCurrentOrganization();
// const { isLoading } = useCurrentOrganization();
return (
<DashboardLoadingIndicator isLoading={isLoading}>
<DashboardLoadingIndicator isLoading={false}>
{children}
</DashboardLoadingIndicator>
)

View File

@@ -1,12 +1,12 @@
import React from 'react';
import { Menu, MenuItem } from '@blueprintjs/core';
import SidebarContainer from 'components/Sidebar/SidebarContainer';
import SidebarHead from 'components/Sidebar/SidebarHead';
import SidebarMenu from 'components/Sidebar/SidebarMenu';
import SidebarOverlay from 'components/SidebarOverlay';
import 'style/containers/Dashboard/Sidebar.scss';
export default function Sidebar() {
export default function Sidebar({ dashboardContentRef }) {
return (
<SidebarContainer>
<SidebarHead />
@@ -14,10 +14,8 @@ export default function Sidebar() {
<div className="sidebar__menu">
<SidebarMenu />
</div>
<div class="sidebar__version">
0.0.1-beta version.
</div>
<div class="sidebar__version">0.0.1-beta version.</div>
</SidebarContainer>
)
}
);
}

View File

@@ -6,11 +6,15 @@ import Icon from 'components/Icon';
import MenuItem from 'components/MenuItem';
import { MenuItemLabel } from 'components';
import classNames from 'classnames';
import SidebarOverlay from 'components/SidebarOverlay';
export default function SidebarMenu() {
const history = useHistory();
const location = useLocation();
const [isOpen, setIsOpen] = React.useState(false);
const [currentItem, setCurrentItem] = React.useState(null);
const menuItemsMapper = (list) => {
return list.map((item, index) => {
const children = Array.isArray(item.children)
@@ -18,33 +22,41 @@ export default function SidebarMenu() {
: null;
const matchPath = (pathname, path) => {
return item.matchExact ? pathname === path : pathname.indexOf(path) !== -1;
return item.matchExact
? pathname === path
: pathname.indexOf(path) !== -1;
};
const isActive = (item.children) ?
item.children.some((c) => matchPath(location.pathname, c.href)) :
(item.href && matchPath(location.pathname, item.href));
const isActive = item.children
? item.children.some((c) => matchPath(location.pathname, c.href))
: item.href && matchPath(location.pathname, item.href);
const handleItemClick = () => {
if (item.href) {
history.push(item.href);
}
setIsOpen(true);
setCurrentItem(item);
};
const maybeRenderLabel = (item) => item.newTabHref ? (
<Button
className="menu-item__add-btn"
icon={<Icon icon={'plus'} iconSize={16} />}
onClick={(event) => {
history.push(item.newTabHref);
event.stopPropagation();
}}
/>
) : null;
const maybeRenderLabel = (item) =>
item.newTabHref ? (
<Button
className="menu-item__add-btn"
icon={<Icon icon={'plus'} iconSize={16} />}
onClick={(event) => {
history.push(item.newTabHref);
event.stopPropagation();
}}
/>
) : null;
return item.spacer ? (
<div class="bp3-menu-spacer" style={{
'height': `${item.spacer}px`,
}}></div>
<div
class="bp3-menu-spacer"
style={{
height: `${item.spacer}px`,
}}
></div>
) : item.divider ? (
<MenuDivider key={index} title={item.title} />
) : item.label ? (
@@ -72,5 +84,14 @@ export default function SidebarMenu() {
};
const items = menuItemsMapper(sidebarMenuList);
return <Menu className="sidebar-menu">{items}</Menu>;
return (
<div>
<Menu className="sidebar-menu">{items}</Menu>{' '}
<SidebarOverlay
isOpen={isOpen}
items={currentItem?.children || []}
/>
</div>
);
}

View File

@@ -0,0 +1,19 @@
import React from 'react';
import { Scrollbar } from 'react-scrollbars-custom';
interface ISidebarOverlayContainerProps {
children: JSX.Element | JSX.Element[],
}
/**
* Sidebar overlay container.
*/
export default function SidebarOverlayContainer({ children }: ISidebarOverlayContainerProps) {
return (
<div className={'sidebar-overlay__scroll-wrapper'}>
<Scrollbar noDefaultStyles={true}>
<div className="sidebar-overlay__inner">{children}</div>
</Scrollbar>
</div>
);
}

View File

@@ -0,0 +1,90 @@
import React from 'react';
import { Overlay } from '@blueprintjs/core';
import { Link } from 'react-router-dom';
import SidebarOverlayContainer from './SidebarOverlayContainer';
interface ISidebarOverlayItem {
text: string;
href: string;
divider?: boolean;
label?: boolean
}
interface ISidebarOverlayProps {
isOpen: boolean;
items: ISidebarOverlayItem[];
overlayProps: any;
overlayContainerRef: any;
}
interface ISidebarOverlayItemProps {
text: string;
href: string;
}
interface ISidebarOverlayItemDivider {
divider: boolean;
}
/**
* Sidebar overlay item.
*/
function SidebarOverlayItem({ text, href }: ISidebarOverlayItemProps) {
return (
<div className="sidebar-overlay__item">
<Link to={href}>{text}</Link>
</div>
);
}
interface ISidebarOverlayItemLabel {
text: string;
}
function SidebarOverlayLabel({ text }: ISidebarOverlayItemLabel) {
return <div className="sidebar-overlay__label">{text}</div>;
}
function SidebarOverlayDivider() {
return <div className={'sidebar-overlay__divider'}></div>;
}
/**
* Sidebar overlay component.
*/
export default function SidebarOverlay({
isOpen = false,
items,
}: ISidebarOverlayProps) {
//
if (!isOpen) {
return '';
}
const handleOverlayClose = () => {
};
return (
<Overlay
isOpen={isOpen}
portalContainer={document.getElementById('dashboard') || document.body}
onClose={handleOverlayClose}
>
<div className="sidebar-overlay">
<SidebarOverlayContainer>
<div className="sidebar-overlay__menu">
{items.map((item) =>
item.divider ? (
<SidebarOverlayDivider />
) : item.label ? (
<SidebarOverlayLabel text={item.text} />
) : (
<SidebarOverlayItem text={item.text} href={item.href} />
),
)}
</div>
</SidebarOverlayContainer>
</div>
</Overlay>
);
}