@mpen/react-basic-inputs 0.1.11 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +0 -0
- package/dist/react-basic-inputs.d.ts +150 -0
- package/dist/react-basic-inputs.js +289 -0
- package/dist/react-basic-inputs.umd.cjs +291 -0
- package/package.json +33 -48
- package/dist/bundle.cjs +0 -328
- package/dist/bundle.d.ts +0 -5
- package/dist/bundle.mjs +0 -318
- package/dist/components/Input.d.ts +0 -25
- package/dist/components/RadioMenu.d.ts +0 -33
- package/dist/components/Select.d.ts +0 -33
- package/dist/components/TextArea.d.ts +0 -14
- package/dist/components/TextInput.d.ts +0 -3
- package/dist/hooks/useEvent.d.ts +0 -6
- package/dist/types/utility.d.ts +0 -31
- package/dist/util/assert.d.ts +0 -1
- package/dist/util/constants.d.ts +0 -5
- package/dist/util/format.d.ts +0 -9
- package/dist/util/key-fixer.d.ts +0 -8
- package/dist/util/resolvable.d.ts +0 -4
package/README.md
CHANGED
|
File without changes
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
import { ComponentPropsWithoutRef } from 'react';
|
|
2
|
+
import { DetailedHTMLProps } from 'react';
|
|
3
|
+
import { ElementType } from 'react';
|
|
4
|
+
import { ForwardRefExoticComponent } from 'react';
|
|
5
|
+
import { InputHTMLAttributes } from 'react';
|
|
6
|
+
import { JSX as JSX_2 } from 'react/jsx-runtime';
|
|
7
|
+
import { Key } from 'react';
|
|
8
|
+
import { ReactNode } from 'react';
|
|
9
|
+
import { RefAttributes } from 'react';
|
|
10
|
+
import { TextareaHTMLAttributes } from 'react';
|
|
11
|
+
|
|
12
|
+
declare type EventCallback<T = never> = (ev: T) => void;
|
|
13
|
+
|
|
14
|
+
declare type HtmlInputElement = HTMLElementTagNameMap['input'];
|
|
15
|
+
|
|
16
|
+
declare type HtmlSelectElement = HTMLElementTagNameMap['select'];
|
|
17
|
+
|
|
18
|
+
/** Hack to de-conflict React's HTMLInputElement vs the standard dom lib */
|
|
19
|
+
declare type HtmlTextAreaElement = HTMLElementTagNameMap['textarea'];
|
|
20
|
+
|
|
21
|
+
export declare const Input: ForwardRefExoticComponent<Omit<Omit<DetailedHTMLProps<InputHTMLAttributes<HTMLInputElement>, HTMLInputElement>, "ref">, "value" | "onChange" | "formatOnChange"> & {
|
|
22
|
+
onChange?: InputChangeEventHandler | undefined;
|
|
23
|
+
value?: string | undefined;
|
|
24
|
+
/**
|
|
25
|
+
* Function used to format value on blur.
|
|
26
|
+
*/
|
|
27
|
+
formatOnChange?: ((value: string) => string) | undefined;
|
|
28
|
+
} & RefAttributes<HTMLInputElement>>;
|
|
29
|
+
|
|
30
|
+
export declare type InputChangeEvent = {
|
|
31
|
+
value: string;
|
|
32
|
+
type: 'change';
|
|
33
|
+
timeStamp: number;
|
|
34
|
+
target: HtmlInputElement;
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
export declare type InputChangeEventHandler = EventCallback<InputChangeEvent>;
|
|
38
|
+
|
|
39
|
+
export declare type InputProps = OverrideProps<'input', {
|
|
40
|
+
onChange?: InputChangeEventHandler;
|
|
41
|
+
value?: string;
|
|
42
|
+
/**
|
|
43
|
+
* Function used to format value on blur.
|
|
44
|
+
*/
|
|
45
|
+
formatOnChange?: (value: string) => string;
|
|
46
|
+
}>;
|
|
47
|
+
|
|
48
|
+
export declare type InvalidValueToOption<T> = (value: T) => SelectOption<T>;
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Not null or undefined.
|
|
52
|
+
*/
|
|
53
|
+
declare type NonNil = {};
|
|
54
|
+
|
|
55
|
+
declare type Override<Base, Extension, DeleteKeys extends PropertyKey = never> = Omit<Base, keyof Extension | DeleteKeys> & Extension;
|
|
56
|
+
|
|
57
|
+
declare type OverrideProps<Base extends ElementType, Extension, DeleteKeys extends PropertyKey = never> = Override<ComponentPropsWithoutRef<Base>, Extension, DeleteKeys>;
|
|
58
|
+
|
|
59
|
+
export declare function RadioMenu<T extends NonNil>(menu: RadioMenuProps<T>): JSX_2.Element;
|
|
60
|
+
|
|
61
|
+
export declare type RadioMenuChangeEvent<T> = {
|
|
62
|
+
value: T;
|
|
63
|
+
index: number;
|
|
64
|
+
type: 'change';
|
|
65
|
+
timeStamp: number;
|
|
66
|
+
target: HtmlInputElement;
|
|
67
|
+
};
|
|
68
|
+
|
|
69
|
+
export declare type RadioMenuChangeEventHandler<T> = EventCallback<RadioMenuChangeEvent<T>>;
|
|
70
|
+
|
|
71
|
+
export declare type RadioMenuOption<T extends NonNil> = OverrideProps<'input', {
|
|
72
|
+
value: T;
|
|
73
|
+
text: ReactNode;
|
|
74
|
+
key?: Resolvable<Key, [RadioMenuOption<T>, number]>;
|
|
75
|
+
itemClassName?: string;
|
|
76
|
+
labelClassName?: string;
|
|
77
|
+
inputClassName?: string;
|
|
78
|
+
textClassName?: string;
|
|
79
|
+
}, 'type' | 'children' | 'checked' | 'name' | 'className'>;
|
|
80
|
+
|
|
81
|
+
export declare type RadioMenuProps<T extends NonNil> = {
|
|
82
|
+
options: RadioMenuOption<T>[];
|
|
83
|
+
value?: T | null;
|
|
84
|
+
className?: string;
|
|
85
|
+
/**
|
|
86
|
+
* Value comparison function. Defaults to {@linkcode https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is|Object.is}
|
|
87
|
+
*/
|
|
88
|
+
valueEquals?: (a: T, b: T) => boolean;
|
|
89
|
+
onChange?: RadioMenuChangeEventHandler<T>;
|
|
90
|
+
name?: string;
|
|
91
|
+
};
|
|
92
|
+
|
|
93
|
+
declare type Resolvable<TValue = unknown, TArgs extends ReadonlyArray<unknown> = []> = TValue extends any ? TValue | ((...args: TArgs) => TValue) : never;
|
|
94
|
+
|
|
95
|
+
export declare function Select<T extends NonNil>({ options, value, invalidValueOption, onChange, placeholder, ...selectAttrs }: SelectProps<T>): JSX_2.Element;
|
|
96
|
+
|
|
97
|
+
export declare interface SelectChangeEvent<T> {
|
|
98
|
+
value: T;
|
|
99
|
+
index: number;
|
|
100
|
+
type: 'change';
|
|
101
|
+
timeStamp: number;
|
|
102
|
+
target: HtmlSelectElement;
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
export declare type SelectChangeEventHandler<T> = EventCallback<SelectChangeEvent<T>>;
|
|
106
|
+
|
|
107
|
+
export declare type SelectOption<T> = OverrideProps<'option', {
|
|
108
|
+
value: T;
|
|
109
|
+
text: ReactNode;
|
|
110
|
+
key?: Resolvable<Key, [SelectOption<T>, number]>;
|
|
111
|
+
}, 'children' | 'selected'>;
|
|
112
|
+
|
|
113
|
+
export declare type SelectProps<T extends NonNil> = OverrideProps<'select', {
|
|
114
|
+
options: SelectOption<T>[];
|
|
115
|
+
value?: T | null;
|
|
116
|
+
onChange?: SelectChangeEventHandler<T>;
|
|
117
|
+
/**
|
|
118
|
+
* Function used to create an <option> when `value` cannot be found in the list of `options`.
|
|
119
|
+
* Set to `null` to disable this behavior.
|
|
120
|
+
* By default, stringifies `value`.
|
|
121
|
+
*/
|
|
122
|
+
invalidValueOption?: InvalidValueToOption<T> | null;
|
|
123
|
+
/**
|
|
124
|
+
* Text to display when `value` is nullish.
|
|
125
|
+
*/
|
|
126
|
+
placeholder?: ReactNode;
|
|
127
|
+
}, 'children' | 'defaultValue'>;
|
|
128
|
+
|
|
129
|
+
export declare const TextArea: ForwardRefExoticComponent<Omit<Omit<DetailedHTMLProps<TextareaHTMLAttributes<HTMLTextAreaElement>, HTMLTextAreaElement>, "ref">, "initialHeight"> & {
|
|
130
|
+
/** Initial/minimum height. "0" or "auto" are good choices. Defaults to "auto" */
|
|
131
|
+
initialHeight?: string | undefined;
|
|
132
|
+
} & RefAttributes<TextAreaRef>>;
|
|
133
|
+
|
|
134
|
+
export declare type TextAreaProps = OverrideProps<'textarea', {
|
|
135
|
+
/** Initial/minimum height. "0" or "auto" are good choices. Defaults to "auto" */
|
|
136
|
+
initialHeight?: string;
|
|
137
|
+
}>;
|
|
138
|
+
|
|
139
|
+
export declare type TextAreaRef = {
|
|
140
|
+
element: HtmlTextAreaElement | null;
|
|
141
|
+
adjustHeight: VoidFn;
|
|
142
|
+
};
|
|
143
|
+
|
|
144
|
+
export declare function TextInput({ formatOnChange, ...otherProps }: TextInputProps): JSX_2.Element;
|
|
145
|
+
|
|
146
|
+
export declare type TextInputProps = Omit<InputProps, 'text'>;
|
|
147
|
+
|
|
148
|
+
declare type VoidFn = () => void;
|
|
149
|
+
|
|
150
|
+
export { }
|
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
var __defProp = Object.defineProperty;
|
|
2
|
+
var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
|
|
3
|
+
var __publicField = (obj, key, value) => {
|
|
4
|
+
__defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
|
|
5
|
+
return value;
|
|
6
|
+
};
|
|
7
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
8
|
+
import { useDebugValue, useRef, useInsertionEffect, useEffect, useMemo, useCallback, createElement, forwardRef, useState, useImperativeHandle, useLayoutEffect, useId } from "react";
|
|
9
|
+
const NOOP = Object.freeze(() => {
|
|
10
|
+
});
|
|
11
|
+
function identity(x) {
|
|
12
|
+
return x;
|
|
13
|
+
}
|
|
14
|
+
let useEventHandler;
|
|
15
|
+
if (typeof window !== "undefined") {
|
|
16
|
+
useEventHandler = (callback) => {
|
|
17
|
+
useDebugValue(callback);
|
|
18
|
+
const latestRef = useRef(useEvent_shouldNotBeInvokedBeforeMount);
|
|
19
|
+
useInsertionEffect(() => {
|
|
20
|
+
latestRef.current = callback;
|
|
21
|
+
}, [callback]);
|
|
22
|
+
const stableRef = useRef(null);
|
|
23
|
+
if (!stableRef.current) {
|
|
24
|
+
stableRef.current = function() {
|
|
25
|
+
return latestRef.current.apply(this, arguments);
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
return stableRef.current;
|
|
29
|
+
};
|
|
30
|
+
} else {
|
|
31
|
+
useEventHandler = NOOP;
|
|
32
|
+
}
|
|
33
|
+
function useEvent(handler) {
|
|
34
|
+
return useEventHandler(handler);
|
|
35
|
+
}
|
|
36
|
+
function useEvent_shouldNotBeInvokedBeforeMount() {
|
|
37
|
+
throw new Error("INVALID_USE_EVENT_INVOCATION: the callback from useEvent cannot be invoked before the component has mounted.");
|
|
38
|
+
}
|
|
39
|
+
function useFirstMountState() {
|
|
40
|
+
var isFirst = useRef(true);
|
|
41
|
+
if (isFirst.current) {
|
|
42
|
+
isFirst.current = false;
|
|
43
|
+
return true;
|
|
44
|
+
}
|
|
45
|
+
return isFirst.current;
|
|
46
|
+
}
|
|
47
|
+
var useUpdateEffect = function(effect, deps) {
|
|
48
|
+
var isFirstMount = useFirstMountState();
|
|
49
|
+
useEffect(function() {
|
|
50
|
+
if (!isFirstMount) {
|
|
51
|
+
return effect();
|
|
52
|
+
}
|
|
53
|
+
}, deps);
|
|
54
|
+
};
|
|
55
|
+
function resolveValue(val, ...args) {
|
|
56
|
+
return typeof val === "function" ? val(...args) : val;
|
|
57
|
+
}
|
|
58
|
+
function defaultMakeKey(opt, idx) {
|
|
59
|
+
if (opt.key != null) {
|
|
60
|
+
return resolveValue(opt.key, opt, idx);
|
|
61
|
+
} else if (typeof opt.value === "string" || typeof opt.value === "number") {
|
|
62
|
+
return opt.value;
|
|
63
|
+
}
|
|
64
|
+
return idx;
|
|
65
|
+
}
|
|
66
|
+
class KeyFixer {
|
|
67
|
+
constructor() {
|
|
68
|
+
__publicField(this, "usedKeys", /* @__PURE__ */ new Map());
|
|
69
|
+
}
|
|
70
|
+
fix(opt, idx) {
|
|
71
|
+
let fixedKey = defaultMakeKey(opt, idx);
|
|
72
|
+
for (; ; ) {
|
|
73
|
+
let suffix = this.usedKeys.get(fixedKey);
|
|
74
|
+
if (suffix === void 0) {
|
|
75
|
+
this.usedKeys.set(fixedKey, 1);
|
|
76
|
+
break;
|
|
77
|
+
}
|
|
78
|
+
this.usedKeys.set(fixedKey, ++suffix);
|
|
79
|
+
fixedKey = `${fixedKey}(${suffix})`;
|
|
80
|
+
}
|
|
81
|
+
return fixedKey;
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
const defaultMakeInvalidValueOption = (value) => ({
|
|
85
|
+
value,
|
|
86
|
+
text: String(value),
|
|
87
|
+
disabled: true,
|
|
88
|
+
key: INVALID_OPTION_KEY
|
|
89
|
+
});
|
|
90
|
+
const PLACEHOLDER_KEY = "3c9369b7-0a5e-46ea-93c2-e8b9fec67fdb";
|
|
91
|
+
const INVALID_OPTION_KEY = "1a53f789-77f5-4ce6-a829-b00e563f1ee8";
|
|
92
|
+
function Select({
|
|
93
|
+
options,
|
|
94
|
+
value,
|
|
95
|
+
invalidValueOption = defaultMakeInvalidValueOption,
|
|
96
|
+
onChange,
|
|
97
|
+
placeholder,
|
|
98
|
+
...selectAttrs
|
|
99
|
+
}) {
|
|
100
|
+
const isNotSelected = value == null;
|
|
101
|
+
const isValid = useMemo(() => value != null && options.some((o) => o.value == value), [options, value]);
|
|
102
|
+
const extraOption = useMemo(() => {
|
|
103
|
+
if (value == null || !invalidValueOption)
|
|
104
|
+
return null;
|
|
105
|
+
return invalidValueOption(value);
|
|
106
|
+
}, [invalidValueOption, value]);
|
|
107
|
+
const fixedOptions = useMemo(() => {
|
|
108
|
+
if (isValid)
|
|
109
|
+
return options;
|
|
110
|
+
const fixedOptions2 = [...options];
|
|
111
|
+
if (isNotSelected) {
|
|
112
|
+
if (placeholder != null) {
|
|
113
|
+
fixedOptions2.unshift({ text: placeholder, hidden: true, value: null, key: PLACEHOLDER_KEY });
|
|
114
|
+
}
|
|
115
|
+
} else if (extraOption) {
|
|
116
|
+
fixedOptions2.push(extraOption);
|
|
117
|
+
}
|
|
118
|
+
return fixedOptions2;
|
|
119
|
+
}, [isValid, options, isNotSelected, extraOption, placeholder]);
|
|
120
|
+
const handleChange = useEvent((ev) => {
|
|
121
|
+
const idx = ev.target.selectedIndex;
|
|
122
|
+
const opt = fixedOptions[idx];
|
|
123
|
+
onChange == null ? void 0 : onChange({
|
|
124
|
+
value: opt.value,
|
|
125
|
+
// option: opt,
|
|
126
|
+
// event: ev,
|
|
127
|
+
index: idx,
|
|
128
|
+
type: "change",
|
|
129
|
+
timeStamp: ev.timeStamp,
|
|
130
|
+
target: ev.target
|
|
131
|
+
});
|
|
132
|
+
});
|
|
133
|
+
const ref = useRef(null);
|
|
134
|
+
const refreshSelectedIndex = useCallback(() => {
|
|
135
|
+
if (!ref.current)
|
|
136
|
+
return;
|
|
137
|
+
if (ref.current.selectedIndex < 0 || fixedOptions[ref.current.selectedIndex].value != value) {
|
|
138
|
+
ref.current.selectedIndex = fixedOptions.findIndex((opt) => opt.value == value);
|
|
139
|
+
}
|
|
140
|
+
}, [fixedOptions, value]);
|
|
141
|
+
const setRef = (el) => {
|
|
142
|
+
ref.current = el;
|
|
143
|
+
refreshSelectedIndex();
|
|
144
|
+
};
|
|
145
|
+
useUpdateEffect(() => {
|
|
146
|
+
refreshSelectedIndex();
|
|
147
|
+
}, [refreshSelectedIndex]);
|
|
148
|
+
const fixer = new KeyFixer();
|
|
149
|
+
return /* @__PURE__ */ jsx("select", { ...selectAttrs, onChange: handleChange, ref: setRef, children: fixedOptions.map((opt, idx) => {
|
|
150
|
+
const { value: value2, text, key, ...optAttrs } = opt;
|
|
151
|
+
const fixedKey = fixer.fix(opt, idx);
|
|
152
|
+
return /* @__PURE__ */ createElement("option", { ...optAttrs, key: fixedKey, value: fixedKey }, opt.text);
|
|
153
|
+
}) });
|
|
154
|
+
}
|
|
155
|
+
function collapseWhitespace(str) {
|
|
156
|
+
if (!str)
|
|
157
|
+
return "";
|
|
158
|
+
return String(str).replace(/\s+/gu, " ").trim();
|
|
159
|
+
}
|
|
160
|
+
const Input = forwardRef(function Input2({ value = "", onChange, onInput, onBlur, formatOnChange = identity, ...otherProps }, ref) {
|
|
161
|
+
const [currentValue, setCurrentValue] = useState(value);
|
|
162
|
+
const lastValue = useRef(value);
|
|
163
|
+
const modified = useRef(false);
|
|
164
|
+
useUpdateEffect(() => {
|
|
165
|
+
setCurrentValue(value);
|
|
166
|
+
modified.current = false;
|
|
167
|
+
lastValue.current = value;
|
|
168
|
+
}, [value]);
|
|
169
|
+
const props = {
|
|
170
|
+
type: "text",
|
|
171
|
+
...otherProps,
|
|
172
|
+
value: currentValue,
|
|
173
|
+
onChange: (ev) => {
|
|
174
|
+
setCurrentValue(ev.target.value);
|
|
175
|
+
},
|
|
176
|
+
// TODO: fire a change event onPaste ?
|
|
177
|
+
// formatOnPaste?
|
|
178
|
+
onInput: (ev) => {
|
|
179
|
+
modified.current = true;
|
|
180
|
+
onInput == null ? void 0 : onInput(ev);
|
|
181
|
+
},
|
|
182
|
+
onBlur: (ev) => {
|
|
183
|
+
const formattedValue = formatOnChange(currentValue);
|
|
184
|
+
if (modified.current) {
|
|
185
|
+
if (formattedValue !== lastValue.current) {
|
|
186
|
+
onChange == null ? void 0 : onChange({
|
|
187
|
+
type: "change",
|
|
188
|
+
value: formattedValue,
|
|
189
|
+
timeStamp: ev.timeStamp,
|
|
190
|
+
target: ev.target
|
|
191
|
+
});
|
|
192
|
+
lastValue.current = formattedValue;
|
|
193
|
+
}
|
|
194
|
+
if (formattedValue !== ev.target.value) {
|
|
195
|
+
setCurrentValue(formattedValue);
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
onBlur == null ? void 0 : onBlur(ev);
|
|
199
|
+
}
|
|
200
|
+
};
|
|
201
|
+
return /* @__PURE__ */ jsx("input", { ...props, ref });
|
|
202
|
+
});
|
|
203
|
+
function TextInput({ formatOnChange = collapseWhitespace, ...otherProps }) {
|
|
204
|
+
return /* @__PURE__ */ jsx(Input, { formatOnChange, ...otherProps, type: "text" });
|
|
205
|
+
}
|
|
206
|
+
const TextArea = forwardRef(function TextArea2({
|
|
207
|
+
onInput,
|
|
208
|
+
style,
|
|
209
|
+
initialHeight = "auto",
|
|
210
|
+
...rest
|
|
211
|
+
}, fwdRef) {
|
|
212
|
+
const ref = useRef(null);
|
|
213
|
+
const [height, setHeight] = useState(initialHeight);
|
|
214
|
+
const adjustHeight = useCallback(() => {
|
|
215
|
+
const textarea = ref.current;
|
|
216
|
+
if (!textarea)
|
|
217
|
+
return;
|
|
218
|
+
textarea.style.height = initialHeight;
|
|
219
|
+
const newHeight = `${textarea.scrollHeight}px`;
|
|
220
|
+
setHeight(newHeight);
|
|
221
|
+
textarea.style.height = newHeight;
|
|
222
|
+
}, [initialHeight]);
|
|
223
|
+
useImperativeHandle(fwdRef, () => ({
|
|
224
|
+
element: ref.current,
|
|
225
|
+
adjustHeight
|
|
226
|
+
}), [adjustHeight]);
|
|
227
|
+
const input = useEventHandler((ev) => {
|
|
228
|
+
adjustHeight();
|
|
229
|
+
onInput == null ? void 0 : onInput(ev);
|
|
230
|
+
});
|
|
231
|
+
useLayoutEffect(() => {
|
|
232
|
+
adjustHeight();
|
|
233
|
+
const textarea = ref.current;
|
|
234
|
+
if (!textarea)
|
|
235
|
+
return;
|
|
236
|
+
const resizeObserver = new ResizeObserver((_entries) => {
|
|
237
|
+
adjustHeight();
|
|
238
|
+
});
|
|
239
|
+
resizeObserver.observe(textarea);
|
|
240
|
+
return () => {
|
|
241
|
+
resizeObserver.unobserve(textarea);
|
|
242
|
+
};
|
|
243
|
+
}, [adjustHeight]);
|
|
244
|
+
return /* @__PURE__ */ jsx("textarea", { ...rest, style: {
|
|
245
|
+
overflow: "hidden",
|
|
246
|
+
// these 2 styles aren't needed if the caller sets them in CSS.
|
|
247
|
+
resize: "none",
|
|
248
|
+
...style,
|
|
249
|
+
height
|
|
250
|
+
}, onInput: input, ref });
|
|
251
|
+
});
|
|
252
|
+
function RadioMenu(menu) {
|
|
253
|
+
const defaultId = useId();
|
|
254
|
+
const name = menu.name ?? defaultId;
|
|
255
|
+
const eq = menu.valueEquals ?? Object.is;
|
|
256
|
+
const fixedOptions = menu.options ?? [];
|
|
257
|
+
const fixer = new KeyFixer();
|
|
258
|
+
const onChange = useEventHandler((ev) => {
|
|
259
|
+
const selectedIndex = Number(ev.target.value);
|
|
260
|
+
const selectedOption = fixedOptions[selectedIndex];
|
|
261
|
+
if (selectedOption != null && menu.onChange != null) {
|
|
262
|
+
menu.onChange({
|
|
263
|
+
value: selectedOption.value,
|
|
264
|
+
index: selectedIndex,
|
|
265
|
+
type: "change",
|
|
266
|
+
timeStamp: ev.timeStamp,
|
|
267
|
+
target: ev.target
|
|
268
|
+
});
|
|
269
|
+
}
|
|
270
|
+
});
|
|
271
|
+
return /* @__PURE__ */ jsx("ul", { className: menu.className, children: fixedOptions.map((opt, idx) => {
|
|
272
|
+
const { value, text, key, itemClassName, labelClassName, inputClassName, textClassName, ...rest } = opt;
|
|
273
|
+
const fixedKey = fixer.fix(opt, idx);
|
|
274
|
+
if (menu.value !== void 0) {
|
|
275
|
+
rest.checked = eq(value, menu.value);
|
|
276
|
+
}
|
|
277
|
+
return /* @__PURE__ */ jsx("li", { className: itemClassName, "aria-disabled": rest.disabled, children: /* @__PURE__ */ jsxs("label", { className: labelClassName, children: [
|
|
278
|
+
/* @__PURE__ */ jsx("input", { ...rest, className: inputClassName, value: idx, onChange, name, type: "radio" }),
|
|
279
|
+
/* @__PURE__ */ jsx("span", { className: textClassName, children: text })
|
|
280
|
+
] }) }, fixedKey);
|
|
281
|
+
}) });
|
|
282
|
+
}
|
|
283
|
+
export {
|
|
284
|
+
Input,
|
|
285
|
+
RadioMenu,
|
|
286
|
+
Select,
|
|
287
|
+
TextArea,
|
|
288
|
+
TextInput
|
|
289
|
+
};
|