Layout accordion updates

This commit is contained in:
Bill 2021-11-17 16:38:36 -05:00
parent f489bacd31
commit a5fcea1cd7
7 changed files with 120 additions and 10 deletions

View File

@ -70,3 +70,7 @@ ul {
.grayscale { .grayscale {
filter: grayscale(1); filter: grayscale(1);
} }
.flex-none {
flex: none;
}

View File

@ -0,0 +1,21 @@
import { createContext, Dispatch, FC, ProviderProps, SetStateAction, useContext } from 'react';
export interface INitroCardAccordionContext
{
closers: Function[];
setClosers: Dispatch<SetStateAction<Function[]>>;
closeAll: () => void;
}
const NitroCardAccordionContext = createContext<INitroCardAccordionContext>({
closers: null,
setClosers: null,
closeAll: null
});
export const NitroCardAccordionContextProvider: FC<ProviderProps<INitroCardAccordionContext>> = props =>
{
return <NitroCardAccordionContext.Provider { ...props } />;
}
export const useNitroCardAccordionContext = () => useContext(NitroCardAccordionContext);

View File

@ -1 +1,6 @@
.nitro-card-accordion {
display: flex;
height: 100%;
}
@import "./set/NitroCardAccordionSetView"; @import "./set/NitroCardAccordionSetView";

View File

@ -1,13 +1,32 @@
import { FC } from 'react'; import { FC, useCallback, useMemo, useState } from 'react';
import { NitroLayoutFlexColumn } from '../..';
import { NitroCardAccordionContextProvider } from './NitroCardAccordionContext';
import { NitroCardAccordionViewProps } from './NitroCardAccordionView.types'; import { NitroCardAccordionViewProps } from './NitroCardAccordionView.types';
export const NitroCardAccordionView: FC<NitroCardAccordionViewProps> = props => export const NitroCardAccordionView: FC<NitroCardAccordionViewProps> = props =>
{ {
const { className = '' } = props; const { className = '', children = null, ...rest } = props;
const [ closers, setClosers ] = useState<Function[]>([]);
const getClassName = useMemo(() =>
{
let newClassName = 'nitro-card-accordion text-black';
if(className && className.length) newClassName += ` ${ className }`;
return newClassName;
}, [ className ]);
const closeAll = useCallback(() =>
{
for(const closer of closers) closer();
}, [ closers ]);
return ( return (
<div className={ 'nitro-card-accordion text-black ' + className }> <NitroCardAccordionContextProvider value={ { closers, setClosers, closeAll } }>
{ props.children } <NitroLayoutFlexColumn className={ getClassName } { ...rest }>
</div> { children }
</NitroLayoutFlexColumn>
</NitroCardAccordionContextProvider>
); );
} }

View File

@ -1,4 +1,6 @@
export interface NitroCardAccordionViewProps import { NitroLayoutFlexColumnProps } from '../..';
export interface NitroCardAccordionViewProps extends NitroLayoutFlexColumnProps
{ {
className?: string;
} }

View File

@ -1,9 +1,14 @@
.nitro-card-accordion-set { .nitro-card-accordion-set {
&.active {
height: 100%;
background: rgba($white, 0.5);
}
.nitro-card-accordion-set-header { .nitro-card-accordion-set-header {
border-bottom: 1px solid rgba($black, 0.2); border-bottom: 1px solid rgba($black, 0.2);
} }
.nitro-card-accordion-set-content { .nitro-card-accordion-set-content {
background: rgba($white, 0.5);
} }
} }

View File

@ -1,13 +1,15 @@
import classNames from 'classnames'; import classNames from 'classnames';
import { FC, useEffect, useMemo, useState } from 'react'; import { FC, useCallback, useEffect, useMemo, useState } from 'react';
import { NitroLayoutFlex } from '../../..'; import { NitroLayoutFlex } from '../../..';
import { NitroLayoutBase } from '../../../base'; import { NitroLayoutBase } from '../../../base';
import { useNitroCardAccordionContext } from '../NitroCardAccordionContext';
import { NitroCardAccordionSetViewProps } from './NitroCardAccordionSetView.types'; import { NitroCardAccordionSetViewProps } from './NitroCardAccordionSetView.types';
export const NitroCardAccordionSetView: FC<NitroCardAccordionSetViewProps> = props => export const NitroCardAccordionSetView: FC<NitroCardAccordionSetViewProps> = props =>
{ {
const { headerText = '', isExpanded = false, className = '', children = null, ...rest } = props; const { headerText = '', isExpanded = false, className = '', children = null, ...rest } = props;
const [ isOpen, setIsOpen ] = useState(false); const [ isOpen, setIsOpen ] = useState(false);
const { setClosers = null, closeAll = null } = useNitroCardAccordionContext();
const getClassName = useMemo(() => const getClassName = useMemo(() =>
{ {
@ -20,14 +22,66 @@ export const NitroCardAccordionSetView: FC<NitroCardAccordionSetViewProps> = pro
return newClassName; return newClassName;
}, [ className, isOpen ]); }, [ className, isOpen ]);
const onClick = useCallback(() =>
{
closeAll();
setIsOpen(prevValue => !prevValue);
// if(isOpen)
// {
// closeAll();
// }
// else
// {
// BatchUpdates(() =>
// {
// closeAll();
// setIsOpen(true);
// });
// }
}, [ closeAll ]);
const close = useCallback(() =>
{
setIsOpen(false);
}, []);
useEffect(() => useEffect(() =>
{ {
setIsOpen(isExpanded); setIsOpen(isExpanded);
}, [ isExpanded ]); }, [ isExpanded ]);
useEffect(() =>
{
const closeFunction = close;
setClosers(prevValue =>
{
const newClosers = [ ...prevValue ];
newClosers.push(closeFunction);
return newClosers;
});
return () =>
{
setClosers(prevValue =>
{
const newClosers = [ ...prevValue ];
const index = newClosers.indexOf(closeFunction);
if(index >= 0) newClosers.splice(index, 1);
return newClosers;
});
}
}, [ close, setClosers ]);
return ( return (
<NitroLayoutBase className={ getClassName } { ...rest }> <NitroLayoutBase className={ getClassName } { ...rest }>
<NitroLayoutFlex className="nitro-card-accordion-set-header px-2 py-1" onClick={ event => setIsOpen(!isOpen) }> <NitroLayoutFlex className="nitro-card-accordion-set-header px-2 py-1" onClick={ onClick }>
<div className="w-100"> <div className="w-100">
{ headerText } { headerText }
</div> </div>