From 063185a1b71a2b9dfe7f2c9e27ca45560dc3ad2a Mon Sep 17 00:00:00 2001 From: MadCcc Date: Thu, 14 Dec 2023 17:01:50 +0800 Subject: [PATCH] refactor: BaseInput (#55) --- src/BaseInput.tsx | 120 ++++++++++++++++++--------------------- src/Input.tsx | 5 +- src/interface.ts | 6 +- tests/BaseInput.test.tsx | 101 +++++++++++++++----------------- 4 files changed, 107 insertions(+), 125 deletions(-) diff --git a/src/BaseInput.tsx b/src/BaseInput.tsx index e1ed697..3364328 100644 --- a/src/BaseInput.tsx +++ b/src/BaseInput.tsx @@ -1,12 +1,13 @@ import clsx from 'classnames'; -import type { FC, ReactElement } from 'react'; +import type { FC, ReactElement, ReactNode } from 'react'; import React, { cloneElement, useRef } from 'react'; import type { BaseInputProps } from './interface'; import { hasAddon, hasPrefixSuffix } from './utils/commonUtils'; const BaseInput: FC = (props) => { const { - inputElement, + inputElement: inputEl, + children, prefixCls, prefix, suffix, @@ -29,6 +30,8 @@ const BaseInput: FC = (props) => { components, } = props; + const inputElement = children ?? inputEl; + const AffixWrapperComponent = components?.affixWrapper || 'span'; const GroupWrapperComponent = components?.groupWrapper || 'span'; const WrapperComponent = components?.wrapper || 'span'; @@ -42,63 +45,51 @@ const BaseInput: FC = (props) => { } }; - // ================== Clear Icon ================== // - const getClearIcon = () => { - if (!allowClear) { - return null; - } - const needClear = !disabled && !readOnly && value; - const clearIconCls = `${prefixCls}-clear-icon`; - const iconNode = - typeof allowClear === 'object' && allowClear?.clearIcon - ? allowClear.clearIcon - : '✖'; - - return ( - e.preventDefault()} - className={clsx(clearIconCls, { - [`${clearIconCls}-hidden`]: !needClear, - [`${clearIconCls}-has-suffix`]: !!suffix, - })} - role="button" - tabIndex={-1} - > - {iconNode} - - ); - }; - let element: ReactElement = cloneElement(inputElement, { value, - hidden, - className: - clsx( - inputElement.props?.className, - !hasPrefixSuffix(props) && !hasAddon(props) && className, - ) || null, - style: { - ...inputElement.props?.style, - ...(!hasPrefixSuffix(props) && !hasAddon(props) ? style : {}), - }, }); // ================== Prefix & Suffix ================== // if (hasPrefixSuffix(props)) { + // ================== Clear Icon ================== // + let clearIcon: ReactNode = null; + if (allowClear) { + const needClear = !disabled && !readOnly && value; + const clearIconCls = `${prefixCls}-clear-icon`; + const iconNode = + typeof allowClear === 'object' && allowClear?.clearIcon + ? allowClear.clearIcon + : '✖'; + + clearIcon = ( + e.preventDefault()} + className={clsx(clearIconCls, { + [`${clearIconCls}-hidden`]: !needClear, + [`${clearIconCls}-has-suffix`]: !!suffix, + })} + role="button" + tabIndex={-1} + > + {iconNode} + + ); + } + const affixWrapperPrefixCls = `${prefixCls}-affix-wrapper`; const affixWrapperCls = clsx( affixWrapperPrefixCls, { - [`${affixWrapperPrefixCls}-disabled`]: disabled, - [`${affixWrapperPrefixCls}-focused`]: focused, + [`${prefixCls}-disabled`]: disabled, + [`${affixWrapperPrefixCls}-disabled`]: disabled, // Not used, but keep it + [`${affixWrapperPrefixCls}-focused`]: focused, // Not used, but keep it [`${affixWrapperPrefixCls}-readonly`]: readOnly, [`${affixWrapperPrefixCls}-input-with-clear-btn`]: suffix && allowClear && value, }, - !hasAddon(props) && className, classes?.affixWrapper, classNames?.affixWrapper, ); @@ -108,7 +99,7 @@ const BaseInput: FC = (props) => { className={clsx(`${prefixCls}-suffix`, classNames?.suffix)} style={styles?.suffix} > - {getClearIcon()} + {clearIcon} {suffix} ); @@ -116,11 +107,7 @@ const BaseInput: FC = (props) => { element = ( ); @@ -151,31 +135,26 @@ const BaseInput: FC = (props) => { `${prefixCls}-wrapper`, wrapperCls, classes?.wrapper, + classNames?.wrapper, ); const mergedGroupClassName = clsx( `${prefixCls}-group-wrapper`, - className, classes?.group, + classNames?.groupWrapper, ); // Need another wrapper for changing display:table to display:inline-block // and put style prop in wrapper - return ( -