63 lines
1.9 KiB
TypeScript
63 lines
1.9 KiB
TypeScript
'use client';
|
|
|
|
import { bool } from 'prop-types';
|
|
import { CheckboxProps } from './checkbox.types';
|
|
import { RippleEffect } from '../../ripple/ripple-effect';
|
|
import { InputLayout } from '../input-layout/input-layout';
|
|
import useRippleEffect from '../../ripple/hooks/useRippleEffect';
|
|
import {
|
|
forwardRef,
|
|
useEffect,
|
|
useImperativeHandle,
|
|
useRef,
|
|
useState,
|
|
} from 'react';
|
|
|
|
/**
|
|
* Checkbox component
|
|
** description
|
|
*/
|
|
|
|
export const Checkbox = forwardRef<HTMLInputElement, CheckboxProps>(
|
|
({ centralRipple = true, ...props }, ref) => {
|
|
const [isActive, setIsActive] = useState<boolean>(false),
|
|
[checked, setChecked] = useState<boolean>(props.checked ?? false),
|
|
ripplesRef = useRef(null),
|
|
checkboxRef = useRef(null),
|
|
events = useRippleEffect(ripplesRef, setIsActive);
|
|
|
|
const extraClassStyles =
|
|
`m3 m3-checkbox-container ${isActive === true ? 'visible' : ''}`.trimEnd();
|
|
|
|
useImperativeHandle(ref, () => checkboxRef.current);
|
|
|
|
useEffect(() => {
|
|
setChecked(!checked);
|
|
}, [checkboxRef.current?.checked]);
|
|
|
|
return (
|
|
<div {...events} className={extraClassStyles}>
|
|
<InputLayout
|
|
{...props}
|
|
indeterminate={props.indeterminate}
|
|
ref={checkboxRef}
|
|
type={'checkbox'}
|
|
/>
|
|
<span className={'m3 m3-checkbox-state'} />
|
|
<span className={'m3 m3-checkbox-state-layer'} />
|
|
<RippleEffect
|
|
callback={setIsActive}
|
|
central={centralRipple}
|
|
className={'m3-checkbox-ripple-layer'}
|
|
ref={ripplesRef}
|
|
/>
|
|
</div>
|
|
);
|
|
},
|
|
);
|
|
|
|
Checkbox.propTypes = {
|
|
indeterminate: bool,
|
|
centralRipple: bool,
|
|
};
|