From 6eb620f0792fb561cb516c8fd77743566a884ff5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E4=BA=8C=E8=B4=A7=E6=9C=BA=E5=99=A8=E4=BA=BA?= Date: Tue, 10 Jan 2023 14:33:19 +0800 Subject: [PATCH] chore: radio wave --- components/_util/wave/WaveEffect.tsx | 19 ++++++++++-- components/config-provider/index.tsx | 12 ++++---- components/radio/radio.tsx | 30 ++++++++++++------- components/radio/style/index.tsx | 19 ++++-------- .../theme/themesToken/happy/style/wave.ts | 3 +- components/theme/themesToken/happy/wave.tsx | 12 ++++++-- 6 files changed, 58 insertions(+), 37 deletions(-) diff --git a/components/_util/wave/WaveEffect.tsx b/components/_util/wave/WaveEffect.tsx index de8552fdb4..2890f6637f 100644 --- a/components/_util/wave/WaveEffect.tsx +++ b/components/_util/wave/WaveEffect.tsx @@ -122,6 +122,12 @@ const WaveEffect: React.FC = (props) => { export interface WaveWrapperProps { className: string; + currentTarget: HTMLElement; + /** + * In most case same as `currentTarget`. + * Only when `currentTarget` has children element with `.antd-wave-target` className. + * `target` will be the classNamed one. + */ target: HTMLElement; token: ReturnType; wave: ConfigProviderProps['wave']; @@ -129,7 +135,7 @@ export interface WaveWrapperProps { } function WaveWrapper(props: WaveWrapperProps) { - const { token, target, wave, holder } = props; + const { token, target, currentTarget, wave, holder } = props; function onFinish() { unmount(holder).then(() => { @@ -138,7 +144,7 @@ function WaveWrapper(props: WaveWrapperProps) { } if (wave?.render) { - return wave?.render({ target, token, onFinish }) as React.ReactElement; + return wave?.render({ target, currentTarget, token, onFinish }) as React.ReactElement; } return ; @@ -161,7 +167,14 @@ export default function showWaveEffect( const target = node.querySelector('.antd-wave-target') || node; render( - , + , holder, ); } diff --git a/components/config-provider/index.tsx b/components/config-provider/index.tsx index 0ee892dc20..60edfe774e 100644 --- a/components/config-provider/index.tsx +++ b/components/config-provider/index.tsx @@ -12,7 +12,6 @@ import LocaleProvider, { ANT_MARK } from '../locale'; import LocaleReceiver from '../locale/LocaleReceiver'; import defaultLocale from '../locale/en_US'; import { DesignTokenContext } from '../theme/internal'; -import type { useToken } from '../theme/internal'; import defaultSeedToken from '../theme/themes/seed'; import type { ConfigConsumerProps, CSPConfig, DirectionType, Theme, ThemeConfig } from './context'; import { ConfigConsumer, ConfigContext, defaultIconPrefixCls } from './context'; @@ -23,6 +22,7 @@ import useTheme from './hooks/useTheme'; import type { SizeType } from './SizeContext'; import SizeContext, { SizeContextProvider } from './SizeContext'; import useStyle from './style'; +import type { WaveWrapperProps } from '../_util/wave/WaveEffect'; export { type RenderEmptyHandler, @@ -84,11 +84,11 @@ export interface ConfigProviderProps { showSizeChanger?: boolean; }; wave?: { - render?: (props: { - target: HTMLElement; - token: ReturnType; - onFinish: VoidFunction; - }) => React.ReactNode; + render?: ( + props: Omit & { + onFinish: VoidFunction; + }, + ) => React.ReactNode; }; locale?: Locale; pageHeader?: { diff --git a/components/radio/radio.tsx b/components/radio/radio.tsx index 85629d0af2..0584ded66d 100644 --- a/components/radio/radio.tsx +++ b/components/radio/radio.tsx @@ -6,6 +6,7 @@ import { ConfigContext } from '../config-provider'; import DisabledContext from '../config-provider/DisabledContext'; import { FormItemInputContext } from '../form/context'; import warning from '../_util/warning'; +import Wave from '../_util/wave'; import RadioGroupContext, { RadioOptionTypeContext } from './context'; import type { RadioChangeEvent, RadioProps } from './interface'; @@ -68,18 +69,27 @@ const InternalRadio: React.ForwardRefRenderFunction = ( hashId, ); + /* eslint-disable jsx-a11y/label-has-associated-control */ return wrapSSR( - // eslint-disable-next-line jsx-a11y/label-has-associated-control - , + + + , ); + /* eslint-enable */ }; const Radio = React.forwardRef(InternalRadio); diff --git a/components/radio/style/index.tsx b/components/radio/style/index.tsx index a942061c9a..1bb53b9ee5 100644 --- a/components/radio/style/index.tsx +++ b/components/radio/style/index.tsx @@ -1,4 +1,3 @@ -import { Keyframes } from '@ant-design/cssinjs'; import type { FullToken, GenerateStyle } from '../../theme/internal'; import { genComponentStyleHook, mergeToken } from '../../theme/internal'; import { genFocusOutline, resetComponent } from '../../style'; @@ -30,11 +29,6 @@ interface RadioToken extends FullToken<'Radio'> { } // ============================== Styles ============================== -const antRadioEffect = new Keyframes('antRadioEffect', { - '0%': { transform: 'scale(1)', opacity: 0.5 }, - '100%': { transform: 'scale(1.6)', opacity: 0 }, -}); - // styles from RadioGroup only const getGroupRadioStyle: GenerateStyle = (token) => { const { componentCls, antCls } = token; @@ -71,7 +65,6 @@ const getRadioBasicStyle: GenerateStyle = (token) => { radioSize, motionDurationSlow, motionDurationMid, - motionEaseInOut, motionEaseInOutCirc, radioButtonBg, colorBorder, @@ -91,7 +84,6 @@ const getRadioBasicStyle: GenerateStyle = (token) => { return { [`${componentCls}-wrapper`]: { ...resetComponent(token), - position: 'relative', display: 'inline-flex', alignItems: 'baseline', marginInlineStart: 0, @@ -124,10 +116,6 @@ const getRadioBasicStyle: GenerateStyle = (token) => { border: `${lineWidth}px ${lineType} ${radioCheckedColor}`, borderRadius: '50%', visibility: 'hidden', - animationName: antRadioEffect, - animationDuration: motionDurationSlow, - animationTimingFunction: motionEaseInOut, - animationFillMode: 'both', content: '""', }, @@ -138,6 +126,7 @@ const getRadioBasicStyle: GenerateStyle = (token) => { outline: 'none', cursor: 'pointer', alignSelf: 'center', + borderRadius: '50%', }, [`${componentCls}-wrapper:hover &, @@ -192,9 +181,11 @@ const getRadioBasicStyle: GenerateStyle = (token) => { [`${componentCls}-input`]: { position: 'absolute', insetBlockStart: 0, - insetInlineEnd: 0, - insetBlockEnd: 0, insetInlineStart: 0, + width: 0, + height: 0, + padding: 0, + margin: 0, zIndex: 1, cursor: 'pointer', opacity: 0, diff --git a/components/theme/themesToken/happy/style/wave.ts b/components/theme/themesToken/happy/style/wave.ts index 87e93182ff..f9096fbba9 100644 --- a/components/theme/themesToken/happy/style/wave.ts +++ b/components/theme/themesToken/happy/style/wave.ts @@ -56,11 +56,12 @@ export default function useStyle(tokenConfig: UseTokenType) { const { motionDurationSlow } = token; const prefixCls = '.happy-wave'; + const targetPrefixCls = `${prefixCls}-target`; return [ { // ======================== Target ======================== - [`${prefixCls}-target`]: { + [`${targetPrefixCls}, & ${targetPrefixCls}`]: { animationName: antWaveTargetEffect, animationDuration: `0.45s`, animationTimingFunction: 'ease-in-out', diff --git a/components/theme/themesToken/happy/wave.tsx b/components/theme/themesToken/happy/wave.tsx index 7ff756c377..f83973fb8a 100644 --- a/components/theme/themesToken/happy/wave.tsx +++ b/components/theme/themesToken/happy/wave.tsx @@ -14,7 +14,8 @@ interface HappyWaveProps { onFinish: VoidFunction; } -const DOT_COUNT = 10; +const DOT_COUNT = 7; +const DOT_COUNT_LG = 10; interface DotInfo { key: number; @@ -68,13 +69,15 @@ function HappyWave({ target, token, onFinish }: HappyWaveProps) { const halfOffsetMaxWidth = halfWidth + OFFSET_MAX; const halfOffsetMaxHeight = halfHeight + OFFSET_MAX; + const dotCount = minSize >= 20 ? DOT_COUNT_LG : DOT_COUNT; + // Delay to start dot motion setTimeout(() => { const offsetAngle = Math.random() * 360; setDots( new Array(DOT_COUNT).fill(null).map((_, index) => { - const rotate: number = 360 / DOT_COUNT; + const rotate: number = 360 / dotCount; const randomAngle = offsetAngle + rotate * index; // Get start XY (Which should align the rect edge) @@ -111,7 +114,10 @@ function HappyWave({ target, token, onFinish }: HappyWaveProps) { inRange(endX, endY, -endHalfWidth, -endHalfHeight, endHalfWidth, endHalfHeight) ); - const size = Math.random() * 4 + 6; + let size = Math.random() * 3 + 3; + if (height >= 20) { + size = Math.random() * 4 + 6; + } return { key: index + 1,