@totalsoft/rocket-ui
Version:
A set of reusable and composable React components built on top of Material UI core for developing fast and friendly web applications interfaces.
100 lines • 4.11 kB
JavaScript
import React, { useCallback, useLayoutEffect, useState } from 'react';
import PropTypes from 'prop-types';
import { StyledSlider, StyledTextField, FormControl, FormHelperText } from './SliderStyles';
import useDebouncedCallback from '../../utils/useDebouncedCallback';
/**
* Sliders allow users to make selections from a range of values.
*/
const Slider = ({ label, fullWidth, value: origValue, min = 0, max = 100, onChange: origOnChange, error, helperText, required, decimalScale, thousandSeparator, decimalSeparator, disabled, showSliderLimits, color = 'primary', ...rest }) => {
const [value, setValue] = useState(origValue || null);
const [validationError, setValidationError] = useState(false);
useLayoutEffect(() => {
if (origValue != undefined)
setValue(origValue);
}, [origValue]);
const onSliderChange = useCallback((_event, value) => (origOnChange ? origOnChange(value) : setValue(value)), [origOnChange]);
const onTextChanged = useCallback((value) => {
if (value >= min && value <= max) {
onSliderChange(null, value);
setValidationError(false);
}
else {
setValidationError(true);
}
}, [min, max, onSliderChange]);
const debouncedOnChange = useDebouncedCallback(onTextChanged, 500);
return (React.createElement(FormControl, { fullWidth: fullWidth, error: error, required: required },
React.createElement(StyledTextField, { label: label, fullWidth: fullWidth, required: required, value: value, onChange: debouncedOnChange, isNumeric: true, inputProps: { decimalScale, thousandSeparator, decimalSeparator }, InputProps: { disableUnderline: true }, disabled: disabled, error: error || validationError }),
React.createElement(StyledSlider, { size: "small", value: value, min: min, max: max, "aria-labelledby": "continuous-slider", onChange: onSliderChange, disabled: disabled, color: error || validationError ? 'error' : color, marks: showSliderLimits && [
{ value: min, label: min.toFixed(decimalScale).toString() },
{ value: max, label: max.toFixed(decimalScale).toString() }
], ...rest }),
helperText && React.createElement(FormHelperText, { error: error }, helperText)));
};
Slider.propTypes = {
/**
* @default "primary"
* Slide color.
*/
color: PropTypes.oneOf(['primary', 'secondary', 'info', 'success', 'warning', 'rose', 'dark']),
/**
* The value of the label.
*/
label: PropTypes.string,
/**
* The value of the slider. For ranged sliders, provide an array with two values.
*/
value: PropTypes.number,
/**
* Callback function that is fired when the slider's value changed.
*/
onChange: PropTypes.func,
/**
* If true, the component will take up the full width of its container.
*/
fullWidth: PropTypes.bool,
/**
* @default 0
* The minimum allowed value of the slider. Should not be equal to max.
*/
min: PropTypes.number,
/**
* @default 100
* The maximum allowed value of the slider. Should not be equal to min.
*/
max: PropTypes.number,
/**
* If true, the error styles are applied.
*/
error: PropTypes.bool,
/**
* The helper text content.
*/
helperText: PropTypes.string,
/**
* If true, the label is displayed as required.
*/
required: PropTypes.bool,
/**
* The number of decimals to be displayed.
*/
decimalScale: PropTypes.number,
/**
* Add thousand separators on number; single character string or boolean true.
*/
thousandSeparator: PropTypes.oneOfType([PropTypes.bool, PropTypes.string]),
/**
* Character that separates decimals from integers.
*/
decimalSeparator: PropTypes.string,
/**
* If true, the slider and input will be disabled.
*/
disabled: PropTypes.bool,
/**
* If true, the slider limits will be displayed.
*/
showSliderLimits: PropTypes.bool
};
export default Slider;
//# sourceMappingURL=Slider.js.map