import { Dispatch, RefObject, SetStateAction } from 'react'; import { AutoCompleteSelector } from '@mezzanine-ui/core/autocomplete'; import { DropdownInputPosition, DropdownLoadingPosition } from '@mezzanine-ui/core/dropdown/dropdown'; import { PopperProps } from '../Popper'; import type { SelectTriggerInputProps, SelectTriggerProps } from '../Select/typings'; import { SelectValue } from '../Select/typings'; import { PickRenameMulti } from '../utils/general'; export interface AutoCompleteBaseProps extends Omit, PickRenameMulti, { options: 'popperOptions'; }> { /** * Set to true when options can be added dynamically * @default false */ addable?: boolean; /** * Whether the data is fetched asynchronously. * If true, input change will trigger loading until onSearch promise resolves. * @default false */ asyncData?: boolean; /** * Whether to clear search text when leaving the textfield/dropdown scope. * When `false`, typed text persists after blur. In `single` mode, a clearable * icon will appear if the user has typed text without selecting an option. * @default true */ clearSearchText?: boolean; /** * Characters that can be used to separate multiple items when creating. * When these characters are entered, they will trigger item creation. * @default [',', '+', '\n'] */ createSeparators?: string[]; /** * Should the filter rules be disabled (If you need to control options filter by yourself) * @default false */ disabledOptionsFilter?: boolean; /** * The text of the dropdown empty status. */ emptyText?: string; /** * The id attribute of the input element. * * @important When using with react-hook-form or native forms, this prop is recommended. */ id?: string; /** * The position of the search input relative to the dropdown. * - `'outside'`: input is always visible above the dropdown (default trigger layout). * - `'inside'`: input is rendered inside the dropdown panel; the trigger shows only * the selected value(s) and opens the dropdown on click. * @default 'outside' */ inputPosition?: DropdownInputPosition; /** * The other native props for input element. */ inputProps?: Omit; /** * Whether the dropdown is in loading state. * @default false */ loading?: boolean; /** * The text of the dropdown loading status. */ loadingText?: string; /** * The position to display the loading status. * Only takes effect when `loading` is true. * @default 'bottom' */ loadingPosition?: DropdownLoadingPosition; /** * The max height of the dropdown list. */ menuMaxHeight?: number | string; /** * The name attribute of the input element. * * @important When using with react-hook-form or native forms, this prop is recommended. * * @example With react-hook-form * ```tsx * const { register } = useForm(); * * ``` */ name?: string; /** * Callback fired when the user confirms a new item creation. * Receives the typed text and the current options array; must return the updated options array. * Use this to append the new item to your options state. * Required when `addable` is true; omitting it will disable the creation feature. */ onInsert?(text: string, currentOptions: SelectValue[]): SelectValue[]; /** * The search event handler * Can return a Promise for async data loading */ onSearch?(input: string): void | Promise; /** * Callback fired on every input change (no debounce). */ onSearchTextChange?(text: string): void; /** * Callback fired when the dropdown visibility changes. */ onVisibilityChange?: (open: boolean) => void; /** * Whether the dropdown is open (controlled). */ open?: boolean; /** * The options that mapped autocomplete options */ options: SelectValue[]; /** * select input placeholder */ placeholder?: string; /** * Whether the selection is required. * @default false */ required?: boolean; /** * The debounce time of the search event handler. * @default 300 */ searchDebounceTime?: number; /** * Imperative handle to control search text externally (e.g. reset or sync). */ searchTextControlRef?: RefObject<{ reset: () => void; setSearchText: Dispatch>; } | undefined>; /** * Whether to trim whitespace from created items. * @default true */ trimOnCreate?: boolean; /** * When true, pasted bulk text is kept in the input and user creates one item at a time * (create button shows only the first pending item; after create, input updates to remaining). * When false, pasted bulk text creates all items at once (default). * @default false */ stepByStepBulkCreate?: boolean; /** * Custom text for the create action button. * @default '建立 "{text}"' */ createActionText?: (text: string) => string; /** * Default template for the create action button text. * Use this to customize the default text format when createActionText is not provided. * The template should contain {text} placeholder which will be replaced with the actual text. * @default '建立 "{text}"' */ createActionTextTemplate?: string; /** * The z-index of the dropdown. */ dropdownZIndex?: number | string; /** * Whether to enable portal for the dropdown. * @default true */ globalPortal?: boolean; /** * Callback fired when the dropdown list reaches the bottom. * Only fires when `menuMaxHeight` is set and the list is scrollable. */ onReachBottom?: () => void; /** * Callback fired when the dropdown list leaves the bottom. * Only fires when `menuMaxHeight` is set and the list is scrollable. */ onLeaveBottom?: () => void; /** * Called when the dropdown closes (on blur or Escape) and `addable` mode has * items that were created but never selected. * Receives the cleaned options array with unselected created items already removed. * Use this to sync your options state and strip the dangling created entries. * Only called when `addable` is true and there are unselected created items. */ onRemoveCreated?(cleanedOptions: SelectValue[]): void; } export type AutoCompleteMultipleProps = AutoCompleteBaseProps & { /** * The default selection */ defaultValue?: SelectValue[]; /** * Controls the layout of trigger. */ mode: 'multiple'; /** * The change event handler of input element. */ onChange?(newOptions: SelectValue[]): void; /** * Tag overflow strategy: * - counter: collapse extra tags into a counter tag showing the remaining count. * - wrap: wrap to new lines to display all tags. * @default 'counter' * */ overflowStrategy?: 'counter' | 'wrap'; /** * The selector of input. * @default 'input' */ selector?: AutoCompleteSelector; /** * The value of selection. * @default undefined */ value?: SelectValue[]; }; export type AutoCompleteSingleProps = AutoCompleteBaseProps & { /** * The default selection */ defaultValue?: SelectValue; /** * Controls the layout of trigger. */ mode?: 'single'; /** * The change event handler of input element. */ onChange?(newOptions: SelectValue): void; /** * The selector of input. * @default 'input' */ selector?: AutoCompleteSelector; /** * The value of selection. * @default undefined */ value?: SelectValue | null; }; export type AutoCompleteProps = AutoCompleteMultipleProps | AutoCompleteSingleProps; /** * 自動完成輸入元件,在使用者輸入時即時顯示符合的下拉選項。 * * 支援 `single`(單選)與 `multiple`(多選標籤)兩種模式;`inputPosition` 控制搜尋輸入框 * 位於下拉選單外(`'outside'`,預設)或內(`'inside'`)。設定 `addable` 與 `onInsert` * 可讓使用者動態建立不在選項清單中的項目。`asyncData` 搭配 `onSearch` 可實現非同步搜尋, * 輸入時觸發 debounce 查詢並顯示 loading 狀態。若僅需從固定選項中搜尋,請改用 `Select` 元件。 * * @example * ```tsx * import AutoComplete from '@mezzanine-ui/react/AutoComplete'; * * // 單選基本用法 * * * // 多選模式 * * * // 搜尋框置於下拉選單內(inside 模式) * * * // 非同步搜尋 * { const res = await fetchOptions(text); setAsyncOptions(res); }} * value={selected} * onChange={setSelected} * /> * * // 可新增選項 * [...current, { id: text, name: text }]} * value={selectedList} * onChange={setSelectedList} * /> * ``` * * @see {@link Select} 從固定選項清單中選取時使用 * @see {@link Input} 純文字輸入欄位 * @see {@link useAutoCompleteValueControl} 管理 AutoComplete 內部值狀態的 hook */ declare const AutoComplete: import("react").ForwardRefExoticComponent>; export default AutoComplete;