diff --git a/src/__tests__/wheel-web.00.test.tsx b/src/__tests__/wheel-web.00.test.tsx
new file mode 100644
index 0000000..a0d1dd2
--- /dev/null
+++ b/src/__tests__/wheel-web.00.test.tsx
@@ -0,0 +1,82 @@
+/**
+ * - Render the *web* wheel component and simulate a drag that lands on "00".
+ * - Assert the component calls setValue(0) (a number).
+ */
+
+import React from 'react';
+import { render } from '@testing-library/react-native';
+import { PanResponder } from 'react-native';
+import WheelWeb from '../components/time-picker/wheel-web';
+import type { PickerOption } from '../types';
+
+// Helper to build options that reproduce a web bug where 00 wasn't selectable.
+const makeItems = (n = 5): PickerOption[] =>
+ Array.from({ length: n }, (_, i) => ({
+ value: i === 0 ? '00' : i, // "00", 1, 2, 3, ...
+ text: String(i).padStart(2, '0'), // "00", "01", "02", ...
+ }));
+
+describe('WheelWeb — selecting 00', () => {
+ let panSpec: any | null = null;
+
+ beforeEach(() => {
+ panSpec = null;
+ jest.spyOn(PanResponder, 'create').mockImplementation((spec: any) => {
+ panSpec = spec;
+ return { panHandlers: spec } as any;
+ });
+ });
+
+ afterEach(() => {
+ jest.restoreAllMocks();
+ });
+
+ test('emits numeric 0 when landing on "00"', () => {
+ // Build the wheel options the component will render (replicate bug condition):
+ const items = makeItems(5); // ["00", 1, 2, 3, 4]
+ const setValue = jest.fn();
+
+ render(
+
+ );
+
+ expect(panSpec).toBeTruthy(); // Sanity: confirm we captured the gesture handlers
+
+ const STEP = 28;
+ panSpec.onPanResponderGrant(); // Simulates “finger down” (gesture start).
+ panSpec.onPanResponderRelease({}, { dy: STEP }); // Simulates “finger up” after dragging by 1 row.
+
+ expect(setValue).toHaveBeenCalledTimes(1);
+ expect(setValue).toHaveBeenCalledWith(0);
+ });
+
+ test('no change when releasing on the same value (including "00")', () => {
+ const items = makeItems(5);
+ const setValue = jest.fn();
+
+ // Start already on 0 (which will match "00" thanks to Number(...))
+ render(
+
+ );
+
+ expect(panSpec).toBeTruthy();
+
+ // Release without moving (dy = 0) → should not emit anything
+ panSpec.onPanResponderGrant();
+ panSpec.onPanResponderRelease({}, { dy: 0 });
+
+ expect(setValue).not.toHaveBeenCalled();
+ });
+});
diff --git a/src/components/time-picker/wheel-web.tsx b/src/components/time-picker/wheel-web.tsx
index e74fd8b..968f60d 100644
--- a/src/components/time-picker/wheel-web.tsx
+++ b/src/components/time-picker/wheel-web.tsx
@@ -38,7 +38,10 @@ const WheelWeb = ({
const radius = height / 2;
const valueIndex = useMemo(() => {
- return items.findIndex((item) => item.value === value) || 0;
+ const idx = items.findIndex(
+ (item) => Number(item?.value) === Number(value)
+ );
+ return idx >= 0 ? idx : 0;
}, [items, value]);
const panResponder = useMemo(() => {
@@ -67,13 +70,13 @@ const WheelWeb = ({
}
}
const newValue = items[newValueIndex];
- if (newValue?.value === value) {
+ if (Number(newValue?.value) === Number(value)) {
translateY.setOffset(0);
translateY.setValue(0);
- } else if (newValue?.value) {
- setValue(newValue.value);
- } else if (items[0]?.value) {
- setValue(items[0].value);
+ } else if (newValue?.value != null) {
+ setValue(Number(newValue.value));
+ } else if (items[0]?.value != null) {
+ setValue(Number(items[0].value));
}
},
});
@@ -107,7 +110,7 @@ const WheelWeb = ({
//translateY.setValue(0);
translateY.setOffset(0);
const currentIndex = displayValues.findIndex(
- (item) => item?.value === value
+ (item) => Number(item?.value) === Number(value)
);
return displayValues && displayValues.length > 0
? displayValues.map((_, index) =>
@@ -166,7 +169,7 @@ const WheelWeb = ({
},
]
: [],
- opacity: displayValue?.value !== value ? 0.3 : 1,
+ opacity: Number(displayValue?.value) !== Number(value) ? 0.3 : 1,
}}
>