@hzab/form-render-mobile 0.5.1 → 0.5.2
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 +4 -0
- package/lib/index.js +1 -1
- package/package.json +1 -1
- package/src/components/FormItem/index.less +182 -22
- package/src/components/FormItem/index.tsx +210 -104
- package/src/components/index.ts +3 -2
package/package.json
CHANGED
|
@@ -1,6 +1,9 @@
|
|
|
1
1
|
.formily-form-item {
|
|
2
2
|
display: flex;
|
|
3
3
|
margin-bottom: 2vw;
|
|
4
|
+
.adm-list-item-content {
|
|
5
|
+
width: 100%;
|
|
6
|
+
}
|
|
4
7
|
// 栅格布局重置样式
|
|
5
8
|
&.adm-grid {
|
|
6
9
|
display: grid;
|
|
@@ -8,29 +11,13 @@
|
|
|
8
11
|
&:last-child {
|
|
9
12
|
margin-bottom: unset;
|
|
10
13
|
}
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
justify-content: flex-start;
|
|
14
|
-
align-items: center;
|
|
15
|
-
.form-item-label-text {
|
|
16
|
-
white-space: pre;
|
|
17
|
-
overflow: hidden;
|
|
18
|
-
text-overflow: ellipsis;
|
|
19
|
-
}
|
|
20
|
-
&.item-label-wrap {
|
|
21
|
-
.form-item-label-text {
|
|
22
|
-
white-space: pre-line;
|
|
23
|
-
word-break: break-all;
|
|
24
|
-
overflow: unset;
|
|
25
|
-
text-overflow: unset;
|
|
26
|
-
}
|
|
27
|
-
}
|
|
28
|
-
&.label-align-right {
|
|
14
|
+
&.adm-formily-item-label-align-right {
|
|
15
|
+
.adm-formily-item-label {
|
|
29
16
|
justify-content: flex-end;
|
|
30
17
|
text-align: right;
|
|
31
18
|
}
|
|
32
19
|
}
|
|
33
|
-
.
|
|
20
|
+
.adm-formily-item-control {
|
|
34
21
|
flex: 1;
|
|
35
22
|
color: #808080;
|
|
36
23
|
}
|
|
@@ -43,10 +30,183 @@
|
|
|
43
30
|
}
|
|
44
31
|
}
|
|
45
32
|
&.layout-between {
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
33
|
+
.adm-list-item-content {
|
|
34
|
+
width: 100%;
|
|
35
|
+
justify-content: space-between;
|
|
49
36
|
text-align: right;
|
|
50
37
|
}
|
|
51
38
|
}
|
|
39
|
+
|
|
40
|
+
// 内容栅格样式
|
|
41
|
+
&.wrapper-col-24 .adm-list-item-content-main {
|
|
42
|
+
-webkit-box-flex: 0;
|
|
43
|
+
-ms-flex: 0 0 100%;
|
|
44
|
+
flex: 0 0 100%;
|
|
45
|
+
max-width: 100%;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
&.wrapper-col-23 .adm-list-item-content-main {
|
|
49
|
+
-webkit-box-flex: 0;
|
|
50
|
+
-ms-flex: 0 0 95.83333333%;
|
|
51
|
+
flex: 0 0 95.83333333%;
|
|
52
|
+
max-width: 95.83333333%;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
&.wrapper-col-22 .adm-list-item-content-main {
|
|
56
|
+
-webkit-box-flex: 0;
|
|
57
|
+
-ms-flex: 0 0 91.66666667%;
|
|
58
|
+
flex: 0 0 91.66666667%;
|
|
59
|
+
max-width: 91.66666667%;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
&.wrapper-col-21 .adm-list-item-content-main {
|
|
63
|
+
-webkit-box-flex: 0;
|
|
64
|
+
-ms-flex: 0 0 87.5%;
|
|
65
|
+
flex: 0 0 87.5%;
|
|
66
|
+
max-width: 87.5%;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
&.wrapper-col-20 .adm-list-item-content-main {
|
|
70
|
+
-webkit-box-flex: 0;
|
|
71
|
+
-ms-flex: 0 0 83.33333333%;
|
|
72
|
+
flex: 0 0 83.33333333%;
|
|
73
|
+
max-width: 83.33333333%;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
&.wrapper-col-19 .adm-list-item-content-main {
|
|
77
|
+
-webkit-box-flex: 0;
|
|
78
|
+
-ms-flex: 0 0 79.16666667%;
|
|
79
|
+
flex: 0 0 79.16666667%;
|
|
80
|
+
max-width: 79.16666667%;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
&.wrapper-col-18 .adm-list-item-content-main {
|
|
84
|
+
-webkit-box-flex: 0;
|
|
85
|
+
-ms-flex: 0 0 75%;
|
|
86
|
+
flex: 0 0 75%;
|
|
87
|
+
max-width: 75%;
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
&.wrapper-col-17 .adm-list-item-content-main {
|
|
91
|
+
-webkit-box-flex: 0;
|
|
92
|
+
-ms-flex: 0 0 70.83333333%;
|
|
93
|
+
flex: 0 0 70.83333333%;
|
|
94
|
+
max-width: 70.83333333%;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
&.wrapper-col-16 .adm-list-item-content-main {
|
|
98
|
+
-webkit-box-flex: 0;
|
|
99
|
+
-ms-flex: 0 0 66.66666667%;
|
|
100
|
+
flex: 0 0 66.66666667%;
|
|
101
|
+
max-width: 66.66666667%;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
&.wrapper-col-15 .adm-list-item-content-main {
|
|
105
|
+
-webkit-box-flex: 0;
|
|
106
|
+
-ms-flex: 0 0 62.5%;
|
|
107
|
+
flex: 0 0 62.5%;
|
|
108
|
+
max-width: 62.5%;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
&.wrapper-col-14 .adm-list-item-content-main {
|
|
112
|
+
-webkit-box-flex: 0;
|
|
113
|
+
-ms-flex: 0 0 58.33333333%;
|
|
114
|
+
flex: 0 0 58.33333333%;
|
|
115
|
+
max-width: 58.33333333%;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
&.wrapper-col-13 .adm-list-item-content-main {
|
|
119
|
+
-webkit-box-flex: 0;
|
|
120
|
+
-ms-flex: 0 0 54.16666667%;
|
|
121
|
+
flex: 0 0 54.16666667%;
|
|
122
|
+
max-width: 54.16666667%;
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
&.wrapper-col-12 .adm-list-item-content-main {
|
|
126
|
+
-webkit-box-flex: 0;
|
|
127
|
+
-ms-flex: 0 0 50%;
|
|
128
|
+
flex: 0 0 50%;
|
|
129
|
+
max-width: 50%;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
&.wrapper-col-11 .adm-list-item-content-main {
|
|
133
|
+
-webkit-box-flex: 0;
|
|
134
|
+
-ms-flex: 0 0 45.83333333%;
|
|
135
|
+
flex: 0 0 45.83333333%;
|
|
136
|
+
max-width: 45.83333333%;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
&.wrapper-col-10 .adm-list-item-content-main {
|
|
140
|
+
-webkit-box-flex: 0;
|
|
141
|
+
-ms-flex: 0 0 41.66666667%;
|
|
142
|
+
flex: 0 0 41.66666667%;
|
|
143
|
+
max-width: 41.66666667%;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
&.wrapper-col-9 .adm-list-item-content-main {
|
|
147
|
+
-webkit-box-flex: 0;
|
|
148
|
+
-ms-flex: 0 0 37.5%;
|
|
149
|
+
flex: 0 0 37.5%;
|
|
150
|
+
max-width: 37.5%;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
&.wrapper-col-8 .adm-list-item-content-main {
|
|
154
|
+
-webkit-box-flex: 0;
|
|
155
|
+
-ms-flex: 0 0 33.33333333%;
|
|
156
|
+
flex: 0 0 33.33333333%;
|
|
157
|
+
max-width: 33.33333333%;
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
&.wrapper-col-7 .adm-list-item-content-main {
|
|
161
|
+
-webkit-box-flex: 0;
|
|
162
|
+
-ms-flex: 0 0 29.16666667%;
|
|
163
|
+
flex: 0 0 29.16666667%;
|
|
164
|
+
max-width: 29.16666667%;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
&.wrapper-col-6 .adm-list-item-content-main {
|
|
168
|
+
-webkit-box-flex: 0;
|
|
169
|
+
-ms-flex: 0 0 25%;
|
|
170
|
+
flex: 0 0 25%;
|
|
171
|
+
max-width: 25%;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
&.wrapper-col-5 .adm-list-item-content-main {
|
|
175
|
+
-webkit-box-flex: 0;
|
|
176
|
+
-ms-flex: 0 0 20.83333333%;
|
|
177
|
+
flex: 0 0 20.83333333%;
|
|
178
|
+
max-width: 20.83333333%;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
&.wrapper-col-4 .adm-list-item-content-main {
|
|
182
|
+
-webkit-box-flex: 0;
|
|
183
|
+
-ms-flex: 0 0 16.66666667%;
|
|
184
|
+
flex: 0 0 16.66666667%;
|
|
185
|
+
max-width: 16.66666667%;
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
&.wrapper-col-3 .adm-list-item-content-main {
|
|
189
|
+
-webkit-box-flex: 0;
|
|
190
|
+
-ms-flex: 0 0 12.5%;
|
|
191
|
+
flex: 0 0 12.5%;
|
|
192
|
+
max-width: 12.5%;
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
&.wrapper-col-2 .adm-list-item-content-main {
|
|
196
|
+
-webkit-box-flex: 0;
|
|
197
|
+
-ms-flex: 0 0 8.33333333%;
|
|
198
|
+
flex: 0 0 8.33333333%;
|
|
199
|
+
max-width: 8.33333333%;
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
&.wrapper-col-1 .adm-list-item-content-main {
|
|
203
|
+
-webkit-box-flex: 0;
|
|
204
|
+
-ms-flex: 0 0 4.16666667%;
|
|
205
|
+
flex: 0 0 4.16666667%;
|
|
206
|
+
max-width: 4.16666667%;
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
&.wrapper-col-0 .adm-list-item-content-main {
|
|
210
|
+
display: none;
|
|
211
|
+
}
|
|
52
212
|
}
|
|
@@ -1,32 +1,23 @@
|
|
|
1
|
+
import React, { useEffect, useRef, useState } from "react";
|
|
2
|
+
import cls from "classnames";
|
|
3
|
+
import { pickDataProps, usePrefixCls } from "@formily/antd-mobile/esm/__builtins__";
|
|
1
4
|
import { isVoidField } from "@formily/core";
|
|
2
|
-
import { connect, mapProps
|
|
3
|
-
import { useFormLayout } from "../FormLayout";
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
CheckCircleOutline,
|
|
9
|
-
ExclamationCircleOutline,
|
|
10
|
-
} from "antd-mobile-icons";
|
|
5
|
+
import { connect, mapProps } from "@formily/react";
|
|
6
|
+
import { FormLayoutShallowContext, useFormLayout } from "../FormLayout";
|
|
7
|
+
import { List, Popover } from "antd-mobile";
|
|
8
|
+
import { ListItemProps } from "antd-mobile/es/components/list";
|
|
9
|
+
import { CheckCircleOutline, CloseCircleOutline, ExclamationCircleOutline } from "antd-mobile-icons";
|
|
10
|
+
|
|
11
11
|
import { useGlobalPropsContext } from "../../common/global-props-context";
|
|
12
12
|
|
|
13
13
|
import "./index.less";
|
|
14
14
|
|
|
15
|
-
export
|
|
16
|
-
|
|
17
|
-
export interface IFormItemProps {
|
|
15
|
+
export interface IFormItemProps extends ListItemProps {
|
|
18
16
|
className?: string;
|
|
19
17
|
style?: React.CSSProperties;
|
|
20
|
-
|
|
21
|
-
label?: React.ReactNode;
|
|
22
|
-
colon?: boolean;
|
|
23
|
-
tooltip?: React.ReactNode;
|
|
24
|
-
tooltipIcon?: React.ReactNode;
|
|
25
|
-
layout?: "vertical" | "horizontal" | "inline" | "between";
|
|
26
|
-
tooltipLayout?: "icon" | "text";
|
|
18
|
+
label?: string;
|
|
27
19
|
labelStyle?: React.CSSProperties;
|
|
28
20
|
labelAlign?: "left" | "right";
|
|
29
|
-
labelFor?: string;
|
|
30
21
|
labelWrap?: boolean;
|
|
31
22
|
labelWidth?: number | string;
|
|
32
23
|
wrapperWidth?: number | string;
|
|
@@ -35,43 +26,44 @@ export interface IFormItemProps {
|
|
|
35
26
|
wrapperAlign?: "left" | "right";
|
|
36
27
|
wrapperWrap?: boolean;
|
|
37
28
|
wrapperStyle?: React.CSSProperties;
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
29
|
+
help?: string;
|
|
30
|
+
hasFeedback?: boolean;
|
|
31
|
+
required?: boolean;
|
|
32
|
+
noStyle?: boolean;
|
|
33
|
+
disabled?: boolean;
|
|
34
|
+
hidden?: boolean;
|
|
43
35
|
extra?: React.ReactNode;
|
|
36
|
+
layout?: "vertical" | "horizontal" | "between";
|
|
44
37
|
feedbackText?: React.ReactNode;
|
|
45
38
|
feedbackLayout?: "loose" | "terse" | "popover" | "none" | (string & {});
|
|
46
39
|
feedbackStatus?: "error" | "warning" | "success" | "pending" | (string & {});
|
|
47
40
|
feedbackIcon?: React.ReactNode;
|
|
48
|
-
|
|
49
|
-
|
|
41
|
+
size?: "mini" | "small" | "middle" | "large";
|
|
42
|
+
inset?: boolean;
|
|
43
|
+
bordered?: boolean;
|
|
44
|
+
tooltipLayout?: "icon" | "text";
|
|
45
|
+
tooltip?: React.ReactNode;
|
|
46
|
+
tooltipIcon?: React.ReactNode;
|
|
50
47
|
asterisk?: boolean;
|
|
51
|
-
optionalMarkHidden?: boolean;
|
|
52
48
|
gridSpan?: number;
|
|
53
|
-
|
|
49
|
+
__layout__?: boolean;
|
|
54
50
|
}
|
|
55
51
|
|
|
56
|
-
type ComposeFormItem = React.FC<
|
|
57
|
-
BaseItem?: React.FC<
|
|
58
|
-
};
|
|
59
|
-
|
|
60
|
-
const ICON_MAP = {
|
|
61
|
-
error: <CloseCircleOutline />,
|
|
62
|
-
success: <CheckCircleOutline />,
|
|
63
|
-
warning: <ExclamationCircleOutline />,
|
|
52
|
+
type ComposeFormItem = React.FC<IFormItemProps> & {
|
|
53
|
+
BaseItem?: React.FC<IFormItemProps>;
|
|
64
54
|
};
|
|
65
55
|
|
|
66
56
|
const useFormItemLayout = (props: IFormItemProps) => {
|
|
67
57
|
const layout = useFormLayout();
|
|
68
|
-
const layoutType = props.layout ?? layout.layout ?? "horizontal";
|
|
69
58
|
return {
|
|
70
|
-
...props,
|
|
71
59
|
...layout,
|
|
72
|
-
|
|
60
|
+
...props,
|
|
61
|
+
__layout__: layout.__layout__,
|
|
62
|
+
layout: props.layout ?? layout.layout ?? "horizontal",
|
|
73
63
|
labelAlign:
|
|
74
|
-
|
|
64
|
+
layout.layout === "vertical"
|
|
65
|
+
? props.labelAlign ?? layout.labelAlign ?? "left"
|
|
66
|
+
: props.labelAlign ?? layout.labelAlign ?? "left",
|
|
75
67
|
labelWrap: props.labelWrap ?? layout.labelWrap,
|
|
76
68
|
labelWidth: props.labelWidth ?? layout.labelWidth,
|
|
77
69
|
wrapperWidth: props.wrapperWidth ?? layout.wrapperWidth,
|
|
@@ -79,43 +71,58 @@ const useFormItemLayout = (props: IFormItemProps) => {
|
|
|
79
71
|
wrapperWrap: props.wrapperWrap ?? layout.wrapperWrap,
|
|
80
72
|
size: props.size ?? layout.size,
|
|
81
73
|
inset: props.inset ?? layout.inset,
|
|
82
|
-
asterisk: props.asterisk,
|
|
83
|
-
optionalMarkHidden: props.optionalMarkHidden,
|
|
84
74
|
bordered: props.bordered ?? layout.bordered,
|
|
85
75
|
feedbackIcon: props.feedbackIcon,
|
|
86
76
|
feedbackLayout: props.feedbackLayout ?? layout.feedbackLayout ?? "loose",
|
|
87
77
|
tooltipLayout: props.tooltipLayout ?? layout.tooltipLayout ?? "icon",
|
|
88
|
-
tooltipIcon: props.tooltipIcon ?? layout.tooltipIcon ?? <
|
|
78
|
+
tooltipIcon: props.tooltipIcon ?? layout.tooltipIcon ?? <ExclamationCircleOutline />,
|
|
89
79
|
};
|
|
90
80
|
};
|
|
91
81
|
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
const
|
|
95
|
-
const
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
82
|
+
function useOverflow<Container extends HTMLElement, Content extends HTMLElement>() {
|
|
83
|
+
const [overflow, setOverflow] = useState(false);
|
|
84
|
+
const containerRef = useRef<Container>();
|
|
85
|
+
const contentRef = useRef<Content>();
|
|
86
|
+
|
|
87
|
+
useEffect(() => {
|
|
88
|
+
if (containerRef.current && contentRef.current) {
|
|
89
|
+
const contentWidth = contentRef.current.getBoundingClientRect().width;
|
|
90
|
+
const containerWidth = containerRef.current.getBoundingClientRect().width;
|
|
91
|
+
if (contentWidth && containerWidth && containerWidth < contentWidth) {
|
|
92
|
+
if (!overflow) setOverflow(true);
|
|
93
|
+
} else {
|
|
94
|
+
if (overflow) setOverflow(false);
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}, []);
|
|
98
|
+
|
|
99
|
+
return {
|
|
100
|
+
overflow,
|
|
101
|
+
containerRef,
|
|
102
|
+
contentRef,
|
|
103
|
+
};
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
const ICON_MAP = {
|
|
107
|
+
error: <CloseCircleOutline />,
|
|
108
|
+
success: <CheckCircleOutline />,
|
|
109
|
+
warning: <ExclamationCircleOutline />,
|
|
110
|
+
};
|
|
100
111
|
|
|
101
|
-
|
|
112
|
+
export const BaseItem: React.FC<IFormItemProps> = ({ children, ...props }) => {
|
|
113
|
+
const [active, setActive] = useState(false);
|
|
114
|
+
const formLayout = useFormItemLayout(props);
|
|
102
115
|
|
|
116
|
+
const { containerRef, contentRef, overflow } = useOverflow<HTMLDivElement, HTMLLabelElement>();
|
|
103
117
|
const {
|
|
104
118
|
label,
|
|
105
119
|
style,
|
|
106
120
|
layout,
|
|
107
|
-
addonBefore,
|
|
108
|
-
addonAfter,
|
|
109
|
-
asterisk,
|
|
110
|
-
optionalMarkHidden = false,
|
|
111
121
|
feedbackStatus,
|
|
112
122
|
extra,
|
|
113
123
|
feedbackText,
|
|
114
|
-
fullness,
|
|
115
124
|
feedbackLayout,
|
|
116
125
|
feedbackIcon,
|
|
117
|
-
enableOutlineFeedback = true,
|
|
118
|
-
getPopupContainer,
|
|
119
126
|
inset,
|
|
120
127
|
bordered = true,
|
|
121
128
|
labelWidth,
|
|
@@ -130,11 +137,12 @@ export const BaseItem = ({ children, ...props }) => {
|
|
|
130
137
|
tooltipLayout,
|
|
131
138
|
tooltip,
|
|
132
139
|
tooltipIcon,
|
|
140
|
+
asterisk,
|
|
133
141
|
} = formLayout;
|
|
134
|
-
|
|
135
142
|
const labelStyle = { ...formLayout.labelStyle };
|
|
136
143
|
const wrapperStyle = { ...formLayout.wrapperStyle };
|
|
137
|
-
|
|
144
|
+
// 固定宽度
|
|
145
|
+
// let enableCol = false
|
|
138
146
|
if (labelWidth || wrapperWidth) {
|
|
139
147
|
if (labelWidth) {
|
|
140
148
|
labelStyle.width = labelWidth === "auto" ? undefined : labelWidth;
|
|
@@ -147,80 +155,174 @@ export const BaseItem = ({ children, ...props }) => {
|
|
|
147
155
|
// 栅格模式
|
|
148
156
|
}
|
|
149
157
|
|
|
150
|
-
|
|
158
|
+
const prefixCls = usePrefixCls("formily-item");
|
|
159
|
+
const formatChildren =
|
|
151
160
|
feedbackLayout === "popover" ? (
|
|
152
161
|
<Popover
|
|
153
162
|
placement="top"
|
|
154
163
|
content={
|
|
155
164
|
<div
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
165
|
+
className={cls({
|
|
166
|
+
[`${prefixCls}-${feedbackStatus}-help`]: !!feedbackStatus,
|
|
167
|
+
[`${prefixCls}-help`]: true,
|
|
168
|
+
})}
|
|
160
169
|
>
|
|
161
170
|
{ICON_MAP[feedbackStatus]} {feedbackText}
|
|
162
171
|
</div>
|
|
163
172
|
}
|
|
164
173
|
visible={!!feedbackText}
|
|
165
|
-
// getPopupContainer={getPopupContainer}
|
|
166
174
|
>
|
|
167
|
-
{children}
|
|
175
|
+
<>{children}</>
|
|
168
176
|
</Popover>
|
|
169
177
|
) : (
|
|
170
178
|
children
|
|
171
179
|
);
|
|
172
180
|
|
|
173
|
-
|
|
174
|
-
const Com = Slots[name];
|
|
175
|
-
// 获取数据
|
|
181
|
+
const gridStyles: React.CSSProperties = {
|
|
176
182
|
// @ts-ignore
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
183
|
+
["--prefix-width"]: !isNaN(labelCol) ? `${(labelCol * 100) / 24}%` : undefined,
|
|
184
|
+
};
|
|
185
|
+
|
|
186
|
+
const getOverflowTooltip = () => {
|
|
187
|
+
if (overflow) {
|
|
188
|
+
return (
|
|
189
|
+
<div>
|
|
190
|
+
<div>{label}</div>
|
|
191
|
+
<div>{tooltip}</div>
|
|
192
|
+
</div>
|
|
193
|
+
);
|
|
194
|
+
}
|
|
195
|
+
return tooltip;
|
|
196
|
+
};
|
|
197
|
+
|
|
198
|
+
const renderLabelText = () => {
|
|
199
|
+
const labelChildren = (
|
|
200
|
+
<>
|
|
201
|
+
{asterisk && <span className={`${prefixCls}-asterisk`}>{"*"}</span>}
|
|
202
|
+
<div className={`${prefixCls}-label-content`} ref={containerRef}>
|
|
203
|
+
<label ref={contentRef}>{label}</label>
|
|
204
|
+
</div>
|
|
205
|
+
</>
|
|
180
206
|
);
|
|
181
|
-
}
|
|
182
207
|
|
|
183
|
-
|
|
208
|
+
if ((tooltipLayout === "text" && tooltip) || overflow) {
|
|
209
|
+
return (
|
|
210
|
+
<Popover placement="top" content={getOverflowTooltip()}>
|
|
211
|
+
{labelChildren}
|
|
212
|
+
</Popover>
|
|
213
|
+
);
|
|
214
|
+
}
|
|
215
|
+
return labelChildren;
|
|
216
|
+
};
|
|
184
217
|
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
218
|
+
const renderTooltipIcon = () => {
|
|
219
|
+
if (tooltip && tooltipLayout === "icon" && !overflow) {
|
|
220
|
+
return (
|
|
221
|
+
<span className={`${prefixCls}-label-tooltip-icon`}>
|
|
222
|
+
<Popover placement="right" mode="dark" trigger="click" content={tooltip}>
|
|
223
|
+
<span>{tooltipIcon}</span>
|
|
224
|
+
</Popover>
|
|
225
|
+
</span>
|
|
226
|
+
);
|
|
227
|
+
}
|
|
228
|
+
};
|
|
189
229
|
|
|
190
|
-
const renderLabel = () =>
|
|
191
|
-
|
|
230
|
+
const renderLabel = () => {
|
|
231
|
+
if (!label) return null;
|
|
232
|
+
return (
|
|
192
233
|
<div
|
|
193
|
-
className={
|
|
234
|
+
className={cls({
|
|
235
|
+
[`${prefixCls}-label`]: true,
|
|
236
|
+
[`${prefixCls}-label-tooltip`]: (tooltip && tooltipLayout === "text") || overflow,
|
|
237
|
+
})}
|
|
194
238
|
style={labelStyle}
|
|
195
239
|
>
|
|
196
240
|
{renderLabelText()}
|
|
197
|
-
{
|
|
241
|
+
{renderTooltipIcon()}
|
|
198
242
|
</div>
|
|
199
243
|
);
|
|
200
|
-
|
|
201
|
-
if (labelCol && wrapperCol && (layout === "horizontal" || layout === "inline")) {
|
|
202
|
-
return (
|
|
203
|
-
<Grid columns={GRID_COLUMNS} className={`formily-form-item layout-${layout}`}>
|
|
204
|
-
<Grid.Item span={labelCol}>{renderLabel()}</Grid.Item>
|
|
205
|
-
<Grid.Item className="form-item-content" span={wrapperCol}>
|
|
206
|
-
{formatChildren}
|
|
207
|
-
</Grid.Item>
|
|
208
|
-
</Grid>
|
|
209
|
-
);
|
|
210
|
-
}
|
|
244
|
+
};
|
|
211
245
|
|
|
212
246
|
return (
|
|
213
|
-
<
|
|
214
|
-
{
|
|
215
|
-
|
|
216
|
-
|
|
247
|
+
<List.Item
|
|
248
|
+
{...pickDataProps(props)}
|
|
249
|
+
style={{
|
|
250
|
+
...style,
|
|
251
|
+
...gridStyles,
|
|
252
|
+
}}
|
|
253
|
+
className={cls({
|
|
254
|
+
[`wrapper-col-${wrapperCol}`]: true,
|
|
255
|
+
"formily-form-item": true,
|
|
256
|
+
[`layout-${layout}`]: true,
|
|
257
|
+
[`${prefixCls}`]: true,
|
|
258
|
+
[`${prefixCls}-layout-${layout}`]: true,
|
|
259
|
+
[`${prefixCls}-${feedbackStatus}`]: !!feedbackStatus,
|
|
260
|
+
[`${prefixCls}-feedback-has-text`]: !!feedbackText,
|
|
261
|
+
[`${prefixCls}-size-${size}`]: !!size,
|
|
262
|
+
[`${prefixCls}-feedback-layout-${feedbackLayout}`]: !!feedbackLayout,
|
|
263
|
+
[`${prefixCls}-active`]: active,
|
|
264
|
+
[`${prefixCls}-label-align-${labelAlign}`]: true,
|
|
265
|
+
[`${prefixCls}-control-align-${wrapperAlign}`]: true,
|
|
266
|
+
[`${prefixCls}-label-wrap`]: !!labelWrap,
|
|
267
|
+
[`${prefixCls}-control-wrap`]: !!wrapperWrap,
|
|
268
|
+
// [`${prefixCls}-no-form-layout`]: !formLayout.__layout__,
|
|
269
|
+
[`${prefixCls}-bordered-none`]: bordered === false || !!inset || !!feedbackIcon,
|
|
270
|
+
[props.className]: !!props.className,
|
|
271
|
+
})}
|
|
272
|
+
title={layout === "vertical" && renderLabel()}
|
|
273
|
+
prefix={layout !== "vertical" && renderLabel()}
|
|
274
|
+
extra={extra && <div className={cls(`${prefixCls}-extra`)}>{extra}</div>}
|
|
275
|
+
data-grid-span={props.gridSpan}
|
|
276
|
+
>
|
|
277
|
+
<div
|
|
278
|
+
onFocus={() => {
|
|
279
|
+
if (feedbackIcon) {
|
|
280
|
+
setActive(true);
|
|
281
|
+
}
|
|
282
|
+
}}
|
|
283
|
+
onBlur={() => {
|
|
284
|
+
if (feedbackIcon) {
|
|
285
|
+
setActive(false);
|
|
286
|
+
}
|
|
287
|
+
}}
|
|
288
|
+
className={cls({
|
|
289
|
+
[`${prefixCls}-control`]: true,
|
|
290
|
+
})}
|
|
291
|
+
>
|
|
292
|
+
<div className={cls(`${prefixCls}-control-content`)}>
|
|
293
|
+
<div
|
|
294
|
+
style={wrapperStyle}
|
|
295
|
+
className={cls({
|
|
296
|
+
[`${prefixCls}-control-content-component`]: true,
|
|
297
|
+
[`${prefixCls}-control-content-component-has-feedback-icon`]: !!feedbackIcon,
|
|
298
|
+
})}
|
|
299
|
+
>
|
|
300
|
+
<FormLayoutShallowContext.Provider value={undefined}>{formatChildren}</FormLayoutShallowContext.Provider>
|
|
301
|
+
{feedbackIcon && <div className={cls(`${prefixCls}-feedback-icon`)}>{feedbackIcon}</div>}
|
|
302
|
+
</div>
|
|
303
|
+
</div>
|
|
304
|
+
{!!feedbackText && feedbackLayout !== "popover" && feedbackLayout !== "none" && (
|
|
305
|
+
<div
|
|
306
|
+
className={cls({
|
|
307
|
+
[`${prefixCls}-${feedbackStatus}-help`]: !!feedbackStatus,
|
|
308
|
+
[`${prefixCls}-help`]: true,
|
|
309
|
+
[`${prefixCls}-help-enter`]: true,
|
|
310
|
+
[`${prefixCls}-help-enter-active`]: true,
|
|
311
|
+
})}
|
|
312
|
+
>
|
|
313
|
+
{feedbackText}
|
|
314
|
+
</div>
|
|
315
|
+
)}
|
|
316
|
+
</div>
|
|
317
|
+
</List.Item>
|
|
217
318
|
);
|
|
218
319
|
};
|
|
219
320
|
|
|
220
321
|
// 适配
|
|
221
|
-
export const FormItem:
|
|
322
|
+
export const FormItem: ComposeFormItem = connect(
|
|
222
323
|
BaseItem,
|
|
223
|
-
mapProps((props
|
|
324
|
+
mapProps((props, field) => {
|
|
325
|
+
const globalProps: any = useGlobalPropsContext();
|
|
224
326
|
if (isVoidField(field))
|
|
225
327
|
return {
|
|
226
328
|
label: field.title || props.label,
|
|
@@ -246,6 +348,9 @@ export const FormItem: any = connect(
|
|
|
246
348
|
if (field.selfSuccesses.length) return split(field.selfSuccesses);
|
|
247
349
|
};
|
|
248
350
|
const takeAsterisk = () => {
|
|
351
|
+
if (globalProps._scenario_ === "descriptions") {
|
|
352
|
+
return false;
|
|
353
|
+
}
|
|
249
354
|
if (field.required && field.pattern !== "readPretty") {
|
|
250
355
|
return true;
|
|
251
356
|
}
|
|
@@ -255,14 +360,15 @@ export const FormItem: any = connect(
|
|
|
255
360
|
return false;
|
|
256
361
|
};
|
|
257
362
|
return {
|
|
258
|
-
label:
|
|
363
|
+
label: field.title || props.label,
|
|
259
364
|
feedbackStatus: takeFeedbackStatus(),
|
|
260
365
|
feedbackText: takeMessage(),
|
|
261
366
|
asterisk: takeAsterisk(),
|
|
262
|
-
optionalMarkHidden: field.pattern === "readPretty" && !("asterisk" in props),
|
|
263
367
|
extra: props.extra || field.description,
|
|
264
368
|
};
|
|
265
369
|
}),
|
|
266
370
|
);
|
|
267
371
|
|
|
372
|
+
FormItem.BaseItem = BaseItem;
|
|
373
|
+
|
|
268
374
|
export default FormItem;
|
package/src/components/index.ts
CHANGED
|
@@ -15,7 +15,8 @@ export * from "./Checkbox";
|
|
|
15
15
|
export * from "./LocationPicker";
|
|
16
16
|
export * from "./TreeSelect";
|
|
17
17
|
export * from "./Slider";
|
|
18
|
-
|
|
18
|
+
|
|
19
|
+
import FormItem from "./FormItem";
|
|
19
20
|
import FormLayout from "./FormLayout";
|
|
20
21
|
|
|
21
|
-
export { FormLayout };
|
|
22
|
+
export { FormItem, FormLayout };
|