@uiw/react-native
Version:
UIW for React Native
86 lines • 2.91 kB
JavaScript
import React, { useRef, useEffect } from 'react';
import { View } from 'react-native';
import ControlValue from './ControlValue';
import ShowValue from './ShowValue';
import { styles as ControlStyle } from './ControlValue';
function Stepper(props) {
const {
size = 'default',
color = {
color: '#108ee9',
borderColor: '#108ee9',
controlColor: '#108ee9',
valueColor: '#108ee9'
},
value = 0,
step = 1,
min = 0,
max = 100,
onChange,
onErrorInput,
disabled = false,
disabledInput = true,
disabledLongPress = false,
delayLong = 500,
width
} = props;
const textInput = useRef();
const accuracy = useRef(0);
const valueRef = useRef(0);
useEffect(() => {
const length = (step + '.').toString().split('.')[1].length;
accuracy.current = Math.pow(10, length);
}, [step]);
useEffect(() => {
valueRef.current = value ?? 0;
const length = Math.pow(10, (valueRef.current + '.').toString().split('.')[1].length);
if (length > accuracy.current) {
accuracy.current = length;
}
}, [value]);
const isErrorHandle = result => {
if (result === 'min') {
onChange(min);
valueRef.current = min;
return;
}
if (Number(result) > max) {
onErrorInput?.('OVER', result);
onChange(max);
valueRef.current = max;
return;
}
if (Number(result) < min) {
onErrorInput?.('LOW', result);
onChange(min);
valueRef.current = min;
return;
}
valueRef.current = result;
onChange(result);
};
const control = type => {
textInput.current && textInput.current.blur();
let result = 0;
if (type === 'decrease') {
result = Number((valueRef.current * accuracy.current - step * accuracy.current).toFixed(0)) / accuracy.current;
result = result <= min ? min : result;
}
if (type === 'increase') {
result = Number((valueRef.current * accuracy.current + step * accuracy.current).toFixed(0)) / accuracy.current;
// result = Number(valueRef.current) + Number(step)
result = result >= max ? max : result;
}
// valueRef.current = Number(result.toFixed(accuracy.current))
valueRef.current = result;
onChange(valueRef.current);
};
return <View style={[ControlStyle.elementCenter, {
justifyContent: 'flex-start'
}]}>
<ControlValue size={size} delayLong={delayLong} disabledLongPress={disabledLongPress} action="decrease" color={color} disabled={disabled || value <= min} control={control} />
<ShowValue size={size} width={width} textInput={textInput} color={color} value={value + ''} onChange={isErrorHandle} disabled={!disabledInput} />
<ControlValue size={size} delayLong={delayLong} disabledLongPress={disabledLongPress} action="increase" color={color} disabled={disabled || value >= max} control={control} />
</View>;
}
export default Stepper;