@sats-group/ui-lib 75.8.0 → 75.10.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/package.json
CHANGED
|
@@ -163,12 +163,19 @@
|
|
|
163
163
|
}
|
|
164
164
|
|
|
165
165
|
&__help {
|
|
166
|
+
display: flex;
|
|
167
|
+
align-items: center;
|
|
168
|
+
gap: spacing.$xs;
|
|
166
169
|
margin-top: spacing.$xxs;
|
|
167
170
|
color: light.$on-background-primary-disabled;
|
|
168
171
|
}
|
|
169
172
|
|
|
170
173
|
&__error {
|
|
174
|
+
display: flex;
|
|
175
|
+
align-items: center;
|
|
176
|
+
gap: spacing.$xs;
|
|
171
177
|
margin-top: spacing.$xxs;
|
|
178
|
+
color: light.$on-surface-error;
|
|
172
179
|
}
|
|
173
180
|
|
|
174
181
|
&__asterisk {
|
|
@@ -5,6 +5,9 @@ import Text from '../text';
|
|
|
5
5
|
import useInputValidation from '../use-input-validation';
|
|
6
6
|
|
|
7
7
|
import { themes, variants, TextInput as Props } from './text-input.types';
|
|
8
|
+
import { useEffect } from 'react';
|
|
9
|
+
import SvgError from '@sats-group/icons/16/error';
|
|
10
|
+
import SvgInfo from '@sats-group/icons/16/info';
|
|
8
11
|
|
|
9
12
|
const RefTextInput = React.forwardRef<HTMLInputElement, Props>(
|
|
10
13
|
(
|
|
@@ -29,8 +32,16 @@ const RefTextInput = React.forwardRef<HTMLInputElement, Props>(
|
|
|
29
32
|
},
|
|
30
33
|
ref,
|
|
31
34
|
) => {
|
|
32
|
-
const [
|
|
33
|
-
|
|
35
|
+
const [isError, setIsError] = React.useState(hasError);
|
|
36
|
+
const [validationOnChange, onInvalid, error] = useInputValidation(
|
|
37
|
+
customErrorMessages,
|
|
38
|
+
customErrorMessages ? customErrorMessages.defaultError : undefined,
|
|
39
|
+
isError,
|
|
40
|
+
);
|
|
41
|
+
|
|
42
|
+
useEffect(() => {
|
|
43
|
+
setIsError(hasError);
|
|
44
|
+
}, [hasError]);
|
|
34
45
|
|
|
35
46
|
return (
|
|
36
47
|
<label
|
|
@@ -38,7 +49,7 @@ const RefTextInput = React.forwardRef<HTMLInputElement, Props>(
|
|
|
38
49
|
'text-input--theme-dark': theme === themes.dark,
|
|
39
50
|
'text-input--theme-light': theme === themes.light,
|
|
40
51
|
'text-input--disabled': disabled,
|
|
41
|
-
'text-input--error': error ||
|
|
52
|
+
'text-input--error': error || isError,
|
|
42
53
|
'text-input--moving-label': icon ? false : hasMovingLabel,
|
|
43
54
|
'text-input--icon': icon,
|
|
44
55
|
'text-input--variant-small': variant === variants.small,
|
|
@@ -57,6 +68,7 @@ const RefTextInput = React.forwardRef<HTMLInputElement, Props>(
|
|
|
57
68
|
onChange={e => {
|
|
58
69
|
onChange(e);
|
|
59
70
|
validationOnChange(e);
|
|
71
|
+
setIsError(false); // NOTE: We want to reset error state on change to not confuse users.
|
|
60
72
|
}}
|
|
61
73
|
// NOTE: Using " " as placeholder for moving label theme to enable using `:placeholder-shown` to determine when to move the label
|
|
62
74
|
placeholder={
|
|
@@ -87,12 +99,14 @@ const RefTextInput = React.forwardRef<HTMLInputElement, Props>(
|
|
|
87
99
|
|
|
88
100
|
{helpText ? (
|
|
89
101
|
<div className="text-input__help">
|
|
102
|
+
<SvgInfo />
|
|
90
103
|
<Text size={Text.sizes.interface}>{helpText}</Text>
|
|
91
104
|
</div>
|
|
92
105
|
) : null}
|
|
93
106
|
{/* NOTE: This is aria-hidden because reporting of validation errors is handled by the browser */}
|
|
94
107
|
{error ? (
|
|
95
108
|
<div aria-hidden="true" className="text-input__error">
|
|
109
|
+
<SvgError />
|
|
96
110
|
<Text size={Text.sizes.interface}>{error}</Text>
|
|
97
111
|
</div>
|
|
98
112
|
) : null}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { useRef, useState } from 'react';
|
|
1
|
+
import { useRef, useState, useEffect } from 'react';
|
|
2
2
|
|
|
3
3
|
import { Messages } from './use-input-validation.types';
|
|
4
4
|
|
|
@@ -18,14 +18,28 @@ const getCustomMessage = (validity: ValidityState, messages: Messages) => {
|
|
|
18
18
|
if (validity.tooShort) return messages.tooShort;
|
|
19
19
|
if (validity.typeMismatch) return messages.typeMismatch;
|
|
20
20
|
if (validity.valueMissing) return messages.valueMissing;
|
|
21
|
+
return undefined;
|
|
21
22
|
};
|
|
22
23
|
|
|
23
|
-
export default (
|
|
24
|
+
export default (
|
|
25
|
+
customMessages: Messages = {},
|
|
26
|
+
defaultError?: string,
|
|
27
|
+
isError?: boolean,
|
|
28
|
+
) => {
|
|
24
29
|
const [error, setError] = useState<string | undefined>();
|
|
25
30
|
const validationEnabled = useRef(false);
|
|
26
31
|
|
|
32
|
+
useEffect(() => {
|
|
33
|
+
if (isError && defaultError) {
|
|
34
|
+
setError(defaultError);
|
|
35
|
+
} else {
|
|
36
|
+
setError(undefined);
|
|
37
|
+
}
|
|
38
|
+
}, [isError, defaultError]);
|
|
39
|
+
|
|
27
40
|
const onInvalid = (e: React.FormEvent<SupportedElement>) => {
|
|
28
41
|
validationEnabled.current = true;
|
|
42
|
+
|
|
29
43
|
const message = getCustomMessage(
|
|
30
44
|
(e.target as HTMLInputElement).validity,
|
|
31
45
|
customMessages,
|
|
@@ -34,7 +48,6 @@ export default (customMessages: Messages = {}) => {
|
|
|
34
48
|
};
|
|
35
49
|
|
|
36
50
|
const onChange = (e: React.ChangeEvent<SupportedElement>) => {
|
|
37
|
-
if (!validationEnabled.current) return;
|
|
38
51
|
const message = getCustomMessage(e.target.validity, customMessages);
|
|
39
52
|
setError(message || e.target?.validationMessage || undefined);
|
|
40
53
|
};
|