@instructure/ui-form-field 10.4.2-snapshot-10 → 10.4.2-snapshot-11
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/CHANGELOG.md +5 -2
- package/es/FormFieldGroup/index.js +2 -1
- package/es/FormFieldLayout/index.js +7 -2
- package/es/FormFieldLayout/props.js +2 -1
- package/es/FormFieldLayout/styles.js +3 -0
- package/es/FormFieldMessage/index.js +11 -2
- package/es/FormFieldMessage/styles.js +8 -0
- package/es/FormFieldMessage/theme.js +4 -2
- package/es/FormPropTypes.js +1 -1
- package/lib/FormFieldGroup/index.js +2 -1
- package/lib/FormFieldLayout/index.js +7 -2
- package/lib/FormFieldLayout/props.js +2 -1
- package/lib/FormFieldLayout/styles.js +3 -0
- package/lib/FormFieldMessage/index.js +11 -2
- package/lib/FormFieldMessage/styles.js +8 -0
- package/lib/FormFieldMessage/theme.js +4 -2
- package/lib/FormPropTypes.js +1 -1
- package/package.json +15 -15
- package/src/FormFieldGroup/index.tsx +1 -0
- package/src/FormFieldLayout/index.tsx +8 -2
- package/src/FormFieldLayout/props.ts +6 -3
- package/src/FormFieldLayout/styles.ts +3 -0
- package/src/FormFieldMessage/index.tsx +11 -2
- package/src/FormFieldMessage/props.ts +1 -1
- package/src/FormFieldMessage/styles.ts +6 -0
- package/src/FormFieldMessage/theme.ts +3 -2
- package/src/FormPropTypes.ts +7 -1
- package/tsconfig.build.tsbuildinfo +1 -1
- package/types/FormFieldGroup/index.d.ts.map +1 -1
- package/types/FormFieldLayout/index.d.ts.map +1 -1
- package/types/FormFieldLayout/props.d.ts +2 -1
- package/types/FormFieldLayout/props.d.ts.map +1 -1
- package/types/FormFieldLayout/styles.d.ts.map +1 -1
- package/types/FormFieldMessage/index.d.ts.map +1 -1
- package/types/FormFieldMessage/props.d.ts +1 -1
- package/types/FormFieldMessage/props.d.ts.map +1 -1
- package/types/FormFieldMessage/styles.d.ts.map +1 -1
- package/types/FormFieldMessage/theme.d.ts.map +1 -1
- package/types/FormPropTypes.d.ts +1 -1
- package/types/FormPropTypes.d.ts.map +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -3,9 +3,12 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
-
## [10.4.2-snapshot-
|
|
6
|
+
## [10.4.2-snapshot-11](https://github.com/instructure/instructure-ui/compare/v10.4.1...v10.4.2-snapshot-11) (2024-11-06)
|
|
7
7
|
|
|
8
|
-
|
|
8
|
+
|
|
9
|
+
### Features
|
|
10
|
+
|
|
11
|
+
* **many:** add new form field error msg style + add asterisk for required fields ([9b03683](https://github.com/instructure/instructure-ui/commit/9b03683dadeef4c5deae2c60bea10686f143ff5d))
|
|
9
12
|
|
|
10
13
|
|
|
11
14
|
|
|
@@ -103,7 +103,8 @@ let FormFieldGroup = (_dec = withStyle(generateStyle, generateComponentTheme), _
|
|
|
103
103
|
label: props.description,
|
|
104
104
|
"aria-disabled": props.disabled ? 'true' : void 0,
|
|
105
105
|
"aria-invalid": this.invalid ? 'true' : void 0,
|
|
106
|
-
elementRef: this.handleRef
|
|
106
|
+
elementRef: this.handleRef,
|
|
107
|
+
isGroup: true
|
|
107
108
|
}), this.renderFields());
|
|
108
109
|
}
|
|
109
110
|
}, _FormFieldGroup.displayName = "FormFieldGroup", _FormFieldGroup.componentId = 'FormFieldGroup', _FormFieldGroup.propTypes = propTypes, _FormFieldGroup.allowedProps = allowedProps, _FormFieldGroup.defaultProps = {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import _objectWithoutProperties from "@babel/runtime/helpers/esm/objectWithoutProperties";
|
|
2
|
-
const _excluded = ["makeStyles", "styles"];
|
|
2
|
+
const _excluded = ["makeStyles", "styles", "messages", "isGroup"];
|
|
3
3
|
var _dec, _dec2, _class, _FormFieldLayout;
|
|
4
4
|
/*
|
|
5
5
|
* The MIT License (MIT)
|
|
@@ -123,10 +123,13 @@ let FormFieldLayout = (_dec = withDeterministicId(), _dec2 = withStyle(generateS
|
|
|
123
123
|
const _this$props3 = this.props,
|
|
124
124
|
makeStyles = _this$props3.makeStyles,
|
|
125
125
|
styles = _this$props3.styles,
|
|
126
|
+
messages = _this$props3.messages,
|
|
127
|
+
isGroup = _this$props3.isGroup,
|
|
126
128
|
props = _objectWithoutProperties(_this$props3, _excluded);
|
|
127
129
|
const width = props.width,
|
|
128
130
|
layout = props.layout,
|
|
129
131
|
children = props.children;
|
|
132
|
+
const hasNewErrorMsg = !!(messages !== null && messages !== void 0 && messages.find(m => m.type === 'newError')) && isGroup;
|
|
130
133
|
return jsx(ElementType, Object.assign({}, omitProps(props, [...FormFieldLayout.allowedProps, ...Grid.allowedProps]), {
|
|
131
134
|
css: styles === null || styles === void 0 ? void 0 : styles.formFieldLayout,
|
|
132
135
|
style: {
|
|
@@ -141,7 +144,9 @@ let FormFieldLayout = (_dec = withDeterministicId(), _dec2 = withStyle(generateS
|
|
|
141
144
|
}, pickProps(props, Grid.allowedProps)), jsx(Grid.Row, null, this.renderLabel(), jsx(Grid.Col, {
|
|
142
145
|
width: this.inlineContainerAndLabel ? 'auto' : void 0,
|
|
143
146
|
elementRef: this.handleInputContainerRef
|
|
144
|
-
},
|
|
147
|
+
}, hasNewErrorMsg && jsx("div", {
|
|
148
|
+
css: styles === null || styles === void 0 ? void 0 : styles.groupErrorMessage
|
|
149
|
+
}, this.renderVisibleMessages()), children)), !hasNewErrorMsg && this.renderVisibleMessages()));
|
|
145
150
|
}
|
|
146
151
|
}, _FormFieldLayout.displayName = "FormFieldLayout", _FormFieldLayout.componentId = 'FormFieldLayout', _FormFieldLayout.propTypes = propTypes, _FormFieldLayout.allowedProps = allowedProps, _FormFieldLayout.defaultProps = {
|
|
147
152
|
inline: false,
|
|
@@ -37,7 +37,8 @@ const propTypes = {
|
|
|
37
37
|
vAlign: PropTypes.oneOf(['top', 'middle', 'bottom']),
|
|
38
38
|
width: PropTypes.string,
|
|
39
39
|
inputContainerRef: PropTypes.func,
|
|
40
|
-
elementRef: PropTypes.func
|
|
40
|
+
elementRef: PropTypes.func,
|
|
41
|
+
isGroup: PropTypes.bool
|
|
41
42
|
};
|
|
42
43
|
const allowedProps = ['label', 'id', 'as', 'messages', 'messagesId', 'children', 'inline', 'layout', 'labelAlign', 'width', 'inputContainerRef', 'elementRef'
|
|
43
44
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
var _dec, _class, _FormFieldMessage;
|
|
1
|
+
var _dec, _class, _FormFieldMessage, _IconWarningSolid;
|
|
2
2
|
/*
|
|
3
3
|
* The MIT License (MIT)
|
|
4
4
|
*
|
|
@@ -26,6 +26,7 @@ var _dec, _class, _FormFieldMessage;
|
|
|
26
26
|
/** @jsx jsx */
|
|
27
27
|
import { Component } from 'react';
|
|
28
28
|
import { ScreenReaderContent } from '@instructure/ui-a11y-content';
|
|
29
|
+
import { IconWarningSolid } from '@instructure/ui-icons';
|
|
29
30
|
import { withStyle, jsx } from '@instructure/emotion';
|
|
30
31
|
import generateStyle from './styles';
|
|
31
32
|
import generateComponentTheme from './theme';
|
|
@@ -66,9 +67,17 @@ let FormFieldMessage = (_dec = withStyle(generateStyle, generateComponentTheme),
|
|
|
66
67
|
children = _this$props3.children,
|
|
67
68
|
styles = _this$props3.styles;
|
|
68
69
|
return this.props.variant !== 'screenreader-only' ? jsx("span", {
|
|
70
|
+
css: {
|
|
71
|
+
display: 'flex'
|
|
72
|
+
}
|
|
73
|
+
}, this.props.variant === 'newError' && jsx("span", {
|
|
74
|
+
css: styles === null || styles === void 0 ? void 0 : styles.errorIcon
|
|
75
|
+
}, _IconWarningSolid || (_IconWarningSolid = jsx(IconWarningSolid, {
|
|
76
|
+
color: "error"
|
|
77
|
+
}))), jsx("span", {
|
|
69
78
|
css: styles === null || styles === void 0 ? void 0 : styles.formFieldMessage,
|
|
70
79
|
ref: this.handleRef
|
|
71
|
-
}, children) : jsx(ScreenReaderContent, {
|
|
80
|
+
}, children)) : jsx(ScreenReaderContent, {
|
|
72
81
|
elementRef: this.handleRef
|
|
73
82
|
}, children);
|
|
74
83
|
}
|
|
@@ -41,12 +41,20 @@ const generateStyle = (componentTheme, props) => {
|
|
|
41
41
|
error: {
|
|
42
42
|
color: componentTheme.colorError
|
|
43
43
|
},
|
|
44
|
+
newError: {
|
|
45
|
+
color: componentTheme.colorError
|
|
46
|
+
},
|
|
44
47
|
success: {
|
|
45
48
|
color: componentTheme.colorSuccess
|
|
46
49
|
},
|
|
47
50
|
'screenreader-only': {}
|
|
48
51
|
};
|
|
49
52
|
return {
|
|
53
|
+
errorIcon: {
|
|
54
|
+
fontSize: componentTheme.fontSize,
|
|
55
|
+
marginRight: componentTheme.errorIconMarginRight,
|
|
56
|
+
lineHeight: 1.25
|
|
57
|
+
},
|
|
50
58
|
formFieldMessage: {
|
|
51
59
|
label: 'formFieldMessage',
|
|
52
60
|
fontFamily: componentTheme.fontFamily,
|
|
@@ -31,7 +31,8 @@ const generateComponentTheme = theme => {
|
|
|
31
31
|
var _colors$contrasts, _colors$contrasts2, _colors$contrasts3;
|
|
32
32
|
const colors = theme.colors,
|
|
33
33
|
typography = theme.typography,
|
|
34
|
-
themeName = theme.key
|
|
34
|
+
themeName = theme.key,
|
|
35
|
+
spacing = theme.spacing;
|
|
35
36
|
const themeSpecificStyle = {
|
|
36
37
|
canvas: {
|
|
37
38
|
colorHint: theme['ic-brand-font-color-dark']
|
|
@@ -44,7 +45,8 @@ const generateComponentTheme = theme => {
|
|
|
44
45
|
fontFamily: typography === null || typography === void 0 ? void 0 : typography.fontFamily,
|
|
45
46
|
fontWeight: typography === null || typography === void 0 ? void 0 : typography.fontWeightNormal,
|
|
46
47
|
fontSize: typography === null || typography === void 0 ? void 0 : typography.fontSizeSmall,
|
|
47
|
-
lineHeight: typography === null || typography === void 0 ? void 0 : typography.lineHeight
|
|
48
|
+
lineHeight: typography === null || typography === void 0 ? void 0 : typography.lineHeight,
|
|
49
|
+
errorIconMarginRight: spacing.xxSmall
|
|
48
50
|
};
|
|
49
51
|
return {
|
|
50
52
|
...componentVariables,
|
package/es/FormPropTypes.js
CHANGED
|
@@ -23,7 +23,7 @@
|
|
|
23
23
|
*/
|
|
24
24
|
|
|
25
25
|
import PropTypes from 'prop-types';
|
|
26
|
-
const formMessageTypePropType = PropTypes.oneOf(['error', 'hint', 'success', 'screenreader-only']);
|
|
26
|
+
const formMessageTypePropType = PropTypes.oneOf(['error', 'newError', 'hint', 'success', 'screenreader-only']);
|
|
27
27
|
const formMessageChildPropType = PropTypes.node;
|
|
28
28
|
/**
|
|
29
29
|
* ---
|
|
@@ -110,7 +110,8 @@ let FormFieldGroup = exports.FormFieldGroup = (_dec = (0, _emotion.withStyle)(_s
|
|
|
110
110
|
label: props.description,
|
|
111
111
|
"aria-disabled": props.disabled ? 'true' : void 0,
|
|
112
112
|
"aria-invalid": this.invalid ? 'true' : void 0,
|
|
113
|
-
elementRef: this.handleRef
|
|
113
|
+
elementRef: this.handleRef,
|
|
114
|
+
isGroup: true
|
|
114
115
|
}), this.renderFields());
|
|
115
116
|
}
|
|
116
117
|
}, _FormFieldGroup.displayName = "FormFieldGroup", _FormFieldGroup.componentId = 'FormFieldGroup', _FormFieldGroup.propTypes = _props.propTypes, _FormFieldGroup.allowedProps = _props.allowedProps, _FormFieldGroup.defaultProps = {
|
|
@@ -20,7 +20,7 @@ var _FormFieldLabel = require("../FormFieldLabel");
|
|
|
20
20
|
var _FormFieldMessages = require("../FormFieldMessages");
|
|
21
21
|
var _styles = _interopRequireDefault(require("./styles"));
|
|
22
22
|
var _props = require("./props");
|
|
23
|
-
const _excluded = ["makeStyles", "styles"];
|
|
23
|
+
const _excluded = ["makeStyles", "styles", "messages", "isGroup"];
|
|
24
24
|
var _dec, _dec2, _class, _FormFieldLayout;
|
|
25
25
|
/*
|
|
26
26
|
* The MIT License (MIT)
|
|
@@ -132,10 +132,13 @@ let FormFieldLayout = exports.FormFieldLayout = (_dec = (0, _withDeterministicId
|
|
|
132
132
|
const _this$props3 = this.props,
|
|
133
133
|
makeStyles = _this$props3.makeStyles,
|
|
134
134
|
styles = _this$props3.styles,
|
|
135
|
+
messages = _this$props3.messages,
|
|
136
|
+
isGroup = _this$props3.isGroup,
|
|
135
137
|
props = (0, _objectWithoutProperties2.default)(_this$props3, _excluded);
|
|
136
138
|
const width = props.width,
|
|
137
139
|
layout = props.layout,
|
|
138
140
|
children = props.children;
|
|
141
|
+
const hasNewErrorMsg = !!(messages !== null && messages !== void 0 && messages.find(m => m.type === 'newError')) && isGroup;
|
|
139
142
|
return (0, _emotion.jsx)(ElementType, Object.assign({}, (0, _omitProps.omitProps)(props, [...FormFieldLayout.allowedProps, ..._Grid.Grid.allowedProps]), {
|
|
140
143
|
css: styles === null || styles === void 0 ? void 0 : styles.formFieldLayout,
|
|
141
144
|
style: {
|
|
@@ -150,7 +153,9 @@ let FormFieldLayout = exports.FormFieldLayout = (_dec = (0, _withDeterministicId
|
|
|
150
153
|
}, (0, _pickProps.pickProps)(props, _Grid.Grid.allowedProps)), (0, _emotion.jsx)(_Grid.Grid.Row, null, this.renderLabel(), (0, _emotion.jsx)(_Grid.Grid.Col, {
|
|
151
154
|
width: this.inlineContainerAndLabel ? 'auto' : void 0,
|
|
152
155
|
elementRef: this.handleInputContainerRef
|
|
153
|
-
},
|
|
156
|
+
}, hasNewErrorMsg && (0, _emotion.jsx)("div", {
|
|
157
|
+
css: styles === null || styles === void 0 ? void 0 : styles.groupErrorMessage
|
|
158
|
+
}, this.renderVisibleMessages()), children)), !hasNewErrorMsg && this.renderVisibleMessages()));
|
|
154
159
|
}
|
|
155
160
|
}, _FormFieldLayout.displayName = "FormFieldLayout", _FormFieldLayout.componentId = 'FormFieldLayout', _FormFieldLayout.propTypes = _props.propTypes, _FormFieldLayout.allowedProps = _props.allowedProps, _FormFieldLayout.defaultProps = {
|
|
156
161
|
inline: false,
|
|
@@ -44,7 +44,8 @@ const propTypes = exports.propTypes = {
|
|
|
44
44
|
vAlign: _propTypes.default.oneOf(['top', 'middle', 'bottom']),
|
|
45
45
|
width: _propTypes.default.string,
|
|
46
46
|
inputContainerRef: _propTypes.default.func,
|
|
47
|
-
elementRef: _propTypes.default.func
|
|
47
|
+
elementRef: _propTypes.default.func,
|
|
48
|
+
isGroup: _propTypes.default.bool
|
|
48
49
|
};
|
|
49
50
|
const allowedProps = exports.allowedProps = ['label', 'id', 'as', 'messages', 'messagesId', 'children', 'inline', 'layout', 'labelAlign', 'width', 'inputContainerRef', 'elementRef'
|
|
50
51
|
|
|
@@ -7,11 +7,12 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
7
7
|
exports.default = exports.FormFieldMessage = void 0;
|
|
8
8
|
var _react = require("react");
|
|
9
9
|
var _ScreenReaderContent = require("@instructure/ui-a11y-content/lib/ScreenReaderContent");
|
|
10
|
+
var _IconWarningSolid2 = require("@instructure/ui-icons/lib/IconWarningSolid.js");
|
|
10
11
|
var _emotion = require("@instructure/emotion");
|
|
11
12
|
var _styles = _interopRequireDefault(require("./styles"));
|
|
12
13
|
var _theme = _interopRequireDefault(require("./theme"));
|
|
13
14
|
var _props = require("./props");
|
|
14
|
-
var _dec, _class, _FormFieldMessage;
|
|
15
|
+
var _dec, _class, _FormFieldMessage, _IconWarningSolid;
|
|
15
16
|
/*
|
|
16
17
|
* The MIT License (MIT)
|
|
17
18
|
*
|
|
@@ -72,9 +73,17 @@ let FormFieldMessage = exports.FormFieldMessage = (_dec = (0, _emotion.withStyle
|
|
|
72
73
|
children = _this$props3.children,
|
|
73
74
|
styles = _this$props3.styles;
|
|
74
75
|
return this.props.variant !== 'screenreader-only' ? (0, _emotion.jsx)("span", {
|
|
76
|
+
css: {
|
|
77
|
+
display: 'flex'
|
|
78
|
+
}
|
|
79
|
+
}, this.props.variant === 'newError' && (0, _emotion.jsx)("span", {
|
|
80
|
+
css: styles === null || styles === void 0 ? void 0 : styles.errorIcon
|
|
81
|
+
}, _IconWarningSolid || (_IconWarningSolid = (0, _emotion.jsx)(_IconWarningSolid2.IconWarningSolid, {
|
|
82
|
+
color: "error"
|
|
83
|
+
}))), (0, _emotion.jsx)("span", {
|
|
75
84
|
css: styles === null || styles === void 0 ? void 0 : styles.formFieldMessage,
|
|
76
85
|
ref: this.handleRef
|
|
77
|
-
}, children) : (0, _emotion.jsx)(_ScreenReaderContent.ScreenReaderContent, {
|
|
86
|
+
}, children)) : (0, _emotion.jsx)(_ScreenReaderContent.ScreenReaderContent, {
|
|
78
87
|
elementRef: this.handleRef
|
|
79
88
|
}, children);
|
|
80
89
|
}
|
|
@@ -47,12 +47,20 @@ const generateStyle = (componentTheme, props) => {
|
|
|
47
47
|
error: {
|
|
48
48
|
color: componentTheme.colorError
|
|
49
49
|
},
|
|
50
|
+
newError: {
|
|
51
|
+
color: componentTheme.colorError
|
|
52
|
+
},
|
|
50
53
|
success: {
|
|
51
54
|
color: componentTheme.colorSuccess
|
|
52
55
|
},
|
|
53
56
|
'screenreader-only': {}
|
|
54
57
|
};
|
|
55
58
|
return {
|
|
59
|
+
errorIcon: {
|
|
60
|
+
fontSize: componentTheme.fontSize,
|
|
61
|
+
marginRight: componentTheme.errorIconMarginRight,
|
|
62
|
+
lineHeight: 1.25
|
|
63
|
+
},
|
|
56
64
|
formFieldMessage: {
|
|
57
65
|
label: 'formFieldMessage',
|
|
58
66
|
fontFamily: componentTheme.fontFamily,
|
|
@@ -37,7 +37,8 @@ const generateComponentTheme = theme => {
|
|
|
37
37
|
var _colors$contrasts, _colors$contrasts2, _colors$contrasts3;
|
|
38
38
|
const colors = theme.colors,
|
|
39
39
|
typography = theme.typography,
|
|
40
|
-
themeName = theme.key
|
|
40
|
+
themeName = theme.key,
|
|
41
|
+
spacing = theme.spacing;
|
|
41
42
|
const themeSpecificStyle = {
|
|
42
43
|
canvas: {
|
|
43
44
|
colorHint: theme['ic-brand-font-color-dark']
|
|
@@ -50,7 +51,8 @@ const generateComponentTheme = theme => {
|
|
|
50
51
|
fontFamily: typography === null || typography === void 0 ? void 0 : typography.fontFamily,
|
|
51
52
|
fontWeight: typography === null || typography === void 0 ? void 0 : typography.fontWeightNormal,
|
|
52
53
|
fontSize: typography === null || typography === void 0 ? void 0 : typography.fontSizeSmall,
|
|
53
|
-
lineHeight: typography === null || typography === void 0 ? void 0 : typography.lineHeight
|
|
54
|
+
lineHeight: typography === null || typography === void 0 ? void 0 : typography.lineHeight,
|
|
55
|
+
errorIconMarginRight: spacing.xxSmall
|
|
54
56
|
};
|
|
55
57
|
return {
|
|
56
58
|
...componentVariables,
|
package/lib/FormPropTypes.js
CHANGED
|
@@ -30,7 +30,7 @@ var _propTypes = _interopRequireDefault(require("prop-types"));
|
|
|
30
30
|
* SOFTWARE.
|
|
31
31
|
*/
|
|
32
32
|
|
|
33
|
-
const formMessageTypePropType = exports.formMessageTypePropType = _propTypes.default.oneOf(['error', 'hint', 'success', 'screenreader-only']);
|
|
33
|
+
const formMessageTypePropType = exports.formMessageTypePropType = _propTypes.default.oneOf(['error', 'newError', 'hint', 'success', 'screenreader-only']);
|
|
34
34
|
const formMessageChildPropType = exports.formMessageChildPropType = _propTypes.default.node;
|
|
35
35
|
/**
|
|
36
36
|
* ---
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@instructure/ui-form-field",
|
|
3
|
-
"version": "10.4.2-snapshot-
|
|
3
|
+
"version": "10.4.2-snapshot-11",
|
|
4
4
|
"description": "Form layout components.",
|
|
5
5
|
"author": "Instructure, Inc. Engineering and Product Design",
|
|
6
6
|
"module": "./es/index.js",
|
|
@@ -23,26 +23,26 @@
|
|
|
23
23
|
},
|
|
24
24
|
"license": "MIT",
|
|
25
25
|
"devDependencies": {
|
|
26
|
-
"@instructure/ui-axe-check": "10.4.2-snapshot-
|
|
27
|
-
"@instructure/ui-babel-preset": "10.4.2-snapshot-
|
|
28
|
-
"@instructure/ui-test-utils": "10.4.2-snapshot-
|
|
29
|
-
"@instructure/ui-themes": "10.4.2-snapshot-
|
|
26
|
+
"@instructure/ui-axe-check": "10.4.2-snapshot-11",
|
|
27
|
+
"@instructure/ui-babel-preset": "10.4.2-snapshot-11",
|
|
28
|
+
"@instructure/ui-test-utils": "10.4.2-snapshot-11",
|
|
29
|
+
"@instructure/ui-themes": "10.4.2-snapshot-11",
|
|
30
30
|
"@testing-library/jest-dom": "^6.4.6",
|
|
31
31
|
"@testing-library/react": "^16.0.1",
|
|
32
32
|
"vitest": "^2.1.1"
|
|
33
33
|
},
|
|
34
34
|
"dependencies": {
|
|
35
35
|
"@babel/runtime": "^7.25.6",
|
|
36
|
-
"@instructure/console": "10.4.2-snapshot-
|
|
37
|
-
"@instructure/emotion": "10.4.2-snapshot-
|
|
38
|
-
"@instructure/shared-types": "10.4.2-snapshot-
|
|
39
|
-
"@instructure/ui-a11y-content": "10.4.2-snapshot-
|
|
40
|
-
"@instructure/ui-a11y-utils": "10.4.2-snapshot-
|
|
41
|
-
"@instructure/ui-grid": "10.4.2-snapshot-
|
|
42
|
-
"@instructure/ui-icons": "10.4.2-snapshot-
|
|
43
|
-
"@instructure/ui-react-utils": "10.4.2-snapshot-
|
|
44
|
-
"@instructure/ui-utils": "10.4.2-snapshot-
|
|
45
|
-
"@instructure/uid": "10.4.2-snapshot-
|
|
36
|
+
"@instructure/console": "10.4.2-snapshot-11",
|
|
37
|
+
"@instructure/emotion": "10.4.2-snapshot-11",
|
|
38
|
+
"@instructure/shared-types": "10.4.2-snapshot-11",
|
|
39
|
+
"@instructure/ui-a11y-content": "10.4.2-snapshot-11",
|
|
40
|
+
"@instructure/ui-a11y-utils": "10.4.2-snapshot-11",
|
|
41
|
+
"@instructure/ui-grid": "10.4.2-snapshot-11",
|
|
42
|
+
"@instructure/ui-icons": "10.4.2-snapshot-11",
|
|
43
|
+
"@instructure/ui-react-utils": "10.4.2-snapshot-11",
|
|
44
|
+
"@instructure/ui-utils": "10.4.2-snapshot-11",
|
|
45
|
+
"@instructure/uid": "10.4.2-snapshot-11",
|
|
46
46
|
"prop-types": "^15.8.1"
|
|
47
47
|
},
|
|
48
48
|
"peerDependencies": {
|
|
@@ -145,6 +145,7 @@ class FormFieldGroup extends Component<FormFieldGroupProps> {
|
|
|
145
145
|
aria-disabled={props.disabled ? 'true' : undefined}
|
|
146
146
|
aria-invalid={this.invalid ? 'true' : undefined}
|
|
147
147
|
elementRef={this.handleRef}
|
|
148
|
+
isGroup
|
|
148
149
|
>
|
|
149
150
|
{this.renderFields()}
|
|
150
151
|
</FormFieldLayout>
|
|
@@ -179,9 +179,12 @@ class FormFieldLayout extends Component<FormFieldLayoutProps> {
|
|
|
179
179
|
// any cast is needed to prevent Expression produces a union type that is too complex to represent errors
|
|
180
180
|
const ElementType = this.elementType as any
|
|
181
181
|
|
|
182
|
-
const { makeStyles, styles, ...props } = this.props
|
|
182
|
+
const { makeStyles, styles, messages, isGroup, ...props } = this.props
|
|
183
183
|
|
|
184
184
|
const { width, layout, children } = props
|
|
185
|
+
|
|
186
|
+
const hasNewErrorMsg =
|
|
187
|
+
!!messages?.find((m) => m.type === 'newError') && isGroup
|
|
185
188
|
return (
|
|
186
189
|
<ElementType
|
|
187
190
|
{...omitProps(props, [
|
|
@@ -208,10 +211,13 @@ class FormFieldLayout extends Component<FormFieldLayoutProps> {
|
|
|
208
211
|
width={this.inlineContainerAndLabel ? 'auto' : undefined}
|
|
209
212
|
elementRef={this.handleInputContainerRef}
|
|
210
213
|
>
|
|
214
|
+
{hasNewErrorMsg && (
|
|
215
|
+
<div css={styles?.groupErrorMessage}>{this.renderVisibleMessages()}</div>
|
|
216
|
+
)}
|
|
211
217
|
{children}
|
|
212
218
|
</Grid.Col>
|
|
213
219
|
</Grid.Row>
|
|
214
|
-
{this.renderVisibleMessages()}
|
|
220
|
+
{!hasNewErrorMsg && this.renderVisibleMessages()}
|
|
215
221
|
</Grid>
|
|
216
222
|
</ElementType>
|
|
217
223
|
)
|
|
@@ -67,6 +67,7 @@ type FormFieldLayoutOwnProps = {
|
|
|
67
67
|
* provides a reference to the underlying html root element
|
|
68
68
|
*/
|
|
69
69
|
elementRef?: (element: Element | null) => void
|
|
70
|
+
isGroup?: boolean
|
|
70
71
|
}
|
|
71
72
|
|
|
72
73
|
type PropKeys = keyof FormFieldLayoutOwnProps
|
|
@@ -75,9 +76,10 @@ type AllowedPropKeys = Readonly<Array<PropKeys>>
|
|
|
75
76
|
|
|
76
77
|
type FormFieldLayoutProps = FormFieldLayoutOwnProps &
|
|
77
78
|
WithStyleProps<null, FormFieldLayoutStyle> &
|
|
78
|
-
OtherHTMLAttributes<FormFieldLayoutOwnProps> &
|
|
79
|
+
OtherHTMLAttributes<FormFieldLayoutOwnProps> &
|
|
80
|
+
WithDeterministicIdProps
|
|
79
81
|
|
|
80
|
-
type FormFieldLayoutStyle = ComponentStyle<'formFieldLayout'>
|
|
82
|
+
type FormFieldLayoutStyle = ComponentStyle<'formFieldLayout' | 'groupErrorMessage'>
|
|
81
83
|
|
|
82
84
|
const propTypes: PropValidators<PropKeys> = {
|
|
83
85
|
label: PropTypes.node.isRequired,
|
|
@@ -92,7 +94,8 @@ const propTypes: PropValidators<PropKeys> = {
|
|
|
92
94
|
vAlign: PropTypes.oneOf(['top', 'middle', 'bottom']),
|
|
93
95
|
width: PropTypes.string,
|
|
94
96
|
inputContainerRef: PropTypes.func,
|
|
95
|
-
elementRef: PropTypes.func
|
|
97
|
+
elementRef: PropTypes.func,
|
|
98
|
+
isGroup: PropTypes.bool
|
|
96
99
|
}
|
|
97
100
|
|
|
98
101
|
const allowedProps: AllowedPropKeys = [
|
|
@@ -27,6 +27,8 @@ import { Component } from 'react'
|
|
|
27
27
|
|
|
28
28
|
import { ScreenReaderContent } from '@instructure/ui-a11y-content'
|
|
29
29
|
|
|
30
|
+
import { IconWarningSolid } from '@instructure/ui-icons'
|
|
31
|
+
|
|
30
32
|
import { withStyle, jsx } from '@instructure/emotion'
|
|
31
33
|
|
|
32
34
|
import generateStyle from './styles'
|
|
@@ -78,8 +80,15 @@ class FormFieldMessage extends Component<FormFieldMessageProps> {
|
|
|
78
80
|
const { children, styles } = this.props
|
|
79
81
|
|
|
80
82
|
return this.props.variant !== 'screenreader-only' ? (
|
|
81
|
-
<span css={
|
|
82
|
-
{
|
|
83
|
+
<span css={{ display: 'flex' }}>
|
|
84
|
+
{this.props.variant === 'newError' && (
|
|
85
|
+
<span css={styles?.errorIcon}>
|
|
86
|
+
<IconWarningSolid color="error" />
|
|
87
|
+
</span>
|
|
88
|
+
)}
|
|
89
|
+
<span css={styles?.formFieldMessage} ref={this.handleRef}>
|
|
90
|
+
{children}
|
|
91
|
+
</span>
|
|
83
92
|
</span>
|
|
84
93
|
) : (
|
|
85
94
|
<ScreenReaderContent elementRef={this.handleRef}>
|
|
@@ -46,7 +46,7 @@ type AllowedPropKeys = Readonly<Array<PropKeys>>
|
|
|
46
46
|
type FormFieldMessageProps = FormFieldMessageOwnProps &
|
|
47
47
|
WithStyleProps<FormFieldMessageTheme, FormFieldMessageStyle>
|
|
48
48
|
|
|
49
|
-
type FormFieldMessageStyle = ComponentStyle<'formFieldMessage'>
|
|
49
|
+
type FormFieldMessageStyle = ComponentStyle<'formFieldMessage' | 'errorIcon'>
|
|
50
50
|
|
|
51
51
|
const propTypes: PropValidators<PropKeys> = {
|
|
52
52
|
variant: formMessageTypePropType,
|
|
@@ -45,11 +45,17 @@ const generateStyle = (
|
|
|
45
45
|
const variants: Record<FormMessageType, { color?: string }> = {
|
|
46
46
|
hint: { color: componentTheme.colorHint },
|
|
47
47
|
error: { color: componentTheme.colorError },
|
|
48
|
+
newError: { color: componentTheme.colorError },
|
|
48
49
|
success: { color: componentTheme.colorSuccess },
|
|
49
50
|
'screenreader-only': {}
|
|
50
51
|
}
|
|
51
52
|
|
|
52
53
|
return {
|
|
54
|
+
errorIcon: {
|
|
55
|
+
fontSize: componentTheme.fontSize,
|
|
56
|
+
marginRight: componentTheme.errorIconMarginRight,
|
|
57
|
+
lineHeight: 1.25,
|
|
58
|
+
},
|
|
53
59
|
formFieldMessage: {
|
|
54
60
|
label: 'formFieldMessage',
|
|
55
61
|
fontFamily: componentTheme.fontFamily,
|
|
@@ -31,7 +31,7 @@ import { FormFieldMessageTheme } from '@instructure/shared-types'
|
|
|
31
31
|
* @return {Object} The final theme object with the overrides and component variables
|
|
32
32
|
*/
|
|
33
33
|
const generateComponentTheme = (theme: Theme): FormFieldMessageTheme => {
|
|
34
|
-
const { colors, typography, key: themeName } = theme
|
|
34
|
+
const { colors, typography, key: themeName, spacing } = theme
|
|
35
35
|
|
|
36
36
|
const themeSpecificStyle: ThemeSpecificStyle<FormFieldMessageTheme> = {
|
|
37
37
|
canvas: {
|
|
@@ -47,7 +47,8 @@ const generateComponentTheme = (theme: Theme): FormFieldMessageTheme => {
|
|
|
47
47
|
fontFamily: typography?.fontFamily,
|
|
48
48
|
fontWeight: typography?.fontWeightNormal,
|
|
49
49
|
fontSize: typography?.fontSizeSmall,
|
|
50
|
-
lineHeight: typography?.lineHeight
|
|
50
|
+
lineHeight: typography?.lineHeight,
|
|
51
|
+
errorIconMarginRight: spacing.xxSmall
|
|
51
52
|
}
|
|
52
53
|
|
|
53
54
|
return {
|
package/src/FormPropTypes.ts
CHANGED
|
@@ -27,13 +27,19 @@ import PropTypes from 'prop-types'
|
|
|
27
27
|
|
|
28
28
|
const formMessageTypePropType = PropTypes.oneOf([
|
|
29
29
|
'error',
|
|
30
|
+
'newError',
|
|
30
31
|
'hint',
|
|
31
32
|
'success',
|
|
32
33
|
'screenreader-only'
|
|
33
34
|
])
|
|
34
35
|
const formMessageChildPropType = PropTypes.node
|
|
35
36
|
|
|
36
|
-
type FormMessageType =
|
|
37
|
+
type FormMessageType =
|
|
38
|
+
| 'newError'
|
|
39
|
+
| 'error'
|
|
40
|
+
| 'hint'
|
|
41
|
+
| 'success'
|
|
42
|
+
| 'screenreader-only'
|
|
37
43
|
type FormMessageChild = React.ReactNode
|
|
38
44
|
|
|
39
45
|
/**
|