1
- import React , { useState , useRef } from 'react' ;
1
+ /* eslint-disable react-hooks/exhaustive-deps */
2
+ import React , { useState , useRef , useMemo , useEffect } from 'react' ;
2
3
import Input , { InputProps } from './Input' ;
3
4
import Modal from '../Modal' ;
5
+ import cx from 'classnames' ;
6
+ import { StatusWithMessage } from './StatusMessage' ;
4
7
5
- const TolerancePicker : React . FC < InputProps > = ( inputProps ) => {
8
+ type ToleranceRange = { label : string ; value : number } ;
9
+
10
+ export type ToleranceValues = {
11
+ minusTolerance : number ;
12
+ plusTolerance : number ;
13
+ } ;
14
+
15
+ export type TolerancePickerProps = Omit < InputProps , 'value' > & {
16
+ onToleranceChange : ( toleranceValues : ToleranceValues ) => void ;
17
+ toleranceRanges : ToleranceRange [ ] ;
18
+ toleranceValues ?: ToleranceValues ;
19
+ } ;
20
+
21
+ const TolerancePicker : React . FC < TolerancePickerProps > = ( {
22
+ onToleranceChange,
23
+ toleranceRanges,
24
+ toleranceValues : { minusTolerance, plusTolerance } = {
25
+ minusTolerance : toleranceRanges [ 0 ] . value ,
26
+ plusTolerance : toleranceRanges [ 0 ] . value ,
27
+ } ,
28
+ ...inputProps
29
+ } ) => {
6
30
const [ showPicker , setShowPicker ] = useState ( false ) ;
7
- const [ minusTolerance , setMinusTolerance ] = useState ( '00' ) ;
8
- const [ plusTolerance , setPlusTolerance ] = useState ( '00' ) ;
9
- const [ inputValue , setInputValue ] = useState ( '' ) ;
31
+ const [ inputValue , setInputValue ] = useState (
32
+ `-${ toleranceRanges [ 0 ] . label } /+${ toleranceRanges [ 0 ] . label } `
33
+ ) ;
34
+ const [ warningStatus , setWarningStatus ] = useState < StatusWithMessage | undefined > ( undefined ) ;
10
35
const inputRef = useRef < HTMLInputElement > ( null ) ;
11
36
12
- const handleTimeChange = ( newMinusTolerance : string , newPlusTolerance : string ) => {
13
- setMinusTolerance ( newMinusTolerance ) ;
14
- setPlusTolerance ( newPlusTolerance ) ;
15
- const formattedValue = `-${ newMinusTolerance } /+${ newPlusTolerance } ` ;
16
- setInputValue ( formattedValue ) ;
17
- } ;
37
+ const { minusToleranceIndex, plusToleranceIndex } = useMemo ( ( ) => {
38
+ const minusToleranceIndex = toleranceRanges . findIndex (
39
+ ( range ) => range . value === minusTolerance
40
+ ) ;
41
+ const plusToleranceIndex = toleranceRanges . findIndex ( ( range ) => range . value === plusTolerance ) ;
42
+ if ( minusToleranceIndex < 0 || plusToleranceIndex < 0 )
43
+ setWarningStatus ( {
44
+ status : 'warning' ,
45
+ message : "One of the values isn't included in the ranges provided." ,
46
+ } ) ;
47
+ return { minusToleranceIndex, plusToleranceIndex } ;
48
+ } , [ minusTolerance , plusTolerance , toleranceRanges ] ) ;
49
+
50
+ const getToleranceLabel = ( toleranceIndex : number ) =>
51
+ `${ toleranceIndex < 0 ? '' : toleranceRanges [ toleranceIndex ] . label } ` ;
18
52
19
- const TOLERANCE_RANGES = [
20
- '00' ,
21
- '05' ,
22
- '10' ,
23
- '15' ,
24
- '20' ,
25
- '25' ,
26
- '30' ,
27
- '35' ,
28
- '40' ,
29
- '45' ,
30
- '1h' ,
31
- '1h15' ,
32
- '1h30' ,
33
- '1h45' ,
34
- '2h' ,
35
- '2h30' ,
36
- '3h00' ,
37
- '3h30' ,
38
- '4h00' ,
39
- ] ;
53
+ useEffect ( ( ) => {
54
+ const formattedInputValue = `-${ getToleranceLabel ( minusToleranceIndex ) } /+${ getToleranceLabel ( plusToleranceIndex ) } ` ;
55
+ setInputValue ( formattedInputValue ) ;
56
+ } , [ minusTolerance , plusTolerance ] ) ;
40
57
41
58
return (
42
59
< div className = "tolerance-picker" >
43
60
< div >
44
61
< Input
45
62
{ ...inputProps }
46
63
value = { inputValue }
64
+ // Event not used for now
47
65
onChange = { ( e ) => {
48
66
setInputValue ( e . target . value ) ;
49
67
setShowPicker ( true ) ;
50
68
} }
69
+ statusWithMessage = { warningStatus }
51
70
readOnly
52
71
onClick = { ( ) => setShowPicker ( ! showPicker ) }
53
72
type = "text"
@@ -59,33 +78,50 @@ const TolerancePicker: React.FC<InputProps> = (inputProps) => {
59
78
< div className = "time-tolerance" >
60
79
< div className = "time-picker-section" >
61
80
< div className = "tolerance-grid" >
62
- { TOLERANCE_RANGES . map ( ( tolerance , index ) => (
63
- < button
64
- key = { tolerance }
65
- className = { `minute ${ minusTolerance === tolerance ? 'selected' : '' } ` }
66
- style = { { gridArea : `a${ index + 1 } ` } }
67
- onClick = { ( ) => handleTimeChange ( tolerance , plusTolerance ) }
68
- >
69
- { `-${ tolerance } ` }
70
- </ button >
71
- ) ) }
81
+ { toleranceRanges . map ( ( tolerance , index ) => {
82
+ const { label, value } = tolerance ;
83
+ return (
84
+ < button
85
+ key = { `${ label } -${ index } ` }
86
+ className = { cx ( 'minute' , { selected : minusTolerance === value } ) }
87
+ style = { { gridArea : `a${ index + 1 } ` } }
88
+ onClick = { ( ) =>
89
+ onToleranceChange ( {
90
+ minusTolerance : value ,
91
+ plusTolerance : toleranceRanges [ plusToleranceIndex ] . value ,
92
+ } )
93
+ }
94
+ >
95
+ { `-${ label } ` }
96
+ </ button >
97
+ ) ;
98
+ } ) }
72
99
</ div >
73
100
</ div >
74
101
75
102
< div className = "divider" />
76
103
77
104
< div className = "time-picker-section" >
78
105
< div className = "tolerance-grid plus-tolerance" >
79
- { TOLERANCE_RANGES . map ( ( tolerance , index ) => (
80
- < button
81
- key = { tolerance }
82
- className = { `minute ${ plusTolerance === tolerance ? 'selected' : '' } ` }
83
- style = { { gridArea : `a${ index + 1 } ` } }
84
- onClick = { ( ) => handleTimeChange ( minusTolerance , tolerance ) }
85
- >
86
- { `+${ tolerance } ` }
87
- </ button >
88
- ) ) }
106
+ { toleranceRanges . map ( ( tolerance , index ) => {
107
+ const { label, value } = tolerance ;
108
+ return (
109
+ < button
110
+ key = { `${ label } -${ index } ` }
111
+ className = { cx ( 'minute' , { selected : plusTolerance === value } ) }
112
+ style = { { gridArea : `a${ index + 1 } ` } }
113
+ onClick = { ( ) => {
114
+ console . log ( 'plusTolerance -- value: ' , value ) ;
115
+ onToleranceChange ( {
116
+ minusTolerance : toleranceRanges [ minusToleranceIndex ] . value ,
117
+ plusTolerance : value ,
118
+ } ) ;
119
+ } }
120
+ >
121
+ { `+${ label } ` }
122
+ </ button >
123
+ ) ;
124
+ } ) }
89
125
</ div >
90
126
</ div >
91
127
</ div >
0 commit comments