@mackin.com/styleguide 8.0.0-beta.7 → 8.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/index.d.ts +159 -92
- package/index.js +1209 -893
- package/package.json +1 -1
package/index.js
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
Object.defineProperty(exports, '__esModule', { value: true });
|
|
2
2
|
|
|
3
|
-
var css = require('@emotion/css');
|
|
4
|
-
var lodash = require('lodash');
|
|
5
3
|
var React = require('react');
|
|
6
|
-
var
|
|
4
|
+
var css = require('@emotion/css');
|
|
7
5
|
var proRegularSvgIcons = require('@fortawesome/pro-regular-svg-icons');
|
|
8
6
|
var proSolidSvgIcons = require('@fortawesome/pro-solid-svg-icons');
|
|
9
7
|
var proLightSvgIcons = require('@fortawesome/pro-light-svg-icons');
|
|
10
8
|
var reactFontawesome = require('@fortawesome/react-fontawesome');
|
|
9
|
+
var lodash = require('lodash');
|
|
11
10
|
var dateFns = require('date-fns');
|
|
11
|
+
var nanoid = require('nanoid');
|
|
12
12
|
var reactDom = require('react-dom');
|
|
13
13
|
var reactTinyPopover = require('react-tiny-popover');
|
|
14
14
|
var reactRouterDom = require('react-router-dom');
|
|
@@ -17,29 +17,97 @@ var ReactSlider = require('react-slider');
|
|
|
17
17
|
function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; }
|
|
18
18
|
|
|
19
19
|
function _interopNamespace(e) {
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
20
|
+
if (e && e.__esModule) return e;
|
|
21
|
+
var n = Object.create(null);
|
|
22
|
+
if (e) {
|
|
23
|
+
Object.keys(e).forEach(function (k) {
|
|
24
|
+
if (k !== 'default') {
|
|
25
|
+
var d = Object.getOwnPropertyDescriptor(e, k);
|
|
26
|
+
Object.defineProperty(n, k, d.get ? d : {
|
|
27
|
+
enumerable: true,
|
|
28
|
+
get: function () {
|
|
29
|
+
return e[k];
|
|
30
|
+
}
|
|
31
|
+
});
|
|
32
|
+
}
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
n['default'] = e;
|
|
36
|
+
return Object.freeze(n);
|
|
37
37
|
}
|
|
38
38
|
|
|
39
|
-
var React__default = /*#__PURE__*/_interopDefaultLegacy(React);
|
|
40
39
|
var React__namespace = /*#__PURE__*/_interopNamespace(React);
|
|
40
|
+
var React__default = /*#__PURE__*/_interopDefaultLegacy(React);
|
|
41
41
|
var ReactSlider__default = /*#__PURE__*/_interopDefaultLegacy(ReactSlider);
|
|
42
42
|
|
|
43
|
+
/*! *****************************************************************************
|
|
44
|
+
Copyright (c) Microsoft Corporation.
|
|
45
|
+
|
|
46
|
+
Permission to use, copy, modify, and/or distribute this software for any
|
|
47
|
+
purpose with or without fee is hereby granted.
|
|
48
|
+
|
|
49
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
50
|
+
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
51
|
+
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
52
|
+
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
53
|
+
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
54
|
+
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
55
|
+
PERFORMANCE OF THIS SOFTWARE.
|
|
56
|
+
***************************************************************************** */
|
|
57
|
+
|
|
58
|
+
function __rest(s, e) {
|
|
59
|
+
var t = {};
|
|
60
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
61
|
+
t[p] = s[p];
|
|
62
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
63
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
64
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
65
|
+
t[p[i]] = s[p[i]];
|
|
66
|
+
}
|
|
67
|
+
return t;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
const ICONS = {
|
|
71
|
+
add: proSolidSvgIcons.faPlus,
|
|
72
|
+
delete: proSolidSvgIcons.faTrashAlt,
|
|
73
|
+
save: proSolidSvgIcons.faSave,
|
|
74
|
+
activate: proRegularSvgIcons.faCheckCircle,
|
|
75
|
+
deactivate: proRegularSvgIcons.faCircle,
|
|
76
|
+
online: proLightSvgIcons.faWifi,
|
|
77
|
+
offline: proLightSvgIcons.faWifiSlash,
|
|
78
|
+
noIcon: proSolidSvgIcons.faCrow,
|
|
79
|
+
close: proSolidSvgIcons.faTimes,
|
|
80
|
+
waiting: proSolidSvgIcons.faSync,
|
|
81
|
+
refresh: proSolidSvgIcons.faSync,
|
|
82
|
+
menu: proLightSvgIcons.faBars,
|
|
83
|
+
search: proLightSvgIcons.faSearch,
|
|
84
|
+
expand: proRegularSvgIcons.faChevronDown,
|
|
85
|
+
collapse: proRegularSvgIcons.faChevronUp,
|
|
86
|
+
help: proLightSvgIcons.faQuestionCircle,
|
|
87
|
+
debug: proLightSvgIcons.faNarwhal,
|
|
88
|
+
goTo: proLightSvgIcons.faChevronRight,
|
|
89
|
+
goBack: proLightSvgIcons.faChevronLeft,
|
|
90
|
+
download: proLightSvgIcons.faCloudDownload,
|
|
91
|
+
upload: proLightSvgIcons.faCloudUpload,
|
|
92
|
+
selected: proSolidSvgIcons.faCheckSquare,
|
|
93
|
+
unselected: proRegularSvgIcons.faSquare,
|
|
94
|
+
pagerLeft: proLightSvgIcons.faChevronLeft,
|
|
95
|
+
pagerRight: proLightSvgIcons.faChevronRight,
|
|
96
|
+
sortAsc: proRegularSvgIcons.faChevronUp,
|
|
97
|
+
sortDesc: proRegularSvgIcons.faChevronDown,
|
|
98
|
+
pickDate: proLightSvgIcons.faCalendarAlt,
|
|
99
|
+
copy: proLightSvgIcons.faCopy,
|
|
100
|
+
paste: proLightSvgIcons.faPaste,
|
|
101
|
+
clear: proRegularSvgIcons.faTimesCircle,
|
|
102
|
+
hide: proLightSvgIcons.faEyeSlash,
|
|
103
|
+
show: proLightSvgIcons.faEye
|
|
104
|
+
};
|
|
105
|
+
const Icon = (props) => {
|
|
106
|
+
var _a;
|
|
107
|
+
const icon = (_a = ICONS[props.id]) !== null && _a !== void 0 ? _a : ICONS['noIcon'];
|
|
108
|
+
return React__namespace.createElement(reactFontawesome.FontAwesomeIcon, { style: props.style, onClick: props.onClick, spin: props.spin, className: css.cx('icon', props.className), icon: icon });
|
|
109
|
+
};
|
|
110
|
+
|
|
43
111
|
/** Call this on your theme after messing with the props. It will re-build things that depend on sizes and colors. */
|
|
44
112
|
const calcDynamicThemeProps = (theme) => {
|
|
45
113
|
theme.controls.border = `${theme.controls.borderWidth} solid ${theme.colors.border}`;
|
|
@@ -47,6 +115,9 @@ const calcDynamicThemeProps = (theme) => {
|
|
|
47
115
|
theme.controls.focusOutlineShadow = `0px 0px 4px 2px ${theme.colors.focusOutline}`;
|
|
48
116
|
theme.controls.focusOutlineRequiredShadow = `0px 0px 4px 2px ${theme.colors.focusOutlineRequired}`;
|
|
49
117
|
theme.controls.dividerBorder = `2px solid ${theme.colors.divider}`;
|
|
118
|
+
theme.controls.inputErrorMinHeight = `calc(${theme.fonts.sizeSmall} * 1.5 + 4px)`;
|
|
119
|
+
theme.mediaQueries.desktop = `@media(min-width:${theme.breakpoints.desktop})`;
|
|
120
|
+
theme.mediaQueries.tablet = `@media(min-width:${theme.breakpoints.tablet})`;
|
|
50
121
|
};
|
|
51
122
|
const defaultTheme = {
|
|
52
123
|
colors: {
|
|
@@ -76,7 +147,7 @@ const defaultTheme = {
|
|
|
76
147
|
divider: 'rgba(0, 0, 0, 0.50)',
|
|
77
148
|
nav: '#7851a9',
|
|
78
149
|
navFont: 'rgba(255, 255, 255, 0.9)',
|
|
79
|
-
focusOutline: '
|
|
150
|
+
focusOutline: 'rgb(0 188 212 / 75%)',
|
|
80
151
|
progressBg: '#007bff63',
|
|
81
152
|
progressFill: '#007bff',
|
|
82
153
|
modalBg: 'white',
|
|
@@ -115,7 +186,8 @@ const defaultTheme = {
|
|
|
115
186
|
gap: '1rem',
|
|
116
187
|
dividerMargin: '1rem',
|
|
117
188
|
dividerBorder: '',
|
|
118
|
-
headerBoxShadow: '0px 2px 12px 6px rgba(0, 0, 0, 0.2)'
|
|
189
|
+
headerBoxShadow: '0px 2px 12px 6px rgba(0, 0, 0, 0.2)',
|
|
190
|
+
inputErrorMinHeight: ''
|
|
119
191
|
},
|
|
120
192
|
zIndexes: {
|
|
121
193
|
header: 50,
|
|
@@ -133,6 +205,10 @@ const defaultTheme = {
|
|
|
133
205
|
breakpoints: {
|
|
134
206
|
desktop: '800px',
|
|
135
207
|
tablet: '768px'
|
|
208
|
+
},
|
|
209
|
+
mediaQueries: {
|
|
210
|
+
desktop: '',
|
|
211
|
+
tablet: ''
|
|
136
212
|
}
|
|
137
213
|
};
|
|
138
214
|
calcDynamicThemeProps(defaultTheme);
|
|
@@ -153,193 +229,9 @@ const useThemeSafely = () => {
|
|
|
153
229
|
return defaultTheme;
|
|
154
230
|
};
|
|
155
231
|
|
|
156
|
-
|
|
157
|
-
const Backdrop$1 = (props) => {
|
|
158
|
-
var _a;
|
|
159
|
-
const showTimeMs = (_a = props.showTimeMs) !== null && _a !== void 0 ? _a : 250;
|
|
160
|
-
const backdropId = React__namespace.useRef('Backdrop' + nanoid.nanoid());
|
|
161
|
-
const theme = useThemeSafely();
|
|
162
|
-
const backdropStyles = css.css `
|
|
163
|
-
opacity: 0;
|
|
164
|
-
position: fixed;
|
|
165
|
-
top: 0;
|
|
166
|
-
left: 0;
|
|
167
|
-
right: 0;
|
|
168
|
-
bottom: 0;
|
|
169
|
-
background-color: ${theme.colors.backdrop};
|
|
170
|
-
transition: opacity ${showTimeMs}ms ease-in-out;
|
|
171
|
-
visibility: hidden;
|
|
172
|
-
user-select: none;
|
|
173
|
-
-webkit-tap-highlight-color: transparent;
|
|
174
|
-
`;
|
|
175
|
-
const showStyles = css.css `
|
|
176
|
-
z-index: ${theme.zIndexes.backdrop} !important;
|
|
177
|
-
opacity: 1.0 !important;
|
|
178
|
-
label:${backdropId.current};
|
|
179
|
-
`;
|
|
180
|
-
const bodyStyles = css.css `
|
|
181
|
-
overflow: hidden !important;
|
|
182
|
-
label:${backdropId.current};
|
|
183
|
-
`;
|
|
184
|
-
const bodyResponsiveStyles = css.css `
|
|
185
|
-
label:${backdropId.current};
|
|
186
|
-
@media(min-width:${theme.breakpoints.desktop}) {
|
|
187
|
-
overflow: auto !important;
|
|
188
|
-
}
|
|
189
|
-
`;
|
|
190
|
-
const bodyReverseResponsiveStyles = css.css `
|
|
191
|
-
${bodyStyles}
|
|
192
|
-
overflow: auto !important;
|
|
193
|
-
@media(min-width:${theme.breakpoints.desktop}) {
|
|
194
|
-
overflow: hidden !important;
|
|
195
|
-
}
|
|
196
|
-
`;
|
|
197
|
-
const styles = css.css `
|
|
198
|
-
${backdropStyles}
|
|
199
|
-
${props.onClick && `
|
|
200
|
-
cursor: pointer;
|
|
201
|
-
`}
|
|
202
|
-
${props.transparent && `
|
|
203
|
-
background-color: transparent;
|
|
204
|
-
transition: none;
|
|
205
|
-
`}
|
|
206
|
-
${props.children && `
|
|
207
|
-
display: flex;
|
|
208
|
-
justify-content:center;
|
|
209
|
-
align-items: center;
|
|
210
|
-
`}
|
|
211
|
-
${props.responsive && `
|
|
212
|
-
@media(min-width:${theme.breakpoints.desktop}) {
|
|
213
|
-
display: none;
|
|
214
|
-
}
|
|
215
|
-
`}
|
|
216
|
-
${props.reverseResponsive && `
|
|
217
|
-
display: none;
|
|
218
|
-
@media(min-width:${theme.breakpoints.desktop}) {
|
|
219
|
-
display: flex;
|
|
220
|
-
}
|
|
221
|
-
`}
|
|
222
|
-
`;
|
|
223
|
-
const backdrop = React__namespace.useRef(null);
|
|
224
|
-
React__namespace.useEffect(() => {
|
|
225
|
-
if (backdrop && backdrop.current) {
|
|
226
|
-
if (props.show && backdrop.current.style.visibility !== 'visible') {
|
|
227
|
-
backdrop.current.style.visibility = 'visible';
|
|
228
|
-
backdrop.current.classList.add(showStyles);
|
|
229
|
-
if (!props.allowScroll) {
|
|
230
|
-
document.body.classList.add(bodyStyles);
|
|
231
|
-
if (props.responsive) {
|
|
232
|
-
document.body.classList.add(bodyResponsiveStyles);
|
|
233
|
-
}
|
|
234
|
-
else if (props.reverseResponsive) {
|
|
235
|
-
document.body.classList.add(bodyReverseResponsiveStyles);
|
|
236
|
-
}
|
|
237
|
-
}
|
|
238
|
-
}
|
|
239
|
-
else if (!props.show && backdrop.current.style.visibility === 'visible') {
|
|
240
|
-
backdrop.current.classList.remove(showStyles);
|
|
241
|
-
if (backdrop && backdrop.current) {
|
|
242
|
-
backdrop.current.style.visibility = 'hidden';
|
|
243
|
-
if (!props.allowScroll) {
|
|
244
|
-
document.body.classList.remove(bodyStyles);
|
|
245
|
-
if (props.responsive) {
|
|
246
|
-
document.body.classList.remove(bodyResponsiveStyles);
|
|
247
|
-
}
|
|
248
|
-
else if (props.reverseResponsive) {
|
|
249
|
-
document.body.classList.remove(bodyReverseResponsiveStyles);
|
|
250
|
-
}
|
|
251
|
-
}
|
|
252
|
-
}
|
|
253
|
-
}
|
|
254
|
-
}
|
|
255
|
-
return () => {
|
|
256
|
-
if (backdrop && backdrop.current && !props.allowScroll) {
|
|
257
|
-
document.body.classList.remove(bodyStyles);
|
|
258
|
-
}
|
|
259
|
-
};
|
|
260
|
-
}, [props.show]);
|
|
261
|
-
return (React__namespace.createElement("div", { onMouseDown: e => {
|
|
262
|
-
var _a;
|
|
263
|
-
e.stopPropagation();
|
|
264
|
-
e.preventDefault();
|
|
265
|
-
(_a = props.onClick) === null || _a === void 0 ? void 0 : _a.call(props);
|
|
266
|
-
}, onClick: e => {
|
|
267
|
-
e.stopPropagation();
|
|
268
|
-
e.preventDefault();
|
|
269
|
-
}, ref: backdrop, className: css.cx('backdrop', styles, props.className) }, props.children));
|
|
270
|
-
};
|
|
271
|
-
|
|
272
|
-
/*! *****************************************************************************
|
|
273
|
-
Copyright (c) Microsoft Corporation.
|
|
274
|
-
|
|
275
|
-
Permission to use, copy, modify, and/or distribute this software for any
|
|
276
|
-
purpose with or without fee is hereby granted.
|
|
277
|
-
|
|
278
|
-
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
279
|
-
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
280
|
-
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
281
|
-
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
282
|
-
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
283
|
-
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
284
|
-
PERFORMANCE OF THIS SOFTWARE.
|
|
285
|
-
***************************************************************************** */
|
|
286
|
-
|
|
287
|
-
function __rest(s, e) {
|
|
288
|
-
var t = {};
|
|
289
|
-
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
290
|
-
t[p] = s[p];
|
|
291
|
-
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
292
|
-
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
293
|
-
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
294
|
-
t[p[i]] = s[p[i]];
|
|
295
|
-
}
|
|
296
|
-
return t;
|
|
297
|
-
}
|
|
298
|
-
|
|
299
|
-
const ICONS = {
|
|
300
|
-
add: proSolidSvgIcons.faPlus,
|
|
301
|
-
delete: proSolidSvgIcons.faTrashAlt,
|
|
302
|
-
save: proSolidSvgIcons.faSave,
|
|
303
|
-
activate: proRegularSvgIcons.faCheckCircle,
|
|
304
|
-
deactivate: proRegularSvgIcons.faCircle,
|
|
305
|
-
online: proLightSvgIcons.faWifi,
|
|
306
|
-
offline: proLightSvgIcons.faWifiSlash,
|
|
307
|
-
noIcon: proSolidSvgIcons.faCrow,
|
|
308
|
-
close: proSolidSvgIcons.faTimes,
|
|
309
|
-
waiting: proSolidSvgIcons.faSync,
|
|
310
|
-
refresh: proSolidSvgIcons.faSync,
|
|
311
|
-
menu: proLightSvgIcons.faBars,
|
|
312
|
-
search: proLightSvgIcons.faSearch,
|
|
313
|
-
expand: proRegularSvgIcons.faChevronDown,
|
|
314
|
-
collapse: proRegularSvgIcons.faChevronUp,
|
|
315
|
-
help: proLightSvgIcons.faQuestionCircle,
|
|
316
|
-
debug: proLightSvgIcons.faNarwhal,
|
|
317
|
-
goTo: proLightSvgIcons.faChevronRight,
|
|
318
|
-
goBack: proLightSvgIcons.faChevronLeft,
|
|
319
|
-
download: proLightSvgIcons.faCloudDownload,
|
|
320
|
-
upload: proLightSvgIcons.faCloudUpload,
|
|
321
|
-
selected: proSolidSvgIcons.faCheckSquare,
|
|
322
|
-
unselected: proRegularSvgIcons.faSquare,
|
|
323
|
-
pagerLeft: proLightSvgIcons.faChevronLeft,
|
|
324
|
-
pagerRight: proLightSvgIcons.faChevronRight,
|
|
325
|
-
sortAsc: proRegularSvgIcons.faChevronUp,
|
|
326
|
-
sortDesc: proRegularSvgIcons.faChevronDown,
|
|
327
|
-
pickDate: proLightSvgIcons.faCalendarAlt,
|
|
328
|
-
copy: proLightSvgIcons.faCopy,
|
|
329
|
-
paste: proLightSvgIcons.faPaste,
|
|
330
|
-
clear: proRegularSvgIcons.faTimesCircle,
|
|
331
|
-
hide: proLightSvgIcons.faEyeSlash,
|
|
332
|
-
show: proLightSvgIcons.faEye
|
|
333
|
-
};
|
|
334
|
-
const Icon = (props) => {
|
|
232
|
+
const Button = React__namespace.forwardRef((props, ref) => {
|
|
335
233
|
var _a;
|
|
336
|
-
const
|
|
337
|
-
return React__namespace.createElement(reactFontawesome.FontAwesomeIcon, { style: props.style, onClick: props.onClick, spin: props.spin, className: css.cx('icon', props.className), icon: icon });
|
|
338
|
-
};
|
|
339
|
-
|
|
340
|
-
const Button = (props) => {
|
|
341
|
-
var _a, _b;
|
|
342
|
-
const nativeProps = __rest(props, ["variant", "textAlign", "block", "round", "rightIcon", "leftIcon", "iconBlock", "small", "readonly", "waiting", "enforceMinWidth"]);
|
|
234
|
+
const nativeProps = __rest(props, ["variant", "round", "rightIcon", "leftIcon", "iconBlock", "small", "readOnly", "waiting", "enforceMinWidth"]);
|
|
343
235
|
const theme = useThemeSafely();
|
|
344
236
|
const buttonStyles = css.css `
|
|
345
237
|
padding-left: ${theme.controls.padding};
|
|
@@ -356,7 +248,6 @@ const Button = (props) => {
|
|
|
356
248
|
font-weight: bold;
|
|
357
249
|
flex-shrink: 0;
|
|
358
250
|
min-width: ${theme.controls.height};
|
|
359
|
-
text-align: ${(_a = props.textAlign) !== null && _a !== void 0 ? _a : 'center'};
|
|
360
251
|
|
|
361
252
|
&:disabled {
|
|
362
253
|
opacity: ${theme.controls.disabledOpacity};
|
|
@@ -475,7 +366,7 @@ const Button = (props) => {
|
|
|
475
366
|
${props.enforceMinWidth && `
|
|
476
367
|
min-width: ${theme.controls.formButtonMinWidth};
|
|
477
368
|
`}
|
|
478
|
-
${props.
|
|
369
|
+
${props.readOnly && `
|
|
479
370
|
cursor: default;
|
|
480
371
|
box-shadow: none;
|
|
481
372
|
pointer-events:none;
|
|
@@ -495,9 +386,6 @@ const Button = (props) => {
|
|
|
495
386
|
${props.round && `
|
|
496
387
|
border-radius: ${theme.controls.roundRadius};
|
|
497
388
|
`}
|
|
498
|
-
${props.block && `
|
|
499
|
-
width: 100%;
|
|
500
|
-
`}
|
|
501
389
|
${props.iconBlock && `
|
|
502
390
|
display: flex;
|
|
503
391
|
justify-content: space-between;
|
|
@@ -505,10 +393,94 @@ const Button = (props) => {
|
|
|
505
393
|
`}
|
|
506
394
|
`;
|
|
507
395
|
const disabled = props.disabled || props.waiting;
|
|
508
|
-
return (React__namespace.createElement("button", Object.assign({}, nativeProps, { disabled: disabled, className: css.cx('button', styles, props.className), type: (
|
|
396
|
+
return (React__namespace.createElement("button", Object.assign({}, nativeProps, { ref: ref, disabled: disabled, className: css.cx('button', styles, props.className), type: (_a = props.type) !== null && _a !== void 0 ? _a : 'button' }),
|
|
509
397
|
props.leftIcon && React__namespace.createElement("span", { className: css.css({ marginRight: '0.5rem' }) }, props.leftIcon),
|
|
510
398
|
props.waiting ? React__namespace.createElement(Icon, { id: "waiting", spin: true }) : props.children,
|
|
511
399
|
props.rightIcon && React__namespace.createElement("span", { className: css.css({ marginLeft: '0.5rem' }) }, props.rightIcon)));
|
|
400
|
+
});
|
|
401
|
+
|
|
402
|
+
const accordianExpandTimeMs = 250;
|
|
403
|
+
const accordianMaxHeight = 1020;
|
|
404
|
+
const accordianTimingFunction = 'ease-in-out';
|
|
405
|
+
// we need to apply the seperately so stuff doesn't hang over during expand/collapse.
|
|
406
|
+
// if we remove this and just keep overflow:hidden, autocompletes will get cut off in the subpanels.
|
|
407
|
+
const visibleStyle = css.css({
|
|
408
|
+
overflow: 'visible !important'
|
|
409
|
+
});
|
|
410
|
+
const Accordian = (props) => {
|
|
411
|
+
var _a, _b, _c, _d;
|
|
412
|
+
const [open, setOpen] = React__namespace.useState(false);
|
|
413
|
+
const theme = useThemeSafely();
|
|
414
|
+
const content = React__namespace.useRef(null);
|
|
415
|
+
const contentStyles = css.css({
|
|
416
|
+
overflow: 'hidden',
|
|
417
|
+
maxHeight: 0,
|
|
418
|
+
transition: `max-height ${(_a = props.expandTimeMs) !== null && _a !== void 0 ? _a : accordianExpandTimeMs}ms ${(_b = props.transitionTimingFunction) !== null && _b !== void 0 ? _b : accordianTimingFunction}`
|
|
419
|
+
});
|
|
420
|
+
const expandedContentStyles = css.css({
|
|
421
|
+
maxHeight: (_c = props.maxHeight) !== null && _c !== void 0 ? _c : accordianMaxHeight
|
|
422
|
+
});
|
|
423
|
+
const expandedContentWrapperStyles = !props.noPad ? css.css({
|
|
424
|
+
padding: '0 1rem 1rem 1rem'
|
|
425
|
+
}) : undefined;
|
|
426
|
+
React__namespace.useEffect(() => {
|
|
427
|
+
const currentContent = content.current;
|
|
428
|
+
if (currentContent) {
|
|
429
|
+
if (open) {
|
|
430
|
+
currentContent.classList.add(expandedContentStyles);
|
|
431
|
+
window.setTimeout(() => {
|
|
432
|
+
currentContent.classList.add(visibleStyle);
|
|
433
|
+
}, accordianExpandTimeMs);
|
|
434
|
+
}
|
|
435
|
+
else {
|
|
436
|
+
currentContent.classList.remove(visibleStyle, expandedContentStyles);
|
|
437
|
+
}
|
|
438
|
+
}
|
|
439
|
+
}, [open]);
|
|
440
|
+
React__namespace.useEffect(() => {
|
|
441
|
+
var _a;
|
|
442
|
+
if (props.open === undefined) {
|
|
443
|
+
// technically, we only need to use this effect if props.open was initialized with a boolean.
|
|
444
|
+
// you can't have conditional effects so here we go...
|
|
445
|
+
return;
|
|
446
|
+
}
|
|
447
|
+
setOpen((_a = props.open) !== null && _a !== void 0 ? _a : false);
|
|
448
|
+
}, [props.open]);
|
|
449
|
+
return (React__namespace.createElement("div", { className: "accordian" },
|
|
450
|
+
React__namespace.createElement(Button, { readOnly: props.disabled, variant: props.variant, className: css.cx(css.css({
|
|
451
|
+
display: 'flex',
|
|
452
|
+
alignItems: 'center',
|
|
453
|
+
justifyContent: 'space-between',
|
|
454
|
+
height: 'auto',
|
|
455
|
+
minHeight: theme.controls.height,
|
|
456
|
+
width: ((_d = props.block) !== null && _d !== void 0 ? _d : true) ? '100%' : 'auto'
|
|
457
|
+
}, props.className)), onClick: e => {
|
|
458
|
+
e.stopPropagation();
|
|
459
|
+
if (props.onChange) {
|
|
460
|
+
props.onChange(!open);
|
|
461
|
+
}
|
|
462
|
+
else {
|
|
463
|
+
setOpen(!open);
|
|
464
|
+
}
|
|
465
|
+
}, rightIcon: !props.disabled ? React__namespace.createElement(Icon, { id: open ? 'collapse' : 'expand' }) : undefined },
|
|
466
|
+
React__namespace.createElement("span", null, props.header)),
|
|
467
|
+
React__namespace.createElement("div", { ref: content, className: css.cx('accordian__body', contentStyles) },
|
|
468
|
+
React__namespace.createElement("div", { className: expandedContentWrapperStyles }, props.children))));
|
|
469
|
+
};
|
|
470
|
+
const useAccordianState = (count, openIndex) => {
|
|
471
|
+
const [panels, setShowPanel] = React__namespace.useState(new Array(count).fill(false).map((b, i) => {
|
|
472
|
+
return i === openIndex;
|
|
473
|
+
}));
|
|
474
|
+
return [
|
|
475
|
+
panels,
|
|
476
|
+
(index, open) => {
|
|
477
|
+
setShowPanel(previousState => {
|
|
478
|
+
const newState = previousState.slice().fill(false);
|
|
479
|
+
newState[index] = open;
|
|
480
|
+
return newState;
|
|
481
|
+
});
|
|
482
|
+
}
|
|
483
|
+
];
|
|
512
484
|
};
|
|
513
485
|
|
|
514
486
|
const DEFAULT_DEBOUNCE_MS = 250;
|
|
@@ -852,25 +824,12 @@ const Text = (props) => {
|
|
|
852
824
|
}, props.children);
|
|
853
825
|
};
|
|
854
826
|
|
|
855
|
-
|
|
856
|
-
const
|
|
857
|
-
|
|
858
|
-
return '';
|
|
859
|
-
}
|
|
860
|
-
if (typeof v === 'string') {
|
|
861
|
-
return v;
|
|
862
|
-
}
|
|
863
|
-
return v.name;
|
|
864
|
-
};
|
|
865
|
-
const getAutocompleteValueId = (v) => {
|
|
866
|
-
if (typeof v === 'string') {
|
|
867
|
-
return v;
|
|
868
|
-
}
|
|
869
|
-
return v.id;
|
|
870
|
-
};
|
|
871
|
-
//TB: will need to use the new input
|
|
827
|
+
//TB: FUTURE will need to use the new input
|
|
828
|
+
const defaultMaxShownValues = 7;
|
|
829
|
+
const buttonMarkerClass = 'ListItem__button';
|
|
872
830
|
const Autocomplete = (p) => {
|
|
873
831
|
var _a;
|
|
832
|
+
const theme = useThemeSafely();
|
|
874
833
|
const element = React__namespace.useRef(null);
|
|
875
834
|
const input = React__namespace.useRef(null);
|
|
876
835
|
const list = React__namespace.useRef(null);
|
|
@@ -878,7 +837,7 @@ const Autocomplete = (p) => {
|
|
|
878
837
|
const showValues = React__namespace.useMemo(() => values.length > 0, [values]);
|
|
879
838
|
const shownValues = React__namespace.useMemo(() => {
|
|
880
839
|
var _a;
|
|
881
|
-
return values.slice(0, (_a = p.maxShownValues) !== null && _a !== void 0 ? _a :
|
|
840
|
+
return values.slice(0, (_a = p.maxShownValues) !== null && _a !== void 0 ? _a : defaultMaxShownValues);
|
|
882
841
|
}, [values]);
|
|
883
842
|
const onChangeForOptions = React__namespace.useRef(lodash.debounce((value) => {
|
|
884
843
|
if (!p.minChars || value.length >= p.minChars) {
|
|
@@ -892,45 +851,7 @@ const Autocomplete = (p) => {
|
|
|
892
851
|
else {
|
|
893
852
|
setValues([]);
|
|
894
853
|
}
|
|
895
|
-
}, (_a = p.getOptionsDebounceMs) !== null && _a !== void 0 ? _a : 0, { leading:
|
|
896
|
-
const theme = useThemeSafely();
|
|
897
|
-
const baseClass = css.css `
|
|
898
|
-
label: Autocomplete;
|
|
899
|
-
position: relative;
|
|
900
|
-
width: 100%;
|
|
901
|
-
`;
|
|
902
|
-
let listBorderRadius = '';
|
|
903
|
-
if (p.round || theme.controls.borderRadius) {
|
|
904
|
-
listBorderRadius = theme.controls.borderRadius || '0.5rem';
|
|
905
|
-
}
|
|
906
|
-
const listClass = css.css({
|
|
907
|
-
position: 'absolute',
|
|
908
|
-
width: '100%',
|
|
909
|
-
border: theme.controls.border,
|
|
910
|
-
borderRadius: listBorderRadius,
|
|
911
|
-
boxShadow: theme.controls.boxShadow,
|
|
912
|
-
backgroundColor: theme.colors.bg,
|
|
913
|
-
marginTop: `-4px !important`,
|
|
914
|
-
zIndex: theme.zIndexes.backdrop,
|
|
915
|
-
'li:first-child button': {
|
|
916
|
-
borderTopRightRadius: listBorderRadius,
|
|
917
|
-
borderTopLeftRadius: listBorderRadius,
|
|
918
|
-
},
|
|
919
|
-
'li:last-child button': {
|
|
920
|
-
borderBottomRightRadius: listBorderRadius,
|
|
921
|
-
borderBottomLeftRadius: listBorderRadius,
|
|
922
|
-
}
|
|
923
|
-
});
|
|
924
|
-
const inputClass = css.css `
|
|
925
|
-
${showValues && `
|
|
926
|
-
z-index: ${theme.zIndexes.backdrop};
|
|
927
|
-
position: relative;
|
|
928
|
-
`}
|
|
929
|
-
`;
|
|
930
|
-
const buttonStyles = css.css({
|
|
931
|
-
borderRadius: 0,
|
|
932
|
-
});
|
|
933
|
-
const buttonMarkerClass = 'ListItem__button';
|
|
854
|
+
}, (_a = p.getOptionsDebounceMs) !== null && _a !== void 0 ? _a : 0, { leading: false, trailing: true }));
|
|
934
855
|
const getNextTabElement = (fromIndex, direction) => {
|
|
935
856
|
var _a, _b, _c;
|
|
936
857
|
if (fromIndex === -1) {
|
|
@@ -950,15 +871,41 @@ const Autocomplete = (p) => {
|
|
|
950
871
|
}
|
|
951
872
|
}
|
|
952
873
|
};
|
|
953
|
-
|
|
954
|
-
|
|
874
|
+
React__namespace.useEffect(() => {
|
|
875
|
+
const clearItems = () => {
|
|
876
|
+
if (values.length > 0) {
|
|
877
|
+
setValues([]);
|
|
878
|
+
}
|
|
879
|
+
};
|
|
880
|
+
document.addEventListener('click', clearItems);
|
|
881
|
+
return () => {
|
|
882
|
+
document.removeEventListener('click', clearItems);
|
|
883
|
+
};
|
|
884
|
+
}, [values]);
|
|
885
|
+
let listBorderRadius = '';
|
|
886
|
+
if (p.round || theme.controls.borderRadius) {
|
|
887
|
+
listBorderRadius = theme.controls.borderRadius || '0.5rem';
|
|
888
|
+
}
|
|
889
|
+
return (React__namespace.createElement("div", { onClick: e => {
|
|
890
|
+
e.stopPropagation();
|
|
891
|
+
}, onKeyDown: e => {
|
|
892
|
+
var _a;
|
|
893
|
+
if (e.key === 'Escape') {
|
|
894
|
+
setValues([]);
|
|
895
|
+
(_a = input.current) === null || _a === void 0 ? void 0 : _a.focus();
|
|
896
|
+
}
|
|
897
|
+
}, ref: element, className: css.cx(css.css({
|
|
898
|
+
position: 'relative',
|
|
899
|
+
width: '100%',
|
|
900
|
+
label: 'Autocomplete'
|
|
901
|
+
}), 'autocomplete') },
|
|
955
902
|
React__namespace.createElement(TabLocker, { disabled: !showValues, style: { position: 'relative' } },
|
|
956
|
-
React__namespace.createElement(Input, { inputAriaAttributes: p.inputAriaAttributes, ref: input, debounceMs: 0, type: "text", value: getAutocompleteValueText(p.value), round: p.round, rightControl: p.rightControl, placeholder: p.placeholder, id: p.id, disabled: p.disabled, className: p.className, inputClassName:
|
|
903
|
+
React__namespace.createElement(Input, { inputAriaAttributes: p.inputAriaAttributes, ref: input, debounceMs: 0, type: "text", value: getAutocompleteValueText(p.value), round: p.round, rightControl: p.rightControl, placeholder: p.placeholder, id: p.id, disabled: p.disabled, className: p.className, inputClassName: p.inputClassName, maxLength: p.maxLength, required: p.required, onChange: v => {
|
|
957
904
|
const value = v;
|
|
958
905
|
p.onChange(value);
|
|
959
906
|
onChangeForOptions.current(value);
|
|
960
907
|
}, onKeyDown: e => {
|
|
961
|
-
var _a, _b;
|
|
908
|
+
var _a, _b, _c;
|
|
962
909
|
if (showValues) {
|
|
963
910
|
if (e.key === 'ArrowDown') {
|
|
964
911
|
e.preventDefault();
|
|
@@ -971,8 +918,26 @@ const Autocomplete = (p) => {
|
|
|
971
918
|
(_b = getNextTabElement(-1, -1)) === null || _b === void 0 ? void 0 : _b.focus();
|
|
972
919
|
}
|
|
973
920
|
}
|
|
921
|
+
(_c = p.onKeyDown) === null || _c === void 0 ? void 0 : _c.call(p, e);
|
|
974
922
|
}, onKeyPress: e => { var _a; return (_a = p.onKeyPress) === null || _a === void 0 ? void 0 : _a.call(p, e); } }),
|
|
975
|
-
showValues && (React__namespace.createElement(List, { ref: list, className:
|
|
923
|
+
showValues && (React__namespace.createElement(List, { ref: list, className: css.css({
|
|
924
|
+
position: 'absolute',
|
|
925
|
+
width: '100%',
|
|
926
|
+
border: theme.controls.border,
|
|
927
|
+
borderRadius: listBorderRadius,
|
|
928
|
+
boxShadow: theme.controls.boxShadow,
|
|
929
|
+
backgroundColor: theme.colors.bg,
|
|
930
|
+
marginTop: `-4px !important`,
|
|
931
|
+
zIndex: theme.zIndexes.backdrop,
|
|
932
|
+
'li:first-child button': {
|
|
933
|
+
borderTopRightRadius: listBorderRadius,
|
|
934
|
+
borderTopLeftRadius: listBorderRadius,
|
|
935
|
+
},
|
|
936
|
+
'li:last-child button': {
|
|
937
|
+
borderBottomRightRadius: listBorderRadius,
|
|
938
|
+
borderBottomLeftRadius: listBorderRadius,
|
|
939
|
+
}
|
|
940
|
+
}) },
|
|
976
941
|
shownValues.map((value, listItemIndex) => {
|
|
977
942
|
return (React__namespace.createElement(ListItem, { key: getAutocompleteValueId(value), variant: "full" },
|
|
978
943
|
React__namespace.createElement(Button, { onKeyDown: e => {
|
|
@@ -987,7 +952,9 @@ const Autocomplete = (p) => {
|
|
|
987
952
|
e.preventDefault();
|
|
988
953
|
(_b = getNextTabElement(listItemIndex, -1)) === null || _b === void 0 ? void 0 : _b.focus();
|
|
989
954
|
}
|
|
990
|
-
}, className: css.cx(buttonMarkerClass + listItemIndex,
|
|
955
|
+
}, className: css.cx(buttonMarkerClass + listItemIndex, css.css({
|
|
956
|
+
borderRadius: 0,
|
|
957
|
+
})), onClick: () => {
|
|
991
958
|
p.onPick(value);
|
|
992
959
|
setValues([]);
|
|
993
960
|
setTimeout(() => {
|
|
@@ -1006,68 +973,208 @@ const Autocomplete = (p) => {
|
|
|
1006
973
|
" of ",
|
|
1007
974
|
values.length.toLocaleString(),
|
|
1008
975
|
" results."))))))));
|
|
976
|
+
};
|
|
977
|
+
const getAutocompleteValueText = (v) => {
|
|
978
|
+
if (!v) {
|
|
979
|
+
return '';
|
|
980
|
+
}
|
|
981
|
+
if (typeof v === 'string') {
|
|
982
|
+
return v;
|
|
983
|
+
}
|
|
984
|
+
return v.name;
|
|
985
|
+
};
|
|
986
|
+
const getAutocompleteValueId = (v) => {
|
|
987
|
+
if (typeof v === 'string') {
|
|
988
|
+
return v;
|
|
989
|
+
}
|
|
990
|
+
return v.id;
|
|
991
|
+
};
|
|
992
|
+
|
|
993
|
+
/** @deprecated Use Backdrop2 going forward. */
|
|
994
|
+
const Backdrop$1 = (props) => {
|
|
995
|
+
var _a;
|
|
996
|
+
const showTimeMs = (_a = props.showTimeMs) !== null && _a !== void 0 ? _a : 250;
|
|
997
|
+
const backdropId = React__namespace.useRef('Backdrop' + nanoid.nanoid());
|
|
998
|
+
const theme = useThemeSafely();
|
|
999
|
+
const backdropStyles = css.css `
|
|
1000
|
+
opacity: 0;
|
|
1001
|
+
position: fixed;
|
|
1002
|
+
top: 0;
|
|
1003
|
+
left: 0;
|
|
1004
|
+
right: 0;
|
|
1005
|
+
bottom: 0;
|
|
1006
|
+
background-color: ${theme.colors.backdrop};
|
|
1007
|
+
transition: opacity ${showTimeMs}ms ease-in-out;
|
|
1008
|
+
visibility: hidden;
|
|
1009
|
+
user-select: none;
|
|
1010
|
+
-webkit-tap-highlight-color: transparent;
|
|
1011
|
+
`;
|
|
1012
|
+
const showStyles = css.css `
|
|
1013
|
+
z-index: ${theme.zIndexes.backdrop} !important;
|
|
1014
|
+
opacity: 1.0 !important;
|
|
1015
|
+
label:${backdropId.current};
|
|
1016
|
+
`;
|
|
1017
|
+
const bodyStyles = css.css `
|
|
1018
|
+
overflow: hidden !important;
|
|
1019
|
+
label:${backdropId.current};
|
|
1020
|
+
`;
|
|
1021
|
+
const bodyResponsiveStyles = css.css `
|
|
1022
|
+
label:${backdropId.current};
|
|
1023
|
+
@media(min-width:${theme.breakpoints.desktop}) {
|
|
1024
|
+
overflow: auto !important;
|
|
1025
|
+
}
|
|
1026
|
+
`;
|
|
1027
|
+
const bodyReverseResponsiveStyles = css.css `
|
|
1028
|
+
${bodyStyles}
|
|
1029
|
+
overflow: auto !important;
|
|
1030
|
+
@media(min-width:${theme.breakpoints.desktop}) {
|
|
1031
|
+
overflow: hidden !important;
|
|
1032
|
+
}
|
|
1033
|
+
`;
|
|
1034
|
+
const styles = css.css `
|
|
1035
|
+
${backdropStyles}
|
|
1036
|
+
${props.onClick && `
|
|
1037
|
+
cursor: pointer;
|
|
1038
|
+
`}
|
|
1039
|
+
${props.transparent && `
|
|
1040
|
+
background-color: transparent;
|
|
1041
|
+
transition: none;
|
|
1042
|
+
`}
|
|
1043
|
+
${props.children && `
|
|
1044
|
+
display: flex;
|
|
1045
|
+
justify-content:center;
|
|
1046
|
+
align-items: center;
|
|
1047
|
+
`}
|
|
1048
|
+
${props.responsive && `
|
|
1049
|
+
@media(min-width:${theme.breakpoints.desktop}) {
|
|
1050
|
+
display: none;
|
|
1051
|
+
}
|
|
1052
|
+
`}
|
|
1053
|
+
${props.reverseResponsive && `
|
|
1054
|
+
display: none;
|
|
1055
|
+
@media(min-width:${theme.breakpoints.desktop}) {
|
|
1056
|
+
display: flex;
|
|
1057
|
+
}
|
|
1058
|
+
`}
|
|
1059
|
+
`;
|
|
1060
|
+
const backdrop = React__namespace.useRef(null);
|
|
1061
|
+
React__namespace.useEffect(() => {
|
|
1062
|
+
if (backdrop && backdrop.current) {
|
|
1063
|
+
if (props.show && backdrop.current.style.visibility !== 'visible') {
|
|
1064
|
+
backdrop.current.style.visibility = 'visible';
|
|
1065
|
+
backdrop.current.classList.add(showStyles);
|
|
1066
|
+
if (!props.allowScroll) {
|
|
1067
|
+
document.body.classList.add(bodyStyles);
|
|
1068
|
+
if (props.responsive) {
|
|
1069
|
+
document.body.classList.add(bodyResponsiveStyles);
|
|
1070
|
+
}
|
|
1071
|
+
else if (props.reverseResponsive) {
|
|
1072
|
+
document.body.classList.add(bodyReverseResponsiveStyles);
|
|
1073
|
+
}
|
|
1074
|
+
}
|
|
1075
|
+
}
|
|
1076
|
+
else if (!props.show && backdrop.current.style.visibility === 'visible') {
|
|
1077
|
+
backdrop.current.classList.remove(showStyles);
|
|
1078
|
+
if (backdrop && backdrop.current) {
|
|
1079
|
+
backdrop.current.style.visibility = 'hidden';
|
|
1080
|
+
if (!props.allowScroll) {
|
|
1081
|
+
document.body.classList.remove(bodyStyles);
|
|
1082
|
+
if (props.responsive) {
|
|
1083
|
+
document.body.classList.remove(bodyResponsiveStyles);
|
|
1084
|
+
}
|
|
1085
|
+
else if (props.reverseResponsive) {
|
|
1086
|
+
document.body.classList.remove(bodyReverseResponsiveStyles);
|
|
1087
|
+
}
|
|
1088
|
+
}
|
|
1089
|
+
}
|
|
1090
|
+
}
|
|
1091
|
+
}
|
|
1092
|
+
return () => {
|
|
1093
|
+
if (backdrop && backdrop.current && !props.allowScroll) {
|
|
1094
|
+
document.body.classList.remove(bodyStyles);
|
|
1095
|
+
}
|
|
1096
|
+
};
|
|
1097
|
+
}, [props.show]);
|
|
1098
|
+
return (React__namespace.createElement("div", { onMouseDown: e => {
|
|
1099
|
+
var _a;
|
|
1100
|
+
e.stopPropagation();
|
|
1101
|
+
e.preventDefault();
|
|
1102
|
+
(_a = props.onClick) === null || _a === void 0 ? void 0 : _a.call(props);
|
|
1103
|
+
}, onClick: e => {
|
|
1104
|
+
e.stopPropagation();
|
|
1105
|
+
e.preventDefault();
|
|
1106
|
+
}, ref: backdrop, className: css.cx('backdrop', styles, props.className) }, props.children));
|
|
1107
|
+
};
|
|
1108
|
+
|
|
1109
|
+
/** useEffect but ignores the first call on component mount. */
|
|
1110
|
+
const useIgnoreMount = (effect, deps) => {
|
|
1111
|
+
const mounted = React__default['default'].useRef(false);
|
|
1112
|
+
React__default['default'].useEffect(() => {
|
|
1113
|
+
if (!mounted.current) {
|
|
1114
|
+
mounted.current = true;
|
|
1115
|
+
}
|
|
1116
|
+
else {
|
|
1117
|
+
effect();
|
|
1118
|
+
}
|
|
1119
|
+
}, deps);
|
|
1009
1120
|
};
|
|
1010
1121
|
|
|
1011
1122
|
const useLogger = (componentName, enabled) => {
|
|
1012
1123
|
return (...messages) => {
|
|
1013
1124
|
if (enabled) {
|
|
1014
1125
|
// tslint:disable-next-line
|
|
1015
|
-
console.log(componentName
|
|
1126
|
+
console.log(`[${componentName}]`, ...messages);
|
|
1016
1127
|
}
|
|
1017
1128
|
};
|
|
1018
1129
|
};
|
|
1019
1130
|
|
|
1131
|
+
const portalId = 'backdrop';
|
|
1020
1132
|
const BackdropContext = React__default['default'].createContext({
|
|
1021
1133
|
showing: false,
|
|
1022
1134
|
showCount: 0,
|
|
1023
|
-
portalId:
|
|
1024
|
-
setShow: s => {
|
|
1135
|
+
portalId: portalId,
|
|
1136
|
+
setShow: (s, f) => {
|
|
1025
1137
|
/* empty */
|
|
1026
1138
|
}
|
|
1027
1139
|
});
|
|
1028
1140
|
const BackdropContextProvider = (p) => {
|
|
1029
1141
|
var _a;
|
|
1030
1142
|
const [showCount, setShowCount] = React.useState(0);
|
|
1031
|
-
const log = useLogger('BackdropContextProvider', (_a = p.
|
|
1032
|
-
if (p.
|
|
1143
|
+
const log = useLogger('BackdropContextProvider', (_a = p.__debug) !== null && _a !== void 0 ? _a : false);
|
|
1144
|
+
if (p.__debug) {
|
|
1033
1145
|
React.useEffect(() => {
|
|
1034
1146
|
log('mounted');
|
|
1035
1147
|
return () => {
|
|
1036
1148
|
log('un-mounted');
|
|
1037
1149
|
};
|
|
1038
1150
|
}, []);
|
|
1039
|
-
|
|
1040
|
-
log('re-rendered');
|
|
1041
|
-
});
|
|
1042
|
-
React.useEffect(() => {
|
|
1151
|
+
useIgnoreMount(() => {
|
|
1043
1152
|
log('showCount changed', showCount);
|
|
1044
1153
|
}, [showCount]);
|
|
1045
1154
|
}
|
|
1046
1155
|
return (React__default['default'].createElement(BackdropContext.Provider, { value: {
|
|
1047
|
-
portalId:
|
|
1156
|
+
portalId: portalId,
|
|
1048
1157
|
showing: showCount > 0,
|
|
1049
1158
|
showCount: showCount,
|
|
1050
|
-
setShow: (show) => {
|
|
1159
|
+
setShow: (show, from) => {
|
|
1051
1160
|
if (show) {
|
|
1052
1161
|
setShowCount(s => {
|
|
1053
1162
|
const count = s + 1;
|
|
1054
|
-
log(
|
|
1055
|
-
log('showCount was', showCount);
|
|
1163
|
+
log(`setShow from ${from} ${s} -> ${count}`);
|
|
1056
1164
|
return count;
|
|
1057
1165
|
});
|
|
1058
1166
|
}
|
|
1059
1167
|
else {
|
|
1060
1168
|
setShowCount(s => {
|
|
1061
1169
|
const count = Math.max(0, s - 1);
|
|
1062
|
-
log(
|
|
1063
|
-
log('showCount was', showCount);
|
|
1170
|
+
log(`setShow from ${from} ${s} -> ${count}`);
|
|
1064
1171
|
return count;
|
|
1065
1172
|
});
|
|
1066
1173
|
}
|
|
1067
1174
|
}
|
|
1068
1175
|
} },
|
|
1069
1176
|
p.children,
|
|
1070
|
-
p.
|
|
1177
|
+
p.__debug && (React__default['default'].createElement("p", { className: css.css({
|
|
1071
1178
|
position: 'fixed',
|
|
1072
1179
|
top: 0, right: 0,
|
|
1073
1180
|
backgroundColor: '#ff00004f',
|
|
@@ -1084,23 +1191,20 @@ const BackdropOverlay = (p) => {
|
|
|
1084
1191
|
const context = React.useContext(BackdropContext);
|
|
1085
1192
|
const theme = useThemeSafely();
|
|
1086
1193
|
const showTimeMs = (_a = p.showTimeMs) !== null && _a !== void 0 ? _a : 250;
|
|
1087
|
-
const log = useLogger('BackdropOverlay', (_b = p.
|
|
1088
|
-
if (p.
|
|
1194
|
+
const log = useLogger('BackdropOverlay', (_b = p.__debug) !== null && _b !== void 0 ? _b : false);
|
|
1195
|
+
if (p.__debug) {
|
|
1089
1196
|
React.useEffect(() => {
|
|
1090
1197
|
log('mounted');
|
|
1091
1198
|
return () => {
|
|
1092
1199
|
log('unmounted');
|
|
1093
1200
|
};
|
|
1094
1201
|
}, []);
|
|
1095
|
-
|
|
1096
|
-
log('re-rendered');
|
|
1097
|
-
});
|
|
1098
|
-
React.useEffect(() => {
|
|
1202
|
+
useIgnoreMount(() => {
|
|
1099
1203
|
log('context.showing changed', context.showing);
|
|
1100
1204
|
}, [context.showing]);
|
|
1101
1205
|
}
|
|
1102
1206
|
return (React__default['default'].createElement("div", { onClick: () => {
|
|
1103
|
-
context === null || context === void 0 ? void 0 : context.setShow(false);
|
|
1207
|
+
context === null || context === void 0 ? void 0 : context.setShow(false, 'BackdropOverlay');
|
|
1104
1208
|
log('onClick', 'setShow', false);
|
|
1105
1209
|
}, id: context === null || context === void 0 ? void 0 : context.portalId, className: css.css({
|
|
1106
1210
|
cursor: 'pointer',
|
|
@@ -1116,12 +1220,12 @@ const BackdropOverlay = (p) => {
|
|
|
1116
1220
|
}) }));
|
|
1117
1221
|
};
|
|
1118
1222
|
const Backdrop = (p) => {
|
|
1119
|
-
return (React__default['default'].createElement(BackdropContextProvider, {
|
|
1223
|
+
return (React__default['default'].createElement(BackdropContextProvider, { __debug: p.__debug },
|
|
1120
1224
|
React__default['default'].createElement("div", { className: css.css({
|
|
1121
1225
|
height: '100%'
|
|
1122
1226
|
}) },
|
|
1123
1227
|
p.children,
|
|
1124
|
-
React__default['default'].createElement(BackdropOverlay, { showTimeMs: p.showTimeMs,
|
|
1228
|
+
React__default['default'].createElement(BackdropOverlay, { showTimeMs: p.showTimeMs, __debug: p.__debug }))));
|
|
1125
1229
|
};
|
|
1126
1230
|
|
|
1127
1231
|
const Calendar = (p) => {
|
|
@@ -1217,7 +1321,7 @@ const Calendar = (p) => {
|
|
|
1217
1321
|
};
|
|
1218
1322
|
|
|
1219
1323
|
const Checkbox = (props) => {
|
|
1220
|
-
const inputProps = __rest(props, ["checked", "onChange", "label", "checkedIcon", "uncheckedIcon", "checkedThemeColor", "checkedColor", "
|
|
1324
|
+
const inputProps = __rest(props, ["checked", "onChange", "label", "checkedIcon", "uncheckedIcon", "checkedThemeColor", "checkedColor", "readOnly"]);
|
|
1221
1325
|
const selected = props.checkedIcon || 'selected';
|
|
1222
1326
|
const unselected = props.uncheckedIcon || 'unselected';
|
|
1223
1327
|
const theme = useThemeSafely();
|
|
@@ -1232,7 +1336,7 @@ const Checkbox = (props) => {
|
|
|
1232
1336
|
}
|
|
1233
1337
|
const checkboxStyles = css.css `
|
|
1234
1338
|
display: inline-block;
|
|
1235
|
-
${!props.disabled && !props.
|
|
1339
|
+
${!props.disabled && !props.readOnly && `
|
|
1236
1340
|
&:hover {
|
|
1237
1341
|
filter: ${theme.controls.hoverBrightness};
|
|
1238
1342
|
}
|
|
@@ -1246,7 +1350,7 @@ const Checkbox = (props) => {
|
|
|
1246
1350
|
${props.disabled && `
|
|
1247
1351
|
cursor: not-allowed;
|
|
1248
1352
|
`}
|
|
1249
|
-
${props.
|
|
1353
|
+
${props.readOnly && `
|
|
1250
1354
|
cursor: default;
|
|
1251
1355
|
`}
|
|
1252
1356
|
`;
|
|
@@ -1258,7 +1362,7 @@ const Checkbox = (props) => {
|
|
|
1258
1362
|
width: 0;
|
|
1259
1363
|
opacity: 0;
|
|
1260
1364
|
|
|
1261
|
-
${!props.
|
|
1365
|
+
${!props.readOnly && `
|
|
1262
1366
|
&:focus + .checkboxIcon {
|
|
1263
1367
|
box-shadow: ${theme.controls.focusOutlineShadow};
|
|
1264
1368
|
}
|
|
@@ -1272,7 +1376,7 @@ const Checkbox = (props) => {
|
|
|
1272
1376
|
background-color: ${theme.colors.disabled};
|
|
1273
1377
|
cursor: not-allowed;
|
|
1274
1378
|
`}
|
|
1275
|
-
${props.
|
|
1379
|
+
${props.readOnly && `
|
|
1276
1380
|
cursor: default;
|
|
1277
1381
|
`}
|
|
1278
1382
|
${props.checked && `
|
|
@@ -1281,8 +1385,8 @@ const Checkbox = (props) => {
|
|
|
1281
1385
|
`;
|
|
1282
1386
|
return (React__namespace.createElement("span", { className: css.cx('checkbox', checkboxStyles, props.className) },
|
|
1283
1387
|
React__namespace.createElement("label", { className: labelStyles },
|
|
1284
|
-
React__namespace.createElement("input", Object.assign({}, inputProps, { tabIndex: props.
|
|
1285
|
-
if (props.
|
|
1388
|
+
React__namespace.createElement("input", Object.assign({}, inputProps, { tabIndex: props.readOnly ? -1 : undefined, className: nativeCheckboxStyles, type: "checkbox", onChange: e => {
|
|
1389
|
+
if (props.readOnly) {
|
|
1286
1390
|
e.preventDefault();
|
|
1287
1391
|
return;
|
|
1288
1392
|
}
|
|
@@ -1293,11 +1397,41 @@ const Checkbox = (props) => {
|
|
|
1293
1397
|
props.children)));
|
|
1294
1398
|
};
|
|
1295
1399
|
|
|
1400
|
+
/** useEffect but it will only fire when the actual truthiness of the value changes.
|
|
1401
|
+
* Use for comparing previous states to next states without all the bullshit around useEffect and component mounting.
|
|
1402
|
+
*/
|
|
1403
|
+
const useBooleanChanged = (effect, dep) => {
|
|
1404
|
+
/*
|
|
1405
|
+
Why?
|
|
1406
|
+
useEffect with a dependency array will fire once on mount even though the dependency list doesn't change.
|
|
1407
|
+
Components like Modal need to communicate when their show status changes.
|
|
1408
|
+
useIgnoreMount is not enough because it only ignores the first render and is therefore a kludge.
|
|
1409
|
+
This is what we want regardless of mount status:
|
|
1410
|
+
true > false = Change
|
|
1411
|
+
false > true = Change
|
|
1412
|
+
true > true = No Change
|
|
1413
|
+
false > false = No Change
|
|
1414
|
+
undefined > false = No Change
|
|
1415
|
+
undefined > true = Change
|
|
1416
|
+
*/
|
|
1417
|
+
const lastValue = React.useRef(undefined);
|
|
1418
|
+
React.useEffect(() => {
|
|
1419
|
+
//console.log('[useBooleanChanged] useEffect called with', dep, 'was', lastValue.current ?? 'undefined')
|
|
1420
|
+
if (!!lastValue.current !== !!dep) {
|
|
1421
|
+
const previous = lastValue.current;
|
|
1422
|
+
lastValue.current = dep;
|
|
1423
|
+
effect(!!lastValue.current, !!previous);
|
|
1424
|
+
//console.log('[useBooleanChanged] change called')
|
|
1425
|
+
}
|
|
1426
|
+
}, [dep]);
|
|
1427
|
+
};
|
|
1428
|
+
|
|
1296
1429
|
// Taken from: https://github.com/react-bootstrap/dom-helpers/blob/master/src/scrollbarSize.ts
|
|
1297
1430
|
const canUseDom = !!(typeof window !== 'undefined' &&
|
|
1298
1431
|
window.document &&
|
|
1299
1432
|
window.document.createElement);
|
|
1300
1433
|
let size;
|
|
1434
|
+
/** Tells you actual width of the scroll bar. This can vary by browser. */
|
|
1301
1435
|
const useScrollbarSize = (recalc) => {
|
|
1302
1436
|
if ((!size && size !== 0) || recalc) {
|
|
1303
1437
|
if (canUseDom) {
|
|
@@ -1315,7 +1449,6 @@ const useScrollbarSize = (recalc) => {
|
|
|
1315
1449
|
return size;
|
|
1316
1450
|
};
|
|
1317
1451
|
|
|
1318
|
-
let htmlBodyStyles;
|
|
1319
1452
|
const Modal = (p) => {
|
|
1320
1453
|
var _a, _b, _c, _d;
|
|
1321
1454
|
const backdrop = React.useContext(BackdropContext);
|
|
@@ -1323,42 +1456,54 @@ const Modal = (p) => {
|
|
|
1323
1456
|
const theme = useThemeSafely();
|
|
1324
1457
|
const hasHeader = p.closeButton || p.heading;
|
|
1325
1458
|
const contentRef = React__default['default'].useRef(null);
|
|
1326
|
-
const log = useLogger(
|
|
1459
|
+
const log = useLogger((_a = p.id) !== null && _a !== void 0 ? _a : 'Modal', (_b = p.__debug) !== null && _b !== void 0 ? _b : false);
|
|
1460
|
+
const showing = React.useRef(p.show);
|
|
1461
|
+
const bodyStyles = React.useRef('');
|
|
1462
|
+
const tryRemoveBodyStyles = () => {
|
|
1463
|
+
if (bodyStyles.current) {
|
|
1464
|
+
log('removing singleton', bodyStyles.current);
|
|
1465
|
+
document.body.classList.remove(bodyStyles.current);
|
|
1466
|
+
}
|
|
1467
|
+
};
|
|
1327
1468
|
React.useEffect(() => {
|
|
1328
1469
|
log('mounted');
|
|
1329
1470
|
return () => {
|
|
1330
|
-
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
log('backdrop.
|
|
1335
|
-
|
|
1471
|
+
var _a;
|
|
1472
|
+
if (showing.current) {
|
|
1473
|
+
log(`un-mount in progress and this modal is showing. decrement the backdrop and try to remove singleton body styles.`);
|
|
1474
|
+
backdrop.setShow(false, (_a = p.id) !== null && _a !== void 0 ? _a : 'Modal');
|
|
1475
|
+
log('backdrop.setShow', false);
|
|
1476
|
+
tryRemoveBodyStyles();
|
|
1477
|
+
}
|
|
1478
|
+
else {
|
|
1479
|
+
log(`un-mount in progress but this modal is not showing. do nothing with the backdrop.`);
|
|
1336
1480
|
}
|
|
1337
1481
|
log('un-mounted');
|
|
1338
1482
|
};
|
|
1339
1483
|
}, []);
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
|
|
1343
|
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1484
|
+
useBooleanChanged((show, previousShow) => {
|
|
1485
|
+
var _a, _b, _c;
|
|
1486
|
+
log('show changed', `${previousShow !== null && previousShow !== void 0 ? previousShow : 'undefined'} > ${show}`);
|
|
1487
|
+
backdrop.setShow(show, (_a = p.id) !== null && _a !== void 0 ? _a : 'Modal');
|
|
1488
|
+
showing.current = show;
|
|
1489
|
+
log('backdrop.setShow', show);
|
|
1490
|
+
if (!bodyStyles.current) {
|
|
1491
|
+
bodyStyles.current = css.css({
|
|
1492
|
+
label: 'ModalBodyOverrides_' + ((_c = (_b = p.id) === null || _b === void 0 ? void 0 : _b.replace(/\s+/, '')) !== null && _c !== void 0 ? _c : nanoid.nanoid()),
|
|
1347
1493
|
overflow: 'hidden',
|
|
1348
1494
|
paddingRight: `${useScrollbarSize()}px`
|
|
1349
1495
|
});
|
|
1496
|
+
log('creating singleton bodyStyles', bodyStyles.current);
|
|
1350
1497
|
}
|
|
1351
|
-
if (
|
|
1352
|
-
log('adding
|
|
1353
|
-
document.body.classList.add(
|
|
1498
|
+
if (show) {
|
|
1499
|
+
log('this modal is showing. adding singleton bodyStyles', bodyStyles.current);
|
|
1500
|
+
document.body.classList.add(bodyStyles.current);
|
|
1354
1501
|
}
|
|
1355
1502
|
else {
|
|
1356
|
-
|
|
1357
|
-
|
|
1358
|
-
document.body.classList.remove(htmlBodyStyles);
|
|
1359
|
-
}
|
|
1503
|
+
log('this modal is hiding. try removing singleton bodyStyles');
|
|
1504
|
+
tryRemoveBodyStyles();
|
|
1360
1505
|
}
|
|
1361
|
-
},
|
|
1506
|
+
}, p.show);
|
|
1362
1507
|
React__default['default'].useLayoutEffect(() => {
|
|
1363
1508
|
var _a;
|
|
1364
1509
|
if (p.show === true) {
|
|
@@ -1454,320 +1599,47 @@ const ConfirmModal = (props) => {
|
|
|
1454
1599
|
const modalStyle = css.css `
|
|
1455
1600
|
${props.variant === 'omg' && `
|
|
1456
1601
|
.modalHeader {
|
|
1457
|
-
background-color:${theme.colors.omg};
|
|
1458
|
-
color:${theme.colors.omgFont};
|
|
1459
|
-
}
|
|
1460
|
-
`}
|
|
1461
|
-
`;
|
|
1462
|
-
return (React__namespace.createElement(Modal, { id: props.id,
|
|
1463
|
-
React__namespace.createElement("div", { className: css.css({ padding: '1rem' }) },
|
|
1464
|
-
React__namespace.createElement(Text, { align: "center" }, props.text),
|
|
1465
|
-
React__namespace.createElement("div", { className: css.css({ textAlign: 'center' }) },
|
|
1466
|
-
React__namespace.createElement(Button, { className: css.css({ margin: '0 0.5rem' }), enforceMinWidth: true, variant: props.variant === 'omg' ? "omg" : 'primary2', onClick: props.onConfirm }, props.confirmText || 'OK'),
|
|
1467
|
-
React__namespace.createElement(Button, { className: css.css({ margin: '0 0.5rem' }), enforceMinWidth: true, onClick: props.onCancel }, props.cancelText || 'Cancel')))));
|
|
1468
|
-
};
|
|
1469
|
-
|
|
1470
|
-
const CopyButton = (props) => {
|
|
1471
|
-
const [copied, setCopied] = React__namespace.useState(false);
|
|
1472
|
-
return (React__namespace.createElement(Button, { title: copied ? 'Copied!' : (props.title || 'Copy to clipboard'), variant: "icon", onBlur: () => {
|
|
1473
|
-
setCopied(false);
|
|
1474
|
-
}, onClick: e => {
|
|
1475
|
-
const button = e.currentTarget;
|
|
1476
|
-
let copySuccess = false;
|
|
1477
|
-
try {
|
|
1478
|
-
const text = document.querySelector(props.selector);
|
|
1479
|
-
text.select();
|
|
1480
|
-
copySuccess = document.execCommand('copy');
|
|
1481
|
-
// the input gets focus on select. bring it back.
|
|
1482
|
-
button.focus();
|
|
1483
|
-
}
|
|
1484
|
-
catch (err) {
|
|
1485
|
-
// You done wrong.
|
|
1486
|
-
}
|
|
1487
|
-
setCopied(copySuccess);
|
|
1488
|
-
} },
|
|
1489
|
-
React__namespace.createElement(Icon, { id: copied ? 'paste' : 'copy' })));
|
|
1490
|
-
};
|
|
1491
|
-
|
|
1492
|
-
const defaultMaxLength$1 = 100;
|
|
1493
|
-
const BaseInput = React__namespace.forwardRef((props, ref) => {
|
|
1494
|
-
var _a;
|
|
1495
|
-
const theme = useThemeSafely();
|
|
1496
|
-
const { rightControl, round, wrapperClassName } = props, nativeProps = __rest(props, ["rightControl", "round", "wrapperClassName"]);
|
|
1497
|
-
const inputStyles = css.css({
|
|
1498
|
-
fontFamily: theme.fonts.family,
|
|
1499
|
-
fontSize: theme.fonts.size,
|
|
1500
|
-
width: '100%',
|
|
1501
|
-
border: theme.controls.border,
|
|
1502
|
-
borderRadius: theme.controls.borderRadius,
|
|
1503
|
-
color: theme.colors.font,
|
|
1504
|
-
paddingLeft: theme.controls.padding,
|
|
1505
|
-
paddingRight: theme.controls.padding,
|
|
1506
|
-
height: theme.controls.height,
|
|
1507
|
-
transition: theme.controls.transition,
|
|
1508
|
-
':focus': {
|
|
1509
|
-
outline: 'none',
|
|
1510
|
-
boxShadow: theme.controls.focusOutlineShadow
|
|
1511
|
-
},
|
|
1512
|
-
':disabled': {
|
|
1513
|
-
backgroundColor: theme.colors.disabled,
|
|
1514
|
-
cursor: 'not-allowed'
|
|
1515
|
-
},
|
|
1516
|
-
':invalid': {
|
|
1517
|
-
borderColor: theme.colors.required,
|
|
1518
|
-
':focus': {
|
|
1519
|
-
boxShadow: theme.controls.focusOutlineRequiredShadow
|
|
1520
|
-
}
|
|
1521
|
-
},
|
|
1522
|
-
}, props.round && {
|
|
1523
|
-
borderRadius: theme.controls.roundRadius,
|
|
1524
|
-
paddingLeft: `calc(${theme.controls.padding} * 2)`,
|
|
1525
|
-
paddingRight: `calc(${theme.controls.padding} * 2)`
|
|
1526
|
-
}, props.readOnly && {
|
|
1527
|
-
backgroundColor: 'transparent',
|
|
1528
|
-
cursor: 'default',
|
|
1529
|
-
border: 'none',
|
|
1530
|
-
':focus': {
|
|
1531
|
-
outline: 'none',
|
|
1532
|
-
boxShadow: 'none'
|
|
1533
|
-
}
|
|
1534
|
-
}, props.rightControl && {
|
|
1535
|
-
paddingRight: theme.controls.height
|
|
1536
|
-
});
|
|
1537
|
-
const inputElement = React__namespace.createElement("input", Object.assign({}, nativeProps, { ref: ref, autoComplete: (_a = nativeProps.autoComplete) !== null && _a !== void 0 ? _a : 'off', tabIndex: nativeProps.readOnly ? -1 : nativeProps.tabIndex, maxLength: nativeProps.maxLength || defaultMaxLength$1, className: css.cx(inputStyles, props.className) }));
|
|
1538
|
-
const inputWrapperStyles = css.css `
|
|
1539
|
-
width:100%;
|
|
1540
|
-
${props.rightControl && `
|
|
1541
|
-
position: relative;
|
|
1542
|
-
`}
|
|
1543
|
-
`;
|
|
1544
|
-
const rightControlStyles = props.rightControl && css.css `
|
|
1545
|
-
position: absolute;
|
|
1546
|
-
right: ${theme.controls.padding};
|
|
1547
|
-
top: 0;
|
|
1548
|
-
bottom: 0;
|
|
1549
|
-
display: flex;
|
|
1550
|
-
align-items: center;
|
|
1551
|
-
${props.round && `
|
|
1552
|
-
right: calc(${theme.controls.padding} * 2);
|
|
1553
|
-
`}
|
|
1554
|
-
`;
|
|
1555
|
-
return (React__namespace.createElement("div", { className: css.cx('input', inputWrapperStyles, wrapperClassName) },
|
|
1556
|
-
inputElement,
|
|
1557
|
-
props.rightControl && React__namespace.createElement("div", { className: rightControlStyles }, props.rightControl)));
|
|
1558
|
-
});
|
|
1559
|
-
|
|
1560
|
-
const tryClampRange = (value, min = Number.MIN_SAFE_INTEGER, max = Number.MAX_SAFE_INTEGER) => {
|
|
1561
|
-
if (value === undefined) {
|
|
1562
|
-
return value;
|
|
1563
|
-
}
|
|
1564
|
-
if (isNaN(value)) {
|
|
1565
|
-
return undefined;
|
|
1566
|
-
}
|
|
1567
|
-
return Math.min(Math.max(value, min), max);
|
|
1568
|
-
};
|
|
1569
|
-
|
|
1570
|
-
const dateRegex = /(\d{1,2})(?:\/|-)(\d{1,2})(?:\/|-)(\d{4})/;
|
|
1571
|
-
const datePattern = dateRegex.source;
|
|
1572
|
-
//TB: INPUT these need to be moved into the on change handler
|
|
1573
|
-
const validityChecks = [
|
|
1574
|
-
(value) => {
|
|
1575
|
-
return isOutOfRange(parseDateMs(value)) ? 'Out of range' : '';
|
|
1576
|
-
},
|
|
1577
|
-
(value) => {
|
|
1578
|
-
return !dateExists(parseDateMs(value)) ? 'Invalid Date' : '';
|
|
1579
|
-
},
|
|
1580
|
-
];
|
|
1581
|
-
const DateInput = React__namespace.forwardRef((props, ref) => {
|
|
1582
|
-
const [dateMsValue, setDateMsValue] = React__namespace.useState(undefined);
|
|
1583
|
-
const [textValue, setTextValue] = React__namespace.useState(undefined);
|
|
1584
|
-
const inputRef = (ref !== null && ref !== void 0 ? ref : React__namespace.useRef(null));
|
|
1585
|
-
const nativeProps = __rest(props, ["customValidityChecks"]);
|
|
1586
|
-
React__namespace.useEffect(() => {
|
|
1587
|
-
console.log('[DateInput] setting local value to ', props.value);
|
|
1588
|
-
// sync local value to outer value
|
|
1589
|
-
setDateMsValue(props.value);
|
|
1590
|
-
setTextValue(formatDateStringValue(props.value));
|
|
1591
|
-
}, [props.value]);
|
|
1592
|
-
return (React__namespace.createElement(BaseInput, Object.assign({}, nativeProps, { type: "text", ref: inputRef, value: textValue !== null && textValue !== void 0 ? textValue : '', pattern: datePattern, maxLength: 10, onChange: e => {
|
|
1593
|
-
var _a, _b;
|
|
1594
|
-
const text = e.target.value || undefined;
|
|
1595
|
-
let error;
|
|
1596
|
-
validityChecks.some(func => {
|
|
1597
|
-
error = func(text);
|
|
1598
|
-
return !!error;
|
|
1599
|
-
});
|
|
1600
|
-
(_a = props.customValidityChecks) === null || _a === void 0 ? void 0 : _a.some(func => {
|
|
1601
|
-
error = func(text);
|
|
1602
|
-
return !!error;
|
|
1603
|
-
});
|
|
1604
|
-
e.target.setCustomValidity(error !== null && error !== void 0 ? error : '');
|
|
1605
|
-
console.log(e.target.validationMessage);
|
|
1606
|
-
setTextValue(text);
|
|
1607
|
-
setDateMsValue(parseDateMs(text));
|
|
1608
|
-
console.log(e.target.validationMessage);
|
|
1609
|
-
(_b = props.onChange) === null || _b === void 0 ? void 0 : _b.call(props, e);
|
|
1610
|
-
}, onBlur: e => {
|
|
1611
|
-
var _a;
|
|
1612
|
-
if (props.onBlur) {
|
|
1613
|
-
let currentValue = dateMsValue;
|
|
1614
|
-
if ((_a = props.constrainOnBlur) !== null && _a !== void 0 ? _a : true) {
|
|
1615
|
-
currentValue = tryClampRange(currentValue, props.min, props.max);
|
|
1616
|
-
}
|
|
1617
|
-
if (currentValue !== dateMsValue) {
|
|
1618
|
-
// we've constrained the value. update all values
|
|
1619
|
-
setTextValue(formatDateStringValue(currentValue));
|
|
1620
|
-
setDateMsValue(currentValue);
|
|
1621
|
-
}
|
|
1622
|
-
else if (dateMsValue === undefined && !!textValue) {
|
|
1623
|
-
// invalid date but the bad text is still showing
|
|
1624
|
-
// clear the text and reset the validity
|
|
1625
|
-
setTextValue(undefined);
|
|
1626
|
-
e.target.setCustomValidity('');
|
|
1627
|
-
}
|
|
1628
|
-
props.onBlur(dateMsValue, e);
|
|
1629
|
-
}
|
|
1630
|
-
}, onKeyDown: e => {
|
|
1631
|
-
var _a, _b;
|
|
1632
|
-
if (e.key === 'Enter') {
|
|
1633
|
-
// handle form submission on enter for onBlur-only situations.
|
|
1634
|
-
// onBlur will not be fired so any local change will not be communicated to the outside.
|
|
1635
|
-
(_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.blur();
|
|
1636
|
-
}
|
|
1637
|
-
(_b = props.onKeyDown) === null || _b === void 0 ? void 0 : _b.call(props, e);
|
|
1638
|
-
} })));
|
|
1639
|
-
});
|
|
1640
|
-
const isOutOfRange = (value, min = Number.MIN_SAFE_INTEGER, max = Number.MAX_SAFE_INTEGER) => {
|
|
1641
|
-
if (typeof value === 'number') {
|
|
1642
|
-
return value < min || value > max;
|
|
1643
|
-
}
|
|
1644
|
-
return false;
|
|
1645
|
-
};
|
|
1646
|
-
const parseDateMs = (rawValue) => {
|
|
1647
|
-
if (!rawValue) {
|
|
1648
|
-
return undefined;
|
|
1649
|
-
}
|
|
1650
|
-
let dateMs;
|
|
1651
|
-
const dateParts = dateRegex.exec(rawValue);
|
|
1652
|
-
if (dateParts) {
|
|
1653
|
-
const month = parseInt(dateParts[1], 10) - 1;
|
|
1654
|
-
const day = parseInt(dateParts[2], 10);
|
|
1655
|
-
const year = parseInt(dateParts[3], 10);
|
|
1656
|
-
if (dateFns.isExists(year, month, day)) {
|
|
1657
|
-
dateMs = new Date(year, month, day).valueOf();
|
|
1658
|
-
}
|
|
1659
|
-
}
|
|
1660
|
-
return dateMs;
|
|
1661
|
-
};
|
|
1662
|
-
const dateExists = (dateMs) => {
|
|
1663
|
-
if (dateMs === undefined) {
|
|
1664
|
-
return false;
|
|
1665
|
-
}
|
|
1666
|
-
const d = new Date(dateMs);
|
|
1667
|
-
return dateFns.isExists(d.getFullYear(), d.getMonth() - 1, d.getDate());
|
|
1668
|
-
};
|
|
1669
|
-
const formatDateStringValue = (dateMs) => {
|
|
1670
|
-
if (typeof dateMs === 'number') {
|
|
1671
|
-
return dateFns.format(dateMs, 'MM/dd/yyyy');
|
|
1672
|
-
}
|
|
1673
|
-
return '';
|
|
1674
|
-
};
|
|
1675
|
-
|
|
1676
|
-
const Popover = (p) => {
|
|
1677
|
-
var _a, _b;
|
|
1678
|
-
const theme = useThemeSafely();
|
|
1679
|
-
const resposition = (_a = p.reposition) !== null && _a !== void 0 ? _a : true;
|
|
1680
|
-
return (React__namespace.createElement(reactTinyPopover.Popover, { containerClassName: css.css({
|
|
1681
|
-
zIndex: theme.zIndexes.tooltip
|
|
1682
|
-
}), reposition: resposition, isOpen: p.isOpen, positions: (_b = p.positions) !== null && _b !== void 0 ? _b : ['right', 'top', 'left', 'bottom'], onClickOutside: p.onClickOutside, content: ({ position, childRect, popoverRect }) => {
|
|
1683
|
-
var _a, _b, _c, _d;
|
|
1684
|
-
return (React__namespace.createElement(reactTinyPopover.ArrowContainer, { position: position, childRect: childRect, popoverRect: popoverRect, arrowColor: (_a = p.arrorColor) !== null && _a !== void 0 ? _a : theme.colors.border, arrowSize: 10 },
|
|
1685
|
-
React__namespace.createElement(TabLocker, null,
|
|
1686
|
-
React__namespace.createElement("div", { className: css.css({
|
|
1687
|
-
border: (_b = p.border) !== null && _b !== void 0 ? _b : theme.controls.border,
|
|
1688
|
-
borderRadius: (_c = p.border) !== null && _c !== void 0 ? _c : theme.controls.borderRadius,
|
|
1689
|
-
boxShadow: theme.controls.boxShadow,
|
|
1690
|
-
backgroundColor: (_d = p.backgroundColor) !== null && _d !== void 0 ? _d : theme.colors.bg,
|
|
1691
|
-
}) }, p.content))));
|
|
1692
|
-
} },
|
|
1693
|
-
React__namespace.createElement("span", null, p.parent)));
|
|
1694
|
-
};
|
|
1695
|
-
|
|
1696
|
-
const DatePicker = (p) => {
|
|
1697
|
-
var _a;
|
|
1698
|
-
const inputProps = __rest(p, ["reposition", "onPick"]);
|
|
1699
|
-
const [showCalendar, setShowCalendar] = React__namespace.useState(false);
|
|
1700
|
-
const [calendarDate, setCalendarDate] = React__namespace.useState(getCalendarDate(p.value, p.min, p.max));
|
|
1701
|
-
// controls the one-time focus set on show
|
|
1702
|
-
const needsFocus = React__namespace.useRef(false);
|
|
1703
|
-
const popover = React__namespace.useRef(null);
|
|
1704
|
-
React__namespace.useEffect(() => {
|
|
1705
|
-
var _a;
|
|
1706
|
-
setCalendarDate(getCalendarDate((_a = p.value) !== null && _a !== void 0 ? _a : 0, p.min, p.max));
|
|
1707
|
-
}, [p.value]);
|
|
1708
|
-
React__namespace.useLayoutEffect(() => {
|
|
1709
|
-
var _a, _b;
|
|
1710
|
-
if (needsFocus.current) {
|
|
1711
|
-
(_b = (_a = popover.current) === null || _a === void 0 ? void 0 : _a.querySelector('button')) === null || _b === void 0 ? void 0 : _b.focus();
|
|
1712
|
-
needsFocus.current = false;
|
|
1713
|
-
}
|
|
1714
|
-
});
|
|
1715
|
-
return (React__namespace.createElement(Popover, { reposition: p.reposition, isOpen: showCalendar, onClickOutside: () => {
|
|
1716
|
-
needsFocus.current = false;
|
|
1717
|
-
setShowCalendar(false);
|
|
1718
|
-
}, parent: (React__namespace.createElement(DateInput, Object.assign({}, inputProps, { placeholder: (_a = p.placeholder) !== null && _a !== void 0 ? _a : 'MM/DD/YYYY', rightControl: !p.readOnly ? (React__namespace.createElement(Button, { variant: "icon", readonly: p.readOnly, disabled: p.disabled, small: true, style: {
|
|
1719
|
-
fontSize: '1rem'
|
|
1720
|
-
}, onClick: () => {
|
|
1721
|
-
needsFocus.current = !showCalendar;
|
|
1722
|
-
setShowCalendar(!showCalendar);
|
|
1723
|
-
} },
|
|
1724
|
-
React__namespace.createElement(Icon, { id: "pickDate" }))) : undefined, onFocus: e => {
|
|
1725
|
-
var _a;
|
|
1726
|
-
needsFocus.current = false;
|
|
1727
|
-
setShowCalendar(false);
|
|
1728
|
-
(_a = p.onFocus) === null || _a === void 0 ? void 0 : _a.call(p, e);
|
|
1729
|
-
} }))), content: (React__namespace.createElement("div", { ref: popover, className: css.css({
|
|
1730
|
-
paddingLeft: '1rem',
|
|
1731
|
-
paddingRight: '1rem',
|
|
1732
|
-
paddingBottom: '1rem'
|
|
1733
|
-
}) },
|
|
1734
|
-
React__namespace.createElement(Calendar, { onClick: date => {
|
|
1735
|
-
var _a;
|
|
1736
|
-
(_a = p.onPick) === null || _a === void 0 ? void 0 : _a.call(p, date.valueOf());
|
|
1737
|
-
needsFocus.current = false;
|
|
1738
|
-
setShowCalendar(false);
|
|
1739
|
-
}, customTitle: React__namespace.createElement("div", { className: css.css({
|
|
1740
|
-
display: 'flex',
|
|
1741
|
-
justifyContent: 'space-between',
|
|
1742
|
-
alignItems: 'center'
|
|
1743
|
-
}) },
|
|
1744
|
-
React__namespace.createElement(Button, { disabled: !!p.min && dateFns.isBefore(dateFns.endOfMonth(dateFns.addMonths(calendarDate, -1)), p.min), small: true, variant: "icon", onClick: () => setCalendarDate(dateFns.addMonths(calendarDate, -1)) },
|
|
1745
|
-
React__namespace.createElement(Icon, { id: "pagerLeft" })),
|
|
1746
|
-
React__namespace.createElement(Text, { align: "center" },
|
|
1747
|
-
dateFns.format(calendarDate, 'LLLL'),
|
|
1748
|
-
" ",
|
|
1749
|
-
calendarDate.getFullYear()),
|
|
1750
|
-
React__namespace.createElement(Button, { disabled: !!p.max && dateFns.isAfter(dateFns.startOfMonth(dateFns.addMonths(calendarDate, 1)), p.max), small: true, variant: "icon", onClick: () => setCalendarDate(dateFns.addMonths(calendarDate, 1)) },
|
|
1751
|
-
React__namespace.createElement(Icon, { id: "pagerRight" }))), month: calendarDate.getMonth() + 1, year: calendarDate.getFullYear(), showCurrent: true, smallHeader: true, selectedValue: p.value, cellSize: '2rem', min: p.min, max: p.max }))) }));
|
|
1752
|
-
};
|
|
1753
|
-
const getCalendarDate = (date, min, max) => {
|
|
1754
|
-
let calendarDate = date ? new Date(date) : new Date();
|
|
1755
|
-
// if there is a min/max we don't want the calendar to open to the current date if it's out of range
|
|
1756
|
-
if (min && dateFns.isBefore(calendarDate, min)) {
|
|
1757
|
-
calendarDate = new Date(min);
|
|
1758
|
-
}
|
|
1759
|
-
else if (max && dateFns.isAfter(calendarDate, max)) {
|
|
1760
|
-
calendarDate = new Date(max);
|
|
1761
|
-
}
|
|
1762
|
-
return calendarDate;
|
|
1602
|
+
background-color:${theme.colors.omg};
|
|
1603
|
+
color:${theme.colors.omgFont};
|
|
1604
|
+
}
|
|
1605
|
+
`}
|
|
1606
|
+
`;
|
|
1607
|
+
return (React__namespace.createElement(Modal, { id: props.id, __debug: props.__debug, className: css.cx('confirmModal', modalStyle, props.className), heading: props.header, closeButton: true, show: props.show, onClick: props.onCancel },
|
|
1608
|
+
React__namespace.createElement("div", { className: css.css({ padding: '1rem' }) },
|
|
1609
|
+
React__namespace.createElement(Text, { align: "center" }, props.text),
|
|
1610
|
+
React__namespace.createElement("div", { className: css.css({ textAlign: 'center' }) },
|
|
1611
|
+
React__namespace.createElement(Button, { className: css.css({ margin: '0 0.5rem' }), enforceMinWidth: true, variant: props.variant === 'omg' ? "omg" : 'primary2', onClick: props.onConfirm }, props.confirmText || 'OK'),
|
|
1612
|
+
React__namespace.createElement(Button, { className: css.css({ margin: '0 0.5rem' }), enforceMinWidth: true, onClick: props.onCancel }, props.cancelText || 'Cancel')))));
|
|
1613
|
+
};
|
|
1614
|
+
|
|
1615
|
+
const CopyButton = (props) => {
|
|
1616
|
+
const [copied, setCopied] = React__namespace.useState(false);
|
|
1617
|
+
return (React__namespace.createElement(Button, { title: copied ? 'Copied!' : (props.title || 'Copy to clipboard'), variant: "icon", onBlur: () => {
|
|
1618
|
+
setCopied(false);
|
|
1619
|
+
}, onClick: e => {
|
|
1620
|
+
const button = e.currentTarget;
|
|
1621
|
+
let copySuccess = false;
|
|
1622
|
+
try {
|
|
1623
|
+
const text = document.querySelector(props.selector);
|
|
1624
|
+
text.select();
|
|
1625
|
+
copySuccess = document.execCommand('copy');
|
|
1626
|
+
// the input gets focus on select. bring it back.
|
|
1627
|
+
button.focus();
|
|
1628
|
+
}
|
|
1629
|
+
catch (err) {
|
|
1630
|
+
// You done wrong.
|
|
1631
|
+
}
|
|
1632
|
+
setCopied(copySuccess);
|
|
1633
|
+
} },
|
|
1634
|
+
React__namespace.createElement(Icon, { id: copied ? 'paste' : 'copy' })));
|
|
1763
1635
|
};
|
|
1764
1636
|
|
|
1765
|
-
const Divider = () => {
|
|
1637
|
+
const Divider = (p) => {
|
|
1766
1638
|
const theme = useThemeSafely();
|
|
1767
|
-
return (React__namespace.createElement("hr", { className: css.cx("divider", css.css({
|
|
1639
|
+
return (React__namespace.createElement("hr", Object.assign({}, p, { className: css.cx("divider", css.css({
|
|
1768
1640
|
margin: theme.controls.dividerMargin,
|
|
1769
1641
|
border: theme.controls.dividerBorder
|
|
1770
|
-
})) }));
|
|
1642
|
+
}), p.className) })));
|
|
1771
1643
|
};
|
|
1772
1644
|
|
|
1773
1645
|
const ErrorModal = (props) => {
|
|
@@ -1782,7 +1654,7 @@ const ErrorModal = (props) => {
|
|
|
1782
1654
|
color: ${theme.colors.omgFont};
|
|
1783
1655
|
}
|
|
1784
1656
|
`;
|
|
1785
|
-
return (React__namespace.createElement(Modal, { id: props.id,
|
|
1657
|
+
return (React__namespace.createElement(Modal, { id: props.id, __debug: props.__debug, className: css.cx('errorModal', modalStyles), heading: "Error", closeButton: true, show: props.show, onClick: props.close },
|
|
1786
1658
|
React__namespace.createElement("div", { className: css.css({ padding: '1rem' }) },
|
|
1787
1659
|
React__namespace.createElement(Text, { align: "center" }, message))));
|
|
1788
1660
|
};
|
|
@@ -1910,7 +1782,7 @@ const hoverClass = css.css({
|
|
|
1910
1782
|
backgroundColor: 'rgba(0,0,0,0.25) !important'
|
|
1911
1783
|
});
|
|
1912
1784
|
const FileUploader = (p) => {
|
|
1913
|
-
var _a, _b, _c, _d, _e, _f, _g;
|
|
1785
|
+
var _a, _b, _c, _d, _e, _f, _g, _h;
|
|
1914
1786
|
const [message, setMessage] = React.useState(undefined);
|
|
1915
1787
|
const [canUpload, setCanUpload] = React.useState(false);
|
|
1916
1788
|
const [uploading, setUploading] = React.useState(false);
|
|
@@ -1926,7 +1798,7 @@ const FileUploader = (p) => {
|
|
|
1926
1798
|
filesDisplay = (_b = p.instructionMessage) !== null && _b !== void 0 ? _b : `Click or drag and drop files.`;
|
|
1927
1799
|
}
|
|
1928
1800
|
else {
|
|
1929
|
-
filesDisplay = `${files.length.toLocaleString()} file${files.length > 1 ? 's' : ''} selected (${
|
|
1801
|
+
filesDisplay = `${files.length.toLocaleString()} file${files.length > 1 ? 's' : ''} selected (${getFileSizeDisplay(totalFileSize)}): ${files.files.map(f => f.name).join(', ')}`;
|
|
1930
1802
|
}
|
|
1931
1803
|
}
|
|
1932
1804
|
const setAllFiles = (inputFiles) => {
|
|
@@ -1948,8 +1820,9 @@ const FileUploader = (p) => {
|
|
|
1948
1820
|
maxBytes: p.maxBytes
|
|
1949
1821
|
});
|
|
1950
1822
|
};
|
|
1823
|
+
const showInfoOnPick = (_c = p.showInfoOnPick) !== null && _c !== void 0 ? _c : true;
|
|
1951
1824
|
let infoMessage;
|
|
1952
|
-
if (p.infoMessage) {
|
|
1825
|
+
if (p.infoMessage && (!files || showInfoOnPick)) {
|
|
1953
1826
|
if (typeof p.infoMessage === 'string') {
|
|
1954
1827
|
infoMessage = React__default['default'].createElement(Text, { noPad: true }, p.infoMessage);
|
|
1955
1828
|
}
|
|
@@ -1966,6 +1839,8 @@ const FileUploader = (p) => {
|
|
|
1966
1839
|
padding: '1rem',
|
|
1967
1840
|
overflow: 'hidden',
|
|
1968
1841
|
backgroundColor: theme.colors.lightBg,
|
|
1842
|
+
}, p.disabled && {
|
|
1843
|
+
opacity: theme.controls.disabledOpacity
|
|
1969
1844
|
}), onDragOver: e => {
|
|
1970
1845
|
var _a, _b;
|
|
1971
1846
|
e.preventDefault();
|
|
@@ -1999,7 +1874,7 @@ const FileUploader = (p) => {
|
|
|
1999
1874
|
setCanUpload(false);
|
|
2000
1875
|
});
|
|
2001
1876
|
} },
|
|
2002
|
-
React__default['default'].createElement("input", { ref: input, className: css.css({
|
|
1877
|
+
React__default['default'].createElement("input", { disabled: p.disabled, ref: input, className: css.css({
|
|
2003
1878
|
position: 'absolute',
|
|
2004
1879
|
top: -50,
|
|
2005
1880
|
left: 0,
|
|
@@ -2008,6 +1883,8 @@ const FileUploader = (p) => {
|
|
|
2008
1883
|
width: '100%',
|
|
2009
1884
|
cursor: 'pointer',
|
|
2010
1885
|
opacity: 0
|
|
1886
|
+
}, p.disabled && {
|
|
1887
|
+
cursor: 'not-allowed'
|
|
2011
1888
|
}), type: "file", multiple: p.multiple, accept: p.accept, onChange: e => {
|
|
2012
1889
|
try {
|
|
2013
1890
|
if (!e.target.files) {
|
|
@@ -2030,65 +1907,68 @@ const FileUploader = (p) => {
|
|
|
2030
1907
|
zIndex: !!(files === null || files === void 0 ? void 0 : files.length) ? 1 : undefined
|
|
2031
1908
|
}) },
|
|
2032
1909
|
!(files === null || files === void 0 ? void 0 : files.length) && React__default['default'].createElement(Icon, { style: { fontSize: '2rem' }, id: "upload" }),
|
|
2033
|
-
React__default['default'].createElement(Text, { align: "center", noPad: true, spacedOut: true
|
|
1910
|
+
React__default['default'].createElement(Text, { align: "center", noPad: true, spacedOut: true, className: css.css({
|
|
1911
|
+
width: '100%'
|
|
1912
|
+
}) },
|
|
2034
1913
|
filesDisplay,
|
|
2035
1914
|
!!(files === null || files === void 0 ? void 0 : files.length) && (React__default['default'].createElement(Button, { onClick: e => {
|
|
2036
1915
|
e.stopPropagation();
|
|
2037
1916
|
onFilesChange(undefined);
|
|
2038
1917
|
}, className: css.css({ marginLeft: '1rem', color: theme.colors.negative }), rightIcon: React__default['default'].createElement(Icon, { id: "clear" }), variant: "inlineLink" }, "Clear"))),
|
|
2039
1918
|
infoMessage,
|
|
2040
|
-
!!(files === null || files === void 0 ? void 0 : files.invalidFiles.length) && (React__default['default'].createElement(InfoPanel, { variant: "error" },
|
|
1919
|
+
!!(files === null || files === void 0 ? void 0 : files.invalidFiles.length) && (React__default['default'].createElement(InfoPanel, { variant: "error", className: css.css({ width: '100%' }) },
|
|
2041
1920
|
"Invalid files: ",
|
|
2042
1921
|
files.invalidFiles.map(f => f.name).join(', '),
|
|
2043
1922
|
".")),
|
|
2044
|
-
(files === null || files === void 0 ? void 0 : files.overMaxBytes) && (React__default['default'].createElement(InfoPanel, { variant: "error" },
|
|
1923
|
+
(files === null || files === void 0 ? void 0 : files.overMaxBytes) && (React__default['default'].createElement(InfoPanel, { variant: "error", className: css.css({ width: '100%' }) },
|
|
2045
1924
|
"Max file size exceeded (",
|
|
2046
|
-
|
|
1925
|
+
getFileSizeDisplay((_d = p.maxBytes) !== null && _d !== void 0 ? _d : 0),
|
|
2047
1926
|
").")))),
|
|
2048
1927
|
canUpload && !(files === null || files === void 0 ? void 0 : files.hasErrors) && (React__default['default'].createElement(Button, { className: css.css({
|
|
2049
|
-
width: (
|
|
1928
|
+
width: (_e = p.buttonWidth) !== null && _e !== void 0 ? _e : '10rem',
|
|
2050
1929
|
zIndex: 1,
|
|
2051
|
-
}), waiting: uploading, type: "submit", variant: (
|
|
2052
|
-
message === 'success' && (React__default['default'].createElement(UploadInfoPanel, { variant: "positive", message: (
|
|
1930
|
+
}), waiting: uploading, type: "submit", variant: (_f = p.buttonVariant) !== null && _f !== void 0 ? _f : 'primary' }, (_g = p.buttonText) !== null && _g !== void 0 ? _g : 'Upload')),
|
|
1931
|
+
message === 'success' && (React__default['default'].createElement(UploadInfoPanel, { variant: "positive", message: (_h = p.successMessage) !== null && _h !== void 0 ? _h : 'Upload successful.', onClear: () => setMessage(undefined) })),
|
|
2053
1932
|
message === 'failure' && (React__default['default'].createElement(UploadInfoPanel, { variant: "error", message: fullFailureMessage, onClear: () => setMessage(undefined) }))));
|
|
2054
1933
|
};
|
|
2055
1934
|
const UploadInfoPanel = (p) => {
|
|
2056
1935
|
return (React__default['default'].createElement(InfoPanel, { variant: p.variant, className: css.css({ zIndex: 1 }) },
|
|
2057
1936
|
p.message,
|
|
2058
|
-
React__default['default'].createElement(Button, {
|
|
1937
|
+
React__default['default'].createElement(Button, { className: css.css({
|
|
2059
1938
|
color: 'inherit',
|
|
2060
|
-
marginTop: '1rem'
|
|
1939
|
+
marginTop: '1rem',
|
|
1940
|
+
width: '100%'
|
|
2061
1941
|
}), onClick: e => {
|
|
2062
1942
|
e.stopPropagation();
|
|
2063
1943
|
p.onClear();
|
|
2064
1944
|
}, rightIcon: React__default['default'].createElement(Icon, { id: "clear" }), variant: "inlineLink" }, "Clear")));
|
|
2065
1945
|
};
|
|
2066
|
-
|
|
2067
|
-
|
|
2068
|
-
const
|
|
2069
|
-
|
|
2070
|
-
|
|
1946
|
+
// OMG this is dumb. We're sticking with decimals for ease of use.
|
|
1947
|
+
// https://stackoverflow.com/questions/40949135/gigabyte-or-gibibyte-1000-or-1024
|
|
1948
|
+
const getFileSizeDisplay = (size) => {
|
|
1949
|
+
let value = 0;
|
|
1950
|
+
let suffix = '';
|
|
1951
|
+
if (size >= 1000000000) {
|
|
1952
|
+
value = size / 1000000000;
|
|
1953
|
+
suffix = 'GB';
|
|
2071
1954
|
}
|
|
2072
|
-
else if (size
|
|
2073
|
-
|
|
1955
|
+
else if (size >= 1000000) {
|
|
1956
|
+
value = size / 1000000;
|
|
1957
|
+
suffix = 'MB';
|
|
2074
1958
|
}
|
|
2075
|
-
else {
|
|
2076
|
-
|
|
1959
|
+
else if (size >= 1000) {
|
|
1960
|
+
value = size / 1000;
|
|
1961
|
+
suffix = 'KB';
|
|
2077
1962
|
}
|
|
2078
|
-
|
|
2079
|
-
|
|
2080
|
-
|
|
2081
|
-
let actualValue = value || 0;
|
|
2082
|
-
if (isCents) {
|
|
2083
|
-
actualValue /= 100;
|
|
1963
|
+
else {
|
|
1964
|
+
value = size;
|
|
1965
|
+
suffix = 'B';
|
|
2084
1966
|
}
|
|
2085
|
-
return
|
|
2086
|
-
};
|
|
2087
|
-
const noop = () => {
|
|
2088
|
-
// lil' noop would be a great rap name. (thanks linter)
|
|
1967
|
+
return value.toLocaleString(undefined, { minimumFractionDigits: 1, maximumFractionDigits: 1 }) + ` ${suffix}`;
|
|
2089
1968
|
};
|
|
2090
1969
|
|
|
2091
1970
|
const Header = (props) => {
|
|
1971
|
+
var _a;
|
|
2092
1972
|
const theme = useThemeSafely();
|
|
2093
1973
|
const bodyStyles = css.css `
|
|
2094
1974
|
padding-top: calc(${theme.layout.headerHeight} + ${theme.layout.headerBodyOffset});
|
|
@@ -2100,7 +1980,9 @@ const Header = (props) => {
|
|
|
2100
1980
|
document.body.classList.remove(bodyStyles);
|
|
2101
1981
|
};
|
|
2102
1982
|
});
|
|
2103
|
-
const toggleMenu = props.toggleMenu
|
|
1983
|
+
const toggleMenu = (_a = props.toggleMenu) !== null && _a !== void 0 ? _a : (() => {
|
|
1984
|
+
/* noop */
|
|
1985
|
+
});
|
|
2104
1986
|
const headerStyles = css.css `
|
|
2105
1987
|
display: flex;
|
|
2106
1988
|
gap: ${theme.controls.gap};
|
|
@@ -2199,160 +2081,545 @@ const Highlight = (props) => {
|
|
|
2199
2081
|
text = props.text.replace(new RegExp(`(${replaceText})`, 'gi'), `<mark>$1</mark>`);
|
|
2200
2082
|
}
|
|
2201
2083
|
}
|
|
2202
|
-
return (React__namespace.createElement("span", { className: css.cx('highlight', highlightStyles), dangerouslySetInnerHTML: { __html: text } }));
|
|
2203
|
-
};
|
|
2204
|
-
|
|
2205
|
-
const Image = (props) => {
|
|
2206
|
-
return (React__namespace.createElement("img", { alt: props.alt, style: props.style, className: css.cx('image', css.css({
|
|
2207
|
-
maxWidth: '100%',
|
|
2208
|
-
maxHeight: '100%',
|
|
2209
|
-
}), props.className), src: props.src }));
|
|
2084
|
+
return (React__namespace.createElement("span", { className: css.cx('highlight', highlightStyles), dangerouslySetInnerHTML: { __html: text } }));
|
|
2085
|
+
};
|
|
2086
|
+
|
|
2087
|
+
const Image = (props) => {
|
|
2088
|
+
return (React__namespace.createElement("img", { alt: props.alt, style: props.style, className: css.cx('image', css.css({
|
|
2089
|
+
maxWidth: '100%',
|
|
2090
|
+
maxHeight: '100%',
|
|
2091
|
+
}), props.className), src: props.src }));
|
|
2092
|
+
};
|
|
2093
|
+
|
|
2094
|
+
const Popover = (p) => {
|
|
2095
|
+
var _a, _b;
|
|
2096
|
+
const theme = useThemeSafely();
|
|
2097
|
+
const resposition = (_a = p.reposition) !== null && _a !== void 0 ? _a : true;
|
|
2098
|
+
return (React__namespace.createElement(reactTinyPopover.Popover, { containerClassName: css.css({
|
|
2099
|
+
zIndex: theme.zIndexes.tooltip
|
|
2100
|
+
}), reposition: resposition, isOpen: p.isOpen, positions: (_b = p.positions) !== null && _b !== void 0 ? _b : ['right', 'top', 'left', 'bottom'], onClickOutside: p.onClickOutside, content: ({ position, childRect, popoverRect }) => {
|
|
2101
|
+
var _a, _b, _c, _d;
|
|
2102
|
+
return (React__namespace.createElement(reactTinyPopover.ArrowContainer, { position: position, childRect: childRect, popoverRect: popoverRect, arrowColor: (_a = p.arrorColor) !== null && _a !== void 0 ? _a : theme.colors.border, arrowSize: 10 },
|
|
2103
|
+
React__namespace.createElement(TabLocker, null,
|
|
2104
|
+
React__namespace.createElement("div", { className: css.css({
|
|
2105
|
+
border: (_b = p.border) !== null && _b !== void 0 ? _b : theme.controls.border,
|
|
2106
|
+
borderRadius: (_c = p.border) !== null && _c !== void 0 ? _c : theme.controls.borderRadius,
|
|
2107
|
+
boxShadow: theme.controls.boxShadow,
|
|
2108
|
+
backgroundColor: (_d = p.backgroundColor) !== null && _d !== void 0 ? _d : theme.colors.bg,
|
|
2109
|
+
}) }, p.content))));
|
|
2110
|
+
} },
|
|
2111
|
+
React__namespace.createElement("span", null, p.parent)));
|
|
2112
|
+
};
|
|
2113
|
+
|
|
2114
|
+
const InfoTip = (props) => {
|
|
2115
|
+
var _a, _b, _c;
|
|
2116
|
+
const [showTip, setShowTip] = React__namespace.useState(false);
|
|
2117
|
+
const theme = useThemeSafely();
|
|
2118
|
+
const bgColor = (_a = props.bgColor) !== null && _a !== void 0 ? _a : theme.colors.nav;
|
|
2119
|
+
const fontColor = (_b = props.fontColor) !== null && _b !== void 0 ? _b : theme.colors.navFont;
|
|
2120
|
+
const onClick = () => {
|
|
2121
|
+
if (props.onClick) {
|
|
2122
|
+
props.onClick();
|
|
2123
|
+
}
|
|
2124
|
+
else if (props.content) {
|
|
2125
|
+
openTip();
|
|
2126
|
+
}
|
|
2127
|
+
};
|
|
2128
|
+
const onMouseOver = () => {
|
|
2129
|
+
if (props.variant === 'modal') {
|
|
2130
|
+
return;
|
|
2131
|
+
}
|
|
2132
|
+
if (props.loadOnHover) {
|
|
2133
|
+
props.loadOnHover().then(() => {
|
|
2134
|
+
openTip();
|
|
2135
|
+
}).catch(err => {
|
|
2136
|
+
/* Not my responsiblity. */
|
|
2137
|
+
});
|
|
2138
|
+
}
|
|
2139
|
+
else {
|
|
2140
|
+
openTip();
|
|
2141
|
+
}
|
|
2142
|
+
};
|
|
2143
|
+
const onMouseOut = () => {
|
|
2144
|
+
if (props.variant === 'modal') {
|
|
2145
|
+
return;
|
|
2146
|
+
}
|
|
2147
|
+
closeTip();
|
|
2148
|
+
};
|
|
2149
|
+
const openTip = () => {
|
|
2150
|
+
if (!props.content) {
|
|
2151
|
+
return;
|
|
2152
|
+
}
|
|
2153
|
+
setShowTip(props.disabled ? false : true);
|
|
2154
|
+
};
|
|
2155
|
+
const closeTip = () => {
|
|
2156
|
+
if (!props.content) {
|
|
2157
|
+
return;
|
|
2158
|
+
}
|
|
2159
|
+
setShowTip(false);
|
|
2160
|
+
if (props.onClose) {
|
|
2161
|
+
props.onClose();
|
|
2162
|
+
}
|
|
2163
|
+
};
|
|
2164
|
+
const buttonStyles = css.css `
|
|
2165
|
+
font-weight: bold;
|
|
2166
|
+
width: 1.5rem;
|
|
2167
|
+
min-width:1.5rem;
|
|
2168
|
+
height: 1.5rem;
|
|
2169
|
+
padding: 0 !important;
|
|
2170
|
+
font-family: serif;
|
|
2171
|
+
display:inline-block;
|
|
2172
|
+
`;
|
|
2173
|
+
const button = React__namespace.createElement(Button, { className: buttonStyles, disabled: props.disabled, variant: 'circle', tabIndex: props.tabIndex, onClick: onClick, onMouseEnter: onMouseOver, onMouseLeave: onMouseOut }, "i");
|
|
2174
|
+
if (props.variant === 'modal') {
|
|
2175
|
+
return (React__namespace.createElement(React__namespace.Fragment, null,
|
|
2176
|
+
button,
|
|
2177
|
+
React__namespace.createElement(Modal, { id: props.modalId, __debug: props.__modalDebug, show: showTip, heading: props.modalHeader, onClick: closeTip, className: css.css({
|
|
2178
|
+
whiteSpace: 'normal'
|
|
2179
|
+
}), closeButton: true },
|
|
2180
|
+
React__namespace.createElement("div", { className: css.css({ padding: '1rem' }) }, props.content))));
|
|
2181
|
+
}
|
|
2182
|
+
else {
|
|
2183
|
+
return (React__namespace.createElement(Popover, { positions: props.positions, reposition: (_c = props.reposition) !== null && _c !== void 0 ? _c : false, isOpen: showTip, onClickOutside: closeTip, arrorColor: bgColor, border: '', backgroundColor: bgColor, parent: button, content: (React__namespace.createElement("div", { className: css.css({
|
|
2184
|
+
padding: '0.5rem',
|
|
2185
|
+
fontSize: '0.75rem',
|
|
2186
|
+
maxWidth: '22rem'
|
|
2187
|
+
}), style: { backgroundColor: bgColor, color: fontColor }, onMouseOut: closeTip }, props.content)) }));
|
|
2188
|
+
}
|
|
2189
|
+
};
|
|
2190
|
+
|
|
2191
|
+
const InputErrorDisplay = (props) => {
|
|
2192
|
+
const theme = useThemeSafely();
|
|
2193
|
+
return (React__namespace.createElement(Text, { className: css.css({
|
|
2194
|
+
minHeight: theme.controls.inputErrorMinHeight,
|
|
2195
|
+
lineHeight: theme.controls.inputErrorMinHeight,
|
|
2196
|
+
color: theme.colors.negative
|
|
2197
|
+
}), smaller: true, noPad: true }, props.error));
|
|
2198
|
+
};
|
|
2199
|
+
|
|
2200
|
+
const defaultMaxLength$1 = 100;
|
|
2201
|
+
const BaseInput = React__namespace.forwardRef((props, ref) => {
|
|
2202
|
+
var _a;
|
|
2203
|
+
const theme = useThemeSafely();
|
|
2204
|
+
const { rightControl, round, wrapperClassName } = props, nativeProps = __rest(props, ["rightControl", "round", "wrapperClassName"]);
|
|
2205
|
+
const inputStyles = css.css({
|
|
2206
|
+
fontFamily: theme.fonts.family,
|
|
2207
|
+
fontSize: theme.fonts.size,
|
|
2208
|
+
width: '100%',
|
|
2209
|
+
border: theme.controls.border,
|
|
2210
|
+
borderRadius: theme.controls.borderRadius,
|
|
2211
|
+
color: theme.colors.font,
|
|
2212
|
+
paddingLeft: theme.controls.padding,
|
|
2213
|
+
paddingRight: theme.controls.padding,
|
|
2214
|
+
height: theme.controls.height,
|
|
2215
|
+
transition: theme.controls.transition,
|
|
2216
|
+
':focus': {
|
|
2217
|
+
outline: 'none',
|
|
2218
|
+
boxShadow: theme.controls.focusOutlineShadow
|
|
2219
|
+
},
|
|
2220
|
+
':disabled': {
|
|
2221
|
+
backgroundColor: theme.colors.disabled,
|
|
2222
|
+
cursor: 'not-allowed'
|
|
2223
|
+
},
|
|
2224
|
+
':invalid': {
|
|
2225
|
+
borderColor: theme.colors.required,
|
|
2226
|
+
':focus': {
|
|
2227
|
+
boxShadow: theme.controls.focusOutlineRequiredShadow
|
|
2228
|
+
}
|
|
2229
|
+
},
|
|
2230
|
+
}, props.round && {
|
|
2231
|
+
borderRadius: theme.controls.roundRadius,
|
|
2232
|
+
paddingLeft: `calc(${theme.controls.padding} * 2)`,
|
|
2233
|
+
paddingRight: `calc(${theme.controls.padding} * 2)`
|
|
2234
|
+
}, props.readOnly && {
|
|
2235
|
+
backgroundColor: 'transparent',
|
|
2236
|
+
cursor: 'default',
|
|
2237
|
+
border: 'none',
|
|
2238
|
+
':focus': {
|
|
2239
|
+
outline: 'none',
|
|
2240
|
+
boxShadow: 'none'
|
|
2241
|
+
}
|
|
2242
|
+
}, props.rightControl && {
|
|
2243
|
+
paddingRight: theme.controls.height
|
|
2244
|
+
});
|
|
2245
|
+
const inputElement = React__namespace.createElement("input", Object.assign({}, nativeProps, { ref: ref, autoComplete: (_a = nativeProps.autoComplete) !== null && _a !== void 0 ? _a : 'off', tabIndex: nativeProps.readOnly ? -1 : nativeProps.tabIndex, maxLength: nativeProps.maxLength || defaultMaxLength$1, className: css.cx(inputStyles, props.className) }));
|
|
2246
|
+
const inputWrapperStyles = css.css `
|
|
2247
|
+
width:100%;
|
|
2248
|
+
${props.rightControl && `
|
|
2249
|
+
position: relative;
|
|
2250
|
+
`}
|
|
2251
|
+
`;
|
|
2252
|
+
const rightControlStyles = props.rightControl && css.css `
|
|
2253
|
+
position: absolute;
|
|
2254
|
+
right: ${theme.controls.padding};
|
|
2255
|
+
top: 0;
|
|
2256
|
+
bottom: 0;
|
|
2257
|
+
display: flex;
|
|
2258
|
+
align-items: center;
|
|
2259
|
+
${props.round && `
|
|
2260
|
+
right: calc(${theme.controls.padding} * 2);
|
|
2261
|
+
`}
|
|
2262
|
+
`;
|
|
2263
|
+
return (React__namespace.createElement("div", { className: css.css({
|
|
2264
|
+
width: '100%'
|
|
2265
|
+
}) },
|
|
2266
|
+
React__namespace.createElement("div", { className: css.cx('input', inputWrapperStyles, wrapperClassName) },
|
|
2267
|
+
inputElement,
|
|
2268
|
+
props.rightControl && (React__namespace.createElement("div", { className: rightControlStyles }, props.rightControl))),
|
|
2269
|
+
React__namespace.createElement(InputErrorDisplay, { error: props.readOnly ? undefined : props.error })));
|
|
2270
|
+
});
|
|
2271
|
+
|
|
2272
|
+
const tryClampRange = (value, min, max) => {
|
|
2273
|
+
if (value === undefined) {
|
|
2274
|
+
return value;
|
|
2275
|
+
}
|
|
2276
|
+
if (isNaN(value)) {
|
|
2277
|
+
return undefined;
|
|
2278
|
+
}
|
|
2279
|
+
if (min !== undefined && value < min) {
|
|
2280
|
+
return min;
|
|
2281
|
+
}
|
|
2282
|
+
if (max !== undefined && value > max) {
|
|
2283
|
+
return max;
|
|
2284
|
+
}
|
|
2285
|
+
return value;
|
|
2286
|
+
};
|
|
2287
|
+
const isOutOfRange = (value, min, max) => {
|
|
2288
|
+
if (min !== undefined && value < min) {
|
|
2289
|
+
return true;
|
|
2290
|
+
}
|
|
2291
|
+
if (max !== undefined && value > max) {
|
|
2292
|
+
return true;
|
|
2293
|
+
}
|
|
2294
|
+
return false;
|
|
2295
|
+
};
|
|
2296
|
+
const getStepDecimalPlaces = (step) => {
|
|
2297
|
+
var _a, _b;
|
|
2298
|
+
if (!step) {
|
|
2299
|
+
return 0;
|
|
2300
|
+
}
|
|
2301
|
+
const strStep = typeof step === 'number' ? step.toString() : step;
|
|
2302
|
+
return (_b = (_a = strStep.split('.')[1]) === null || _a === void 0 ? void 0 : _a.length) !== null && _b !== void 0 ? _b : 0;
|
|
2303
|
+
};
|
|
2304
|
+
const tryClampDecimals = (value, step = 0) => {
|
|
2305
|
+
if (value === undefined) {
|
|
2306
|
+
return value;
|
|
2307
|
+
}
|
|
2308
|
+
if (isNaN(value)) {
|
|
2309
|
+
return undefined;
|
|
2310
|
+
}
|
|
2311
|
+
const decimals = getStepDecimalPlaces(step);
|
|
2312
|
+
if (decimals === 0) {
|
|
2313
|
+
return Math.floor(value);
|
|
2314
|
+
}
|
|
2315
|
+
return parseFloat(value.toFixed(decimals));
|
|
2316
|
+
};
|
|
2317
|
+
|
|
2318
|
+
/** Common state handling for displaying validation messages with inputs. */
|
|
2319
|
+
const useInputValidationMessage = (ref, props) => {
|
|
2320
|
+
const [validationError, setValidationError] = React__default['default'].useState('');
|
|
2321
|
+
const updateErrorMessage = (customErrorOverride) => {
|
|
2322
|
+
var _a;
|
|
2323
|
+
const customError = customErrorOverride || props.customError || '';
|
|
2324
|
+
// set it OR clear it. either way, update it.
|
|
2325
|
+
(_a = ref.current) === null || _a === void 0 ? void 0 : _a.setCustomValidity(customError);
|
|
2326
|
+
setValidationError(customError || getValidationMessage(ref.current, props.patternErrorMessage));
|
|
2327
|
+
};
|
|
2328
|
+
React.useEffect(() => {
|
|
2329
|
+
updateErrorMessage();
|
|
2330
|
+
}, [props.customError]);
|
|
2331
|
+
React__default['default'].useEffect(() => {
|
|
2332
|
+
updateErrorMessage();
|
|
2333
|
+
}, []);
|
|
2334
|
+
return [validationError, updateErrorMessage];
|
|
2335
|
+
};
|
|
2336
|
+
const getValidationMessage = (element, patternErrorMessage) => {
|
|
2337
|
+
var _a;
|
|
2338
|
+
if (!element) {
|
|
2339
|
+
return '';
|
|
2340
|
+
}
|
|
2341
|
+
const validity = element.validity;
|
|
2342
|
+
if (validity.valid) {
|
|
2343
|
+
return '';
|
|
2344
|
+
}
|
|
2345
|
+
if (validity.customError) {
|
|
2346
|
+
return element.validationMessage;
|
|
2347
|
+
}
|
|
2348
|
+
if (validity.typeMismatch) {
|
|
2349
|
+
switch (element.type) {
|
|
2350
|
+
case 'url':
|
|
2351
|
+
return `Invalid URL.`;
|
|
2352
|
+
case 'email':
|
|
2353
|
+
return `Invalid email.`;
|
|
2354
|
+
default:
|
|
2355
|
+
return element.validationMessage;
|
|
2356
|
+
}
|
|
2357
|
+
}
|
|
2358
|
+
if (element instanceof HTMLInputElement) {
|
|
2359
|
+
if (validity.rangeOverflow) {
|
|
2360
|
+
return `Must be less than or equal to ${element.max}.`;
|
|
2361
|
+
}
|
|
2362
|
+
if (validity.rangeUnderflow) {
|
|
2363
|
+
return `Must be greater than or equal to ${element.min}.`;
|
|
2364
|
+
}
|
|
2365
|
+
if (validity.stepMismatch) {
|
|
2366
|
+
const decimalPlaces = getStepDecimalPlaces(element.step);
|
|
2367
|
+
if (decimalPlaces > 0) {
|
|
2368
|
+
const place = decimalPlaces === 1 ? 'place' : 'places';
|
|
2369
|
+
return `Limited to ${getStepDecimalPlaces(element.step)} decimal ${place}.`;
|
|
2370
|
+
}
|
|
2371
|
+
else {
|
|
2372
|
+
/*
|
|
2373
|
+
step is buggy!
|
|
2374
|
+
|
|
2375
|
+
at least in Chrome, setting step=5 will cause the browser to mark the field as invalid if the number is not divisible
|
|
2376
|
+
by 5. 55 is ok. 50 is ok. 59 is not ok.
|
|
2377
|
+
|
|
2378
|
+
to make things worse, if you enter an invalid number like 59 with step=5 and then clear the input, Chrome will tell
|
|
2379
|
+
you the number 5 is now invalid and should be 4 or 9.
|
|
2380
|
+
*/
|
|
2381
|
+
return `Must be an integer.`;
|
|
2382
|
+
}
|
|
2383
|
+
}
|
|
2384
|
+
}
|
|
2385
|
+
if (validity.tooShort) {
|
|
2386
|
+
return `Must be at least ${((_a = element.minLength) !== null && _a !== void 0 ? _a : 0).toLocaleString()} characters in length.`;
|
|
2387
|
+
}
|
|
2388
|
+
if (validity.valueMissing) {
|
|
2389
|
+
return 'Required.';
|
|
2390
|
+
}
|
|
2391
|
+
if (validity.patternMismatch && patternErrorMessage) {
|
|
2392
|
+
return patternErrorMessage;
|
|
2393
|
+
}
|
|
2394
|
+
// unhandled. let the browser decide.
|
|
2395
|
+
return element.validationMessage;
|
|
2210
2396
|
};
|
|
2211
2397
|
|
|
2212
|
-
const
|
|
2213
|
-
|
|
2214
|
-
|
|
2215
|
-
|
|
2216
|
-
|
|
2217
|
-
const
|
|
2218
|
-
const
|
|
2219
|
-
|
|
2220
|
-
|
|
2398
|
+
const dateRegex = /(\d{1,2})(?:\/|-)(\d{1,2})(?:\/|-)(\d{4})/;
|
|
2399
|
+
const datePattern = dateRegex.source;
|
|
2400
|
+
const invalidDateMessage = 'Invalid date.';
|
|
2401
|
+
const DateInput = React__namespace.forwardRef((props, ref) => {
|
|
2402
|
+
var _a;
|
|
2403
|
+
const [dateValue, setDateValue] = React__namespace.useState(props.value);
|
|
2404
|
+
const [textValue, setTextValue] = React__namespace.useState(parseDateString(props.value));
|
|
2405
|
+
const updateValues = React__namespace.useCallback((value) => {
|
|
2406
|
+
let newDateValue;
|
|
2407
|
+
let newTextValue;
|
|
2408
|
+
if (typeof value === 'number') {
|
|
2409
|
+
newDateValue = value;
|
|
2410
|
+
newTextValue = parseDateString(value);
|
|
2221
2411
|
}
|
|
2222
|
-
else if (
|
|
2223
|
-
|
|
2412
|
+
else if (typeof value === 'string') {
|
|
2413
|
+
newDateValue = parseDateNumber(value);
|
|
2414
|
+
newTextValue = value;
|
|
2224
2415
|
}
|
|
2225
|
-
|
|
2226
|
-
|
|
2227
|
-
|
|
2416
|
+
setDateValue(newDateValue);
|
|
2417
|
+
setTextValue(newTextValue);
|
|
2418
|
+
}, []);
|
|
2419
|
+
const inputRef = (ref !== null && ref !== void 0 ? ref : React__namespace.useRef(null));
|
|
2420
|
+
const [validationError, updateErrorMessage] = useInputValidationMessage(inputRef, { customError: props.customError, patternErrorMessage: invalidDateMessage });
|
|
2421
|
+
const updateDateErrorMessages = React__namespace.useCallback(() => {
|
|
2422
|
+
let dateError = '';
|
|
2423
|
+
if (dateValue === undefined) {
|
|
2424
|
+
if (!!textValue) {
|
|
2425
|
+
// the text pattern is a valid date format, but the numbers are wrong. example: 05/35/2000.
|
|
2426
|
+
dateError = invalidDateMessage;
|
|
2427
|
+
}
|
|
2428
|
+
}
|
|
2429
|
+
else if (isOutOfRange(dateValue, props.min, props.max)) {
|
|
2430
|
+
// out of range
|
|
2431
|
+
if (props.min !== undefined && props.max !== undefined) {
|
|
2432
|
+
dateError = `Must be be between ${parseDateString(props.min)} and ${parseDateString(props.max)}.`;
|
|
2433
|
+
}
|
|
2434
|
+
else if (props.min !== undefined) {
|
|
2435
|
+
dateError = `Must be greater than or equal to ${parseDateString(props.min)}.`;
|
|
2436
|
+
}
|
|
2437
|
+
else {
|
|
2438
|
+
dateError = `Must be less than or equal to ${parseDateString(props.max)}.`;
|
|
2439
|
+
}
|
|
2440
|
+
}
|
|
2441
|
+
updateErrorMessage(dateError);
|
|
2442
|
+
}, [dateValue, textValue]);
|
|
2443
|
+
const [showCalendar, setShowCalendar] = React__namespace.useState(false);
|
|
2444
|
+
const [calendarDate, setCalendarDate] = React__namespace.useState(getCalendarDate(props.value, props.min, props.max));
|
|
2445
|
+
// controls the one-time focus set on show
|
|
2446
|
+
const needsFocus = React__namespace.useRef(false);
|
|
2447
|
+
const toggleCalendar = React__namespace.useCallback((show) => {
|
|
2448
|
+
var _a;
|
|
2449
|
+
if (show === showCalendar) {
|
|
2228
2450
|
return;
|
|
2229
2451
|
}
|
|
2230
|
-
|
|
2231
|
-
|
|
2232
|
-
|
|
2233
|
-
|
|
2234
|
-
/* Not my responsiblity. */
|
|
2235
|
-
});
|
|
2452
|
+
needsFocus.current = show;
|
|
2453
|
+
setShowCalendar(show);
|
|
2454
|
+
if (show) {
|
|
2455
|
+
setCalendarDate(getCalendarDate(dateValue, props.min, props.max));
|
|
2236
2456
|
}
|
|
2237
2457
|
else {
|
|
2238
|
-
|
|
2458
|
+
(_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.focus();
|
|
2239
2459
|
}
|
|
2240
|
-
};
|
|
2241
|
-
const
|
|
2242
|
-
|
|
2243
|
-
|
|
2460
|
+
}, [dateValue, showCalendar]);
|
|
2461
|
+
const popover = React__namespace.useRef(null);
|
|
2462
|
+
const nativeProps = __rest(props, ["customError", "reposition", "onValueChange"]);
|
|
2463
|
+
useIgnoreMount(() => {
|
|
2464
|
+
var _a;
|
|
2465
|
+
if ((_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.checkValidity()) {
|
|
2466
|
+
props.onValueChange(dateValue);
|
|
2244
2467
|
}
|
|
2245
|
-
|
|
2246
|
-
|
|
2247
|
-
const openTip = () => {
|
|
2248
|
-
if (!props.content) {
|
|
2249
|
-
return;
|
|
2468
|
+
else {
|
|
2469
|
+
props.onValueChange(undefined);
|
|
2250
2470
|
}
|
|
2251
|
-
|
|
2252
|
-
};
|
|
2253
|
-
|
|
2254
|
-
|
|
2255
|
-
|
|
2471
|
+
updateDateErrorMessages();
|
|
2472
|
+
}, [dateValue]);
|
|
2473
|
+
useIgnoreMount(() => {
|
|
2474
|
+
updateDateErrorMessages();
|
|
2475
|
+
}, [textValue]);
|
|
2476
|
+
useIgnoreMount(() => {
|
|
2477
|
+
var _a;
|
|
2478
|
+
if (document.activeElement !== inputRef.current) {
|
|
2479
|
+
updateValues(props.value);
|
|
2480
|
+
setCalendarDate(getCalendarDate((_a = props.value) !== null && _a !== void 0 ? _a : 0, props.min, props.max));
|
|
2256
2481
|
}
|
|
2257
|
-
|
|
2258
|
-
|
|
2259
|
-
|
|
2482
|
+
updateDateErrorMessages();
|
|
2483
|
+
}, [props.value]);
|
|
2484
|
+
React__namespace.useLayoutEffect(() => {
|
|
2485
|
+
var _a, _b;
|
|
2486
|
+
if (needsFocus.current) {
|
|
2487
|
+
(_b = (_a = popover.current) === null || _a === void 0 ? void 0 : _a.querySelector('button')) === null || _b === void 0 ? void 0 : _b.focus();
|
|
2488
|
+
needsFocus.current = false;
|
|
2260
2489
|
}
|
|
2261
|
-
};
|
|
2262
|
-
const
|
|
2263
|
-
|
|
2264
|
-
|
|
2265
|
-
|
|
2266
|
-
|
|
2267
|
-
|
|
2268
|
-
|
|
2269
|
-
|
|
2270
|
-
|
|
2271
|
-
|
|
2272
|
-
|
|
2273
|
-
|
|
2274
|
-
|
|
2275
|
-
|
|
2276
|
-
|
|
2277
|
-
|
|
2278
|
-
|
|
2490
|
+
});
|
|
2491
|
+
const input = (React__namespace.createElement(BaseInput, Object.assign({}, nativeProps, { error: validationError, type: "text", ref: inputRef, value: textValue !== null && textValue !== void 0 ? textValue : '', maxLength: 10, placeholder: (_a = props.placeholder) !== null && _a !== void 0 ? _a : 'MM/DD/YYYY', pattern: datePattern, rightControl: (!props.readOnly && !props.disabled) ? (React__namespace.createElement(Button, { variant: "icon", readOnly: props.readOnly, disabled: props.disabled, small: true, style: {
|
|
2492
|
+
fontSize: '1rem'
|
|
2493
|
+
}, onClick: () => {
|
|
2494
|
+
toggleCalendar(!showCalendar);
|
|
2495
|
+
} },
|
|
2496
|
+
React__namespace.createElement(Icon, { id: "pickDate" }))) : undefined, onChange: e => {
|
|
2497
|
+
var _a;
|
|
2498
|
+
updateValues(e.target.value || undefined);
|
|
2499
|
+
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
2500
|
+
}, onFocus: e => {
|
|
2501
|
+
var _a;
|
|
2502
|
+
toggleCalendar(false);
|
|
2503
|
+
(_a = props.onFocus) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
2504
|
+
}, onBlur: e => {
|
|
2505
|
+
var _a, _b;
|
|
2506
|
+
if (!((_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.checkValidity())) {
|
|
2507
|
+
if (dateValue !== undefined) {
|
|
2508
|
+
if (isOutOfRange(dateValue, props.min, props.max)) {
|
|
2509
|
+
// try and fix the range
|
|
2510
|
+
updateValues(tryClampRange(dateValue, props.min, props.max));
|
|
2511
|
+
}
|
|
2512
|
+
}
|
|
2513
|
+
else {
|
|
2514
|
+
// just wipe it all
|
|
2515
|
+
updateValues(undefined);
|
|
2516
|
+
}
|
|
2517
|
+
}
|
|
2518
|
+
(_b = props.onBlur) === null || _b === void 0 ? void 0 : _b.call(props, e);
|
|
2519
|
+
} })));
|
|
2520
|
+
return (React__namespace.createElement(Popover, { reposition: props.reposition, isOpen: showCalendar, onClickOutside: () => {
|
|
2521
|
+
toggleCalendar(false);
|
|
2522
|
+
}, parent: input, content: (React__namespace.createElement("div", { ref: popover, className: css.css({
|
|
2523
|
+
paddingLeft: '1rem',
|
|
2524
|
+
paddingRight: '1rem',
|
|
2525
|
+
paddingBottom: '1rem'
|
|
2526
|
+
}) },
|
|
2527
|
+
React__namespace.createElement(Calendar, { onClick: date => {
|
|
2528
|
+
updateValues(date.valueOf());
|
|
2529
|
+
toggleCalendar(false);
|
|
2530
|
+
}, customTitle: React__namespace.createElement("div", { className: css.css({
|
|
2531
|
+
display: 'flex',
|
|
2532
|
+
justifyContent: 'space-between',
|
|
2533
|
+
alignItems: 'center'
|
|
2534
|
+
}) },
|
|
2535
|
+
React__namespace.createElement(Button, { disabled: !!props.min && dateFns.isBefore(dateFns.endOfMonth(dateFns.addMonths(calendarDate, -1)), props.min), small: true, variant: "icon", onClick: () => setCalendarDate(dateFns.addMonths(calendarDate, -1)) },
|
|
2536
|
+
React__namespace.createElement(Icon, { id: "pagerLeft" })),
|
|
2537
|
+
React__namespace.createElement(Text, { align: "center" },
|
|
2538
|
+
dateFns.format(calendarDate, 'LLLL'),
|
|
2539
|
+
" ",
|
|
2540
|
+
calendarDate.getFullYear()),
|
|
2541
|
+
React__namespace.createElement(Button, { disabled: !!props.max && dateFns.isAfter(dateFns.startOfMonth(dateFns.addMonths(calendarDate, 1)), props.max), small: true, variant: "icon", onClick: () => setCalendarDate(dateFns.addMonths(calendarDate, 1)) },
|
|
2542
|
+
React__namespace.createElement(Icon, { id: "pagerRight" }))), month: calendarDate.getMonth() + 1, year: calendarDate.getFullYear(), showCurrent: true, smallHeader: true, selectedValue: dateValue, cellSize: '2rem', min: props.min, max: props.max }))) }));
|
|
2543
|
+
});
|
|
2544
|
+
const parseDateNumber = (rawValue) => {
|
|
2545
|
+
if (!rawValue) {
|
|
2546
|
+
return undefined;
|
|
2279
2547
|
}
|
|
2280
|
-
|
|
2281
|
-
|
|
2282
|
-
|
|
2283
|
-
|
|
2284
|
-
|
|
2285
|
-
|
|
2548
|
+
let dateMs;
|
|
2549
|
+
const dateParts = dateRegex.exec(rawValue);
|
|
2550
|
+
if (dateParts) {
|
|
2551
|
+
const month = parseInt(dateParts[1], 10) - 1;
|
|
2552
|
+
const day = parseInt(dateParts[2], 10);
|
|
2553
|
+
const year = parseInt(dateParts[3], 10);
|
|
2554
|
+
if (dateFns.isExists(year, month, day)) {
|
|
2555
|
+
dateMs = new Date(year, month, day).valueOf();
|
|
2556
|
+
}
|
|
2557
|
+
}
|
|
2558
|
+
return dateMs;
|
|
2559
|
+
};
|
|
2560
|
+
const parseDateString = (dateMs) => {
|
|
2561
|
+
if (typeof dateMs === 'number') {
|
|
2562
|
+
return dateFns.format(dateMs, 'MM/dd/yyyy');
|
|
2563
|
+
}
|
|
2564
|
+
return undefined;
|
|
2565
|
+
};
|
|
2566
|
+
const getCalendarDate = (date, min, max) => {
|
|
2567
|
+
let calendarDate = date ? new Date(date) : new Date();
|
|
2568
|
+
// if there is a min/max we don't want the calendar to open to the current date if it's out of range
|
|
2569
|
+
if (min && dateFns.isBefore(calendarDate, min)) {
|
|
2570
|
+
calendarDate = new Date(min);
|
|
2286
2571
|
}
|
|
2572
|
+
else if (max && dateFns.isAfter(calendarDate, max)) {
|
|
2573
|
+
calendarDate = new Date(max);
|
|
2574
|
+
}
|
|
2575
|
+
return calendarDate;
|
|
2287
2576
|
};
|
|
2288
2577
|
|
|
2289
2578
|
const NumberInput = React__namespace.forwardRef((props, ref) => {
|
|
2290
|
-
const [localValue, setLocalValue] = React__namespace.useState(
|
|
2579
|
+
const [localValue, setLocalValue] = React__namespace.useState(props.value);
|
|
2291
2580
|
const inputRef = (ref !== null && ref !== void 0 ? ref : React__namespace.useRef(null));
|
|
2292
|
-
const
|
|
2293
|
-
|
|
2294
|
-
|
|
2295
|
-
|
|
2296
|
-
|
|
2581
|
+
const [validationError, updateErrorMessage] = useInputValidationMessage(inputRef, props);
|
|
2582
|
+
const nativeProps = __rest(props, ["customError", "onValueChange"]);
|
|
2583
|
+
useIgnoreMount(() => {
|
|
2584
|
+
var _a;
|
|
2585
|
+
if ((_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.checkValidity()) {
|
|
2586
|
+
props.onValueChange(localValue);
|
|
2587
|
+
}
|
|
2588
|
+
else {
|
|
2589
|
+
props.onValueChange(undefined);
|
|
2590
|
+
}
|
|
2591
|
+
updateErrorMessage();
|
|
2592
|
+
}, [localValue]);
|
|
2593
|
+
useIgnoreMount(() => {
|
|
2594
|
+
if (document.activeElement !== inputRef.current) {
|
|
2595
|
+
setLocalValue(props.value);
|
|
2596
|
+
}
|
|
2597
|
+
updateErrorMessage();
|
|
2297
2598
|
}, [props.value]);
|
|
2298
|
-
return (React__namespace.createElement(BaseInput, Object.assign({}, nativeProps, {
|
|
2599
|
+
return (React__namespace.createElement(BaseInput, Object.assign({}, nativeProps, { error: validationError, type: "number", ref: inputRef, value: localValue !== null && localValue !== void 0 ? localValue : '', maxLength: 20, onChange: e => {
|
|
2299
2600
|
var _a;
|
|
2300
2601
|
const newLocalValue = parseNumber(e.target.value);
|
|
2301
|
-
if (props.customValidityChecks) {
|
|
2302
|
-
let error;
|
|
2303
|
-
for (const func of props.customValidityChecks) {
|
|
2304
|
-
error = func(newLocalValue);
|
|
2305
|
-
if (error) {
|
|
2306
|
-
break;
|
|
2307
|
-
}
|
|
2308
|
-
}
|
|
2309
|
-
e.target.setCustomValidity(error !== null && error !== void 0 ? error : '');
|
|
2310
|
-
}
|
|
2311
2602
|
setLocalValue(newLocalValue);
|
|
2312
|
-
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props,
|
|
2603
|
+
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
2313
2604
|
}, onBlur: e => {
|
|
2314
|
-
var _a;
|
|
2315
|
-
if (props.onBlur) {
|
|
2316
|
-
let currentValue = localValue;
|
|
2317
|
-
if ((_a = props.constrainOnBlur) !== null && _a !== void 0 ? _a : true) {
|
|
2318
|
-
currentValue = tryClampRange(currentValue, props.min, props.max);
|
|
2319
|
-
currentValue = tryClampDecimals(currentValue, props.step);
|
|
2320
|
-
}
|
|
2321
|
-
if (currentValue !== localValue) {
|
|
2322
|
-
setLocalValue(currentValue);
|
|
2323
|
-
}
|
|
2324
|
-
// after all we've done, it's still possible to have strange characters in the box.
|
|
2325
|
-
// examples are '-' and 'e'. the box will show as invalid and no number will be sent from the control or be included in the local state.
|
|
2326
|
-
// here we will clean that up locally in the control.
|
|
2327
|
-
if (!e.target.checkValidity()) {
|
|
2328
|
-
e.target.value = '';
|
|
2329
|
-
}
|
|
2330
|
-
props.onBlur(currentValue, e);
|
|
2331
|
-
}
|
|
2332
|
-
}, onKeyDown: e => {
|
|
2333
2605
|
var _a, _b;
|
|
2334
|
-
|
|
2335
|
-
|
|
2336
|
-
//
|
|
2337
|
-
|
|
2606
|
+
let adjustedValue = localValue;
|
|
2607
|
+
if (e.target.validity.customError) {
|
|
2608
|
+
// if we're invalid due to a custom error, just wipe everything
|
|
2609
|
+
adjustedValue = undefined;
|
|
2610
|
+
}
|
|
2611
|
+
else {
|
|
2612
|
+
// try and fix the value
|
|
2613
|
+
adjustedValue = tryClampRange(adjustedValue, props.min, props.max);
|
|
2614
|
+
adjustedValue = tryClampDecimals(adjustedValue, props.step);
|
|
2338
2615
|
}
|
|
2339
|
-
(
|
|
2616
|
+
setLocalValue(adjustedValue);
|
|
2617
|
+
// makes our displayed value always matches the adjusted value
|
|
2618
|
+
// examples of failures are 'e', '-', and 5.0 in an integer (step=0) field.
|
|
2619
|
+
e.target.value = (_a = adjustedValue === null || adjustedValue === void 0 ? void 0 : adjustedValue.toString()) !== null && _a !== void 0 ? _a : '';
|
|
2620
|
+
(_b = props.onBlur) === null || _b === void 0 ? void 0 : _b.call(props, e);
|
|
2340
2621
|
} })));
|
|
2341
2622
|
});
|
|
2342
|
-
const tryClampDecimals = (value, step = 0) => {
|
|
2343
|
-
var _a;
|
|
2344
|
-
if (value === undefined) {
|
|
2345
|
-
return value;
|
|
2346
|
-
}
|
|
2347
|
-
if (isNaN(value)) {
|
|
2348
|
-
return undefined;
|
|
2349
|
-
}
|
|
2350
|
-
const decimals = step === 0 ? 0 : (_a = step.toString().split('.')[1]) === null || _a === void 0 ? void 0 : _a.length;
|
|
2351
|
-
if (decimals === 0) {
|
|
2352
|
-
return Math.floor(value);
|
|
2353
|
-
}
|
|
2354
|
-
return parseFloat(value.toFixed(decimals));
|
|
2355
|
-
};
|
|
2356
2623
|
const parseNumber = (rawValue) => {
|
|
2357
2624
|
let value;
|
|
2358
2625
|
if (rawValue) {
|
|
@@ -2366,39 +2633,41 @@ const parseNumber = (rawValue) => {
|
|
|
2366
2633
|
|
|
2367
2634
|
const TextInput = React__namespace.forwardRef((props, ref) => {
|
|
2368
2635
|
var _a;
|
|
2369
|
-
const [localValue, setLocalValue] = React__namespace.useState(
|
|
2636
|
+
const [localValue, setLocalValue] = React__namespace.useState(props.value);
|
|
2370
2637
|
const inputRef = (ref !== null && ref !== void 0 ? ref : React__namespace.useRef(null));
|
|
2371
|
-
const
|
|
2372
|
-
|
|
2373
|
-
|
|
2374
|
-
|
|
2638
|
+
const [validationError, updateErrorMessage] = useInputValidationMessage(inputRef, props);
|
|
2639
|
+
const nativeProps = __rest(props, ["emptyString", "onValueChange", "customError", "patternErrorMessage"]);
|
|
2640
|
+
useIgnoreMount(() => {
|
|
2641
|
+
var _a;
|
|
2642
|
+
if ((_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.checkValidity()) {
|
|
2643
|
+
props.onValueChange(localValue);
|
|
2644
|
+
}
|
|
2645
|
+
else {
|
|
2646
|
+
props.onValueChange(undefined);
|
|
2647
|
+
}
|
|
2648
|
+
updateErrorMessage();
|
|
2649
|
+
}, [localValue]);
|
|
2650
|
+
useIgnoreMount(() => {
|
|
2651
|
+
if (document.activeElement !== inputRef.current) {
|
|
2652
|
+
setLocalValue(props.value);
|
|
2653
|
+
}
|
|
2654
|
+
updateErrorMessage();
|
|
2375
2655
|
}, [props.value]);
|
|
2376
|
-
return (React__namespace.createElement(BaseInput, Object.assign({}, nativeProps, { type: (_a = props.type) !== null && _a !== void 0 ? _a : 'text', ref: inputRef, value: localValue !== null && localValue !== void 0 ? localValue : '', onChange: e => {
|
|
2656
|
+
return (React__namespace.createElement(BaseInput, Object.assign({}, nativeProps, { error: validationError, type: (_a = props.type) !== null && _a !== void 0 ? _a : 'text', ref: inputRef, value: localValue !== null && localValue !== void 0 ? localValue : '', onChange: e => {
|
|
2377
2657
|
var _a;
|
|
2378
|
-
|
|
2379
|
-
|
|
2380
|
-
let error;
|
|
2381
|
-
for (const func of props.customValidityChecks) {
|
|
2382
|
-
error = func(value);
|
|
2383
|
-
if (error) {
|
|
2384
|
-
break;
|
|
2385
|
-
}
|
|
2386
|
-
}
|
|
2387
|
-
e.target.setCustomValidity(error !== null && error !== void 0 ? error : '');
|
|
2388
|
-
}
|
|
2389
|
-
setLocalValue(value);
|
|
2390
|
-
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, value, e);
|
|
2658
|
+
setLocalValue(props.emptyString ? e.target.value : e.target.value || undefined);
|
|
2659
|
+
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
2391
2660
|
}, onBlur: e => {
|
|
2392
|
-
var _a;
|
|
2393
|
-
(_a = props.onBlur) === null || _a === void 0 ? void 0 : _a.call(props, localValue, e);
|
|
2394
|
-
}, onKeyDown: e => {
|
|
2395
2661
|
var _a, _b;
|
|
2396
|
-
if (e.
|
|
2397
|
-
|
|
2398
|
-
|
|
2399
|
-
|
|
2662
|
+
if (!e.target.checkValidity()) {
|
|
2663
|
+
setLocalValue(undefined);
|
|
2664
|
+
}
|
|
2665
|
+
else if ((_a = props.trim) !== null && _a !== void 0 ? _a : true) {
|
|
2666
|
+
setLocalValue(currentValue => {
|
|
2667
|
+
return currentValue === null || currentValue === void 0 ? void 0 : currentValue.trim();
|
|
2668
|
+
});
|
|
2400
2669
|
}
|
|
2401
|
-
(_b = props.
|
|
2670
|
+
(_b = props.onBlur) === null || _b === void 0 ? void 0 : _b.call(props, e);
|
|
2402
2671
|
} })));
|
|
2403
2672
|
});
|
|
2404
2673
|
|
|
@@ -2494,6 +2763,9 @@ const Label = (props) => {
|
|
|
2494
2763
|
From https://fireship.io/snippets/use-media-query-hook/.
|
|
2495
2764
|
Tried using https://www.npmjs.com/package/react-media, but it cause Webpack build issues.
|
|
2496
2765
|
*/
|
|
2766
|
+
/** React wrapper around window resizing and window.matchMedia.
|
|
2767
|
+
* https://developer.mozilla.org/en-US/docs/Web/API/Window/matchMedia
|
|
2768
|
+
*/
|
|
2497
2769
|
const useMediaQuery = (query) => {
|
|
2498
2770
|
const [matches, setMatches] = React.useState(false);
|
|
2499
2771
|
React.useEffect(() => {
|
|
@@ -2509,11 +2781,13 @@ const useMediaQuery = (query) => {
|
|
|
2509
2781
|
};
|
|
2510
2782
|
|
|
2511
2783
|
const Nav = (props) => {
|
|
2784
|
+
var _a, _b;
|
|
2512
2785
|
const nav = React__namespace.useRef(null);
|
|
2513
2786
|
const theme = useThemeSafely();
|
|
2514
2787
|
const totalNavOffset = `calc(${theme.layout.navWidth} + 20px)`;
|
|
2515
2788
|
const backdrop = React__namespace.useContext(BackdropContext);
|
|
2516
2789
|
const isLargeScreen = useMediaQuery(`(min-width:${theme.breakpoints.desktop})`);
|
|
2790
|
+
const log = useLogger(`Nav ${(_a = props.id) !== null && _a !== void 0 ? _a : '?'}`, (_b = props.__debug) !== null && _b !== void 0 ? _b : false);
|
|
2517
2791
|
const slideRight = css.keyframes `
|
|
2518
2792
|
0% {
|
|
2519
2793
|
transform: translateX(0);
|
|
@@ -2574,9 +2848,11 @@ const Nav = (props) => {
|
|
|
2574
2848
|
props.toggle(false);
|
|
2575
2849
|
}
|
|
2576
2850
|
}, [backdrop.showing]);
|
|
2577
|
-
|
|
2578
|
-
|
|
2579
|
-
|
|
2851
|
+
useBooleanChanged((current, previous) => {
|
|
2852
|
+
var _a;
|
|
2853
|
+
log('show changed', `${previous !== null && previous !== void 0 ? previous : 'undefined'} > ${current}`);
|
|
2854
|
+
backdrop.setShow(current, (_a = props.id) !== null && _a !== void 0 ? _a : 'Nav');
|
|
2855
|
+
}, props.show);
|
|
2580
2856
|
React__namespace.useLayoutEffect(() => {
|
|
2581
2857
|
if (nav && nav.current) {
|
|
2582
2858
|
if (props.show) {
|
|
@@ -2607,6 +2883,7 @@ const Nav = (props) => {
|
|
|
2607
2883
|
return (React__namespace.createElement("nav", { ref: nav, className: css.cx('nav', navStyles, props.className) }, props.children));
|
|
2608
2884
|
};
|
|
2609
2885
|
|
|
2886
|
+
//TB: FUTURE make just a basic styled link so you don't have to go with React Router if you don't want to.
|
|
2610
2887
|
const OmniLink = (props) => {
|
|
2611
2888
|
var _a, _b, _c;
|
|
2612
2889
|
const theme = useThemeSafely();
|
|
@@ -2783,7 +3060,7 @@ const OmniLink = (props) => {
|
|
|
2783
3060
|
const Picker = (props) => {
|
|
2784
3061
|
const selectProps = __rest(props
|
|
2785
3062
|
// if we put numbers in, we expect them out
|
|
2786
|
-
, ["value", "options", "
|
|
3063
|
+
, ["value", "options", "onValueChange", "readOnly", "round", "controlAlign"]);
|
|
2787
3064
|
// if we put numbers in, we expect them out
|
|
2788
3065
|
let isNumber = false;
|
|
2789
3066
|
if (props.options && props.options.length) {
|
|
@@ -2819,7 +3096,7 @@ const Picker = (props) => {
|
|
|
2819
3096
|
${props.round && `
|
|
2820
3097
|
border-radius: ${theme.controls.roundRadius};
|
|
2821
3098
|
`}
|
|
2822
|
-
${props.
|
|
3099
|
+
${props.readOnly && `
|
|
2823
3100
|
background-color: transparent !important;
|
|
2824
3101
|
border: none;
|
|
2825
3102
|
-webkit-appearance: none;
|
|
@@ -2830,9 +3107,9 @@ const Picker = (props) => {
|
|
|
2830
3107
|
}
|
|
2831
3108
|
`}
|
|
2832
3109
|
`;
|
|
2833
|
-
|
|
3110
|
+
const select = (React__namespace.createElement("select", Object.assign({}, selectProps, { tabIndex: props.readOnly ? -1 : selectProps.tabIndex, className: css.cx('picker', selectStyles, props.className), value: props.value, onKeyDown: e => {
|
|
2834
3111
|
var _a;
|
|
2835
|
-
if (props.
|
|
3112
|
+
if (props.readOnly) {
|
|
2836
3113
|
if (e.keyCode === 9) {
|
|
2837
3114
|
//TAB
|
|
2838
3115
|
return;
|
|
@@ -2845,7 +3122,7 @@ const Picker = (props) => {
|
|
|
2845
3122
|
}
|
|
2846
3123
|
}, onMouseDown: e => {
|
|
2847
3124
|
var _a;
|
|
2848
|
-
if (props.
|
|
3125
|
+
if (props.readOnly) {
|
|
2849
3126
|
e.preventDefault();
|
|
2850
3127
|
e.stopPropagation();
|
|
2851
3128
|
}
|
|
@@ -2853,6 +3130,7 @@ const Picker = (props) => {
|
|
|
2853
3130
|
(_a = selectProps.onMouseDown) === null || _a === void 0 ? void 0 : _a.call(selectProps, e);
|
|
2854
3131
|
}
|
|
2855
3132
|
}, onChange: e => {
|
|
3133
|
+
var _a;
|
|
2856
3134
|
let val = e.target.value;
|
|
2857
3135
|
if (isNumber) {
|
|
2858
3136
|
val = parseInt(val, 10);
|
|
@@ -2860,7 +3138,8 @@ const Picker = (props) => {
|
|
|
2860
3138
|
val = '';
|
|
2861
3139
|
}
|
|
2862
3140
|
}
|
|
2863
|
-
props.
|
|
3141
|
+
props.onValueChange(val);
|
|
3142
|
+
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
2864
3143
|
} }), (props.options || []).map(o => {
|
|
2865
3144
|
var _a;
|
|
2866
3145
|
let val;
|
|
@@ -2875,6 +3154,14 @@ const Picker = (props) => {
|
|
|
2875
3154
|
}
|
|
2876
3155
|
return React__namespace.createElement("option", { key: val, value: val }, label);
|
|
2877
3156
|
})));
|
|
3157
|
+
if (props.controlAlign) {
|
|
3158
|
+
return (React__namespace.createElement("span", { className: css.css({
|
|
3159
|
+
display: 'inline-block',
|
|
3160
|
+
width: '100%',
|
|
3161
|
+
paddingBottom: theme.controls.inputErrorMinHeight
|
|
3162
|
+
}) }, select));
|
|
3163
|
+
}
|
|
3164
|
+
return select;
|
|
2878
3165
|
};
|
|
2879
3166
|
|
|
2880
3167
|
const Pager = (props) => {
|
|
@@ -2939,8 +3226,8 @@ const BoundMemoryPager = (p) => {
|
|
|
2939
3226
|
var _a, _b, _c;
|
|
2940
3227
|
const { pager, showPageText } = p, rest = __rest(p, ["pager", "showPageText"]);
|
|
2941
3228
|
return (React__namespace.createElement(Pager, Object.assign({}, rest, { pageIndex: p.showPageText ? pager.page : undefined, totalPages: p.showPageText ? pager.totalPages : undefined, canGoNext: pager.hasNext, canGoPrevious: pager.hasPrevious, minItem: pager.minItemIndex + 1, maxItem: pager.maxItemIndex + 1, totalItems: pager.totalItems, leftControls: pager.limitOptions.length > 1 && p.onLimit ? (React__namespace.createElement(Label, { text: (_a = p.limitText) !== null && _a !== void 0 ? _a : 'Limit', orientation: "horizontal" },
|
|
2942
|
-
React__namespace.createElement(Picker, { value: pager.limit, options: pager.limitOptions,
|
|
2943
|
-
React__namespace.createElement(Picker, { value: (_c = pager.sort) !== null && _c !== void 0 ? _c : '', options: pager.sortOptions,
|
|
3229
|
+
React__namespace.createElement(Picker, { value: pager.limit, options: pager.limitOptions, onValueChange: v => { var _a; return (_a = p.onLimit) === null || _a === void 0 ? void 0 : _a.call(p, v); } }))) : undefined, rightControls: pager.sortOptions.length > 1 && p.onSort ? (React__namespace.createElement(Label, { text: (_b = p.sortText) !== null && _b !== void 0 ? _b : 'Sort', orientation: "horizontalReverse" },
|
|
3230
|
+
React__namespace.createElement(Picker, { value: (_c = pager.sort) !== null && _c !== void 0 ? _c : '', options: pager.sortOptions, onValueChange: v => { var _a; return (_a = p.onSort) === null || _a === void 0 ? void 0 : _a.call(p, v); } }))) : undefined, page: d => {
|
|
2944
3231
|
p.onPage(d);
|
|
2945
3232
|
} })));
|
|
2946
3233
|
};
|
|
@@ -2951,8 +3238,8 @@ const BoundStaticPager = (p) => {
|
|
|
2951
3238
|
const showLimit = !!(result.limit && p.limitOptions && p.limitOptions.length > 1 && p.onLimit);
|
|
2952
3239
|
const showSort = !!(p.sort !== undefined && p.sortOptions && p.sortOptions.length > 1 && p.onSort);
|
|
2953
3240
|
return (React__namespace.createElement(Pager, Object.assign({}, rest, { pageIndex: p.showPageText ? result.page : undefined, totalPages: p.showPageText ? result.totalPages : undefined, canGoNext: result.hasNext, canGoPrevious: result.hasPrevious, minItem: result.minPageItemIndex + 1, maxItem: result.maxPageItemIndex + 1, totalItems: result.total, leftControls: showLimit ? (React__namespace.createElement(Label, { text: (_a = p.limitText) !== null && _a !== void 0 ? _a : 'Limit', orientation: "horizontal" },
|
|
2954
|
-
React__namespace.createElement(Picker, { value: (_b = result.limit) !== null && _b !== void 0 ? _b : 1, options: (_c = p.limitOptions) !== null && _c !== void 0 ? _c : [1],
|
|
2955
|
-
React__namespace.createElement(Picker, { value: (_e = p.sort) !== null && _e !== void 0 ? _e : '', options: (_f = p.sortOptions) !== null && _f !== void 0 ? _f : [],
|
|
3241
|
+
React__namespace.createElement(Picker, { value: (_b = result.limit) !== null && _b !== void 0 ? _b : 1, options: (_c = p.limitOptions) !== null && _c !== void 0 ? _c : [1], onValueChange: v => { var _a; return (_a = p.onLimit) === null || _a === void 0 ? void 0 : _a.call(p, v); } }))) : undefined, rightControls: showSort ? (React__namespace.createElement(Label, { text: (_d = p.sortText) !== null && _d !== void 0 ? _d : 'Sort', orientation: "horizontalReverse" },
|
|
3242
|
+
React__namespace.createElement(Picker, { value: (_e = p.sort) !== null && _e !== void 0 ? _e : '', options: (_f = p.sortOptions) !== null && _f !== void 0 ? _f : [], onValueChange: v => {
|
|
2956
3243
|
var _a;
|
|
2957
3244
|
(_a = p.onSort) === null || _a === void 0 ? void 0 : _a.call(p, v);
|
|
2958
3245
|
} }))) : undefined, page: d => {
|
|
@@ -2960,6 +3247,7 @@ const BoundStaticPager = (p) => {
|
|
|
2960
3247
|
} })));
|
|
2961
3248
|
};
|
|
2962
3249
|
|
|
3250
|
+
/** A page of data with helpers props. */
|
|
2963
3251
|
class PagedResult {
|
|
2964
3252
|
constructor(items = [], total = 0, page = 0, limit = 0) {
|
|
2965
3253
|
this.items = items;
|
|
@@ -2970,10 +3258,6 @@ class PagedResult {
|
|
|
2970
3258
|
static fromDto(dto) {
|
|
2971
3259
|
return new PagedResult(dto.items, dto.total, dto.page, dto.limit);
|
|
2972
3260
|
}
|
|
2973
|
-
// allItems: T[]
|
|
2974
|
-
// get pageItems(): T[] {
|
|
2975
|
-
// return this.allItems.slice(this.minPageItemIndex, this.maxPageItemIndex + 1)
|
|
2976
|
-
// }
|
|
2977
3261
|
/** Helper for items.length */
|
|
2978
3262
|
get length() {
|
|
2979
3263
|
return this.items ? this.items.length : 0;
|
|
@@ -3097,7 +3381,7 @@ class PagedResult {
|
|
|
3097
3381
|
}
|
|
3098
3382
|
}
|
|
3099
3383
|
|
|
3100
|
-
/**
|
|
3384
|
+
/** In-memory pager. */
|
|
3101
3385
|
class ItemPager {
|
|
3102
3386
|
constructor(allItems, options) {
|
|
3103
3387
|
var _a, _b, _c, _d;
|
|
@@ -3347,6 +3631,7 @@ const cleanPct = (value) => {
|
|
|
3347
3631
|
return 0;
|
|
3348
3632
|
};
|
|
3349
3633
|
|
|
3634
|
+
/** Provides stateful notifications around async calls. */
|
|
3350
3635
|
const useWaiting = (func) => {
|
|
3351
3636
|
// Guard against the owner of this hook being unmounted at the time of .finally.
|
|
3352
3637
|
const isCancelled = React.useRef(false);
|
|
@@ -3379,12 +3664,12 @@ const SearchBox = (props) => {
|
|
|
3379
3664
|
return (_c = props.onSubmit) === null || _c === void 0 ? void 0 : _c.call(props);
|
|
3380
3665
|
});
|
|
3381
3666
|
const theme = useThemeSafely();
|
|
3382
|
-
const submitButton = (React__namespace.createElement(Button, { disabled: waiting,
|
|
3667
|
+
const submitButton = (React__namespace.createElement(Button, { disabled: waiting, readOnly: !props.onSubmit, type: "submit", className: css.css({
|
|
3383
3668
|
color: `${theme.colors.font} !important;`,
|
|
3384
3669
|
fontSize: '1rem'
|
|
3385
3670
|
}), variant: "icon", small: true },
|
|
3386
3671
|
React__namespace.createElement(Icon, { id: waiting ? 'waiting' : 'search', spin: waiting })));
|
|
3387
|
-
//TB: replace with new inputs
|
|
3672
|
+
//TB: FUTURE replace with new inputs
|
|
3388
3673
|
return (React__namespace.createElement(Form, { role: "search", className: css.cx('searchBox', props.className), onSubmit: onSubmit },
|
|
3389
3674
|
React__namespace.createElement(Input, { id: props.id, debounceMs: props.debounceMs, disabled: waiting, type: "text", value: props.value, placeholder: props.placeholder, round: props.round, onChange: props.onChange, rightControl: submitButton })));
|
|
3390
3675
|
};
|
|
@@ -3417,6 +3702,28 @@ const GlobalStyles = () => {
|
|
|
3417
3702
|
return null;
|
|
3418
3703
|
};
|
|
3419
3704
|
|
|
3705
|
+
const getCurrencyDisplay = (value, isCents, denomination = '$') => {
|
|
3706
|
+
let actualValue = value || 0;
|
|
3707
|
+
if (isCents) {
|
|
3708
|
+
actualValue /= 100;
|
|
3709
|
+
}
|
|
3710
|
+
return `${denomination}${actualValue.toLocaleString(undefined, { minimumFractionDigits: 2, maximumFractionDigits: 2 })}`;
|
|
3711
|
+
};
|
|
3712
|
+
/** Converts an enum to an array of entities with id and name. The enum can be an integer or string enum.*/
|
|
3713
|
+
const enumToEntities = (enumObj) => {
|
|
3714
|
+
const entities = [];
|
|
3715
|
+
for (const key in enumObj) {
|
|
3716
|
+
if (isNaN(parseInt(key, 10))) {
|
|
3717
|
+
entities.push({
|
|
3718
|
+
id: enumObj[key],
|
|
3719
|
+
name: key
|
|
3720
|
+
});
|
|
3721
|
+
}
|
|
3722
|
+
}
|
|
3723
|
+
return entities;
|
|
3724
|
+
};
|
|
3725
|
+
//TB: FUTURE Expose in UI.
|
|
3726
|
+
|
|
3420
3727
|
const Slider = (p) => {
|
|
3421
3728
|
const theme = useThemeSafely();
|
|
3422
3729
|
const currentValue = React.useRef(p.value);
|
|
@@ -3562,7 +3869,7 @@ const TabHeader = (p) => {
|
|
|
3562
3869
|
});
|
|
3563
3870
|
}
|
|
3564
3871
|
return (React__namespace.createElement("li", { key: index, className: tabStyles },
|
|
3565
|
-
React__namespace.createElement(Button, { className: buttonStyles, variant: buttonVariant, title: tab.name,
|
|
3872
|
+
React__namespace.createElement(Button, { className: buttonStyles, variant: buttonVariant, title: tab.name, readOnly: active, onClick: () => {
|
|
3566
3873
|
setTabIndex(index);
|
|
3567
3874
|
if (p.onTabChanged) {
|
|
3568
3875
|
p.onTabChanged(index);
|
|
@@ -3698,13 +4005,29 @@ const defaultMaxLength = 200;
|
|
|
3698
4005
|
const defaultRows = 10;
|
|
3699
4006
|
const TextArea = React__namespace.forwardRef((props, ref) => {
|
|
3700
4007
|
var _a, _b;
|
|
3701
|
-
const [localValue, setLocalValue] = React__namespace.useState(
|
|
4008
|
+
const [localValue, setLocalValue] = React__namespace.useState(props.value);
|
|
3702
4009
|
const inputRef = (ref !== null && ref !== void 0 ? ref : React__namespace.useRef(null));
|
|
3703
|
-
const
|
|
4010
|
+
const [validationError, updateErrorMessage] = useInputValidationMessage(inputRef, props);
|
|
4011
|
+
const nativeProps = __rest(props, ["onValueChange"]);
|
|
3704
4012
|
const theme = useThemeSafely();
|
|
3705
4013
|
React__namespace.useEffect(() => {
|
|
3706
|
-
|
|
3707
|
-
|
|
4014
|
+
updateErrorMessage();
|
|
4015
|
+
}, []);
|
|
4016
|
+
useIgnoreMount(() => {
|
|
4017
|
+
var _a;
|
|
4018
|
+
if ((_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.checkValidity()) {
|
|
4019
|
+
props.onValueChange(localValue);
|
|
4020
|
+
}
|
|
4021
|
+
else {
|
|
4022
|
+
props.onValueChange(undefined);
|
|
4023
|
+
}
|
|
4024
|
+
updateErrorMessage();
|
|
4025
|
+
}, [localValue]);
|
|
4026
|
+
useIgnoreMount(() => {
|
|
4027
|
+
if (document.activeElement !== inputRef.current) {
|
|
4028
|
+
setLocalValue(props.value);
|
|
4029
|
+
}
|
|
4030
|
+
updateErrorMessage();
|
|
3708
4031
|
}, [props.value]);
|
|
3709
4032
|
const styles = css.css({
|
|
3710
4033
|
maxWidth: '100%',
|
|
@@ -3743,35 +4066,24 @@ const TextArea = React__namespace.forwardRef((props, ref) => {
|
|
|
3743
4066
|
boxShadow: 'none'
|
|
3744
4067
|
}
|
|
3745
4068
|
});
|
|
3746
|
-
return (React__namespace.createElement("
|
|
3747
|
-
|
|
3748
|
-
|
|
3749
|
-
|
|
3750
|
-
|
|
3751
|
-
|
|
3752
|
-
|
|
3753
|
-
|
|
3754
|
-
|
|
3755
|
-
|
|
3756
|
-
|
|
3757
|
-
|
|
3758
|
-
|
|
3759
|
-
|
|
3760
|
-
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, value, e);
|
|
3761
|
-
}, onBlur: e => {
|
|
3762
|
-
var _a;
|
|
3763
|
-
(_a = props.onBlur) === null || _a === void 0 ? void 0 : _a.call(props, localValue, e);
|
|
3764
|
-
}, onKeyDown: e => {
|
|
3765
|
-
var _a, _b;
|
|
3766
|
-
if (e.key === 'Enter') {
|
|
3767
|
-
// handle form submission on enter for onBlur-only situations.
|
|
3768
|
-
// onBlur will not be fired so any local change will not be communicated to the outside.
|
|
3769
|
-
if (!props.onChange) {
|
|
3770
|
-
(_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.blur();
|
|
4069
|
+
return (React__namespace.createElement("span", { className: css.css({
|
|
4070
|
+
display: 'inline-block',
|
|
4071
|
+
width: '100%'
|
|
4072
|
+
}) },
|
|
4073
|
+
React__namespace.createElement("textarea", Object.assign({}, nativeProps, { className: css.cx(styles, props.className), autoComplete: (_a = props.autoComplete) !== null && _a !== void 0 ? _a : 'off', tabIndex: props.readOnly ? -1 : props.tabIndex, maxLength: props.maxLength || defaultMaxLength, rows: (_b = props.rows) !== null && _b !== void 0 ? _b : defaultRows, ref: inputRef, value: localValue !== null && localValue !== void 0 ? localValue : '', onChange: e => {
|
|
4074
|
+
var _a;
|
|
4075
|
+
setLocalValue(e.target.value || undefined);
|
|
4076
|
+
(_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
4077
|
+
}, onBlur: e => {
|
|
4078
|
+
var _a;
|
|
4079
|
+
if (!props.noTrim) {
|
|
4080
|
+
setLocalValue(currentValue => {
|
|
4081
|
+
return currentValue === null || currentValue === void 0 ? void 0 : currentValue.trim();
|
|
4082
|
+
});
|
|
3771
4083
|
}
|
|
3772
|
-
|
|
3773
|
-
|
|
3774
|
-
|
|
4084
|
+
(_a = props.onBlur) === null || _a === void 0 ? void 0 : _a.call(props, e);
|
|
4085
|
+
} })),
|
|
4086
|
+
React__namespace.createElement(InputErrorDisplay, { error: validationError })));
|
|
3775
4087
|
});
|
|
3776
4088
|
|
|
3777
4089
|
const ToggleButton = (props) => {
|
|
@@ -3841,10 +4153,9 @@ const ToggleButtonGroup = (props) => {
|
|
|
3841
4153
|
})));
|
|
3842
4154
|
};
|
|
3843
4155
|
|
|
3844
|
-
const TogglePasswordInput = (
|
|
4156
|
+
const TogglePasswordInput = React__namespace.forwardRef((props, ref) => {
|
|
3845
4157
|
const [show, setShow] = React__namespace.useState(false);
|
|
3846
|
-
|
|
3847
|
-
return (React__namespace.createElement(Input, Object.assign({}, p, { type: show ? 'text' : 'password', rightControl: (React__namespace.createElement(Button, { small: true, style: {
|
|
4158
|
+
return (React__namespace.createElement(TextInput, Object.assign({}, props, { ref: ref, type: show ? 'text' : 'password', rightControl: (React__namespace.createElement(Button, { small: true, style: {
|
|
3848
4159
|
// small button is required here due to the icon pushing outside the boundries of the
|
|
3849
4160
|
// parent textbox. increasing the font size here to fill the small button.
|
|
3850
4161
|
fontSize: '1rem'
|
|
@@ -3852,24 +4163,21 @@ const TogglePasswordInput = (p) => {
|
|
|
3852
4163
|
setShow(previous => !previous);
|
|
3853
4164
|
} },
|
|
3854
4165
|
React__namespace.createElement(Icon, { id: show ? 'show' : 'hide' }))) })));
|
|
3855
|
-
};
|
|
4166
|
+
});
|
|
3856
4167
|
|
|
3857
4168
|
const WaitingIndicator = (p) => {
|
|
3858
4169
|
var _a, _b;
|
|
3859
4170
|
const [show, setShow] = React.useState(p.show);
|
|
3860
4171
|
const hideTimer = React.useRef(0);
|
|
3861
4172
|
const lastShowStatus = React.useRef(false);
|
|
3862
|
-
const log = useLogger(`WaitingIndicator ${(_a = p.id) !== null && _a !== void 0 ? _a : '?'}`, (_b = p.
|
|
3863
|
-
if (p.
|
|
4173
|
+
const log = useLogger(`WaitingIndicator ${(_a = p.id) !== null && _a !== void 0 ? _a : '?'}`, (_b = p.__debug) !== null && _b !== void 0 ? _b : false);
|
|
4174
|
+
if (p.__debug) {
|
|
3864
4175
|
React.useEffect(() => {
|
|
3865
4176
|
log('mounted');
|
|
3866
4177
|
return () => {
|
|
3867
4178
|
log('unmounted');
|
|
3868
4179
|
};
|
|
3869
4180
|
}, []);
|
|
3870
|
-
React.useEffect(() => {
|
|
3871
|
-
log('re-rendered');
|
|
3872
|
-
});
|
|
3873
4181
|
}
|
|
3874
4182
|
React.useEffect(() => {
|
|
3875
4183
|
log('show changed', p.show);
|
|
@@ -3910,7 +4218,7 @@ const WaitingIndicator = (p) => {
|
|
|
3910
4218
|
}
|
|
3911
4219
|
}
|
|
3912
4220
|
}, [p.show]);
|
|
3913
|
-
return (React__default['default'].createElement(Modal, { id: p.id,
|
|
4221
|
+
return (React__default['default'].createElement(Modal, { id: p.id, __debug: p.__debug, className: "waitingIndicator", show: show, noBackground: true },
|
|
3914
4222
|
React__default['default'].createElement("div", { className: css.css({
|
|
3915
4223
|
color: 'white',
|
|
3916
4224
|
fontSize: '3rem'
|
|
@@ -3918,6 +4226,7 @@ const WaitingIndicator = (p) => {
|
|
|
3918
4226
|
React__default['default'].createElement(Icon, { id: "waiting", spin: true }))));
|
|
3919
4227
|
};
|
|
3920
4228
|
|
|
4229
|
+
exports.Accordian = Accordian;
|
|
3921
4230
|
exports.Autocomplete = Autocomplete;
|
|
3922
4231
|
exports.Backdrop = Backdrop$1;
|
|
3923
4232
|
exports.Backdrop2 = Backdrop;
|
|
@@ -3928,7 +4237,7 @@ exports.Calendar = Calendar;
|
|
|
3928
4237
|
exports.Checkbox = Checkbox;
|
|
3929
4238
|
exports.ConfirmModal = ConfirmModal;
|
|
3930
4239
|
exports.CopyButton = CopyButton;
|
|
3931
|
-
exports.
|
|
4240
|
+
exports.DateInput = DateInput;
|
|
3932
4241
|
exports.Divider = Divider;
|
|
3933
4242
|
exports.ErrorModal = ErrorModal;
|
|
3934
4243
|
exports.FileUploader = FileUploader;
|
|
@@ -3978,7 +4287,14 @@ exports.Tr = Tr;
|
|
|
3978
4287
|
exports.WaitingIndicator = WaitingIndicator;
|
|
3979
4288
|
exports.calcDynamicThemeProps = calcDynamicThemeProps;
|
|
3980
4289
|
exports.defaultTheme = defaultTheme;
|
|
4290
|
+
exports.enumToEntities = enumToEntities;
|
|
3981
4291
|
exports.getCurrencyDisplay = getCurrencyDisplay;
|
|
4292
|
+
exports.getFileSizeDisplay = getFileSizeDisplay;
|
|
4293
|
+
exports.useAccordianState = useAccordianState;
|
|
4294
|
+
exports.useBooleanChanged = useBooleanChanged;
|
|
4295
|
+
exports.useIgnoreMount = useIgnoreMount;
|
|
3982
4296
|
exports.useMediaQuery = useMediaQuery;
|
|
4297
|
+
exports.useScrollbarSize = useScrollbarSize;
|
|
3983
4298
|
exports.useThemeSafely = useThemeSafely;
|
|
4299
|
+
exports.useWaiting = useWaiting;
|
|
3984
4300
|
//# sourceMappingURL=index.js.map
|