mirror of
https://gitee.com/ant-design/ant-design.git
synced 2024-12-02 12:09:14 +08:00
refactor(select): rewrite with hook (#27318)
* refactor(select): rewrite with hook * Update index.tsx * Update index.tsx * Update index.tsx * fix test * Update index.tsx * Update index.tsx
This commit is contained in:
parent
5c072cdec9
commit
b0245e742b
@ -7,9 +7,9 @@
|
||||
|
||||
import * as React from 'react';
|
||||
import toArray from 'rc-util/lib/Children/toArray';
|
||||
import { SelectProps as RcSelectProps } from 'rc-select';
|
||||
import classNames from 'classnames';
|
||||
import omit from 'omit.js';
|
||||
import RcSelect from 'rc-select';
|
||||
import Select, { InternalSelectProps, OptionType } from '../select';
|
||||
import { ConfigConsumer, ConfigConsumerProps } from '../config-provider';
|
||||
import devWarning from '../_util/devWarning';
|
||||
@ -17,8 +17,6 @@ import { isValidElement } from '../_util/reactNode';
|
||||
|
||||
const { Option } = Select;
|
||||
|
||||
const InternalSelect = Select as React.ComponentClass<RcSelectProps>;
|
||||
|
||||
export interface DataSourceItemObject {
|
||||
value: string;
|
||||
text: string;
|
||||
@ -37,14 +35,13 @@ function isSelectOptionOrSelectOptGroup(child: any): Boolean {
|
||||
return child && child.type && (child.type.isSelectOption || child.type.isSelectOptGroup);
|
||||
}
|
||||
|
||||
const AutoComplete: React.ForwardRefRenderFunction<Select, AutoCompleteProps> = (props, ref) => {
|
||||
const AutoComplete: React.ForwardRefRenderFunction<RcSelect<any>, AutoCompleteProps> = (
|
||||
props,
|
||||
ref,
|
||||
) => {
|
||||
const { prefixCls: customizePrefixCls, className, children, dataSource } = props;
|
||||
const childNodes: React.ReactElement[] = toArray(children);
|
||||
|
||||
const selectRef = React.useRef<Select>();
|
||||
|
||||
React.useImperativeHandle<Select, Select>(ref, () => selectRef.current!);
|
||||
|
||||
// ============================= Input =============================
|
||||
let customizeInput: React.ReactElement | undefined;
|
||||
|
||||
@ -113,8 +110,8 @@ const AutoComplete: React.ForwardRefRenderFunction<Select, AutoCompleteProps> =
|
||||
const prefixCls = getPrefixCls('select', customizePrefixCls);
|
||||
|
||||
return (
|
||||
<InternalSelect
|
||||
ref={selectRef as any}
|
||||
<Select
|
||||
ref={ref}
|
||||
{...omit(props, ['dataSource'])}
|
||||
prefixCls={prefixCls}
|
||||
className={classNames(`${prefixCls}-auto-complete`, className)}
|
||||
@ -122,14 +119,14 @@ const AutoComplete: React.ForwardRefRenderFunction<Select, AutoCompleteProps> =
|
||||
getInputElement={getInputElement}
|
||||
>
|
||||
{optionChildren}
|
||||
</InternalSelect>
|
||||
</Select>
|
||||
);
|
||||
}}
|
||||
</ConfigConsumer>
|
||||
);
|
||||
};
|
||||
|
||||
const RefAutoComplete = React.forwardRef<Select, AutoCompleteProps>(AutoComplete);
|
||||
const RefAutoComplete = React.forwardRef<unknown, AutoCompleteProps>(AutoComplete);
|
||||
|
||||
type RefAutoCompleteWithOption = typeof RefAutoComplete & {
|
||||
Option: OptionType;
|
||||
|
@ -1,5 +1,951 @@
|
||||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||
|
||||
exports[`Calendar Calendar MonthSelect should display correct label 1`] = `
|
||||
<div
|
||||
class="ant-picker-calendar ant-picker-calendar-full"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-header"
|
||||
>
|
||||
<div
|
||||
class="ant-select ant-picker-calendar-year-select ant-select-single ant-select-show-arrow"
|
||||
>
|
||||
<div
|
||||
class="ant-select-selector"
|
||||
>
|
||||
<span
|
||||
class="ant-select-selection-search"
|
||||
>
|
||||
<input
|
||||
aria-activedescendant="rc_select_TEST_OR_SSR_list_0"
|
||||
aria-autocomplete="list"
|
||||
aria-controls="rc_select_TEST_OR_SSR_list"
|
||||
aria-haspopup="listbox"
|
||||
aria-owns="rc_select_TEST_OR_SSR_list"
|
||||
autocomplete="off"
|
||||
class="ant-select-selection-search-input"
|
||||
id="rc_select_TEST_OR_SSR"
|
||||
readonly=""
|
||||
role="combobox"
|
||||
style="opacity: 0;"
|
||||
type="search"
|
||||
unselectable="on"
|
||||
value=""
|
||||
/>
|
||||
</span>
|
||||
<span
|
||||
class="ant-select-selection-item"
|
||||
title="2019"
|
||||
>
|
||||
2019
|
||||
</span>
|
||||
</div>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
class="ant-select-arrow"
|
||||
style="user-select: none;"
|
||||
unselectable="on"
|
||||
>
|
||||
<span
|
||||
aria-label="down"
|
||||
class="anticon anticon-down ant-select-suffix"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="down"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M884 256h-75c-5.1 0-9.9 2.5-12.9 6.6L512 654.2 227.9 262.6c-3-4.1-7.8-6.6-12.9-6.6h-75c-6.5 0-10.3 7.4-6.5 12.7l352.6 486.1c12.8 17.6 39 17.6 51.7 0l352.6-486.1c3.9-5.3.1-12.7-6.4-12.7z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</div>
|
||||
<div
|
||||
class="ant-select ant-picker-calendar-month-select ant-select-single ant-select-show-arrow"
|
||||
>
|
||||
<div
|
||||
class="ant-select-selector"
|
||||
>
|
||||
<span
|
||||
class="ant-select-selection-search"
|
||||
>
|
||||
<input
|
||||
aria-activedescendant="rc_select_TEST_OR_SSR_list_0"
|
||||
aria-autocomplete="list"
|
||||
aria-controls="rc_select_TEST_OR_SSR_list"
|
||||
aria-haspopup="listbox"
|
||||
aria-owns="rc_select_TEST_OR_SSR_list"
|
||||
autocomplete="off"
|
||||
class="ant-select-selection-search-input"
|
||||
id="rc_select_TEST_OR_SSR"
|
||||
readonly=""
|
||||
role="combobox"
|
||||
style="opacity: 0;"
|
||||
type="search"
|
||||
unselectable="on"
|
||||
value=""
|
||||
/>
|
||||
</span>
|
||||
<span
|
||||
class="ant-select-selection-item"
|
||||
title="Jan"
|
||||
>
|
||||
Jan
|
||||
</span>
|
||||
</div>
|
||||
<span
|
||||
aria-hidden="true"
|
||||
class="ant-select-arrow"
|
||||
style="user-select: none;"
|
||||
unselectable="on"
|
||||
>
|
||||
<span
|
||||
aria-label="down"
|
||||
class="anticon anticon-down ant-select-suffix"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="down"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M884 256h-75c-5.1 0-9.9 2.5-12.9 6.6L512 654.2 227.9 262.6c-3-4.1-7.8-6.6-12.9-6.6h-75c-6.5 0-10.3 7.4-6.5 12.7l352.6 486.1c12.8 17.6 39 17.6 51.7 0l352.6-486.1c3.9-5.3.1-12.7-6.4-12.7z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</div>
|
||||
<div
|
||||
class="ant-radio-group ant-radio-group-outline ant-picker-calendar-mode-switch"
|
||||
>
|
||||
<label
|
||||
class="ant-radio-button-wrapper ant-radio-button-wrapper-checked"
|
||||
>
|
||||
<span
|
||||
class="ant-radio-button ant-radio-button-checked"
|
||||
>
|
||||
<input
|
||||
checked=""
|
||||
class="ant-radio-button-input"
|
||||
type="radio"
|
||||
value="month"
|
||||
/>
|
||||
<span
|
||||
class="ant-radio-button-inner"
|
||||
/>
|
||||
</span>
|
||||
<span>
|
||||
Month
|
||||
</span>
|
||||
</label>
|
||||
<label
|
||||
class="ant-radio-button-wrapper"
|
||||
>
|
||||
<span
|
||||
class="ant-radio-button"
|
||||
>
|
||||
<input
|
||||
class="ant-radio-button-input"
|
||||
type="radio"
|
||||
value="year"
|
||||
/>
|
||||
<span
|
||||
class="ant-radio-button-inner"
|
||||
/>
|
||||
</span>
|
||||
<span>
|
||||
Year
|
||||
</span>
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-panel"
|
||||
tabindex="0"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-date-panel"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-body"
|
||||
>
|
||||
<table
|
||||
class="ant-picker-content"
|
||||
>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>
|
||||
Su
|
||||
</th>
|
||||
<th>
|
||||
Mo
|
||||
</th>
|
||||
<th>
|
||||
Tu
|
||||
</th>
|
||||
<th>
|
||||
We
|
||||
</th>
|
||||
<th>
|
||||
Th
|
||||
</th>
|
||||
<th>
|
||||
Fr
|
||||
</th>
|
||||
<th>
|
||||
Sa
|
||||
</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2018-12-30"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
30
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2018-12-31"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
31
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view ant-picker-cell-selected"
|
||||
title="2019-01-01"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
01
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-02"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
02
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-03"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
03
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-04"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
04
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-05"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
05
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-06"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
06
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-07"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
07
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-08"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
08
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-09"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
09
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-10"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
10
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-11"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
11
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-12"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
12
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-13"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
13
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-14"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
14
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-15"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
15
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-16"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
16
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-17"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
17
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-18"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
18
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-19"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
19
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-20"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
20
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-21"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
21
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-22"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
22
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-23"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
23
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-24"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
24
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-25"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
25
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-26"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
26
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-27"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
27
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-28"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
28
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-29"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
29
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-30"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
30
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell ant-picker-cell-in-view"
|
||||
title="2019-01-31"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
31
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-01"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
01
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-02"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
02
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-03"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
03
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-04"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
04
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-05"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
05
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-06"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
06
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-07"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
07
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-08"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
08
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
<td
|
||||
class="ant-picker-cell"
|
||||
title="2019-02-09"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-cell-inner ant-picker-calendar-date"
|
||||
>
|
||||
<div
|
||||
class="ant-picker-calendar-date-value"
|
||||
>
|
||||
09
|
||||
</div>
|
||||
<div
|
||||
class="ant-picker-calendar-date-content"
|
||||
/>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
||||
exports[`Calendar Calendar should support locale 1`] = `
|
||||
<div
|
||||
class="ant-picker-calendar ant-picker-calendar-full"
|
||||
|
@ -117,9 +117,7 @@ describe('Calendar', () => {
|
||||
it('Calendar MonthSelect should display correct label', () => {
|
||||
const validRange = [Moment('2018-02-02'), Moment('2019-06-1')];
|
||||
const wrapper = mount(<Calendar validRange={validRange} defaultValue={Moment('2019-01-01')} />);
|
||||
const { options } = wrapper.find('MonthSelect > Select').props();
|
||||
expect(options.length).toBe(6);
|
||||
expect(options[5]).toEqual({ label: 'Jun', value: 5 });
|
||||
expect(wrapper.render()).toMatchSnapshot();
|
||||
});
|
||||
|
||||
it('Calendar should change mode by prop', () => {
|
||||
|
@ -10,7 +10,7 @@ import rtlTest from '../../../tests/shared/rtlTest';
|
||||
const { Option } = Select;
|
||||
|
||||
describe('Select', () => {
|
||||
focusTest(Select);
|
||||
focusTest(Select, { refFocus: true });
|
||||
mountTest(Select);
|
||||
rtlTest(Select);
|
||||
|
||||
|
@ -5,7 +5,7 @@ import omit from 'omit.js';
|
||||
import classNames from 'classnames';
|
||||
import RcSelect, { Option, OptGroup, SelectProps as RcSelectProps } from 'rc-select';
|
||||
import { OptionProps } from 'rc-select/lib/Option';
|
||||
import { ConfigConsumer, ConfigConsumerProps } from '../config-provider';
|
||||
import { ConfigContext } from '../config-provider';
|
||||
import getIcons from './utils/iconUtil';
|
||||
import SizeContext, { SizeType } from '../config-provider/SizeContext';
|
||||
|
||||
@ -35,148 +35,126 @@ export interface SelectProps<VT>
|
||||
mode?: 'multiple' | 'tags';
|
||||
}
|
||||
|
||||
// We still use class here since `forwardRef` not support generic in typescript
|
||||
class Select<ValueType extends SelectValue = SelectValue> extends React.Component<
|
||||
SelectProps<ValueType>
|
||||
> {
|
||||
static Option = Option;
|
||||
const SECRET_COMBOBOX_MODE_DO_NOT_USE = 'SECRET_COMBOBOX_MODE_DO_NOT_USE';
|
||||
|
||||
static OptGroup = OptGroup;
|
||||
|
||||
static SECRET_COMBOBOX_MODE_DO_NOT_USE = 'SECRET_COMBOBOX_MODE_DO_NOT_USE';
|
||||
|
||||
static defaultProps = {
|
||||
transitionName: 'slide-up',
|
||||
choiceTransitionName: '',
|
||||
bordered: true,
|
||||
};
|
||||
|
||||
selectRef = React.createRef<RcSelect<ValueType>>();
|
||||
|
||||
public focus = () => {
|
||||
if (this.selectRef.current) {
|
||||
this.selectRef.current.focus();
|
||||
}
|
||||
};
|
||||
|
||||
public blur = () => {
|
||||
if (this.selectRef.current) {
|
||||
this.selectRef.current.blur();
|
||||
}
|
||||
};
|
||||
|
||||
getMode = () => {
|
||||
const { mode } = this.props as InternalSelectProps<ValueType>;
|
||||
|
||||
if ((mode as any) === 'combobox') {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
if (mode === Select.SECRET_COMBOBOX_MODE_DO_NOT_USE) {
|
||||
return 'combobox';
|
||||
}
|
||||
|
||||
return mode;
|
||||
};
|
||||
|
||||
renderSelect = ({
|
||||
const InternalSelect = <VT extends SelectValue = SelectValue>(
|
||||
{
|
||||
prefixCls: customizePrefixCls,
|
||||
bordered = true,
|
||||
className,
|
||||
getPopupContainer,
|
||||
dropdownClassName,
|
||||
listHeight = 256,
|
||||
listItemHeight = 24,
|
||||
size: customizeSize,
|
||||
notFoundContent,
|
||||
transitionName = 'slide-up',
|
||||
...props
|
||||
}: SelectProps<VT>,
|
||||
ref: React.Ref<RcSelect<VT>>,
|
||||
) => {
|
||||
const {
|
||||
getPopupContainer: getContextPopupContainer,
|
||||
getPrefixCls,
|
||||
renderEmpty,
|
||||
direction,
|
||||
virtual,
|
||||
dropdownMatchSelectWidth,
|
||||
}: ConfigConsumerProps) => {
|
||||
const {
|
||||
prefixCls: customizePrefixCls,
|
||||
notFoundContent,
|
||||
className,
|
||||
size: customizeSize,
|
||||
listHeight = 256,
|
||||
listItemHeight = 24,
|
||||
getPopupContainer,
|
||||
dropdownClassName,
|
||||
bordered,
|
||||
} = this.props as InternalSelectProps<ValueType>;
|
||||
} = React.useContext(ConfigContext);
|
||||
const size = React.useContext(SizeContext);
|
||||
|
||||
const prefixCls = getPrefixCls('select', customizePrefixCls);
|
||||
const mode = this.getMode();
|
||||
const prefixCls = getPrefixCls('select', customizePrefixCls);
|
||||
|
||||
const isMultiple = mode === 'multiple' || mode === 'tags';
|
||||
const mode = React.useMemo(() => {
|
||||
const { mode: m } = props as InternalSelectProps<VT>;
|
||||
|
||||
// ===================== Empty =====================
|
||||
let mergedNotFound: React.ReactNode;
|
||||
if (notFoundContent !== undefined) {
|
||||
mergedNotFound = notFoundContent;
|
||||
} else if (mode === 'combobox') {
|
||||
mergedNotFound = null;
|
||||
} else {
|
||||
mergedNotFound = renderEmpty('Select');
|
||||
if ((m as any) === 'combobox') {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
// ===================== Icons =====================
|
||||
const { suffixIcon, itemIcon, removeIcon, clearIcon } = getIcons({
|
||||
...this.props,
|
||||
multiple: isMultiple,
|
||||
prefixCls,
|
||||
});
|
||||
if (m === SECRET_COMBOBOX_MODE_DO_NOT_USE) {
|
||||
return 'combobox';
|
||||
}
|
||||
|
||||
const selectProps = omit(this.props, [
|
||||
'prefixCls',
|
||||
'suffixIcon',
|
||||
'itemIcon',
|
||||
'removeIcon',
|
||||
'clearIcon',
|
||||
'size',
|
||||
'bordered',
|
||||
]);
|
||||
return m;
|
||||
}, [props.mode]);
|
||||
|
||||
const rcSelectRtlDropDownClassName = classNames(dropdownClassName, {
|
||||
[`${prefixCls}-dropdown-${direction}`]: direction === 'rtl',
|
||||
});
|
||||
return (
|
||||
<SizeContext.Consumer>
|
||||
{size => {
|
||||
const mergedSize = customizeSize || size;
|
||||
const mergedClassName = classNames(
|
||||
{
|
||||
[`${prefixCls}-lg`]: mergedSize === 'large',
|
||||
[`${prefixCls}-sm`]: mergedSize === 'small',
|
||||
[`${prefixCls}-rtl`]: direction === 'rtl',
|
||||
[`${prefixCls}-borderless`]: !bordered,
|
||||
},
|
||||
className,
|
||||
);
|
||||
const isMultiple = mode === 'multiple' || mode === 'tags';
|
||||
|
||||
return (
|
||||
<RcSelect<ValueType>
|
||||
ref={this.selectRef}
|
||||
virtual={virtual}
|
||||
dropdownMatchSelectWidth={dropdownMatchSelectWidth}
|
||||
{...selectProps}
|
||||
listHeight={listHeight}
|
||||
listItemHeight={listItemHeight}
|
||||
mode={mode}
|
||||
prefixCls={prefixCls}
|
||||
direction={direction}
|
||||
inputIcon={suffixIcon}
|
||||
menuItemSelectedIcon={itemIcon}
|
||||
removeIcon={removeIcon}
|
||||
clearIcon={clearIcon}
|
||||
notFoundContent={mergedNotFound}
|
||||
className={mergedClassName}
|
||||
getPopupContainer={getPopupContainer || getContextPopupContainer}
|
||||
dropdownClassName={rcSelectRtlDropDownClassName}
|
||||
/>
|
||||
);
|
||||
}}
|
||||
</SizeContext.Consumer>
|
||||
);
|
||||
};
|
||||
|
||||
render() {
|
||||
return <ConfigConsumer>{this.renderSelect}</ConfigConsumer>;
|
||||
// ===================== Empty =====================
|
||||
let mergedNotFound: React.ReactNode;
|
||||
if (notFoundContent !== undefined) {
|
||||
mergedNotFound = notFoundContent;
|
||||
} else if (mode === 'combobox') {
|
||||
mergedNotFound = null;
|
||||
} else {
|
||||
mergedNotFound = renderEmpty('Select');
|
||||
}
|
||||
|
||||
// ===================== Icons =====================
|
||||
const { suffixIcon, itemIcon, removeIcon, clearIcon } = getIcons({
|
||||
...props,
|
||||
multiple: isMultiple,
|
||||
prefixCls,
|
||||
});
|
||||
|
||||
const selectProps = omit(props, ['suffixIcon', 'itemIcon']);
|
||||
|
||||
const rcSelectRtlDropDownClassName = classNames(dropdownClassName, {
|
||||
[`${prefixCls}-dropdown-${direction}`]: direction === 'rtl',
|
||||
});
|
||||
|
||||
const mergedSize = customizeSize || size;
|
||||
const mergedClassName = classNames(
|
||||
{
|
||||
[`${prefixCls}-lg`]: mergedSize === 'large',
|
||||
[`${prefixCls}-sm`]: mergedSize === 'small',
|
||||
[`${prefixCls}-rtl`]: direction === 'rtl',
|
||||
[`${prefixCls}-borderless`]: !bordered,
|
||||
},
|
||||
className,
|
||||
);
|
||||
|
||||
return (
|
||||
<RcSelect<VT>
|
||||
ref={ref}
|
||||
virtual={virtual}
|
||||
dropdownMatchSelectWidth={dropdownMatchSelectWidth}
|
||||
{...selectProps}
|
||||
transitionName={transitionName}
|
||||
listHeight={listHeight}
|
||||
listItemHeight={listItemHeight}
|
||||
mode={mode}
|
||||
prefixCls={prefixCls}
|
||||
direction={direction}
|
||||
inputIcon={suffixIcon}
|
||||
menuItemSelectedIcon={itemIcon}
|
||||
removeIcon={removeIcon}
|
||||
clearIcon={clearIcon}
|
||||
notFoundContent={mergedNotFound}
|
||||
className={mergedClassName}
|
||||
getPopupContainer={getPopupContainer || getContextPopupContainer}
|
||||
dropdownClassName={rcSelectRtlDropDownClassName}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
const SelectRef = React.forwardRef(InternalSelect) as <VT extends SelectValue = SelectValue>(
|
||||
props: SelectProps<VT> & { ref?: React.Ref<RcSelect<VT>> },
|
||||
) => React.ReactElement;
|
||||
|
||||
type InternalSelectType = typeof SelectRef;
|
||||
|
||||
interface SelectInterface extends InternalSelectType {
|
||||
SECRET_COMBOBOX_MODE_DO_NOT_USE: string;
|
||||
Option: typeof Option;
|
||||
OptGroup: typeof OptGroup;
|
||||
}
|
||||
|
||||
const Select = SelectRef as SelectInterface;
|
||||
|
||||
Select.SECRET_COMBOBOX_MODE_DO_NOT_USE = SECRET_COMBOBOX_MODE_DO_NOT_USE;
|
||||
Select.Option = Option;
|
||||
Select.OptGroup = OptGroup;
|
||||
|
||||
export default Select;
|
||||
|
Loading…
Reference in New Issue
Block a user