-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathpower-select.ts
87 lines (72 loc) · 2.62 KB
/
power-select.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
import { assert } from '@ember/debug';
import { action } from '@ember/object';
import { scheduleOnce } from '@ember/runloop';
import attachDropdown from '@upfluence/oss-components/utils/attach-dropdown';
import BaseDropdown, { type BaseDropdownArgs } from './private/base-dropdown';
type OperationType = 'selection' | 'deletion';
interface OSSPowerSelectArgs extends BaseDropdownArgs {
items: any[];
selectedItems: any[];
loading?: boolean;
loadingMore?: boolean;
placeholder?: string;
searchPlaceholder?: string;
addressableAs?: string;
onChange: (item: any, operation: OperationType) => void;
onSearch?: (keyword: string) => void;
onBottomReached?: () => void;
borderless?: boolean;
}
const DEFAULT_PLACEHOLDER = 'Select an item';
export default class OSSPowerSelect extends BaseDropdown<OSSPowerSelectArgs> {
cleanupDrodpownAutoplacement?: () => void;
get placeholder(): string {
return this.args.placeholder ?? DEFAULT_PLACEHOLDER;
}
get dropdownAddressableClass(): string {
return this.args.addressableAs ? `${this.args.addressableAs}__dropdown` : '';
}
@action
ensureBlockPresence(hasSelectedItem: boolean, hasOptionItem: boolean): void | never {
assert(`[component][OSS::PowerSelect] You must pass selected-item named block`, hasSelectedItem);
assert(`[component][OSS::PowerSelect] You must pass option-item named block`, hasOptionItem);
}
@action
onSelect(item: any): void {
this.args.onChange(item, 'selection');
}
@action
handleSelectorClose(): void {
if (!this.container.hasAttribute('open') && document.querySelector(`#${this.portalId}`)) {
document.querySelector(`#${this.portalId}`)!.remove();
this.cleanupDrodpownAutoplacement?.();
this.closeDropdown();
}
}
@action
toggleDropdown(event: MouseEvent): void {
super.toggleDropdown(event);
if (!this.isOpen) {
this.args.onSearch?.('');
return;
}
scheduleOnce('afterRender', this, () => {
const referenceTarget = this.container.querySelector('.upf-power-select__array-container');
const floatingTarget = document.querySelector(`#${this.portalId}`);
if (referenceTarget && floatingTarget) {
this.cleanupDrodpownAutoplacement = attachDropdown(
referenceTarget as HTMLElement,
floatingTarget as HTMLElement,
{ maxHeight: 300, placementStrategy: 'auto' }
);
}
});
}
@action
onClickOutside(_: HTMLElement, event: MouseEvent): void {
super.onClickOutside(_, event);
this.cleanupDrodpownAutoplacement?.();
this.args.onSearch?.('');
document.querySelector(`#${this.portalId}`)?.remove();
}
}