@choice-ui/react 2.0.1 → 2.0.2
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/dist/components/button/dist/index.js +7 -0
- package/dist/components/checkbox/dist/index.d.ts +10 -1
- package/dist/components/checkbox/dist/index.js +49 -5
- package/dist/components/colors/dist/index.d.ts +39 -6
- package/dist/components/colors/src/color-image-paint/color-image-paint.js +2 -2
- package/dist/components/command/dist/index.d.ts +13 -0
- package/dist/components/dropdown/dist/index.d.ts +6 -0
- package/dist/components/dropdown/dist/index.js +20 -10
- package/dist/components/emoji-picker/dist/index.d.ts +29 -1
- package/dist/components/emoji-picker/dist/index.js +144 -42
- package/dist/components/form/src/adapters/range-adapter.js +2 -2
- package/dist/components/icon-button/dist/index.d.ts +1 -1
- package/dist/components/icon-button/dist/index.js +39 -0
- package/dist/components/list/dist/index.d.ts +1 -1
- package/dist/components/md-render/src/md-render.js +4 -0
- package/dist/components/md-render/src/types.d.ts +3 -0
- package/dist/components/menus/dist/index.d.ts +5 -0
- package/dist/components/menus/dist/index.js +32 -3
- package/dist/components/numeric-input/dist/index.d.ts +2 -0
- package/dist/components/numeric-input/dist/index.js +64 -24
- package/dist/components/numeric-input/src/hooks/use-input-interactions.d.ts +3 -1
- package/dist/components/numeric-input/src/hooks/use-input-interactions.js +7 -3
- package/dist/components/numeric-input/src/hooks/use-numeric-input.js +15 -4
- package/dist/components/numeric-input/src/numeric-input.js +5 -4
- package/dist/components/numeric-input/src/utils/value-comparator.js +1 -5
- package/dist/components/radio/dist/index.d.ts +9 -1
- package/dist/components/radio/dist/index.js +50 -6
- package/dist/components/range/dist/index.d.ts +276 -20
- package/dist/components/range/dist/index.js +1030 -602
- package/dist/components/scroll-area/dist/index.d.ts +4 -27
- package/dist/components/scroll-area/dist/index.js +96 -123
- package/dist/components/textarea/dist/index.js +3 -1
- package/dist/components/tooltip/dist/index.d.ts +2 -0
- package/dist/components/tooltip/dist/index.js +23 -5
- package/dist/components/virtual-select/dist/index.d.ts +48 -0
- package/package.json +19 -31
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Tooltip } from "../../tooltip/dist/index.js";
|
|
2
|
-
import { forwardRef, useRef, useState, useMemo, createContext, cloneElement, memo,
|
|
2
|
+
import { forwardRef, useRef, useState, useMemo, createContext, cloneElement, memo, useCallback, useEffect, Children, isValidElement, useContext } from "react";
|
|
3
3
|
import { useEventCallback } from "usehooks-ts";
|
|
4
4
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
5
5
|
import { IconButton } from "../../icon-button/dist/index.js";
|
|
@@ -774,9 +774,6 @@ function compareNumberResults(result1, result2) {
|
|
|
774
774
|
const isSameObject = compareNumericObjects(result1.object, result2.object);
|
|
775
775
|
return isSameArray || isSameObject;
|
|
776
776
|
}
|
|
777
|
-
function isExpressionInput(displayValue, processedValue) {
|
|
778
|
-
return displayValue !== processedValue.string;
|
|
779
|
-
}
|
|
780
777
|
function useInputInteractions({
|
|
781
778
|
inputRef,
|
|
782
779
|
displayValue,
|
|
@@ -787,6 +784,7 @@ function useInputInteractions({
|
|
|
787
784
|
min,
|
|
788
785
|
max,
|
|
789
786
|
decimal,
|
|
787
|
+
defaultValue,
|
|
790
788
|
disabled,
|
|
791
789
|
readOnly,
|
|
792
790
|
innerValue,
|
|
@@ -794,11 +792,14 @@ function useInputInteractions({
|
|
|
794
792
|
updateValue,
|
|
795
793
|
getCurrentStep,
|
|
796
794
|
onChange,
|
|
795
|
+
onRawInputEditingChange,
|
|
797
796
|
onEmpty,
|
|
798
797
|
value
|
|
799
798
|
}) {
|
|
800
799
|
const initialValueRef = useRef("");
|
|
800
|
+
const outputShapeSource = value ?? defaultValue;
|
|
801
801
|
const handleInputChange = useEventCallback((e) => {
|
|
802
|
+
onRawInputEditingChange == null ? void 0 : onRawInputEditingChange(true);
|
|
802
803
|
setDisplayValue(e.target.value);
|
|
803
804
|
});
|
|
804
805
|
const handleInputFocus = useEventCallback((e) => {
|
|
@@ -807,6 +808,7 @@ function useInputInteractions({
|
|
|
807
808
|
e.target.select();
|
|
808
809
|
});
|
|
809
810
|
const handleInputBlur = useEventCallback(() => {
|
|
811
|
+
onRawInputEditingChange == null ? void 0 : onRawInputEditingChange(false);
|
|
810
812
|
setIsFocused(false);
|
|
811
813
|
if (disabled || readOnly) return;
|
|
812
814
|
try {
|
|
@@ -817,7 +819,6 @@ function useInputInteractions({
|
|
|
817
819
|
min,
|
|
818
820
|
decimal
|
|
819
821
|
});
|
|
820
|
-
const isExpressionInputValue = isExpressionInput(displayValue, valuePre);
|
|
821
822
|
const isSameValue = compareNumberResults(innerValue, valuePre);
|
|
822
823
|
if (isSameValue) {
|
|
823
824
|
setDisplayValue(valuePre.string);
|
|
@@ -826,7 +827,7 @@ function useInputInteractions({
|
|
|
826
827
|
}
|
|
827
828
|
setValue(valuePre);
|
|
828
829
|
onChange == null ? void 0 : onChange(
|
|
829
|
-
typeof
|
|
830
|
+
typeof outputShapeSource === "string" ? valuePre.string : typeof outputShapeSource === "number" ? valuePre.array[0] : Array.isArray(outputShapeSource) ? valuePre.array : valuePre.object,
|
|
830
831
|
valuePre
|
|
831
832
|
);
|
|
832
833
|
setDisplayValue(valuePre.string);
|
|
@@ -919,11 +920,16 @@ function useNumericInput(props) {
|
|
|
919
920
|
step = 1,
|
|
920
921
|
value,
|
|
921
922
|
onChange,
|
|
923
|
+
onChangeEnd,
|
|
922
924
|
onEmpty,
|
|
923
925
|
onPressEnd,
|
|
924
926
|
onPressStart
|
|
925
927
|
} = props;
|
|
926
928
|
const innerRef = useRef(null);
|
|
929
|
+
const dragHasChangedRef = useRef(false);
|
|
930
|
+
const dragEndValueRef = useRef(void 0);
|
|
931
|
+
const dragEndDetailRef = useRef(void 0);
|
|
932
|
+
const hasPendingRawInputRef = useRef(false);
|
|
927
933
|
const [isFocused, setIsFocused] = useState(false);
|
|
928
934
|
const [displayValue, setDisplayValue] = useState("");
|
|
929
935
|
const { shiftPressed, metaPressed } = useModifierKeys(disabled);
|
|
@@ -941,9 +947,16 @@ function useNumericInput(props) {
|
|
|
941
947
|
defaultValue: defaultValuePre,
|
|
942
948
|
allowEmpty: true
|
|
943
949
|
});
|
|
950
|
+
const outputShapeSource = value ?? defaultValue;
|
|
951
|
+
const mapResultToOutputValue = useCallback(
|
|
952
|
+
(result) => typeof outputShapeSource === "string" ? result.string : typeof outputShapeSource === "number" ? result.array[0] : Array.isArray(outputShapeSource) ? result.array : result.object,
|
|
953
|
+
[outputShapeSource]
|
|
954
|
+
);
|
|
944
955
|
useEffect(() => {
|
|
945
956
|
if (!innerValue) {
|
|
946
|
-
|
|
957
|
+
if (!hasPendingRawInputRef.current) {
|
|
958
|
+
setDisplayValue("");
|
|
959
|
+
}
|
|
947
960
|
return;
|
|
948
961
|
}
|
|
949
962
|
const valuePre2 = dealWithNumericInputValue({
|
|
@@ -956,11 +969,14 @@ function useNumericInput(props) {
|
|
|
956
969
|
if (JSON.stringify(valuePre2.object) !== JSON.stringify(innerValue.object)) {
|
|
957
970
|
setValue(valuePre2);
|
|
958
971
|
}
|
|
959
|
-
|
|
972
|
+
if (!hasPendingRawInputRef.current) {
|
|
973
|
+
setDisplayValue(valuePre2.string);
|
|
974
|
+
}
|
|
960
975
|
}, [innerValue, expression, max, min, decimal, setValue]);
|
|
961
976
|
const updateValue = useCallback(
|
|
962
|
-
(updateFn) => {
|
|
977
|
+
(updateFn, options) => {
|
|
963
978
|
if (disabled || readOnly) return;
|
|
979
|
+
hasPendingRawInputRef.current = false;
|
|
964
980
|
setValue((prev) => {
|
|
965
981
|
if (!prev) {
|
|
966
982
|
const initialValue = dealWithNumericInputValue({
|
|
@@ -971,10 +987,13 @@ function useNumericInput(props) {
|
|
|
971
987
|
min,
|
|
972
988
|
decimal
|
|
973
989
|
});
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
990
|
+
const nextValue = mapResultToOutputValue(initialValue);
|
|
991
|
+
onChange == null ? void 0 : onChange(nextValue, initialValue);
|
|
992
|
+
if ((options == null ? void 0 : options.source) === "drag") {
|
|
993
|
+
dragHasChangedRef.current = true;
|
|
994
|
+
dragEndValueRef.current = nextValue;
|
|
995
|
+
dragEndDetailRef.current = initialValue;
|
|
996
|
+
}
|
|
978
997
|
return initialValue;
|
|
979
998
|
}
|
|
980
999
|
const valuePre2 = dealWithNumericInputValue({
|
|
@@ -998,15 +1017,18 @@ function useNumericInput(props) {
|
|
|
998
1017
|
return true;
|
|
999
1018
|
})();
|
|
1000
1019
|
if (hasChanged) {
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1020
|
+
const nextValue = mapResultToOutputValue(valuePre2);
|
|
1021
|
+
onChange == null ? void 0 : onChange(nextValue, valuePre2);
|
|
1022
|
+
if ((options == null ? void 0 : options.source) === "drag") {
|
|
1023
|
+
dragHasChangedRef.current = true;
|
|
1024
|
+
dragEndValueRef.current = nextValue;
|
|
1025
|
+
dragEndDetailRef.current = valuePre2;
|
|
1026
|
+
}
|
|
1005
1027
|
}
|
|
1006
1028
|
return valuePre2;
|
|
1007
1029
|
});
|
|
1008
1030
|
},
|
|
1009
|
-
[disabled, readOnly, setValue, max, min, decimal, onChange,
|
|
1031
|
+
[disabled, readOnly, setValue, max, min, decimal, onChange, expressionRef, mapResultToOutputValue]
|
|
1010
1032
|
);
|
|
1011
1033
|
const { inputHandlers } = useInputInteractions({
|
|
1012
1034
|
inputRef: innerRef,
|
|
@@ -1018,6 +1040,7 @@ function useNumericInput(props) {
|
|
|
1018
1040
|
min,
|
|
1019
1041
|
max,
|
|
1020
1042
|
decimal,
|
|
1043
|
+
defaultValue,
|
|
1021
1044
|
disabled,
|
|
1022
1045
|
readOnly,
|
|
1023
1046
|
innerValue,
|
|
@@ -1025,12 +1048,18 @@ function useNumericInput(props) {
|
|
|
1025
1048
|
updateValue,
|
|
1026
1049
|
getCurrentStep,
|
|
1027
1050
|
onChange,
|
|
1051
|
+
onRawInputEditingChange: (editing) => {
|
|
1052
|
+
hasPendingRawInputRef.current = editing;
|
|
1053
|
+
},
|
|
1028
1054
|
onEmpty,
|
|
1029
1055
|
value
|
|
1030
1056
|
});
|
|
1031
1057
|
const { isPressed: handlerPressed, pressMoveProps } = usePressMove({
|
|
1032
1058
|
disabled,
|
|
1033
1059
|
onPressStart: (e) => {
|
|
1060
|
+
dragHasChangedRef.current = false;
|
|
1061
|
+
dragEndValueRef.current = void 0;
|
|
1062
|
+
dragEndDetailRef.current = void 0;
|
|
1034
1063
|
const wasFocused = isFocused;
|
|
1035
1064
|
if (onPressStart && "nativeEvent" in e) {
|
|
1036
1065
|
onPressStart(e.nativeEvent);
|
|
@@ -1056,12 +1085,18 @@ function useNumericInput(props) {
|
|
|
1056
1085
|
onPressEnd(e.nativeEvent);
|
|
1057
1086
|
}
|
|
1058
1087
|
onPressEnd == null ? void 0 : onPressEnd(e);
|
|
1088
|
+
if (dragHasChangedRef.current && dragEndValueRef.current !== void 0 && dragEndDetailRef.current !== void 0) {
|
|
1089
|
+
onChangeEnd == null ? void 0 : onChangeEnd(dragEndValueRef.current, dragEndDetailRef.current);
|
|
1090
|
+
}
|
|
1091
|
+
dragHasChangedRef.current = false;
|
|
1092
|
+
dragEndValueRef.current = void 0;
|
|
1093
|
+
dragEndDetailRef.current = void 0;
|
|
1059
1094
|
},
|
|
1060
1095
|
onPressMoveLeft: (delta) => {
|
|
1061
|
-
updateValue((value2) => value2 - delta * getCurrentStep());
|
|
1096
|
+
updateValue((value2) => value2 - delta * getCurrentStep(), { source: "drag" });
|
|
1062
1097
|
},
|
|
1063
1098
|
onPressMoveRight: (delta) => {
|
|
1064
|
-
updateValue((value2) => value2 + delta * getCurrentStep());
|
|
1099
|
+
updateValue((value2) => value2 + delta * getCurrentStep(), { source: "drag" });
|
|
1065
1100
|
}
|
|
1066
1101
|
});
|
|
1067
1102
|
const inputProps = {
|
|
@@ -1104,6 +1139,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1104
1139
|
selected = false,
|
|
1105
1140
|
tooltip,
|
|
1106
1141
|
onChange,
|
|
1142
|
+
onChangeEnd,
|
|
1107
1143
|
onEmpty,
|
|
1108
1144
|
onPressEnd,
|
|
1109
1145
|
onPressStart,
|
|
@@ -1127,6 +1163,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1127
1163
|
step,
|
|
1128
1164
|
value,
|
|
1129
1165
|
onChange,
|
|
1166
|
+
onChangeEnd,
|
|
1130
1167
|
onEmpty,
|
|
1131
1168
|
onPressEnd,
|
|
1132
1169
|
onPressStart,
|
|
@@ -1134,6 +1171,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1134
1171
|
});
|
|
1135
1172
|
const { disableScrollProps } = useDisableScroll({ ref: inputRef });
|
|
1136
1173
|
const [isFocused, setIsFocused] = useState(false);
|
|
1174
|
+
const mergedFocused = focused || isFocused;
|
|
1137
1175
|
const handleFocus = useEventCallback((e) => {
|
|
1138
1176
|
var _a;
|
|
1139
1177
|
onIsEditingChange == null ? void 0 : onIsEditingChange(true);
|
|
@@ -1156,7 +1194,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1156
1194
|
disabled,
|
|
1157
1195
|
readOnly,
|
|
1158
1196
|
selected,
|
|
1159
|
-
focused,
|
|
1197
|
+
focused: mergedFocused,
|
|
1160
1198
|
handlerPressed,
|
|
1161
1199
|
// Configuration
|
|
1162
1200
|
min,
|
|
@@ -1167,6 +1205,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1167
1205
|
expression,
|
|
1168
1206
|
// Event handling methods
|
|
1169
1207
|
onChange,
|
|
1208
|
+
onChangeEnd,
|
|
1170
1209
|
onEmpty,
|
|
1171
1210
|
onPressStart,
|
|
1172
1211
|
onPressEnd,
|
|
@@ -1182,7 +1221,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1182
1221
|
disabled,
|
|
1183
1222
|
readOnly,
|
|
1184
1223
|
selected,
|
|
1185
|
-
|
|
1224
|
+
mergedFocused,
|
|
1186
1225
|
handlerPressed,
|
|
1187
1226
|
min,
|
|
1188
1227
|
max,
|
|
@@ -1191,6 +1230,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1191
1230
|
decimal,
|
|
1192
1231
|
expression,
|
|
1193
1232
|
onChange,
|
|
1233
|
+
onChangeEnd,
|
|
1194
1234
|
onEmpty,
|
|
1195
1235
|
onPressStart,
|
|
1196
1236
|
onPressEnd,
|
|
@@ -1234,7 +1274,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1234
1274
|
variant,
|
|
1235
1275
|
size,
|
|
1236
1276
|
selected: selected || handlerPressed,
|
|
1237
|
-
focused,
|
|
1277
|
+
focused: mergedFocused,
|
|
1238
1278
|
disabled,
|
|
1239
1279
|
prefixElement: !!prefixNode,
|
|
1240
1280
|
suffixElement: !!suffixNode,
|
|
@@ -1277,7 +1317,7 @@ var NumericInputBase = forwardRef((props, ref) => {
|
|
|
1277
1317
|
variableNode && cloneElement(variableNode, { hasPrefixElement: !!prefixNode }),
|
|
1278
1318
|
actionPromptNode && cloneElement(actionPromptNode),
|
|
1279
1319
|
suffixNode && cloneElement(suffixNode, { position: "suffix" }),
|
|
1280
|
-
tooltip && !
|
|
1320
|
+
tooltip && !mergedFocused && /* @__PURE__ */ jsx(Tooltip, { ...tooltip, children: /* @__PURE__ */ jsx(
|
|
1281
1321
|
"span",
|
|
1282
1322
|
{
|
|
1283
1323
|
tabIndex: -1,
|
|
@@ -2,6 +2,7 @@ import { default as React, RefObject } from 'react';
|
|
|
2
2
|
import { NumberResult, NumericInputValue } from '../types';
|
|
3
3
|
interface UseInputInteractionsProps<T extends NumericInputValue> {
|
|
4
4
|
decimal?: number;
|
|
5
|
+
defaultValue?: T;
|
|
5
6
|
disabled?: boolean;
|
|
6
7
|
displayValue: string;
|
|
7
8
|
expression: string;
|
|
@@ -12,6 +13,7 @@ interface UseInputInteractionsProps<T extends NumericInputValue> {
|
|
|
12
13
|
max?: number;
|
|
13
14
|
min?: number;
|
|
14
15
|
onChange?: (value: T, detail: NumberResult) => void;
|
|
16
|
+
onRawInputEditingChange?: (editing: boolean) => void;
|
|
15
17
|
onEmpty?: () => void;
|
|
16
18
|
readOnly?: boolean;
|
|
17
19
|
setDisplayValue: (value: string) => void;
|
|
@@ -27,7 +29,7 @@ interface UseInputInteractionsProps<T extends NumericInputValue> {
|
|
|
27
29
|
* @param props Input interaction configuration
|
|
28
30
|
* @returns Input handlers and initial value reference
|
|
29
31
|
*/
|
|
30
|
-
export declare function useInputInteractions<T extends NumericInputValue>({ inputRef, displayValue, setDisplayValue, isFocused, setIsFocused, expression, min, max, decimal, disabled, readOnly, innerValue, setValue, updateValue, getCurrentStep, onChange, onEmpty, value, }: UseInputInteractionsProps<T>): {
|
|
32
|
+
export declare function useInputInteractions<T extends NumericInputValue>({ inputRef, displayValue, setDisplayValue, isFocused, setIsFocused, expression, min, max, decimal, defaultValue, disabled, readOnly, innerValue, setValue, updateValue, getCurrentStep, onChange, onRawInputEditingChange, onEmpty, value, }: UseInputInteractionsProps<T>): {
|
|
31
33
|
inputHandlers: {
|
|
32
34
|
onChange: (e: React.ChangeEvent<HTMLInputElement>) => void;
|
|
33
35
|
onFocus: (e: React.FocusEvent<HTMLInputElement, Element>) => void;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { useRef } from "react";
|
|
2
2
|
import { useEventCallback } from "usehooks-ts";
|
|
3
3
|
import { dealWithNumericInputValue } from "../utils/numeric-value-processor.js";
|
|
4
|
-
import {
|
|
4
|
+
import { compareNumberResults } from "../utils/value-comparator.js";
|
|
5
5
|
function useInputInteractions({
|
|
6
6
|
inputRef,
|
|
7
7
|
displayValue,
|
|
@@ -12,6 +12,7 @@ function useInputInteractions({
|
|
|
12
12
|
min,
|
|
13
13
|
max,
|
|
14
14
|
decimal,
|
|
15
|
+
defaultValue,
|
|
15
16
|
disabled,
|
|
16
17
|
readOnly,
|
|
17
18
|
innerValue,
|
|
@@ -19,11 +20,14 @@ function useInputInteractions({
|
|
|
19
20
|
updateValue,
|
|
20
21
|
getCurrentStep,
|
|
21
22
|
onChange,
|
|
23
|
+
onRawInputEditingChange,
|
|
22
24
|
onEmpty,
|
|
23
25
|
value
|
|
24
26
|
}) {
|
|
25
27
|
const initialValueRef = useRef("");
|
|
28
|
+
const outputShapeSource = value ?? defaultValue;
|
|
26
29
|
const handleInputChange = useEventCallback((e) => {
|
|
30
|
+
onRawInputEditingChange == null ? void 0 : onRawInputEditingChange(true);
|
|
27
31
|
setDisplayValue(e.target.value);
|
|
28
32
|
});
|
|
29
33
|
const handleInputFocus = useEventCallback((e) => {
|
|
@@ -32,6 +36,7 @@ function useInputInteractions({
|
|
|
32
36
|
e.target.select();
|
|
33
37
|
});
|
|
34
38
|
const handleInputBlur = useEventCallback(() => {
|
|
39
|
+
onRawInputEditingChange == null ? void 0 : onRawInputEditingChange(false);
|
|
35
40
|
setIsFocused(false);
|
|
36
41
|
if (disabled || readOnly) return;
|
|
37
42
|
try {
|
|
@@ -42,7 +47,6 @@ function useInputInteractions({
|
|
|
42
47
|
min,
|
|
43
48
|
decimal
|
|
44
49
|
});
|
|
45
|
-
const isExpressionInputValue = isExpressionInput(displayValue, valuePre);
|
|
46
50
|
const isSameValue = compareNumberResults(innerValue, valuePre);
|
|
47
51
|
if (isSameValue) {
|
|
48
52
|
setDisplayValue(valuePre.string);
|
|
@@ -51,7 +55,7 @@ function useInputInteractions({
|
|
|
51
55
|
}
|
|
52
56
|
setValue(valuePre);
|
|
53
57
|
onChange == null ? void 0 : onChange(
|
|
54
|
-
typeof
|
|
58
|
+
typeof outputShapeSource === "string" ? valuePre.string : typeof outputShapeSource === "number" ? valuePre.array[0] : Array.isArray(outputShapeSource) ? valuePre.array : valuePre.object,
|
|
55
59
|
valuePre
|
|
56
60
|
);
|
|
57
61
|
setDisplayValue(valuePre.string);
|
|
@@ -30,6 +30,7 @@ function useNumericInput(props) {
|
|
|
30
30
|
const dragHasChangedRef = useRef(false);
|
|
31
31
|
const dragEndValueRef = useRef(void 0);
|
|
32
32
|
const dragEndDetailRef = useRef(void 0);
|
|
33
|
+
const hasPendingRawInputRef = useRef(false);
|
|
33
34
|
const [isFocused, setIsFocused] = useState(false);
|
|
34
35
|
const [displayValue, setDisplayValue] = useState("");
|
|
35
36
|
const { shiftPressed, metaPressed } = useModifierKeys(disabled);
|
|
@@ -47,13 +48,16 @@ function useNumericInput(props) {
|
|
|
47
48
|
defaultValue: defaultValuePre,
|
|
48
49
|
allowEmpty: true
|
|
49
50
|
});
|
|
51
|
+
const outputShapeSource = value ?? defaultValue;
|
|
50
52
|
const mapResultToOutputValue = useCallback(
|
|
51
|
-
(result) => typeof
|
|
52
|
-
[
|
|
53
|
+
(result) => typeof outputShapeSource === "string" ? result.string : typeof outputShapeSource === "number" ? result.array[0] : Array.isArray(outputShapeSource) ? result.array : result.object,
|
|
54
|
+
[outputShapeSource]
|
|
53
55
|
);
|
|
54
56
|
useEffect(() => {
|
|
55
57
|
if (!innerValue) {
|
|
56
|
-
|
|
58
|
+
if (!hasPendingRawInputRef.current) {
|
|
59
|
+
setDisplayValue("");
|
|
60
|
+
}
|
|
57
61
|
return;
|
|
58
62
|
}
|
|
59
63
|
const valuePre2 = dealWithNumericInputValue({
|
|
@@ -66,11 +70,14 @@ function useNumericInput(props) {
|
|
|
66
70
|
if (JSON.stringify(valuePre2.object) !== JSON.stringify(innerValue.object)) {
|
|
67
71
|
setValue(valuePre2);
|
|
68
72
|
}
|
|
69
|
-
|
|
73
|
+
if (!hasPendingRawInputRef.current) {
|
|
74
|
+
setDisplayValue(valuePre2.string);
|
|
75
|
+
}
|
|
70
76
|
}, [innerValue, expression, max, min, decimal, setValue]);
|
|
71
77
|
const updateValue = useCallback(
|
|
72
78
|
(updateFn, options) => {
|
|
73
79
|
if (disabled || readOnly) return;
|
|
80
|
+
hasPendingRawInputRef.current = false;
|
|
74
81
|
setValue((prev) => {
|
|
75
82
|
if (!prev) {
|
|
76
83
|
const initialValue = dealWithNumericInputValue({
|
|
@@ -134,6 +141,7 @@ function useNumericInput(props) {
|
|
|
134
141
|
min,
|
|
135
142
|
max,
|
|
136
143
|
decimal,
|
|
144
|
+
defaultValue,
|
|
137
145
|
disabled,
|
|
138
146
|
readOnly,
|
|
139
147
|
innerValue,
|
|
@@ -141,6 +149,9 @@ function useNumericInput(props) {
|
|
|
141
149
|
updateValue,
|
|
142
150
|
getCurrentStep,
|
|
143
151
|
onChange,
|
|
152
|
+
onRawInputEditingChange: (editing) => {
|
|
153
|
+
hasPendingRawInputRef.current = editing;
|
|
154
|
+
},
|
|
144
155
|
onEmpty,
|
|
145
156
|
value
|
|
146
157
|
});
|
|
@@ -67,6 +67,7 @@ const NumericInputBase = forwardRef((props, ref) => {
|
|
|
67
67
|
});
|
|
68
68
|
const { disableScrollProps } = useDisableScroll({ ref: inputRef });
|
|
69
69
|
const [isFocused, setIsFocused] = useState(false);
|
|
70
|
+
const mergedFocused = focused || isFocused;
|
|
70
71
|
const handleFocus = useEventCallback((e) => {
|
|
71
72
|
var _a;
|
|
72
73
|
onIsEditingChange == null ? void 0 : onIsEditingChange(true);
|
|
@@ -89,7 +90,7 @@ const NumericInputBase = forwardRef((props, ref) => {
|
|
|
89
90
|
disabled,
|
|
90
91
|
readOnly,
|
|
91
92
|
selected,
|
|
92
|
-
focused,
|
|
93
|
+
focused: mergedFocused,
|
|
93
94
|
handlerPressed,
|
|
94
95
|
// Configuration
|
|
95
96
|
min,
|
|
@@ -116,7 +117,7 @@ const NumericInputBase = forwardRef((props, ref) => {
|
|
|
116
117
|
disabled,
|
|
117
118
|
readOnly,
|
|
118
119
|
selected,
|
|
119
|
-
|
|
120
|
+
mergedFocused,
|
|
120
121
|
handlerPressed,
|
|
121
122
|
min,
|
|
122
123
|
max,
|
|
@@ -169,7 +170,7 @@ const NumericInputBase = forwardRef((props, ref) => {
|
|
|
169
170
|
variant,
|
|
170
171
|
size,
|
|
171
172
|
selected: selected || handlerPressed,
|
|
172
|
-
focused,
|
|
173
|
+
focused: mergedFocused,
|
|
173
174
|
disabled,
|
|
174
175
|
prefixElement: !!prefixNode,
|
|
175
176
|
suffixElement: !!suffixNode,
|
|
@@ -212,7 +213,7 @@ const NumericInputBase = forwardRef((props, ref) => {
|
|
|
212
213
|
variableNode && cloneElement(variableNode, { hasPrefixElement: !!prefixNode }),
|
|
213
214
|
actionPromptNode && cloneElement(actionPromptNode),
|
|
214
215
|
suffixNode && cloneElement(suffixNode, { position: "suffix" }),
|
|
215
|
-
tooltip && !
|
|
216
|
+
tooltip && !mergedFocused && /* @__PURE__ */ jsx(Tooltip, { ...tooltip, children: /* @__PURE__ */ jsx(
|
|
216
217
|
"span",
|
|
217
218
|
{
|
|
218
219
|
tabIndex: -1,
|
|
@@ -21,12 +21,8 @@ function compareNumberResults(result1, result2) {
|
|
|
21
21
|
const isSameObject = compareNumericObjects(result1.object, result2.object);
|
|
22
22
|
return isSameArray || isSameObject;
|
|
23
23
|
}
|
|
24
|
-
function isExpressionInput(displayValue, processedValue) {
|
|
25
|
-
return displayValue !== processedValue.string;
|
|
26
|
-
}
|
|
27
24
|
export {
|
|
28
25
|
compareNumberResults,
|
|
29
26
|
compareNumericArrays,
|
|
30
|
-
compareNumericObjects
|
|
31
|
-
isExpressionInput
|
|
27
|
+
compareNumericObjects
|
|
32
28
|
};
|
|
@@ -1,6 +1,13 @@
|
|
|
1
1
|
import { HTMLProps, ReactNode } from 'react';
|
|
2
2
|
import * as react from 'react';
|
|
3
3
|
|
|
4
|
+
interface RadioIconProps extends Omit<HTMLProps<HTMLDivElement>, "children"> {
|
|
5
|
+
children?: ReactNode | ((props: {
|
|
6
|
+
value?: boolean;
|
|
7
|
+
}) => ReactNode);
|
|
8
|
+
}
|
|
9
|
+
declare const RadioIcon: react.MemoExoticComponent<react.ForwardRefExoticComponent<Omit<RadioIconProps, "ref"> & react.RefAttributes<HTMLDivElement>>>;
|
|
10
|
+
|
|
4
11
|
interface RadioLabelProps extends Omit<HTMLProps<HTMLLabelElement>, "htmlFor" | "id" | "disabled"> {
|
|
5
12
|
children: ReactNode;
|
|
6
13
|
}
|
|
@@ -19,6 +26,7 @@ interface RadioType {
|
|
|
19
26
|
(props: RadioProps & {
|
|
20
27
|
ref?: React.Ref<HTMLInputElement>;
|
|
21
28
|
}): JSX.Element;
|
|
29
|
+
Icon: typeof RadioIcon;
|
|
22
30
|
Label: typeof RadioLabel;
|
|
23
31
|
displayName?: string;
|
|
24
32
|
}
|
|
@@ -50,4 +58,4 @@ interface RadioGroupType {
|
|
|
50
58
|
}
|
|
51
59
|
declare const RadioGroup: RadioGroupType;
|
|
52
60
|
|
|
53
|
-
export { Radio, RadioGroup, type RadioGroupProps, type RadioProps };
|
|
61
|
+
export { Radio, RadioGroup, type RadioGroupProps, type RadioIconProps, type RadioLabelProps, type RadioProps };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Dot } from "@choiceform/icons-react";
|
|
2
|
-
import { memo, forwardRef, useId, useMemo, createContext, useContext } from "react";
|
|
2
|
+
import { memo, forwardRef, useId, useMemo, createContext, useContext, Children, isValidElement } from "react";
|
|
3
3
|
import { useEventCallback } from "usehooks-ts";
|
|
4
4
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
5
5
|
import { tcx, tcv } from "../../../shared/utils/tcx/tcx.js";
|
|
@@ -145,6 +145,38 @@ var radioTv = tcv({
|
|
|
145
145
|
focused: false
|
|
146
146
|
}
|
|
147
147
|
});
|
|
148
|
+
var RadioIcon = memo(
|
|
149
|
+
forwardRef(function RadioIcon2(props, ref) {
|
|
150
|
+
const { className, children, ...rest } = props;
|
|
151
|
+
const { value, disabled, variant } = useRadioContext();
|
|
152
|
+
const tv = radioTv({
|
|
153
|
+
type: "radio",
|
|
154
|
+
variant,
|
|
155
|
+
disabled,
|
|
156
|
+
checked: value
|
|
157
|
+
});
|
|
158
|
+
const renderIcon = () => {
|
|
159
|
+
if (typeof children === "function") {
|
|
160
|
+
return children({ value });
|
|
161
|
+
}
|
|
162
|
+
if (children !== void 0) {
|
|
163
|
+
return children;
|
|
164
|
+
}
|
|
165
|
+
return value ? /* @__PURE__ */ jsx(Dot, {}) : null;
|
|
166
|
+
};
|
|
167
|
+
return /* @__PURE__ */ jsx(
|
|
168
|
+
"div",
|
|
169
|
+
{
|
|
170
|
+
ref,
|
|
171
|
+
className: tcx(tv.box(), className),
|
|
172
|
+
"data-active": value,
|
|
173
|
+
...rest,
|
|
174
|
+
children: renderIcon()
|
|
175
|
+
}
|
|
176
|
+
);
|
|
177
|
+
})
|
|
178
|
+
);
|
|
179
|
+
RadioIcon.displayName = "Radio.Icon";
|
|
148
180
|
var RadioLabel = memo(
|
|
149
181
|
forwardRef(function RadioLabel2(props, ref) {
|
|
150
182
|
const { children, className, ...rest } = props;
|
|
@@ -201,13 +233,24 @@ var RadioBase = forwardRef(function Radio(props, ref) {
|
|
|
201
233
|
}
|
|
202
234
|
onKeyDown == null ? void 0 : onKeyDown(e);
|
|
203
235
|
});
|
|
236
|
+
const isIconElement = (child) => {
|
|
237
|
+
var _a;
|
|
238
|
+
return isValidElement(child) && (child.type === RadioIcon || ((_a = child.type) == null ? void 0 : _a.displayName) === "Radio.Icon");
|
|
239
|
+
};
|
|
240
|
+
const childArray = Children.toArray(children);
|
|
241
|
+
const iconChild = childArray.find(isIconElement);
|
|
242
|
+
const otherChildren = childArray.filter((child) => !isIconElement(child));
|
|
204
243
|
const renderChildren = () => {
|
|
205
|
-
if (
|
|
206
|
-
|
|
244
|
+
if (otherChildren.length === 1) {
|
|
245
|
+
const child = otherChildren[0];
|
|
246
|
+
if (typeof child === "string" || typeof child === "number") {
|
|
247
|
+
return /* @__PURE__ */ jsx(RadioLabel, { children: child });
|
|
248
|
+
}
|
|
207
249
|
}
|
|
208
|
-
return
|
|
250
|
+
return otherChildren;
|
|
209
251
|
};
|
|
210
|
-
|
|
252
|
+
const renderDefaultIcon = () => /* @__PURE__ */ jsx("div", { className: tv.box(), children: value && /* @__PURE__ */ jsx(Dot, {}) });
|
|
253
|
+
return /* @__PURE__ */ jsx(RadioContext.Provider, { value: { id, descriptionId, disabled, value, variant }, children: /* @__PURE__ */ jsxs("div", { className: tcx(tv.root(), className), children: [
|
|
211
254
|
/* @__PURE__ */ jsxs("div", { className: "pointer-events-none relative", children: [
|
|
212
255
|
/* @__PURE__ */ jsx(
|
|
213
256
|
"input",
|
|
@@ -229,13 +272,14 @@ var RadioBase = forwardRef(function Radio(props, ref) {
|
|
|
229
272
|
...rest
|
|
230
273
|
}
|
|
231
274
|
),
|
|
232
|
-
|
|
275
|
+
iconChild ?? renderDefaultIcon()
|
|
233
276
|
] }),
|
|
234
277
|
renderChildren()
|
|
235
278
|
] }) });
|
|
236
279
|
});
|
|
237
280
|
var MemoizedRadio = memo(RadioBase);
|
|
238
281
|
var Radio2 = MemoizedRadio;
|
|
282
|
+
Radio2.Icon = RadioIcon;
|
|
239
283
|
Radio2.Label = RadioLabel;
|
|
240
284
|
Radio2.displayName = "Radio";
|
|
241
285
|
var RadioGroupItem = memo(
|