feat: CP support Input allowClear (#47602)

This commit is contained in:
lijianan 2024-02-27 10:25:35 +08:00 committed by GitHub
parent b28b0d883f
commit 6c0d3e46c4
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
6 changed files with 30 additions and 14 deletions

View File

@ -478,7 +478,7 @@ describe('ConfigProvider support style and className props', () => {
).toBeTruthy(); ).toBeTruthy();
}); });
it('Should Input className & style & classNames & styles works', () => { it('Should Input className & style & classNames & styles & autoComplete & allowClear works', () => {
const { container } = render( const { container } = render(
<ConfigProvider <ConfigProvider
input={{ input={{
@ -496,13 +496,21 @@ describe('ConfigProvider support style and className props', () => {
color: 'black', color: 'black',
}, },
}, },
allowClear: {
clearIcon: <span className="cp-test-icon">cp-test-icon</span>,
},
}} }}
> >
<Input placeholder="Basic usage" prefix="¥" /> <Input
autoComplete="test-autocomplete"
placeholder="Basic usage"
value="test"
prefix="¥"
/>
</ConfigProvider>, </ConfigProvider>,
); );
const wrapperElement = container.querySelector<HTMLDivElement>('.ant-input-affix-wrapper'); const wrapperElement = container.querySelector<HTMLSpanElement>('.ant-input-affix-wrapper');
expect(wrapperElement).toHaveClass('cp-input'); expect(wrapperElement).toHaveClass('cp-input');
expect(wrapperElement).toHaveStyle({ backgroundColor: 'red' }); expect(wrapperElement).toHaveStyle({ backgroundColor: 'red' });
@ -513,6 +521,10 @@ describe('ConfigProvider support style and className props', () => {
const inputElement = container.querySelector<HTMLDivElement>('.ant-input'); const inputElement = container.querySelector<HTMLDivElement>('.ant-input');
expect(inputElement).toHaveClass('cp-classNames-input'); expect(inputElement).toHaveClass('cp-classNames-input');
expect(inputElement).toHaveStyle({ color: 'blue' }); expect(inputElement).toHaveStyle({ color: 'blue' });
expect(inputElement?.getAttribute('autocomplete')).toBe('test-autocomplete');
expect(
container?.querySelector<HTMLSpanElement>('.ant-input-affix-wrapper .cp-test-icon'),
).toBeTruthy();
}); });
it('Should Layout className & style works', () => { it('Should Layout className & style works', () => {

View File

@ -100,6 +100,9 @@ export type AlertConfig = ComponentStyleConfig & Pick<AlertProps, 'closable' | '
export type BadgeConfig = ComponentStyleConfig & Pick<BadgeProps, 'classNames' | 'styles'>; export type BadgeConfig = ComponentStyleConfig & Pick<BadgeProps, 'classNames' | 'styles'>;
export type InputConfig = ComponentStyleConfig &
Pick<InputProps, 'autoComplete' | 'classNames' | 'styles' | 'allowClear'>;
export type ButtonConfig = ComponentStyleConfig & Pick<ButtonProps, 'classNames' | 'styles'>; export type ButtonConfig = ComponentStyleConfig & Pick<ButtonProps, 'classNames' | 'styles'>;
export type NotificationConfig = ComponentStyleConfig & Pick<ArgsProps, 'closeIcon'>; export type NotificationConfig = ComponentStyleConfig & Pick<ArgsProps, 'closeIcon'>;
@ -134,7 +137,7 @@ export interface ConfigConsumerProps {
renderEmpty?: RenderEmptyHandler; renderEmpty?: RenderEmptyHandler;
csp?: CSPConfig; csp?: CSPConfig;
autoInsertSpaceInButton?: boolean; autoInsertSpaceInButton?: boolean;
input?: ComponentStyleConfig & Pick<InputProps, 'autoComplete' | 'classNames' | 'styles'>; input?: InputConfig;
pagination?: ComponentStyleConfig & Pick<PaginationProps, 'showSizeChanger'>; pagination?: ComponentStyleConfig & Pick<PaginationProps, 'showSizeChanger'>;
locale?: Locale; locale?: Locale;
direction?: DirectionType; direction?: DirectionType;

View File

@ -124,7 +124,7 @@ const {
| flex | Set Flex common props | { className?: string, style?: React.CSSProperties, vertical?: boolean } | - | 5.10.0 | | flex | Set Flex common props | { className?: string, style?: React.CSSProperties, vertical?: boolean } | - | 5.10.0 |
| form | Set Form common props | { className?: string, style?: React.CSSProperties, validateMessages?: [ValidateMessages](/components/form/#validatemessages), requiredMark?: boolean \| `optional`, scrollToFirstError?: boolean \| [Options](https://github.com/stipsan/scroll-into-view-if-needed/tree/ece40bd9143f48caf4b99503425ecb16b0ad8249#options) } | - | requiredMark: 4.8.0; colon: 4.18.0; scrollToFirstError: 5.2.0; className: 5.7.0; style: 5.7.0 | | form | Set Form common props | { className?: string, style?: React.CSSProperties, validateMessages?: [ValidateMessages](/components/form/#validatemessages), requiredMark?: boolean \| `optional`, scrollToFirstError?: boolean \| [Options](https://github.com/stipsan/scroll-into-view-if-needed/tree/ece40bd9143f48caf4b99503425ecb16b0ad8249#options) } | - | requiredMark: 4.8.0; colon: 4.18.0; scrollToFirstError: 5.2.0; className: 5.7.0; style: 5.7.0 |
| image | Set Image common props | { className?: string, style?: React.CSSProperties, preview?: { closeIcon?: React.ReactNode } } | - | 5.7.0, closeIcon: 5.14.0 | | image | Set Image common props | { className?: string, style?: React.CSSProperties, preview?: { closeIcon?: React.ReactNode } } | - | 5.7.0, closeIcon: 5.14.0 |
| input | Set Input common props | { autoComplete?: string, className?: string, style?: React.CSSProperties } | - | 4.2.0 | | input | Set Input common props | { autoComplete?: string, className?: string, style?: React.CSSProperties, allowClear?: boolean \| { clearIcon?: ReactNode } } | - | 4.2.0, allowClear: 5.15.0 |
| layout | Set Layout common props | { className?: string, style?: React.CSSProperties } | - | 5.7.0 | | layout | Set Layout common props | { className?: string, style?: React.CSSProperties } | - | 5.7.0 |
| list | Set List common props | { className?: string, style?: React.CSSProperties } | - | 5.7.0 | | list | Set List common props | { className?: string, style?: React.CSSProperties } | - | 5.7.0 |
| menu | Set Menu common props | { className?: string, style?: React.CSSProperties, expandIcon?: ReactNode \| props => ReactNode } | - | 5.7.0, expandIcon: 5.15.0 | | menu | Set Menu common props | { className?: string, style?: React.CSSProperties, expandIcon?: ReactNode \| props => ReactNode } | - | 5.7.0, expandIcon: 5.15.0 |

View File

@ -8,7 +8,6 @@ import warning, { WarningContext } from '../_util/warning';
import type { WarningContextProps } from '../_util/warning'; import type { WarningContextProps } from '../_util/warning';
import type { FormProps } from '../form/Form'; import type { FormProps } from '../form/Form';
import ValidateMessagesContext from '../form/validateMessagesContext'; import ValidateMessagesContext from '../form/validateMessagesContext';
import type { InputProps } from '../input';
import type { Locale } from '../locale'; import type { Locale } from '../locale';
import LocaleProvider, { ANT_MARK } from '../locale'; import LocaleProvider, { ANT_MARK } from '../locale';
import type { LocaleContextProps } from '../locale/context'; import type { LocaleContextProps } from '../locale/context';
@ -32,6 +31,7 @@ import type {
DrawerConfig, DrawerConfig,
FlexConfig, FlexConfig,
ImageConfig, ImageConfig,
InputConfig,
MenuConfig, MenuConfig,
ModalConfig, ModalConfig,
NotificationConfig, NotificationConfig,
@ -123,7 +123,7 @@ export interface ConfigProviderProps {
autoInsertSpaceInButton?: boolean; autoInsertSpaceInButton?: boolean;
form?: ComponentStyleConfig & form?: ComponentStyleConfig &
Pick<FormProps, 'requiredMark' | 'colon' | 'scrollToFirstError' | 'validateMessages'>; Pick<FormProps, 'requiredMark' | 'colon' | 'scrollToFirstError' | 'validateMessages'>;
input?: ComponentStyleConfig & Pick<InputProps, 'autoComplete' | 'classNames' | 'styles'>; input?: InputConfig;
select?: ComponentStyleConfig & Pick<SelectProps, 'showSearch'>; select?: ComponentStyleConfig & Pick<SelectProps, 'showSearch'>;
pagination?: ComponentStyleConfig & Pick<PaginationProps, 'showSizeChanger'>; pagination?: ComponentStyleConfig & Pick<PaginationProps, 'showSizeChanger'>;
locale?: Locale; locale?: Locale;

View File

@ -126,7 +126,7 @@ const {
| flex | 设置 Flex 组件的通用属性 | { className?: string, style?: React.CSSProperties, vertical?: boolean } | - | 5.10.0 | | flex | 设置 Flex 组件的通用属性 | { className?: string, style?: React.CSSProperties, vertical?: boolean } | - | 5.10.0 |
| form | 设置 Form 组件的通用属性 | { className?: string, style?: React.CSSProperties, validateMessages?: [ValidateMessages](/components/form-cn#validatemessages), requiredMark?: boolean \| `optional`, colon?: boolean, scrollToFirstError?: boolean \| [Options](https://github.com/stipsan/scroll-into-view-if-needed/tree/ece40bd9143f48caf4b99503425ecb16b0ad8249#options)} | - | requiredMark: 4.8.0; colon: 4.18.0; scrollToFirstError: 5.2.0; className: 5.7.0; style: 5.7.0 | | form | 设置 Form 组件的通用属性 | { className?: string, style?: React.CSSProperties, validateMessages?: [ValidateMessages](/components/form-cn#validatemessages), requiredMark?: boolean \| `optional`, colon?: boolean, scrollToFirstError?: boolean \| [Options](https://github.com/stipsan/scroll-into-view-if-needed/tree/ece40bd9143f48caf4b99503425ecb16b0ad8249#options)} | - | requiredMark: 4.8.0; colon: 4.18.0; scrollToFirstError: 5.2.0; className: 5.7.0; style: 5.7.0 |
| image | 设置 Image 组件的通用属性 | { className?: string, style?: React.CSSProperties, preview?: { closeIcon?: React.ReactNode } } | - | 5.7.0, closeIcon: 5.14.0 | | image | 设置 Image 组件的通用属性 | { className?: string, style?: React.CSSProperties, preview?: { closeIcon?: React.ReactNode } } | - | 5.7.0, closeIcon: 5.14.0 |
| input | 设置 Input 组件的通用属性 | { autoComplete?: string, className?: string, style?: React.CSSProperties } | - | 5.7.0 | | input | 设置 Input 组件的通用属性 | { autoComplete?: string, className?: string, style?: React.CSSProperties, allowClear?: boolean \| { clearIcon?: ReactNode } } | - | 5.7.0, allowClear: 5.15.0 |
| layout | 设置 Layout 组件的通用属性 | { className?: string, style?: React.CSSProperties } | - | 5.7.0 | | layout | 设置 Layout 组件的通用属性 | { className?: string, style?: React.CSSProperties } | - | 5.7.0 |
| list | 设置 List 组件的通用属性 | { className?: string, style?: React.CSSProperties } | - | 5.7.0 | | list | 设置 List 组件的通用属性 | { className?: string, style?: React.CSSProperties } | - | 5.7.0 |
| menu | 设置 Menu 组件的通用属性 | { className?: string, style?: React.CSSProperties, expandIcon?: ReactNode \| props => ReactNode } | - | 5.7.0, expandIcon: 5.15.0 | | menu | 设置 Menu 组件的通用属性 | { className?: string, style?: React.CSSProperties, expandIcon?: ReactNode \| props => ReactNode } | - | 5.7.0, expandIcon: 5.15.0 |

View File

@ -1,25 +1,25 @@
import React, { forwardRef, useContext, useEffect, useRef } from 'react'; import React, { forwardRef, useContext, useEffect, useRef } from 'react';
import classNames from 'classnames'; import classNames from 'classnames';
import type { InputProps as RcInputProps, InputRef } from 'rc-input'; import type { InputRef, InputProps as RcInputProps } from 'rc-input';
import RcInput from 'rc-input'; import RcInput from 'rc-input';
import { composeRef } from 'rc-util/lib/ref'; import { composeRef } from 'rc-util/lib/ref';
import getAllowClear from '../_util/getAllowClear';
import type { InputStatus } from '../_util/statusUtils'; import type { InputStatus } from '../_util/statusUtils';
import { getMergedStatus, getStatusClassNames } from '../_util/statusUtils'; import { getMergedStatus, getStatusClassNames } from '../_util/statusUtils';
import { devUseWarning } from '../_util/warning'; import { devUseWarning } from '../_util/warning';
import { ConfigContext } from '../config-provider'; import { ConfigContext } from '../config-provider';
import DisabledContext from '../config-provider/DisabledContext'; import DisabledContext from '../config-provider/DisabledContext';
import useCSSVarCls from '../config-provider/hooks/useCSSVarCls';
import useSize from '../config-provider/hooks/useSize'; import useSize from '../config-provider/hooks/useSize';
import type { SizeType } from '../config-provider/SizeContext'; import type { SizeType } from '../config-provider/SizeContext';
import { FormItemInputContext, NoFormStyle } from '../form/context'; import { FormItemInputContext, NoFormStyle } from '../form/context';
import type { Variant } from '../form/hooks/useVariants';
import useVariant from '../form/hooks/useVariants';
import { NoCompactStyle, useCompactItemContext } from '../space/Compact'; import { NoCompactStyle, useCompactItemContext } from '../space/Compact';
import useRemovePasswordTimeout from './hooks/useRemovePasswordTimeout'; import useRemovePasswordTimeout from './hooks/useRemovePasswordTimeout';
import useStyle from './style'; import useStyle from './style';
import { hasPrefixSuffix } from './utils'; import { hasPrefixSuffix } from './utils';
import useCSSVarCls from '../config-provider/hooks/useCSSVarCls';
import type { Variant } from '../form/hooks/useVariants';
import useVariant from '../form/hooks/useVariants';
import getAllowClear from '../_util/getAllowClear';
export interface InputFocusOptions extends FocusOptions { export interface InputFocusOptions extends FocusOptions {
cursor?: 'start' | 'end' | 'all'; cursor?: 'start' | 'end' | 'all';
@ -172,7 +172,8 @@ const Input = forwardRef<InputRef, InputProps>((props, ref) => {
</> </>
); );
const mergedAllowClear = getAllowClear(allowClear); const mergedAllowClear = getAllowClear(allowClear ?? input?.allowClear);
const [variant, enableVariantCls] = useVariant(customVariant, bordered); const [variant, enableVariantCls] = useVariant(customVariant, bordered);
return wrapCSSVar( return wrapCSSVar(