@hipay/hipay-material-ui 2.0.0-beta.57 → 2.0.0-beta.59
Sign up to get free protection for your applications and to get access to all the features.
- package/CHANGELOG.md +117 -0
- package/HiAlertModal/HiAlertModal.js +56 -13
- package/HiColoredLabel/HiColoredLabel.js +16 -4
- package/HiForm/HiFormControl.js +2 -4
- package/HiForm/HiInput.js +29 -4
- package/HiForm/HiUploadField.js +2 -1
- package/HiSelect/HiSelect.js +6 -5
- package/HiSelect/HiSuggestSelect.js +5 -4
- package/HiSelect/SelectInput.js +1 -0
- package/HiSelectNew/HiNestedSelect.js +20 -6
- package/HiSelectNew/HiNestedSelectContent.js +20 -6
- package/HiSelectNew/HiSelect.js +104 -32
- package/HiSelectNew/HiSelectContent.js +16 -4
- package/HiSelectNew/HiSelectInput.js +10 -3
- package/HiSelectableList/HiSelectableList.js +2 -35
- package/HiSelectableList/HiSelectableListItem.js +6 -4
- package/es/HiAlertModal/HiAlertModal.js +55 -13
- package/es/HiColoredLabel/HiColoredLabel.js +21 -4
- package/es/HiForm/HiFormControl.js +2 -4
- package/es/HiForm/HiInput.js +29 -4
- package/es/HiForm/HiUploadField.js +2 -1
- package/es/HiSelect/HiSelect.js +6 -5
- package/es/HiSelect/HiSuggestSelect.js +5 -4
- package/es/HiSelect/SelectInput.js +1 -0
- package/es/HiSelectNew/HiNestedSelect.js +17 -7
- package/es/HiSelectNew/HiNestedSelectContent.js +16 -6
- package/es/HiSelectNew/HiSelect.js +106 -31
- package/es/HiSelectNew/HiSelectContent.js +11 -2
- package/es/HiSelectNew/HiSelectInput.js +10 -3
- package/es/HiSelectableList/HiSelectableList.js +3 -29
- package/es/HiSelectableList/HiSelectableListItem.js +6 -4
- package/index.es.js +1 -1
- package/index.js +1 -1
- package/package.json +1 -1
- package/umd/hipay-material-ui.development.js +15551 -16279
- package/umd/hipay-material-ui.production.min.js +2 -2
@@ -8,7 +8,7 @@ import withStyles from '../styles/withStyles';
|
|
8
8
|
import { capitalize } from '../utils/helpers';
|
9
9
|
import { fade } from '../styles/colorManipulator';
|
10
10
|
export const styles = theme => ({
|
11
|
-
root:
|
11
|
+
root: {
|
12
12
|
display: 'inline-block',
|
13
13
|
alignItems: 'baseline',
|
14
14
|
maxWidth: '100%',
|
@@ -18,7 +18,12 @@ export const styles = theme => ({
|
|
18
18
|
overflow: 'hidden',
|
19
19
|
whiteSpace: 'nowrap',
|
20
20
|
lineHeight: 1
|
21
|
-
}
|
21
|
+
},
|
22
|
+
body1: _objectSpread({}, theme.typography.b1),
|
23
|
+
body2: _objectSpread({}, theme.typography.b2),
|
24
|
+
body3: _objectSpread({}, theme.typography.b3),
|
25
|
+
body4: _objectSpread({}, theme.typography.b4),
|
26
|
+
body5: _objectSpread({}, theme.typography.b5),
|
22
27
|
color: {
|
23
28
|
fontWeight: 400
|
24
29
|
},
|
@@ -111,6 +116,7 @@ function HiColoredLabel(props) {
|
|
111
116
|
const {
|
112
117
|
classes,
|
113
118
|
className,
|
119
|
+
fontSize,
|
114
120
|
label,
|
115
121
|
color,
|
116
122
|
active,
|
@@ -119,7 +125,7 @@ function HiColoredLabel(props) {
|
|
119
125
|
style,
|
120
126
|
theme
|
121
127
|
} = props,
|
122
|
-
other = _objectWithoutProperties(props, ["classes", "className", "label", "color", "active", "outlined", "fontWeight", "style", "theme"]);
|
128
|
+
other = _objectWithoutProperties(props, ["classes", "className", "fontSize", "label", "color", "active", "outlined", "fontWeight", "style", "theme"]);
|
123
129
|
|
124
130
|
const isHiColor = ['primary', 'secondary', 'positive', 'negative', 'middle', 'neutral'].includes(color);
|
125
131
|
const isHexColor = !isHiColor && /(^#[0-9A-F]{6}$)|(^#[0-9A-F]{3}$)/i.test(color);
|
@@ -129,7 +135,12 @@ function HiColoredLabel(props) {
|
|
129
135
|
[classes.activeColor]: active,
|
130
136
|
[classes.outlined]: outlined,
|
131
137
|
[classes[`activeColor${capitalize(color)}`]]: active && isHiColor,
|
132
|
-
[classes[`color${capitalize(color)}`]]: !active && isHiColor
|
138
|
+
[classes[`color${capitalize(color)}`]]: !active && isHiColor,
|
139
|
+
[classes.body1]: fontSize >= 15,
|
140
|
+
[classes.body2]: fontSize === 14,
|
141
|
+
[classes.body3]: fontSize === 13,
|
142
|
+
[classes.body4]: fontSize === 12,
|
143
|
+
[classes.body5]: fontSize <= 11
|
133
144
|
}, className),
|
134
145
|
style: _objectSpread({}, style, isHexColor && {
|
135
146
|
backgroundColor: active ? color : fade(color, 0.08),
|
@@ -162,6 +173,11 @@ HiColoredLabel.propTypes = process.env.NODE_ENV !== "production" ? {
|
|
162
173
|
*/
|
163
174
|
color: PropTypes.string,
|
164
175
|
|
176
|
+
/**
|
177
|
+
* Taille du text
|
178
|
+
*/
|
179
|
+
fontSize: PropTypes.number,
|
180
|
+
|
165
181
|
/**
|
166
182
|
* Graisse du text
|
167
183
|
*/
|
@@ -180,6 +196,7 @@ HiColoredLabel.propTypes = process.env.NODE_ENV !== "production" ? {
|
|
180
196
|
HiColoredLabel.defaultProps = {
|
181
197
|
active: false,
|
182
198
|
color: 'primary',
|
199
|
+
fontSize: 15,
|
183
200
|
outlined: false
|
184
201
|
};
|
185
202
|
export default withStyles(styles, {
|
@@ -199,16 +199,14 @@ class HiFormControl extends React.PureComponent {
|
|
199
199
|
focused: !disabled && (focused || hovered)
|
200
200
|
}, InputLabelProps), error && errorText && React.createElement(HiIconButton, {
|
201
201
|
className: classNames(classes.iconButton, classes.iconButtonError),
|
202
|
-
onClick: this.handleHelperClick
|
203
|
-
onKeyDown: this.handleKeyDown
|
202
|
+
onClick: this.handleHelperClick
|
204
203
|
}, React.createElement(Warning, {
|
205
204
|
className: classNames(classes.icon)
|
206
205
|
})), helperIcon && helperText && !error && React.createElement(HiIconButton, {
|
207
206
|
className: classNames(classes.iconButton, classes.iconButtonInfo, {
|
208
207
|
[classes.iconButtonInfoActive]: helperOpen
|
209
208
|
}),
|
210
|
-
onClick: this.handleHelperClick
|
211
|
-
onKeyDown: this.handleKeyDown
|
209
|
+
onClick: this.handleHelperClick
|
212
210
|
}, React.createElement(Info, {
|
213
211
|
className: classNames(classes.icon)
|
214
212
|
}))), React.createElement("div", {
|
package/es/HiForm/HiInput.js
CHANGED
@@ -127,6 +127,13 @@ var _ref = React.createElement(HiIcon, {
|
|
127
127
|
class HiInput extends React.PureComponent {
|
128
128
|
constructor() {
|
129
129
|
super();
|
130
|
+
|
131
|
+
this.handleClick = () => {
|
132
|
+
if (this.props.onClick) {
|
133
|
+
this.props.onClick();
|
134
|
+
}
|
135
|
+
};
|
136
|
+
|
130
137
|
this.state = {
|
131
138
|
focused: false
|
132
139
|
};
|
@@ -177,10 +184,15 @@ class HiInput extends React.PureComponent {
|
|
177
184
|
// Si on click sur un élément de HiInput, on garde le focus
|
178
185
|
// Par exemple sur l'icone reset
|
179
186
|
if (event.relatedTarget && this.overlayNode && this.overlayNode.contains(event.relatedTarget)) {
|
180
|
-
|
187
|
+
// If blur came from erase icon => stay focused and don't call onBlur props
|
188
|
+
if (this.eraseIconNode && this.eraseIconNode.contains(event.relatedTarget)) {
|
189
|
+
event.preventDefault();
|
190
|
+
event.stopPropagation();
|
191
|
+
} else if (this.endAdornmentNode.contains(event.relatedTarget) && this.props.onBlur) {
|
181
192
|
this.props.onBlur(event);
|
182
193
|
}
|
183
194
|
|
195
|
+
event.preventDefault();
|
184
196
|
event.stopPropagation();
|
185
197
|
} else {
|
186
198
|
this.setState({
|
@@ -201,9 +213,13 @@ class HiInput extends React.PureComponent {
|
|
201
213
|
this.setState({
|
202
214
|
focused: true
|
203
215
|
});
|
204
|
-
}
|
216
|
+
} // If focus came from erase icon => stay focused and don't call onFocus props
|
217
|
+
|
205
218
|
|
206
|
-
if (this.
|
219
|
+
if (this.eraseIconNode && this.eraseIconNode.contains(event.relatedTarget)) {
|
220
|
+
event.preventDefault();
|
221
|
+
event.stopPropagation();
|
222
|
+
} else if (this.props.onFocus) {
|
207
223
|
this.props.onFocus(event);
|
208
224
|
}
|
209
225
|
}
|
@@ -306,7 +322,10 @@ class HiInput extends React.PureComponent {
|
|
306
322
|
label: classes.eraseButtonLabel
|
307
323
|
},
|
308
324
|
onClick: this.handleReset,
|
309
|
-
onBlur: this.handleBlur
|
325
|
+
onBlur: this.handleBlur,
|
326
|
+
buttonRef: el => {
|
327
|
+
this.eraseIconNode = el;
|
328
|
+
}
|
310
329
|
}, _ref);
|
311
330
|
let endAdornment = endAdornmentProps;
|
312
331
|
|
@@ -335,6 +354,7 @@ class HiInput extends React.PureComponent {
|
|
335
354
|
placeholder: placeholder,
|
336
355
|
onFocus: this.handleFocus,
|
337
356
|
onKeyDown: this.props.onKeyDown,
|
357
|
+
onClick: this.handleClick,
|
338
358
|
onBlur: this.handleBlur,
|
339
359
|
inputRef: this.getInputElement,
|
340
360
|
disabled: disabled,
|
@@ -454,6 +474,11 @@ HiInput.propTypes = process.env.NODE_ENV !== "production" ? {
|
|
454
474
|
*/
|
455
475
|
onChange: PropTypes.func,
|
456
476
|
|
477
|
+
/**
|
478
|
+
* Fonction de callback appelée au click dans l'input
|
479
|
+
*/
|
480
|
+
onClick: PropTypes.func,
|
481
|
+
|
457
482
|
/**
|
458
483
|
* Fonction de callback appelée au focus du champs
|
459
484
|
*/
|
package/es/HiSelect/HiSelect.js
CHANGED
@@ -193,17 +193,13 @@ class HiSelect extends React.PureComponent {
|
|
193
193
|
nextItem = getNextItemSelectable(document.activeElement, 'down');
|
194
194
|
} else if (event.key === 'ArrowUp') {
|
195
195
|
nextItem = getNextItemSelectable(document.activeElement, 'up');
|
196
|
-
} else if (event.key === 'Tab') {
|
196
|
+
} else if (event.key === 'Tab' || event.key === 'Escape') {
|
197
197
|
/* if (!this.props.staticPosition) {
|
198
198
|
document.body.style.overflow = 'auto';
|
199
199
|
} */
|
200
200
|
this.setState({
|
201
201
|
open: false
|
202
202
|
});
|
203
|
-
} else if (event.key === 'Escape') {
|
204
|
-
this.setState({
|
205
|
-
open: false
|
206
|
-
});
|
207
203
|
}
|
208
204
|
|
209
205
|
if (nextItem) {
|
@@ -216,6 +212,10 @@ class HiSelect extends React.PureComponent {
|
|
216
212
|
this.focusOnSelectedItem();
|
217
213
|
} else if (event.key === 'Enter' && this.props.onSubmit) {
|
218
214
|
this.props.onSubmit(event);
|
215
|
+
} else if (event.key === 'Tab' || event.key === 'Escape') {
|
216
|
+
this.setState({
|
217
|
+
open: false
|
218
|
+
});
|
219
219
|
}
|
220
220
|
};
|
221
221
|
|
@@ -682,6 +682,7 @@ class HiSelect extends React.PureComponent {
|
|
682
682
|
onClick: this.handleClick,
|
683
683
|
onFocus: this.handleFocus,
|
684
684
|
onBlur: this.handleBlur,
|
685
|
+
onKeyDown: this.handleKeyDown,
|
685
686
|
onMouseEnter: this.props.onMouseEnter,
|
686
687
|
onMouseLeave: this.props.onMouseLeave,
|
687
688
|
refElement: el => {
|
@@ -24,7 +24,8 @@ export const styles = theme => ({
|
|
24
24
|
width: '100% !important',
|
25
25
|
transform: 'none !important',
|
26
26
|
zIndex: '9 !important',
|
27
|
-
top: '100% !important'
|
27
|
+
top: '100% !important',
|
28
|
+
textOverflow: 'ellipsis'
|
28
29
|
},
|
29
30
|
paper: {
|
30
31
|
borderRadius: '0px 2px',
|
@@ -143,10 +144,10 @@ class HiSuggestSelect extends React.PureComponent {
|
|
143
144
|
options: [],
|
144
145
|
focused: false
|
145
146
|
});
|
146
|
-
}
|
147
147
|
|
148
|
-
|
149
|
-
|
148
|
+
if (this.props.onBlurInput) {
|
149
|
+
this.props.onBlurInput(event);
|
150
|
+
}
|
150
151
|
}
|
151
152
|
}
|
152
153
|
|
@@ -45,6 +45,10 @@ function findFinalItemRecursively(itemList, searchId) {
|
|
45
45
|
});
|
46
46
|
return foundItem;
|
47
47
|
}
|
48
|
+
|
49
|
+
export var filterValue = function (item, searchValue) {
|
50
|
+
return searchValue === '' || foldAccents(item.label.toString().toLowerCase()).search(foldAccents(searchValue.toLowerCase())) !== -1;
|
51
|
+
};
|
48
52
|
/**
|
49
53
|
* Build item list by settings item props relative to the nested parent/child situation
|
50
54
|
* Reduce the item list to build specified items (displayed, pinned, disabled, selected, indeterminate)
|
@@ -62,15 +66,14 @@ function findFinalItemRecursively(itemList, searchId) {
|
|
62
66
|
* @returns {*}
|
63
67
|
*/
|
64
68
|
|
65
|
-
|
66
|
-
function buildFilteredItemList(itemList, selectedItemIdList = [], searchValue = '', visibleParent = false, pinnedParent = false, disabledParent = false, nbChildrenAsInfo = false, translations) {
|
69
|
+
function buildFilteredItemList(itemList, selectedItemIdList = [], searchValue = '', visibleParent = false, pinnedParent = false, disabledParent = false, nbChildrenAsInfo = false, translations, filterFunc = filterValue) {
|
67
70
|
return itemList.reduce(({
|
68
71
|
l: memoItemList,
|
69
72
|
s: memoSelected,
|
70
73
|
u: memoUnselected,
|
71
74
|
v: memoVisible
|
72
75
|
}, item) => {
|
73
|
-
const itemVisible =
|
76
|
+
const itemVisible = filterFunc(item, searchValue); // Parent item
|
74
77
|
|
75
78
|
if (item.children) {
|
76
79
|
const {
|
@@ -78,7 +81,7 @@ function buildFilteredItemList(itemList, selectedItemIdList = [], searchValue =
|
|
78
81
|
s: selected,
|
79
82
|
u: unselected,
|
80
83
|
v: visible
|
81
|
-
} = buildFilteredItemList(item.children, selectedItemIdList, searchValue, itemVisible, pinnedParent, disabledParent);
|
84
|
+
} = buildFilteredItemList(item.children, selectedItemIdList, searchValue, itemVisible, pinnedParent, disabledParent, nbChildrenAsInfo, translations, filterFunc);
|
82
85
|
|
83
86
|
if (nbChildrenAsInfo) {
|
84
87
|
item.info = translations.n_children.replace('%s', item.children.length);
|
@@ -227,7 +230,8 @@ class HiNestedSelect extends React.PureComponent {
|
|
227
230
|
multiple,
|
228
231
|
nbChildrenAsInfo,
|
229
232
|
pinnedParent,
|
230
|
-
translations
|
233
|
+
translations,
|
234
|
+
filterFunc
|
231
235
|
} = this.props; // build item list
|
232
236
|
|
233
237
|
const {
|
@@ -235,7 +239,7 @@ class HiNestedSelect extends React.PureComponent {
|
|
235
239
|
s: allSelected,
|
236
240
|
u: allUnselected,
|
237
241
|
v: visible
|
238
|
-
} = buildFilteredItemList(options, value, search, false, pinnedParent, disabledParent || !multiple, nbChildrenAsInfo, translations);
|
242
|
+
} = buildFilteredItemList(options, value, search, false, pinnedParent, disabledParent || !multiple, nbChildrenAsInfo, translations, filterFunc);
|
239
243
|
const itemList = !visible ? [...(loading ? [{
|
240
244
|
id: '_loading',
|
241
245
|
type: 'loader',
|
@@ -367,7 +371,8 @@ HiNestedSelect.defaultProps = {
|
|
367
371
|
one_item_selected: '%s item selected',
|
368
372
|
n_children: '%s',
|
369
373
|
one_child: '%s item'
|
370
|
-
}
|
374
|
+
},
|
375
|
+
filterFunc: filterValue
|
371
376
|
};
|
372
377
|
HiNestedSelect.propTypes = process.env.NODE_ENV !== "production" ? {
|
373
378
|
/**
|
@@ -385,6 +390,11 @@ HiNestedSelect.propTypes = process.env.NODE_ENV !== "production" ? {
|
|
385
390
|
*/
|
386
391
|
displayAsChip: PropTypes.bool,
|
387
392
|
|
393
|
+
/*
|
394
|
+
* Fonction de filtrage custom
|
395
|
+
*/
|
396
|
+
filterFunc: PropTypes.func,
|
397
|
+
|
388
398
|
/**
|
389
399
|
* Affiche l'élément 'All'
|
390
400
|
*/
|
@@ -42,6 +42,9 @@ export function findFinalItemRecursively(itemList, searchId) {
|
|
42
42
|
});
|
43
43
|
return foundItem;
|
44
44
|
}
|
45
|
+
export var filterValue = function (item, searchValue) {
|
46
|
+
return searchValue === '' || foldAccents(item.label.toString().toLowerCase()).search(foldAccents(searchValue.toLowerCase())) !== -1;
|
47
|
+
};
|
45
48
|
/**
|
46
49
|
* Build item list by settings item props relative to the nested parent/child situation
|
47
50
|
* Reduce the item list to build specified items (displayed, pinned, disabled, selected, indeterminate)
|
@@ -59,14 +62,14 @@ export function findFinalItemRecursively(itemList, searchId) {
|
|
59
62
|
* @returns {*}
|
60
63
|
*/
|
61
64
|
|
62
|
-
function buildFilteredItemList(itemList, selectedItemIdList = [], searchValue = '', visibleParent = false, pinnedParent = false, disabledParent = false, nbChildrenAsInfo = false, translations) {
|
65
|
+
function buildFilteredItemList(itemList, selectedItemIdList = [], searchValue = '', visibleParent = false, pinnedParent = false, disabledParent = false, nbChildrenAsInfo = false, translations, filterFunc = filterValue) {
|
63
66
|
return itemList.reduce(({
|
64
67
|
l: memoItemList,
|
65
68
|
s: memoSelected,
|
66
69
|
u: memoUnselected,
|
67
70
|
v: memoVisible
|
68
71
|
}, item) => {
|
69
|
-
const itemVisible =
|
72
|
+
const itemVisible = filterFunc(item, searchValue); // Parent item
|
70
73
|
|
71
74
|
if (item.children) {
|
72
75
|
const {
|
@@ -74,7 +77,7 @@ function buildFilteredItemList(itemList, selectedItemIdList = [], searchValue =
|
|
74
77
|
s: selected,
|
75
78
|
u: unselected,
|
76
79
|
v: visible
|
77
|
-
} = buildFilteredItemList(item.children, selectedItemIdList, searchValue, itemVisible, pinnedParent, disabledParent);
|
80
|
+
} = buildFilteredItemList(item.children, selectedItemIdList, searchValue, itemVisible, pinnedParent, disabledParent, nbChildrenAsInfo, translations, filterFunc);
|
78
81
|
|
79
82
|
if (nbChildrenAsInfo) {
|
80
83
|
item.info = translations.n_children.replace('%s', item.children.length);
|
@@ -181,7 +184,8 @@ class HiNestedSelectContent extends React.PureComponent {
|
|
181
184
|
multiple,
|
182
185
|
nbChildrenAsInfo,
|
183
186
|
pinnedParent,
|
184
|
-
translations
|
187
|
+
translations,
|
188
|
+
filterFunc
|
185
189
|
} = this.props; // build item list
|
186
190
|
|
187
191
|
const {
|
@@ -189,7 +193,7 @@ class HiNestedSelectContent extends React.PureComponent {
|
|
189
193
|
s: allSelected,
|
190
194
|
u: allUnselected,
|
191
195
|
v: visible
|
192
|
-
} = buildFilteredItemList(options, value, search, false, pinnedParent, disabledParent || !multiple, nbChildrenAsInfo, translations);
|
196
|
+
} = buildFilteredItemList(options, value, search, false, pinnedParent, disabledParent || !multiple, nbChildrenAsInfo, translations, filterFunc);
|
193
197
|
const itemList = !visible ? [...(loading ? [{
|
194
198
|
id: '_loading',
|
195
199
|
type: 'loader',
|
@@ -272,7 +276,8 @@ HiNestedSelectContent.defaultProps = {
|
|
272
276
|
search: 'Search',
|
273
277
|
n_children: '%s',
|
274
278
|
one_child: '%s item'
|
275
|
-
}
|
279
|
+
},
|
280
|
+
filterFunc: filterValue
|
276
281
|
};
|
277
282
|
HiNestedSelectContent.propTypes = process.env.NODE_ENV !== "production" ? {
|
278
283
|
/**
|
@@ -285,6 +290,11 @@ HiNestedSelectContent.propTypes = process.env.NODE_ENV !== "production" ? {
|
|
285
290
|
*/
|
286
291
|
disabledParent: PropTypes.bool,
|
287
292
|
|
293
|
+
/*
|
294
|
+
* Fonction de filtrage custom
|
295
|
+
*/
|
296
|
+
filterFunc: PropTypes.func,
|
297
|
+
|
288
298
|
/**
|
289
299
|
* Affiche l'élément 'All'
|
290
300
|
*/
|
@@ -6,7 +6,6 @@ import Scrollbars from 'react-custom-scrollbars';
|
|
6
6
|
import Grow from '@material-ui/core/Grow';
|
7
7
|
import Paper from '@material-ui/core/Paper';
|
8
8
|
import Popper from '@material-ui/core/Popper';
|
9
|
-
import { findDOMNode } from 'react-dom';
|
10
9
|
import ClickAwayListener from '@material-ui/core/ClickAwayListener';
|
11
10
|
import HiSelectableList from '../HiSelectableList';
|
12
11
|
import HiInput from '../HiForm/HiInput';
|
@@ -69,6 +68,10 @@ export const styles = theme => ({
|
|
69
68
|
borderTop: `1px solid ${theme.palette.input.bottomLine}`
|
70
69
|
}
|
71
70
|
});
|
71
|
+
|
72
|
+
function filterValue(item, search) {
|
73
|
+
return search === '' || foldAccents(item.label.toString().toLowerCase()).search(foldAccents(search.toLowerCase())) !== -1;
|
74
|
+
}
|
72
75
|
/**
|
73
76
|
*
|
74
77
|
* Utilisé pour tous types de selects dans les formulaires.
|
@@ -84,6 +87,7 @@ export const styles = theme => ({
|
|
84
87
|
* - HiSelectableList : affiche la liste des suggestions selon le type des éléments
|
85
88
|
*/
|
86
89
|
|
90
|
+
|
87
91
|
class HiSelect extends React.PureComponent {
|
88
92
|
constructor(props) {
|
89
93
|
super(props);
|
@@ -98,7 +102,7 @@ class HiSelect extends React.PureComponent {
|
|
98
102
|
hideCheckbox: true,
|
99
103
|
label: 'loading'
|
100
104
|
}] : []), // simple one level filter on label
|
101
|
-
...(search !== '' ? [...options.filter(item =>
|
105
|
+
...(search !== '' ? [...options.filter(item => this.props.filterFunc(item, search))] : [...(this.props.hasAll ? [_objectSpread({
|
102
106
|
id: '_all',
|
103
107
|
label: this.props.translations.all
|
104
108
|
}, this.props.iconAll && {
|
@@ -164,11 +168,12 @@ class HiSelect extends React.PureComponent {
|
|
164
168
|
};
|
165
169
|
|
166
170
|
this.focusOnFirstItem = () => {
|
167
|
-
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
171
|
+
if (this.overlay && this.overlay.getElementsByTagName('li')[0]) {
|
172
|
+
setTimeout(() => {
|
173
|
+
const item = this.overlay.getElementsByTagName('li')[0];
|
174
|
+
item.focus();
|
175
|
+
}, 1);
|
176
|
+
}
|
172
177
|
};
|
173
178
|
|
174
179
|
this.getInputElement = el => {
|
@@ -204,21 +209,22 @@ class HiSelect extends React.PureComponent {
|
|
204
209
|
};
|
205
210
|
|
206
211
|
this.focusOnSelectedItem = selectedValue => {
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
211
|
-
|
212
|
-
|
213
|
-
|
214
|
-
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
-
|
219
|
-
|
220
|
-
|
221
|
-
|
212
|
+
if (this.overlay && this.overlay.getElementsByTagName('li')[0]) {
|
213
|
+
setTimeout(() => {
|
214
|
+
// On initialise au premier élément pour être sûr de ne pas se retrouver avec un focus of undefined
|
215
|
+
let item = this.overlay.getElementsByTagName('li')[0];
|
216
|
+
|
217
|
+
if (selectedValue && typeof selectedValue === 'string') {
|
218
|
+
item = this.overlay.getElementsByTagName('li')[selectedValue];
|
219
|
+
} else if (selectedValue && typeof selectedValue === 'number') {
|
220
|
+
item = this.overlay.getElementsByTagName('li')[selectedValue - 1];
|
221
|
+
}
|
222
|
+
|
223
|
+
if (item) {
|
224
|
+
item.focus();
|
225
|
+
}
|
226
|
+
}, 1);
|
227
|
+
}
|
222
228
|
};
|
223
229
|
|
224
230
|
this.handleClickAway = event => {
|
@@ -249,6 +255,17 @@ class HiSelect extends React.PureComponent {
|
|
249
255
|
});
|
250
256
|
};
|
251
257
|
|
258
|
+
this.handleKeyDownInput = event => {
|
259
|
+
const key = keycode(event);
|
260
|
+
|
261
|
+
if (key === 'down' || key === 'up') {
|
262
|
+
this.handleClick();
|
263
|
+
} else if (key === 'enter' && this.props.onSubmit) {
|
264
|
+
event.preventDefault();
|
265
|
+
this.props.onSubmit(event);
|
266
|
+
}
|
267
|
+
};
|
268
|
+
|
252
269
|
this.handleKeyDown = event => {
|
253
270
|
let nextItem;
|
254
271
|
const key = keycode(event);
|
@@ -259,6 +276,13 @@ class HiSelect extends React.PureComponent {
|
|
259
276
|
} else if (key === 'up') {
|
260
277
|
event.preventDefault();
|
261
278
|
nextItem = getNextItemSelectable(document.activeElement, 'up');
|
279
|
+
} else if (key === 'tab' || key === 'esc') {
|
280
|
+
this.setState({
|
281
|
+
open: false
|
282
|
+
});
|
283
|
+
} else if (key === 'space') {
|
284
|
+
// Cancel scroll
|
285
|
+
event.preventDefault();
|
262
286
|
}
|
263
287
|
|
264
288
|
if (nextItem) {
|
@@ -266,17 +290,57 @@ class HiSelect extends React.PureComponent {
|
|
266
290
|
}
|
267
291
|
};
|
268
292
|
|
293
|
+
this.getItemById = id => {
|
294
|
+
let item;
|
295
|
+
|
296
|
+
if (this.props.hasAll && String(id) === '_all') {
|
297
|
+
return {
|
298
|
+
id: '_all'
|
299
|
+
};
|
300
|
+
}
|
301
|
+
|
302
|
+
for (let i = 0; i < this.props.options.length; i += 1) {
|
303
|
+
const elem = this.props.options[i];
|
304
|
+
|
305
|
+
if (String(elem.id) === String(id)) {
|
306
|
+
item = elem;
|
307
|
+
break;
|
308
|
+
}
|
309
|
+
|
310
|
+
if (elem.children) {
|
311
|
+
for (let j = 0; j < elem.children.length; j += 1) {
|
312
|
+
if (String(elem.children[j].id) === String(id)) {
|
313
|
+
item = elem.children[j];
|
314
|
+
break;
|
315
|
+
}
|
316
|
+
}
|
317
|
+
}
|
318
|
+
}
|
319
|
+
|
320
|
+
return item;
|
321
|
+
};
|
322
|
+
|
269
323
|
this.handleKeyUp = event => {
|
270
324
|
const key = keycode(event);
|
271
325
|
|
272
|
-
if (key === '
|
326
|
+
if (key === 'esc') {
|
273
327
|
this.setState({
|
274
328
|
open: false
|
275
329
|
});
|
276
330
|
} else if (key === 'space' || key === 'enter' && !this.props.multiple) {
|
277
331
|
event.preventDefault();
|
278
|
-
const item = this.
|
279
|
-
|
332
|
+
const item = this.getItemById(event.target.id);
|
333
|
+
|
334
|
+
if (item) {
|
335
|
+
// Select for nested select
|
336
|
+
if (this.props.hiSelectableListProps && this.props.hiSelectableListProps.onSelect) {
|
337
|
+
this.props.hiSelectableListProps.onSelect(null, item);
|
338
|
+
} else {
|
339
|
+
this.handleSelect(null, item);
|
340
|
+
}
|
341
|
+
} else {
|
342
|
+
console.warn(`Can not find item #${event.target.id}`);
|
343
|
+
}
|
280
344
|
} else if (key === 'enter' && this.props.multiple) {
|
281
345
|
event.preventDefault();
|
282
346
|
this.handleClose();
|
@@ -291,6 +355,10 @@ class HiSelect extends React.PureComponent {
|
|
291
355
|
} else if (this.overlay && key === 'esc' || key === 'enter') {
|
292
356
|
event.preventDefault();
|
293
357
|
this.handleClose();
|
358
|
+
} else if (key === 'tab') {
|
359
|
+
this.setState({
|
360
|
+
open: false
|
361
|
+
});
|
294
362
|
}
|
295
363
|
};
|
296
364
|
|
@@ -484,8 +552,8 @@ class HiSelect extends React.PureComponent {
|
|
484
552
|
[classes.popperRightAlign]: this.props.containerWidth && this.props.align === 'right'
|
485
553
|
});
|
486
554
|
|
487
|
-
|
488
|
-
if (
|
555
|
+
const searchInput = position => {
|
556
|
+
if (searchable) {
|
489
557
|
return React.createElement(HiInput, _extends({
|
490
558
|
value: searchValue,
|
491
559
|
autoFocus: true,
|
@@ -508,13 +576,13 @@ class HiSelect extends React.PureComponent {
|
|
508
576
|
|
509
577
|
if (this.placement && this.placement.indexOf('top') >= 0 && !!searchable) {
|
510
578
|
// +1 for search input
|
511
|
-
|
579
|
+
const nbItems = itemList.length <= 10 ? itemList.length + 1 : 11;
|
512
580
|
popperStyle.transform = `translate3d(-1px, -${nbItems * 40 + 2}px, 0px)`;
|
513
581
|
} else if (this.placement && this.placement.indexOf('top') < 0 && !!searchable) {
|
514
|
-
popperStyle.transform =
|
582
|
+
popperStyle.transform = 'translate3d(-1px, 40px, 0px)';
|
515
583
|
}
|
516
584
|
|
517
|
-
|
585
|
+
const content = ({
|
518
586
|
placement
|
519
587
|
}) => {
|
520
588
|
if (placement !== this.placement) {
|
@@ -568,6 +636,7 @@ class HiSelect extends React.PureComponent {
|
|
568
636
|
onClick: this.handleClick,
|
569
637
|
onFocus: this.handleFocus,
|
570
638
|
onBlur: this.handleBlur,
|
639
|
+
onKeyDown: this.handleKeyDownInput,
|
571
640
|
onSubmit: onSubmit,
|
572
641
|
onMouseEnter: this.props.onMouseEnter,
|
573
642
|
onMouseLeave: this.props.onMouseLeave,
|
@@ -614,7 +683,8 @@ HiSelect.defaultProps = {
|
|
614
683
|
n_children: '%s items',
|
615
684
|
one_child: '%s item'
|
616
685
|
},
|
617
|
-
type: 'text'
|
686
|
+
type: 'text',
|
687
|
+
filterFunc: filterValue
|
618
688
|
};
|
619
689
|
HiSelect.propTypes = process.env.NODE_ENV !== "production" ? {
|
620
690
|
align: PropTypes.oneOf(['left', 'right']),
|
@@ -649,6 +719,11 @@ HiSelect.propTypes = process.env.NODE_ENV !== "production" ? {
|
|
649
719
|
*/
|
650
720
|
fallbackImage: PropTypes.string,
|
651
721
|
|
722
|
+
/*
|
723
|
+
* Fonction de filtrage custom
|
724
|
+
*/
|
725
|
+
filterFunc: PropTypes.func,
|
726
|
+
|
652
727
|
/**
|
653
728
|
* Affiche l'élément 'All'
|
654
729
|
*/
|