FIXED: Interfaces
This commit is contained in:
parent
ab4ae37015
commit
218b8f61d6
|
@ -1,3 +1,4 @@
|
|||
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
||||
const prettierConfig = require('./.prettierrc.js');
|
||||
|
||||
module.exports = {
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
<component name="InspectionProjectProfileManager">
|
||||
<profile version="1.0">
|
||||
<option name="myName" value="Project Default" />
|
||||
<inspection_tool class="ES6PreferShortImport" enabled="false" level="WARNING" enabled_by_default="false" />
|
||||
<inspection_tool class="Eslint" enabled="true" level="WARNING" enabled_by_default="true" />
|
||||
</profile>
|
||||
</component>
|
|
@ -1,6 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="EslintConfiguration">
|
||||
<option name="fix-on-save" value="true" />
|
||||
</component>
|
||||
</project>
|
|
@ -6,8 +6,14 @@ export default function Badges() {
|
|||
return (
|
||||
<div
|
||||
className={'m3 m3-wrapper'}
|
||||
style={{ display: 'flex', flexDirection: 'row' }}
|
||||
style={{
|
||||
display: 'flex',
|
||||
flexDirection: 'column',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
}}
|
||||
>
|
||||
<h1> Badges </h1>
|
||||
<div>
|
||||
<div
|
||||
style={{
|
||||
|
|
|
@ -7,16 +7,14 @@ import useRippleEffect from '../ripple/hooks/useRippleEffect';
|
|||
import React, { forwardRef, useId, useRef, useState } from 'react';
|
||||
|
||||
export const ButtonLayout = forwardRef<HTMLButtonElement, ButtonLayoutProps>(
|
||||
function ButtonBase({ centralRipple = false, ...props }, ref) {
|
||||
({ centralRipple = false, variant, ...props }, ref) => {
|
||||
const [isActive, setIsActive] = useState<boolean>(false),
|
||||
ripplesRef = useRef(null),
|
||||
buttonId = useId(),
|
||||
events = useRippleEffect(ripplesRef, setIsActive);
|
||||
|
||||
const { variant, disabled, className } = props;
|
||||
|
||||
const classes = className
|
||||
? `m3 ${className} ${variant}${isActive ? ' is-active' : ''}`
|
||||
const classes = props.className
|
||||
? `m3 ${props.className} ${variant}${isActive ? ' is-active' : ''}`
|
||||
: `m3 ${variant}${isActive ? ' is-active' : ''}`;
|
||||
|
||||
return (
|
||||
|
@ -24,7 +22,7 @@ export const ButtonLayout = forwardRef<HTMLButtonElement, ButtonLayoutProps>(
|
|||
{...props}
|
||||
{...events}
|
||||
className={classes}
|
||||
disabled={disabled}
|
||||
disabled={props.disabled}
|
||||
id={buttonId}
|
||||
ref={ref}
|
||||
>
|
||||
|
@ -40,6 +38,7 @@ export const ButtonLayout = forwardRef<HTMLButtonElement, ButtonLayoutProps>(
|
|||
);
|
||||
|
||||
ButtonLayout.propTypes = {
|
||||
variant: string,
|
||||
centralRipple: bool,
|
||||
children: string,
|
||||
};
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { ButtonHTMLAttributes } from 'react';
|
||||
import { IRippleProps } from '../ripple/ripple.types';
|
||||
|
||||
export interface ButtonLayoutProps
|
||||
extends IRippleProps,
|
||||
ButtonHTMLAttributes<HTMLButtonElement> {}
|
||||
export type ButtonLayoutProps = IRippleProps & ButtonHTMLAttributes<HTMLButtonElement> & {
|
||||
variant?: string;
|
||||
};
|
||||
|
|
|
@ -5,6 +5,7 @@ export interface ButtonMainProps
|
|||
extends ButtonHTMLAttributes<HTMLButtonElement> {
|
||||
disabled?: boolean;
|
||||
variant?: 'filled' | 'outlined' | 'elevated' | 'tonal' | 'text';
|
||||
icon?: string;
|
||||
}
|
||||
|
||||
export interface ButtonProps extends IRippleProps, ButtonMainProps {}
|
||||
export type ButtonProps = IRippleProps & ButtonMainProps;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
import { InputHTMLAttributes } from 'react';
|
||||
import { IRippleProps } from '../ripple/ripple.types';
|
||||
|
||||
export interface CheckboxProps
|
||||
extends InputHTMLAttributes<HTMLInputElement>,
|
||||
IRippleProps {}
|
||||
export type CheckboxProps = InputHTMLAttributes<HTMLInputElement> &
|
||||
IRippleProps & {
|
||||
indeterminate?: boolean;
|
||||
};
|
||||
|
|
|
@ -1,12 +1,14 @@
|
|||
import React from 'react';
|
||||
import { ButtonHTMLAttributes } from 'react';
|
||||
import { IRippleProps } from '../ripple/ripple.types';
|
||||
|
||||
export interface FABMainProps
|
||||
extends React.ButtonHTMLAttributes<HTMLButtonElement> {
|
||||
export interface FABMainProps {
|
||||
icon: string;
|
||||
disabled?: boolean;
|
||||
elevated?: boolean;
|
||||
size?: 'small' | 'default' | 'large' | 'extended';
|
||||
variant?: 'surface' | 'primary' | 'secondary' | 'tertiary';
|
||||
}
|
||||
|
||||
export interface FABProps extends FABMainProps, IRippleProps {}
|
||||
export type FABProps = FABMainProps &
|
||||
IRippleProps &
|
||||
ButtonHTMLAttributes<HTMLButtonElement>;
|
||||
|
|
|
@ -5,6 +5,7 @@ import { ButtonLayout } from '../button-layout/button-layout';
|
|||
import { IconButtonProps, StateToggleIconType } from './icon-button.types';
|
||||
import {
|
||||
forwardRef,
|
||||
MouseEventHandler,
|
||||
useCallback,
|
||||
useImperativeHandle,
|
||||
useRef,
|
||||
|
@ -44,7 +45,7 @@ export const IconButton = forwardRef<HTMLButtonElement, IconButtonProps>(
|
|||
const buttonRef = useRef<HTMLButtonElement>(null);
|
||||
|
||||
const callback = useCallback(
|
||||
(e: MouseEvent) => {
|
||||
(event: MouseEventHandler<HTMLButtonElement>) => {
|
||||
if (toggled) {
|
||||
if (toggleIcon.state === 'selected') {
|
||||
toggle('', toggled.unselected ?? 'add_circle');
|
||||
|
@ -53,7 +54,7 @@ export const IconButton = forwardRef<HTMLButtonElement, IconButtonProps>(
|
|||
}
|
||||
}
|
||||
if (props.onClick) {
|
||||
props.onClick.apply(null, e);
|
||||
props.onClick.apply(null, event);
|
||||
}
|
||||
},
|
||||
[toggleIcon],
|
||||
|
@ -72,7 +73,7 @@ export const IconButton = forwardRef<HTMLButtonElement, IconButtonProps>(
|
|||
variant={variant ? variant : 'default'}
|
||||
>
|
||||
<Icon
|
||||
fill={toggleIcon.state === 'selected' ? 1 : 0}
|
||||
fillIcon={toggleIcon.state === 'selected' ? 1 : 0}
|
||||
iconSize={28}
|
||||
svgSize={40}
|
||||
>
|
||||
|
|
|
@ -1,6 +1,14 @@
|
|||
import React from 'react';
|
||||
import { ButtonHTMLAttributes } from 'react';
|
||||
import { IRippleProps } from '../ripple/ripple.types';
|
||||
|
||||
export interface IconButtonMainProps {
|
||||
icon: string;
|
||||
selected?: boolean;
|
||||
disabled?: boolean;
|
||||
toggled?: false | ToggleButtonType;
|
||||
variant?: 'default' | 'filled' | 'tonal' | 'outlined';
|
||||
}
|
||||
|
||||
export type StateToggleIconType = {
|
||||
state: string;
|
||||
icon: string;
|
||||
|
@ -11,12 +19,6 @@ export type ToggleButtonType = {
|
|||
unselected: string;
|
||||
};
|
||||
|
||||
export interface IconButtonMainProps
|
||||
extends React.ButtonHTMLAttributes<HTMLButtonElement> {
|
||||
icon: string;
|
||||
toggled?: false | ToggleButtonType;
|
||||
disabled?: boolean;
|
||||
variant?: 'default' | 'filled' | 'tonal' | 'outlined';
|
||||
}
|
||||
|
||||
export interface IconButtonProps extends IconButtonMainProps, IRippleProps {}
|
||||
export type IconButtonProps = IconButtonMainProps &
|
||||
IRippleProps &
|
||||
ButtonHTMLAttributes<HTMLButtonElement>;
|
|
@ -1,8 +1,7 @@
|
|||
import { InputHTMLAttributes } from 'react';
|
||||
import { IRippleProps } from '../ripple/ripple.types';
|
||||
|
||||
export interface RadioProps
|
||||
extends InputHTMLAttributes<HTMLInputElement>,
|
||||
IRippleProps {
|
||||
export type RadioProps = InputHTMLAttributes<HTMLInputElement> &
|
||||
IRippleProps & {
|
||||
centralRipple?: boolean;
|
||||
}
|
||||
};
|
||||
|
|
|
@ -1,17 +1,36 @@
|
|||
import React, { useEffect, useState } from 'react';
|
||||
import {
|
||||
DragEventHandler,
|
||||
FocusEventHandler,
|
||||
MouseEventHandler,
|
||||
TouchEventHandler,
|
||||
useEffect,
|
||||
useState,
|
||||
} from 'react';
|
||||
|
||||
interface RippleEventHandlers {
|
||||
onBlur: React.FocusEventHandler;
|
||||
onContextMenu: React.MouseEventHandler;
|
||||
onDragLeave: React.DragEventHandler;
|
||||
onMouseDown: React.MouseEventHandler;
|
||||
onMouseLeave: React.MouseEventHandler;
|
||||
onMouseUp: React.MouseEventHandler;
|
||||
onTouchEnd: React.TouchEventHandler;
|
||||
onTouchMove: React.TouchEventHandler;
|
||||
onTouchStart: React.TouchEventHandler;
|
||||
onBlur: FocusEventHandler;
|
||||
onContextMenu: MouseEventHandler;
|
||||
onDragLeave: DragEventHandler;
|
||||
onMouseDown: MouseEventHandler;
|
||||
onMouseLeave: MouseEventHandler;
|
||||
onMouseUp: MouseEventHandler;
|
||||
onTouchEnd: TouchEventHandler;
|
||||
onTouchMove: TouchEventHandler;
|
||||
onTouchStart: TouchEventHandler;
|
||||
}
|
||||
|
||||
export type InteractionEventsType = MouseEvent & TouchEvent & DragEvent & FocusEvent
|
||||
|
||||
export interface InteractionEvents<T>
|
||||
extends MouseEvent,
|
||||
TouchEvent,
|
||||
DragEvent,
|
||||
FocusEvent,
|
||||
MouseEventHandler<T>,
|
||||
DragEventHandler<T>,
|
||||
FocusEventHandler<T>,
|
||||
TouchEventHandler<T> {}
|
||||
|
||||
const UseRippleEffect = (ref, callback): undefined | RippleEventHandlers => {
|
||||
const [mounted, setMounted] = useState<boolean>(false);
|
||||
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
import React, {
|
||||
forwardRef,
|
||||
useCallback,
|
||||
ReactElement,
|
||||
useId,
|
||||
useImperativeHandle,
|
||||
useRef,
|
||||
|
@ -11,16 +11,15 @@ import React, {
|
|||
import { Ripple } from './ripple';
|
||||
import { Ripples } from './ripple';
|
||||
import { RippleAreaProps } from './ripple.types';
|
||||
import {InteractionEvents, InteractionEventsType} from './hooks/useRippleEffect';
|
||||
|
||||
const TIMEOUT: number = 550;
|
||||
const rippleAreaContext = React.createContext(false);
|
||||
|
||||
const RippleArea = forwardRef(function RippleArea(
|
||||
{ central = false, callback, ...props }: RippleAreaProps,
|
||||
ref,
|
||||
) {
|
||||
const [ripples, setRipples] = useState<Array<JSX.Element>>([]),
|
||||
rippleDomain = useRef<any>(null),
|
||||
const RippleArea = forwardRef(
|
||||
({ central = false, ...props }: RippleAreaProps, ref) => {
|
||||
const [ripples, setRipples] = useState<Array<ReactElement>>([]),
|
||||
rippleDomain = useRef(null),
|
||||
clicked = useRef<boolean>(false),
|
||||
uniqueKey = useRef<number>(0),
|
||||
uniqueId = useId();
|
||||
|
@ -29,8 +28,10 @@ const RippleArea = forwardRef(function RippleArea(
|
|||
? `m3 m3-ripple-domain ${props.className}`.trimEnd()
|
||||
: 'm3 m3-ripple-domain';
|
||||
|
||||
const start = useCallback(
|
||||
(event: any, cb: (state: boolean) => void): void => {
|
||||
const start = (
|
||||
event: InteractionEventsType,
|
||||
cb: (state: boolean) => void,
|
||||
): void => {
|
||||
clicked.current = true;
|
||||
cb(clicked.current);
|
||||
|
||||
|
@ -65,7 +66,7 @@ const RippleArea = forwardRef(function RippleArea(
|
|||
2,
|
||||
rippleS: number = (rippleSizeX ** 2 + rippleSizeY ** 2) ** 0.5;
|
||||
|
||||
setRipples((prevRipples: Array<JSX.Element>) => {
|
||||
setRipples((prevRipples: Array<ReactElement>) => {
|
||||
if (prevRipples.length === 0) {
|
||||
return [
|
||||
<Ripple
|
||||
|
@ -91,15 +92,16 @@ const RippleArea = forwardRef(function RippleArea(
|
|||
});
|
||||
|
||||
uniqueKey.current += 1;
|
||||
},
|
||||
[],
|
||||
);
|
||||
};
|
||||
|
||||
const stop = useCallback((_event: any, cb: (state: boolean) => void) => {
|
||||
const stop = (
|
||||
_event: InteractionEventsType,
|
||||
cb: (state: boolean) => void,
|
||||
) => {
|
||||
clicked.current = false;
|
||||
cb(clicked.current);
|
||||
|
||||
setRipples((prevRipples: Array<JSX.Element>) => {
|
||||
setRipples((prevRipples: Array<ReactElement>) => {
|
||||
if (prevRipples.length > 0) {
|
||||
const old = [...prevRipples];
|
||||
old.shift();
|
||||
|
@ -107,7 +109,7 @@ const RippleArea = forwardRef(function RippleArea(
|
|||
}
|
||||
return prevRipples;
|
||||
});
|
||||
}, []);
|
||||
};
|
||||
|
||||
useImperativeHandle(
|
||||
ref,
|
||||
|
@ -125,6 +127,7 @@ const RippleArea = forwardRef(function RippleArea(
|
|||
</rippleAreaContext.Provider>
|
||||
</span>
|
||||
);
|
||||
});
|
||||
},
|
||||
);
|
||||
|
||||
export { rippleAreaContext, RippleArea };
|
||||
|
|
|
@ -1,14 +1,11 @@
|
|||
'use client';
|
||||
|
||||
import isEmpty from './utils/utils';
|
||||
import { rippleProps } from './ripple.types';
|
||||
import { RippleProps, RipplesProps } from './ripple.types';
|
||||
import { rippleAreaContext } from './ripple-area';
|
||||
import RippleEffectBuild from './utils/ripple-effect-builder';
|
||||
import React, {
|
||||
ForwardedRef,
|
||||
forwardRef,
|
||||
JSX,
|
||||
useCallback,
|
||||
ReactElement,
|
||||
useContext,
|
||||
useEffect,
|
||||
useRef,
|
||||
|
@ -16,15 +13,12 @@ import React, {
|
|||
useTransition,
|
||||
} from 'react';
|
||||
|
||||
const Ripples = forwardRef(function Ripples(
|
||||
props: any,
|
||||
ref: ForwardedRef<any>,
|
||||
) {
|
||||
const Ripples = (props: RipplesProps) => {
|
||||
const [ripples, setRipples] = useState({});
|
||||
const firstRender = useRef<boolean>(true);
|
||||
const [pending, startTransition] = useTransition();
|
||||
|
||||
const LifetimeEnd = useCallback((child: JSX.Element) => {
|
||||
const LifetimeEnd = (child: ReactElement) => {
|
||||
if (child.props.endLifetime) {
|
||||
child.props.endLifetime();
|
||||
}
|
||||
|
@ -34,10 +28,10 @@ const Ripples = forwardRef(function Ripples(
|
|||
delete children[child.key];
|
||||
return children;
|
||||
});
|
||||
}, []);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
if (props.children.length > 0) {
|
||||
if (props.children.length > 0 && !pending) {
|
||||
startTransition(() => {
|
||||
if (firstRender.current || isEmpty(ripples)) {
|
||||
setRipples(RippleEffectBuild(props.children, LifetimeEnd));
|
||||
|
@ -52,14 +46,15 @@ const Ripples = forwardRef(function Ripples(
|
|||
}, [props.children]);
|
||||
|
||||
return <>{Object.values(ripples)}</>;
|
||||
});
|
||||
|
||||
const Ripple = forwardRef(function Ripple(
|
||||
props: rippleProps,
|
||||
ref: ForwardedRef<any>,
|
||||
) {
|
||||
const { rippleX, rippleY, rippleS, endLifetime, lifetime } = props;
|
||||
};
|
||||
|
||||
const Ripple = ({
|
||||
rippleX,
|
||||
rippleY,
|
||||
rippleS,
|
||||
endLifetime,
|
||||
lifetime,
|
||||
}: RippleProps) => {
|
||||
const clicked = useContext<boolean>(rippleAreaContext);
|
||||
const [classes, setClasses] = useState<string>('m3 ripple visible');
|
||||
|
||||
|
@ -81,6 +76,6 @@ const Ripple = forwardRef(function Ripple(
|
|||
}}
|
||||
/>
|
||||
);
|
||||
});
|
||||
};
|
||||
|
||||
export { Ripple, Ripples };
|
||||
|
|
|
@ -1,21 +1,23 @@
|
|||
import { Dispatch, SetStateAction } from 'react';
|
||||
import { Dispatch, HTMLAttributes, ReactElement, SetStateAction } from 'react';
|
||||
|
||||
export interface IRippleProps extends PropsWithChildren<any> {
|
||||
export interface RipplesProps extends HTMLAttributes<HTMLElement> {
|
||||
children?: ReactElement[];
|
||||
}
|
||||
|
||||
export interface IRippleProps extends HTMLAttributes<HTMLElement> {
|
||||
centralRipple?: boolean;
|
||||
}
|
||||
|
||||
export interface RippleAreaProps extends PropsWithChildren<any> {
|
||||
export interface RippleAreaProps extends HTMLAttributes<HTMLElement> {
|
||||
callback: Dispatch<SetStateAction<boolean>>;
|
||||
central?: boolean;
|
||||
}
|
||||
|
||||
export type rippleProps = {
|
||||
export interface RippleProps extends HTMLAttributes<HTMLElement> {
|
||||
rippleX: number;
|
||||
rippleY: number;
|
||||
rippleS: number;
|
||||
endLifetime?: () => void;
|
||||
lifetime: number;
|
||||
key?: number;
|
||||
};
|
||||
|
||||
import { PropsWithChildren } from 'react';
|
||||
}
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
import { cloneElement, ReactElement } from 'react';
|
||||
|
||||
export default function ArrayConvertToObj(
|
||||
obj: Object,
|
||||
obj: object,
|
||||
nextChildren: ReactElement[],
|
||||
callback: (child: any) => void,
|
||||
callback: (child: ReactElement) => void,
|
||||
): void {
|
||||
Object.values(nextChildren).forEach(
|
||||
(child: JSX.Element) =>
|
||||
(child: ReactElement) =>
|
||||
(obj[child.key] = cloneElement(child, {
|
||||
...child.props,
|
||||
endLifetime: callback.bind(null, child),
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
import isEmpty from './utils';
|
||||
import ArrayConvertToObj from './array-convert-to-obj';
|
||||
import { cloneElement, ReactElement } from 'react';
|
||||
import isEmpty from './utils';
|
||||
|
||||
export default function RippleEffectBuild(
|
||||
nextRipples: ReactElement[],
|
||||
callback: (child: any) => void,
|
||||
prevRipples?: any | null,
|
||||
callback: (child: ReactElement) => void,
|
||||
prevRipples?: object | null,
|
||||
) {
|
||||
const empty: boolean = isEmpty(prevRipples);
|
||||
const preparedRipples: object = empty ? {} : prevRipples;
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
export default function isEmpty(obj: Object): boolean {
|
||||
export default function isEmpty(obj: object): boolean {
|
||||
for (const _i in obj) {
|
||||
return false;
|
||||
}
|
||||
|
|
|
@ -15,7 +15,7 @@ export const TextField = forwardRef<HTMLInputElement, TextFieldInterface>(
|
|||
},
|
||||
ref,
|
||||
) => {
|
||||
const [raised, setRaised] = useState<boolean>(!props.placeholder);
|
||||
const [raised, setRaised] = useState<boolean>(!!props.placeholder);
|
||||
|
||||
const callback = (e: FocusEvent<HTMLInputElement>): void => {
|
||||
if (
|
||||
|
@ -92,10 +92,10 @@ export const TextField = forwardRef<HTMLInputElement, TextFieldInterface>(
|
|||
|
||||
TextField.propTypes = {
|
||||
children: string,
|
||||
withBeforeIcon: bool,
|
||||
withAfterIcon: bool,
|
||||
className: string,
|
||||
variant: oneOf(['filled', 'outlined']),
|
||||
placeholder: string,
|
||||
withAfterIcon: bool,
|
||||
withBeforeIcon: bool,
|
||||
supportingText: string,
|
||||
variant: oneOf(['filled', 'outlined']),
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue