@nolwenture/formik-jsonschema-form 1.0.4 → 1.0.6

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.
Files changed (54) hide show
  1. package/dist/cjs/Form/components/FieldInfo.js +45 -17
  2. package/dist/cjs/Form/components/FieldInput.js +8 -1
  3. package/dist/cjs/Form/fields/BooleanField/styledComponents.js +2 -1
  4. package/dist/cjs/Form/fields/RadioField/styledComponents.js +5 -0
  5. package/dist/cjs/Form/fields/SearchableMultiTagSelectField/SearchableMultiTagSelectField.js +2 -2
  6. package/dist/cjs/Form/fields/SearchableMultiTagSelectField/SearchableMultiTagSelectFieldInput.js +3 -3
  7. package/dist/cjs/Form/fields/SearchableMultiTagSelectField/styledComponents.js +9 -4
  8. package/dist/cjs/Form/fields/SearchableSelectField/SearchableSelectField.js +7 -1
  9. package/dist/cjs/Form/fields/SearchableSelectField/styledComponents.js +1 -1
  10. package/dist/cjs/Form/fields/TextAreaField/TextAreaField.js +4 -2
  11. package/dist/cjs/Form/fields/ToggleField/styledComponents.js +1 -0
  12. package/dist/cjs/Form/styles/common.js +74 -4
  13. package/dist/cjs/Form/templates/ArrayFieldTemplate/ArrayFieldTemplate.js +2 -2
  14. package/dist/cjs/Form/templates/ArrayFieldTemplate/styledComponents.js +4 -1
  15. package/dist/cjs/Form/templates/CollapsibleObjectFieldTemplate/CollapsibleObjectFieldTemplate.js +4 -4
  16. package/dist/cjs/Form/templates/CollapsibleObjectFieldTemplate/styledComponents.js +4 -1
  17. package/dist/cjs/Form/templates/FieldTemplate/FieldTemplate.js +4 -3
  18. package/dist/cjs/Form/templates/ObjectFieldTemplate/ObjectFieldTemplate.js +2 -2
  19. package/dist/cjs/Form/templates/ObjectFieldTemplate/styledComponents.js +22 -1
  20. package/dist/cjs/FormView/fields/MultipleChoiceField.js +1 -1
  21. package/dist/esm/Form/components/FieldInfo.js +45 -17
  22. package/dist/esm/Form/components/FieldInput.js +7 -0
  23. package/dist/esm/Form/fields/BooleanField/styledComponents.js +2 -1
  24. package/dist/esm/Form/fields/RadioField/styledComponents.js +5 -0
  25. package/dist/esm/Form/fields/SearchableMultiTagSelectField/SearchableMultiTagSelectField.js +2 -2
  26. package/dist/esm/Form/fields/SearchableMultiTagSelectField/SearchableMultiTagSelectFieldInput.js +3 -3
  27. package/dist/esm/Form/fields/SearchableMultiTagSelectField/styledComponents.js +9 -4
  28. package/dist/esm/Form/fields/SearchableSelectField/SearchableSelectField.js +7 -1
  29. package/dist/esm/Form/fields/SearchableSelectField/styledComponents.js +1 -1
  30. package/dist/esm/Form/fields/TextAreaField/TextAreaField.js +4 -2
  31. package/dist/esm/Form/fields/ToggleField/styledComponents.js +1 -0
  32. package/dist/esm/Form/styles/common.js +74 -4
  33. package/dist/esm/Form/templates/ArrayFieldTemplate/ArrayFieldTemplate.js +2 -2
  34. package/dist/esm/Form/templates/ArrayFieldTemplate/styledComponents.js +3 -0
  35. package/dist/esm/Form/templates/CollapsibleObjectFieldTemplate/CollapsibleObjectFieldTemplate.js +4 -4
  36. package/dist/esm/Form/templates/CollapsibleObjectFieldTemplate/styledComponents.js +3 -0
  37. package/dist/esm/Form/templates/FieldTemplate/FieldTemplate.js +4 -3
  38. package/dist/esm/Form/templates/ObjectFieldTemplate/ObjectFieldTemplate.js +2 -2
  39. package/dist/esm/Form/templates/ObjectFieldTemplate/styledComponents.js +21 -0
  40. package/dist/esm/FormView/fields/MultipleChoiceField.js +1 -1
  41. package/dist/types/Form/components/FieldInfo.d.ts +2 -0
  42. package/dist/types/Form/components/FieldInput.d.ts +4 -1
  43. package/dist/types/Form/components/index.d.ts +14 -5
  44. package/dist/types/Form/fields/SearchableMultiTagSelectField/SearchableMultiTagSelectFieldInput.d.ts +3 -1
  45. package/dist/types/Form/fields/SearchableMultiTagSelectField/index.d.ts +3 -3
  46. package/dist/types/Form/fields/SearchableMultiTagSelectField/styledComponents.d.ts +2 -2
  47. package/dist/types/Form/fields/SearchableSelectField/styledComponents.d.ts +1 -1
  48. package/dist/types/Form/fields/index.d.ts +4 -4
  49. package/dist/types/Form/templates/ArrayFieldTemplate/styledComponents.d.ts +3 -1
  50. package/dist/types/Form/templates/CollapsibleObjectFieldTemplate/styledComponents.d.ts +3 -1
  51. package/dist/types/Form/templates/ObjectFieldTemplate/styledComponents.d.ts +2 -0
  52. package/dist/types/Form/templates/index.d.ts +4 -0
  53. package/dist/types/common/types/FieldInfo.d.ts +1 -0
  54. package/package.json +2 -1
@@ -1,4 +1,5 @@
1
- import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
1
+ import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useState } from "react";
2
3
  import { styled } from "styled-components";
3
4
  import { readableColor } from "polished";
4
5
  export const FieldInfoBoxElement = styled.div `
@@ -52,17 +53,17 @@ export const FieldInfoBoxArrowElement = styled.div `
52
53
  width: 0;
53
54
  position: absolute;
54
55
  pointer-events: none;
55
- border-top-color: ${({ position, theme }) => position === "top" ? theme.color.intent.default.none : "transparent"};
56
- border-bottom-color: ${({ position, theme }) => position === "bottom" ? theme.color.intent.default.none : "transparent"};
57
- border-right-color: ${({ position, theme }) => position === "right" ? theme.color.intent.default.none : "transparent"};
58
- border-left-color: ${({ position, theme }) => position === "left" ? theme.color.intent.default.none : "transparent"};
56
+ border-top-color: ${({ position, theme }) => position === "top" ? theme.color.intent.default.warning : "transparent"};
57
+ border-bottom-color: ${({ position, theme }) => position === "bottom" ? theme.color.intent.default.warning : "transparent"};
58
+ border-right-color: ${({ position, theme }) => position === "right" ? theme.color.intent.default.warning : "transparent"};
59
+ border-left-color: ${({ position, theme }) => position === "left" ? theme.color.intent.default.warning : "transparent"};
59
60
  border-width: 5px;
60
61
  margin-left: -5px;
61
62
  `;
62
63
  export const FieldInfoBoxInnerElement = styled.div `
63
- background: ${(props) => props.theme.color.background.default};
64
+ background: ${(props) => props.theme.color.intent.default.warning};
64
65
  border-radius: ${(props) => props.theme.borderRadius.none};
65
- border: ${(props) => `${props.theme.strokeWidth.thin} solid ${props.theme.color.intent.default.none}`};
66
+ border: none;
66
67
  color: ${(props) => props.theme.color.text.default};
67
68
  cursor: default;
68
69
  font-size: ${(props) => props.theme.typography.size.small};
@@ -72,21 +73,31 @@ export const FieldInfoBoxInnerElement = styled.div `
72
73
  text-align: left;
73
74
  white-space: pre-wrap;
74
75
  `;
76
+ export const InlineFieldInfoBoxInnerElement = styled.div `
77
+ background: ${(props) => props.theme.color.intent.default.warning};
78
+ border-radius: ${(props) => props.theme.borderRadius.none};
79
+ border: none;
80
+ color: ${(props) => props.theme.color.text.default};
81
+ cursor: default;
82
+ font-size: ${(props) => props.theme.typography.size.small};
83
+ line-height: ${(props) => props.theme.typography.lineHeight.small};
84
+ padding: ${(props) => `${props.theme.spacing.s} ${props.theme.spacing.m}`};
85
+ text-align: left;
86
+ white-space: pre-wrap;
87
+ `;
75
88
  export const FieldInfoContainer = styled.a `
76
- position: relative;
77
- color: ${(props) => props.theme.color.text.default};
78
89
  background: none;
79
- outline: none;
80
- cursor: pointer;
81
- border: ${(props) => `${props.theme.strokeWidth.thin} solid
82
- ${props.theme.color.border.default}`};
83
90
  border-radius: ${(props) => props.theme.borderRadius.circle};
84
- line-height: 1em;
91
+ border: ${(props) => `${props.theme.strokeWidth.thin} solid ${props.theme.color.border.default}`};
92
+ color: ${(props) => props.theme.color.text.default};
93
+ cursor: pointer;
85
94
  font-family: ${(props) => props.theme.typography.fontFamily.base};
86
95
  font-size: ${(props) => props.theme.typography.size.small};
96
+ margin: ${(props) => `0 ${props.theme.spacing.s} 0 -${props.theme.spacing.xs}`};
97
+ outline: none;
87
98
  padding: ${(props) => `0 ${props.theme.spacing.s}`};
99
+ position: relative;
88
100
  text-decoration: unset;
89
- margin: ${(props) => `0 ${props.theme.spacing.s} 0 -${props.theme.spacing.xs}`};
90
101
  width: fit-content;
91
102
 
92
103
  &:active,
@@ -100,6 +111,23 @@ export const FieldInfoContainer = styled.a `
100
111
  }
101
112
  `;
102
113
  export const FieldInfoLabel = styled.span ``;
103
- export const FieldInfo = ({ label, content, position, props, className, }) => {
104
- return (_jsxs(FieldInfoContainer, { href: "#", onClick: (e) => e.preventDefault(), className: className, children: [_jsx(FieldInfoLabel, { children: label ?? "i" }), _jsxs(FieldInfoBoxElement, { position: position ?? "top", role: "tooltip", children: [_jsx(FieldInfoBoxArrowElement, { position: position ?? "top" }), _jsx(FieldInfoBoxInnerElement, { children: content })] })] }));
114
+ export const InlineFieldInfoWrapper = styled.div `
115
+ display: flex;
116
+ margin: ${(props) => `${props.theme.spacing.m} 0`};
117
+ width: 100%;
118
+ `;
119
+ export const FieldInfo = ({ label, content, position, display = "tooltip", className, }) => {
120
+ const [isInlineVisible, setIsInlineVisible] = useState(false);
121
+ const handleToggle = (e) => {
122
+ e.preventDefault();
123
+ if (display === "inline") {
124
+ setIsInlineVisible((prev) => !prev);
125
+ }
126
+ };
127
+ if (display === "inline") {
128
+ return (_jsxs(_Fragment, { children: [_jsx(FieldInfoContainer, { href: "#", onClick: handleToggle, className: className, children: _jsx(FieldInfoLabel, { children: label ?? "i" }) }), isInlineVisible && (_jsx(InlineFieldInfoWrapper, { children: _jsx(InlineFieldInfoBoxInnerElement, { children: content }) }))] }));
129
+ }
130
+ else {
131
+ return (_jsxs(FieldInfoContainer, { href: "#", onClick: (e) => e.preventDefault(), className: className, children: [_jsx(FieldInfoLabel, { children: label ?? "i" }), _jsxs(FieldInfoBoxElement, { position: position ?? "top", role: "tooltip", children: [_jsx(FieldInfoBoxArrowElement, { position: position ?? "top" }), _jsx(FieldInfoBoxInnerElement, { children: content })] })] }));
132
+ }
105
133
  };
@@ -6,6 +6,13 @@ export const FieldWrapper = styled.div `
6
6
  flex-direction: column;
7
7
  margin: ${(props) => `${props.theme.spacing.s} 0`};
8
8
  color: ${(props) => props.theme.color.text.default};
9
+ opacity: ${(props) => (props.$isDisabled ? 0.6 : 1)};
10
+ pointer-events: ${(props) => (props.$isDisabled ? 'none' : 'auto')};
11
+ `;
12
+ export const FieldTitleInfoWrapper = styled.div `
13
+ display: flex;
14
+ flex-direction: row;
15
+ flex-wrap: wrap;
9
16
  `;
10
17
  export const FieldTitle = styled.label `
11
18
  font-size: ${(props) => props.theme.typography.size.base};
@@ -8,7 +8,8 @@ export const BooleanFieldWrapper = styled(CommonCheckboxStyles) `
8
8
  font-family: ${(props) => props.theme.typography.fontFamily.base};
9
9
  gap: ${(props) => props.theme.spacing.s};
10
10
 
11
- & > input[readonly], & > input[readonly] ~ span {
11
+ &:has(input[readonly]) {
12
12
  pointer-events: none;
13
+ cursor: pointer;
13
14
  }
14
15
  `;
@@ -46,6 +46,11 @@ export const RadioFieldContainer = styled(CommonCheckboxStyles) `
46
46
  transform: scale(1);
47
47
  }
48
48
  }
49
+
50
+ &[readonly] {
51
+ background-color: transparent;
52
+ border: none;
53
+ }
49
54
  }
50
55
  `;
51
56
  export const RadioFieldElement = styled.label `
@@ -6,11 +6,11 @@ import { FormRegistry } from "../../FormRegistry";
6
6
  export const SearchableMultiTagSelectField = (props) => {
7
7
  const { templates, components: { SearchableMultiTagSelectFieldInput }, } = useContext(FormRegistry);
8
8
  useSetDefault(props);
9
- const { name, uiSchema } = props;
9
+ const { name, uiSchema, schema } = props;
10
10
  const { placeholder, emptySearchMessage, props: inputProps, } = useMemo(() => extractUiSchema(uiSchema), [uiSchema]);
11
11
  const enums = useMemo(() => getEnums(props), [props]);
12
12
  const SelectedFieldTemplate = (props.uiSchema?.["ui:template"] &&
13
13
  templates[props.uiSchema?.["ui:template"]]) ??
14
14
  templates.FieldTemplate;
15
- return (_jsx(SelectedFieldTemplate, { ...props, "data-fjsf-array": name, children: _jsx(SearchableMultiTagSelectFieldInput, { ...inputProps, name: name, placeholder: placeholder, emptySearchMessage: emptySearchMessage, enums: enums }) }));
15
+ return (_jsx(SelectedFieldTemplate, { ...props, "data-fjsf-array": name, children: _jsx(SearchableMultiTagSelectFieldInput, { ...inputProps, name: name, placeholder: placeholder, emptySearchMessage: emptySearchMessage, enums: enums, readOnly: schema.readOnly }) }));
16
16
  };
@@ -1,7 +1,7 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { useContext, useState } from "react";
3
3
  import { FormRegistry } from "../../FormRegistry";
4
- export const SearchableMultiTagSelectFieldInput = ({ name, placeholder, enums, emptySearchMessage, closeElement, className, }) => {
4
+ export const SearchableMultiTagSelectFieldInput = ({ name, placeholder, enums, emptySearchMessage, closeElement, className, disabled, readOnly, }) => {
5
5
  const { components: { FieldInput, SearchableMultiTagSelectFieldBadge, SearchableMultiTagSelectFieldBadgeCloseElement, SearchableMultiTagSelectFieldBadgeContainer, SearchableMultiTagSelectFieldContainer, SearchableMultiTagSelectFieldInputElement, SearchableMultiTagSelectFieldOptionList, SearchableMultiTagSelectFieldOptionListItem, SearchableMultiTagSelectFieldOptionListWithoutItem, SearchableMultiTagSelectFieldSearchContainer, }, } = useContext(FormRegistry);
6
6
  const [search, setSearch] = useState("");
7
7
  const searchIncludedInEnum = () => {
@@ -10,7 +10,7 @@ export const SearchableMultiTagSelectFieldInput = ({ name, placeholder, enums, e
10
10
  };
11
11
  return (_jsx(FieldInput, { className: className, name: name, multiple: true, children: ({ field, form: { setFieldValue }, meta, }) => (_jsxs(SearchableMultiTagSelectFieldContainer, { className: className, children: [_jsx(FieldInput, { id: className, type: "hidden", ...field }), _jsxs(SearchableMultiTagSelectFieldSearchContainer, { children: [_jsx(SearchableMultiTagSelectFieldInputElement, { id: className + "_id", className: className, type: "text", onChange: (e) => {
12
12
  setSearch(e.currentTarget.value);
13
- }, placeholder: placeholder, value: search }), search.length > 0 && (_jsx(SearchableMultiTagSelectFieldOptionList, { children: searchIncludedInEnum() ? (enums?.values
13
+ }, placeholder: placeholder, value: search, readOnly: readOnly, disabled: disabled }), search.length > 0 && !disabled && !readOnly && (_jsx(SearchableMultiTagSelectFieldOptionList, { children: searchIncludedInEnum() ? (enums?.values
14
14
  .filter((item) => !(field.value ?? []).includes(item.const))
15
15
  .filter((value) => value.title.toLowerCase().includes(search.toLowerCase()))
16
16
  .map((option, index) => (_jsx(SearchableMultiTagSelectFieldOptionListItem, { value: option.const, onClick: () => {
@@ -19,5 +19,5 @@ export const SearchableMultiTagSelectFieldInput = ({ name, placeholder, enums, e
19
19
  ]);
20
20
  setSearch("");
21
21
  }, children: option.title }, index)))) : (_jsx(SearchableMultiTagSelectFieldOptionListWithoutItem, { children: emptySearchMessage ?? "No match found" })) }))] }), _jsx(SearchableMultiTagSelectFieldBadgeContainer, { children: (field.value ?? []).map((value) => (_jsxs(SearchableMultiTagSelectFieldBadge, { children: [enums?.values.find((option) => option.const === value)
22
- ?.title, _jsx(SearchableMultiTagSelectFieldBadgeCloseElement, { onClick: () => setFieldValue(name, field.value.filter((v) => v !== value)), children: closeElement ?? "✕" })] }, value))) }), meta.touched && meta.error && (_jsx("div", { className: "error", children: meta.error }))] })) }));
22
+ ?.title, _jsx(SearchableMultiTagSelectFieldBadgeCloseElement, { onClick: () => setFieldValue(name, field.value.filter((v) => v !== value)), disabled: disabled || readOnly, children: closeElement ?? "✕" })] }, value))) }), meta.touched && meta.error && (_jsx("div", { className: "error", children: meta.error }))] })) }));
23
23
  };
@@ -19,17 +19,22 @@ export const SearchableMultiTagSelectFieldBadgeContainer = styled.div `
19
19
  display: inline-flex;
20
20
  gap: ${(props) => props.theme.strokeWidth.thin};
21
21
  `;
22
- export const SearchableMultiTagSelectFieldBadge = styled.span `
22
+ export const SearchableMultiTagSelectFieldBadge = styled.div `
23
23
  color: ${(props) => props.theme.color.background.input};
24
24
  background: ${(props) => props.theme.color.text.default};
25
- padding: ${(props) => `0 ${props.theme.spacing.xs} 0 ${props.theme.spacing.s}`};
25
+ padding: ${(props) => `0 ${props.theme.spacing.s}`};
26
26
  border-radius: ${(props) => props.theme.borderRadius.none};
27
27
  display: flex;
28
28
  margin-right: ${(props) => props.theme.spacing.xs};
29
+ gap: ${(props) => props.theme.spacing.s};
29
30
  `;
30
- export const SearchableMultiTagSelectFieldBadgeCloseElement = styled.span `
31
+ export const SearchableMultiTagSelectFieldBadgeCloseElement = styled.button `
32
+ background: transparent;
33
+ color: ${(props) => props.theme.color.background.input};
34
+ border: none;
31
35
  cursor: pointer;
32
- margin-left: ${(props) => props.theme.spacing.s};
36
+ margin: 0;
37
+ padding: 0;
33
38
  font-size: ${(props) => props.theme.typography.size.small};
34
39
  align-self: center;
35
40
  font-family: ${(props) => props.theme.typography.fontFamily.base};
@@ -85,6 +85,8 @@ export const SearchableSelectField = (props) => {
85
85
  };
86
86
  }, [handleKeyPress]);
87
87
  const handleSearchChange = (event) => {
88
+ if (schema.readOnly)
89
+ return;
88
90
  setSearchTerm(event.target.value);
89
91
  setItemsToShow(dropdownOptions.perPage);
90
92
  setShowOptions(true);
@@ -98,6 +100,8 @@ export const SearchableSelectField = (props) => {
98
100
  onSelect?.(item.const);
99
101
  };
100
102
  const handleFocus = () => {
103
+ if (schema.readOnly)
104
+ return;
101
105
  setShowOptions(true);
102
106
  };
103
107
  const handleBlur = (event) => {
@@ -107,6 +111,8 @@ export const SearchableSelectField = (props) => {
107
111
  }
108
112
  };
109
113
  const handleClear = () => {
114
+ if (schema.readOnly)
115
+ return;
110
116
  setSearchTerm("");
111
117
  setValue(undefined);
112
118
  };
@@ -119,7 +125,7 @@ export const SearchableSelectField = (props) => {
119
125
  const SelectedFieldTemplate = (props.uiSchema?.["ui:template"] &&
120
126
  templates[props.uiSchema?.["ui:template"]]) ??
121
127
  templates.FieldTemplate;
122
- return (_jsx(SelectedFieldTemplate, { ...props, ...fieldDataAttribute, children: _jsxs(SearchableSelectFieldContainer, { ref: containerRef, onBlur: handleBlur, children: [_jsxs(SearchableSelectFieldInputContainer, { children: [_jsx(SearchableSelectFieldInputElement, { ...inputProps, name: name, type: "text", placeholder: placeholder, value: searchTerm, onChange: handleSearchChange, onFocus: handleFocus }), searchTerm && !hideClearButton && (_jsx(SearchableSelectFieldClearButton, { onClick: handleClear, children: clearButtonText ?? "✕" }))] }), showOptions && (_jsxs(SearchableSelectFieldDropdownContainer, { role: "dropdown-list",
128
+ return (_jsx(SelectedFieldTemplate, { ...props, ...fieldDataAttribute, children: _jsxs(SearchableSelectFieldContainer, { ref: containerRef, onBlur: handleBlur, children: [_jsxs(SearchableSelectFieldInputContainer, { children: [_jsx(SearchableSelectFieldInputElement, { ...inputProps, name: name, type: "text", placeholder: placeholder, value: searchTerm, onChange: handleSearchChange, onFocus: handleFocus, readOnly: schema.readOnly }), searchTerm && !hideClearButton && (_jsx(SearchableSelectFieldClearButton, { onClick: handleClear, disabled: schema.readOnly, children: clearButtonText ?? "✕" }))] }), showOptions && !schema.readOnly && (_jsxs(SearchableSelectFieldDropdownContainer, { role: "dropdown-list",
123
129
  //ref={moreRef} //TODO
124
130
  style: {
125
131
  maxHeight: dropdownOptions.height,
@@ -29,7 +29,7 @@ export const SearchableSelectFieldInputElement = styled(FieldInput) `
29
29
  padding-right: ${(props) => props.theme.spacing.xxl};
30
30
  text-overflow: ellipsis;
31
31
  `;
32
- export const SearchableSelectFieldClearButton = styled.span `
32
+ export const SearchableSelectFieldClearButton = styled.button `
33
33
  background-color: ${(props) => props.theme.color.palette.neutral[500]};
34
34
  border-radius: ${(props) => props.theme.borderRadius.circle};
35
35
  bottom: 0;
@@ -7,9 +7,11 @@ export const TextAreaField = (props) => {
7
7
  const { templates, components: { TextAreaFieldInput }, } = useContext(FormRegistry);
8
8
  useSetDefault(props);
9
9
  const { name, uiSchema } = props;
10
- const { props: inputProps } = useMemo(() => extractUiSchema(uiSchema), [uiSchema]);
10
+ const { placeholder, props: inputProps } = useMemo(() => extractUiSchema(uiSchema), [uiSchema]);
11
11
  const SelectedFieldTemplate = (props.uiSchema?.["ui:template"] &&
12
12
  templates[props.uiSchema?.["ui:template"]]) ??
13
13
  templates.FieldTemplate;
14
- return (_jsx(SelectedFieldTemplate, { ...props, "data-fjsf-string": name, children: _jsx(TextAreaFieldInput, { readOnly: props.schema.readOnly, ...inputProps, name: name, formikAs: "textarea" }) }));
14
+ return (_jsx(SelectedFieldTemplate, { ...props, "data-fjsf-string": name, children: _jsx(TextAreaFieldInput, { placeholder,
15
+ readOnly: props.schema.readOnly,
16
+ ...inputProps, name: name, formikAs: "textarea" }) }));
15
17
  };
@@ -7,6 +7,7 @@ export const ToggleFieldToggle = styled.span `
7
7
  left: 0;
8
8
  right: 0;
9
9
  bottom: 0;
10
+ height: 1rem;
10
11
  background: ${(props) => props.theme.color.intent.default.none};
11
12
  border: ${(props) => `${props.theme.strokeWidth.thin} solid ${props.theme.color.border.default}`};
12
13
  -webkit-transition: 0.4s;
@@ -20,6 +20,24 @@ export const CommonFieldWrapper = styled.div `
20
20
  }
21
21
 
22
22
  &:read-only {
23
+ border: none;
24
+ background-color: transparent;
25
+ padding: 0;
26
+
27
+ &::placeholder {
28
+ color: ${(props) => props.theme.color.text.default};
29
+ }
30
+ }
31
+
32
+ &:disabled {
33
+ background-color: ${(props) => props.theme.color.background.input};
34
+ border: ${(props) => `${props.theme.strokeWidth.thin} solid
35
+ ${props.theme.color.border.default}`};
36
+ padding: ${(props) => props.theme.spacing.s};
37
+
38
+ &::placeholder {
39
+ color: ${(props) => props.theme.color.text.muted};
40
+ }
23
41
  }
24
42
 
25
43
  &:focus {
@@ -56,13 +74,24 @@ export const CommonFieldWrapper = styled.div `
56
74
  background-repeat: no-repeat;
57
75
  background-size: ${(props) => props.theme.spacing.l}; auto;
58
76
 
59
- &:read-only {
60
-
77
+ &[readonly] {
78
+ background-image: none;
79
+ border: none;
80
+ background-color: transparent;
81
+ padding: 0;
61
82
  }
62
83
 
63
84
  &:focus {
64
85
  ${(props) => props.theme.focus.default};
65
86
  }
87
+
88
+ &:disabled {
89
+ background-color: ${(props) => props.theme.color.background.input};
90
+ background-image: ${(props) => `url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='10' height='10' viewBox='0 0 320 512'%3E%3Cpath fill='${encodeURIComponent(props.theme.color.text.default)}' d='M31 192h258c17 0 26 21 14 33l-129 129c-8 8-21 8-29 0L17 225c-12-12-3-33 14-33z'/%3E%3C/svg%3E")`};
91
+ border: ${(props) => `${props.theme.strokeWidth.thin} solid
92
+ ${props.theme.color.border.default}`};
93
+ padding: ${(props) => `${props.theme.spacing.s} ${props.theme.spacing.xxxxl} ${props.theme.spacing.s} ${props.theme.spacing.m}`};
94
+ }
66
95
  }
67
96
 
68
97
  select[multiple] {
@@ -70,6 +99,40 @@ export const CommonFieldWrapper = styled.div `
70
99
  background-image: none;
71
100
  overflow: auto;
72
101
  }
102
+
103
+ textarea {
104
+
105
+ background-color: ${(props) => props.theme.color.background.input};
106
+ border: ${(props) => `${props.theme.strokeWidth.thin} solid
107
+ ${props.theme.color.border.default}`};
108
+ padding: ${(props) => props.theme.spacing.s};
109
+
110
+ &:read-only {
111
+ border: none;
112
+ background-color: transparent;
113
+ padding: 0;
114
+ min-height: unset;
115
+ resize: none;
116
+ field-sizing: content;
117
+
118
+ &::placeholder {
119
+ color: ${(props) => props.theme.color.text.default};
120
+ }
121
+ }
122
+
123
+ &:disabled {
124
+ background-color: ${(props) => props.theme.color.background.input};
125
+ border: ${(props) => `${props.theme.strokeWidth.thin} solid
126
+ ${props.theme.color.border.default}`};
127
+ min-height: 5rem;
128
+ padding: ${(props) => props.theme.spacing.s};
129
+
130
+ &::placeholder {
131
+ color: ${(props) => props.theme.color.text.muted};
132
+ }
133
+ }
134
+
135
+ }
73
136
  `;
74
137
  export const CommonCheckboxStyles = styled.div `
75
138
  input[type="checkbox"] {
@@ -175,8 +238,15 @@ export const CommonCheckboxStyles = styled.div `
175
238
  }
176
239
  }
177
240
 
178
- &:read-only {
179
-
241
+ &[readonly] {
242
+ background: transparent;
243
+ border: none;
244
+ }
245
+
246
+ &:disabled {
247
+ background-color: ${(props) => props.theme.color.background.input};
248
+ border: ${(props) => props.theme.strokeWidth.thin} solid
249
+ ${(props) => props.theme.color.border.default};
180
250
  }
181
251
  }
182
252
  `;
@@ -6,7 +6,7 @@ import { FormRegistry } from "../../FormRegistry";
6
6
  import { getComponents } from "./styledComponents";
7
7
  export const ArrayFieldTemplate = (props) => {
8
8
  const { components } = useContext(FormRegistry);
9
- const { Wrapper, Title, Description, Help, Info, RequiredIndicator, ErrorMessage, } = getComponents(components);
9
+ const { Wrapper, Title, TitleInfoWrapper, Description, Help, Info, RequiredIndicator, ErrorMessage, } = getComponents(components);
10
10
  const { name, uiSchema, items, renderItem, ...otherProps } = props;
11
11
  const title = getTitle(props);
12
12
  const description = getDescription(props);
@@ -28,5 +28,5 @@ export const ArrayFieldTemplate = (props) => {
28
28
  // In case of array of objects, it will give error message as an object value,
29
29
  // which is incorrect value for React, causing UI to crash.
30
30
  const errorIsString = typeof error === "string";
31
- return (_jsxs(Wrapper, { ...mergedWrapperProps, children: [title && (_jsxs(Title, { ...titleProps, htmlFor: name, children: [title, props?.required && _jsx(RequiredIndicator, {})] })), info && _jsx(Info, { ...info }), description && (_jsx(Description, { ...descriptionProps, children: description })), items && items.map((item, index) => renderItem(item, index)), help && _jsx(Help, { ...helpProps, children: help }), errorIsString && _jsx(ErrorMessage, { ...errorProps, name: name })] }));
31
+ return (_jsxs(Wrapper, { ...mergedWrapperProps, children: [_jsxs(TitleInfoWrapper, { children: [title && (_jsxs(Title, { ...titleProps, htmlFor: name, children: [title, props?.required && _jsx(RequiredIndicator, {})] })), info && _jsx(Info, { ...info })] }), description && (_jsx(Description, { ...descriptionProps, children: description })), items && items.map((item, index) => renderItem(item, index)), help && _jsx(Help, { ...helpProps, children: help }), errorIsString && _jsx(ErrorMessage, { ...errorProps, name: name })] }));
32
32
  };
@@ -1,3 +1,4 @@
1
+ export const ArrayFieldTitleInfoWrapper = undefined;
1
2
  export const ArrayFieldTemplateWrapper = undefined;
2
3
  export const ArrayFieldTemplateIcon = undefined;
3
4
  export const ArrayFieldTemplateTitle = undefined;
@@ -10,6 +11,8 @@ export function getComponents(components) {
10
11
  return {
11
12
  Wrapper: components.ArrayFieldTemplateWrapper ??
12
13
  components.ObjectFieldTemplateWrapper,
14
+ TitleInfoWrapper: components.ArrayFieldTitleInfoWrapper ??
15
+ components.ObjectFieldTitleInfoWrapper,
13
16
  Title: components.ArrayFieldTemplateTitle ?? components.ObjectFieldTemplateTitle,
14
17
  Description: components.ArrayFieldTemplateDescription ?? components.FieldDescription,
15
18
  Help: components.ArrayFieldTemplateHelp ?? components.FieldHelp,
@@ -6,7 +6,7 @@ import { FormRegistry } from "../../FormRegistry";
6
6
  import { getComponents } from "./styledComponents";
7
7
  export const CollapsibleObjectFieldTemplate = (props) => {
8
8
  const { components } = useContext(FormRegistry);
9
- const { Toggle, ChildrenWrapper, RequiredIndicator, Icon, Description, Title, Wrapper, Help, Info, } = getComponents(components);
9
+ const { Toggle, ChildrenWrapper, RequiredIndicator, Icon, Description, Title, TitleInfoWrapper, Wrapper, Help, Info, } = getComponents(components);
10
10
  const { children, name, uiSchema, ...otherProps } = props;
11
11
  const formikCtx = useFormikContext();
12
12
  const values = formikCtx.values
@@ -31,7 +31,7 @@ export const CollapsibleObjectFieldTemplate = (props) => {
31
31
  };
32
32
  const [collapsed, setCollapsed] = useState(isCollapsedOnLoad);
33
33
  const hide = collapsed;
34
- return (_jsxs(Wrapper, { ...mergedWrapperProps, children: [title && (_jsx(Toggle, { onClick: () => setCollapsed(!collapsed),
35
- //ariaExpanded={!hide}
36
- ariaLabel: ariaLabel ?? name, children: _jsxs(Title, { ...titleProps, htmlFor: name, children: [title, props?.required && _jsx(RequiredIndicator, {}), _jsx(Icon, { children: hide ? collapsedIcon ?? "▸" : openIcon ?? "▾" })] }) })), info && _jsx(Info, { ...info }), description && (_jsx(Description, { ...descriptionProps, children: description })), !hide && _jsx(ChildrenWrapper, { children: children }), help && _jsx(Help, { ...helpProps, children: help })] }));
34
+ return (_jsxs(Wrapper, { ...mergedWrapperProps, children: [_jsxs(TitleInfoWrapper, { children: [title && (_jsx(Toggle, { onClick: () => setCollapsed(!collapsed),
35
+ //ariaExpanded={!hide}
36
+ ariaLabel: ariaLabel ?? name, children: _jsxs(Title, { ...titleProps, htmlFor: name, children: [title, props?.required && _jsx(RequiredIndicator, {}), _jsx(Icon, { children: hide ? collapsedIcon ?? "▸" : openIcon ?? "▾" })] }) })), info && _jsx(Info, { ...info })] }), description && (_jsx(Description, { ...descriptionProps, children: description })), !hide && _jsx(ChildrenWrapper, { children: children }), help && _jsx(Help, { ...helpProps, children: help })] }));
37
37
  };
@@ -2,6 +2,7 @@ import { styled } from "styled-components";
2
2
  import { ObjectFieldTemplateTitle, } from "../ObjectFieldTemplate/styledComponents";
3
3
  import { Button } from "@nolwenture/component-library";
4
4
  export const CollapsibleObjectFieldTemplateWrapper = undefined;
5
+ export const CollapsibleObjectTitleInfoWrapper = undefined;
5
6
  export const CollapsibleObjectFieldTemplateIcon = undefined;
6
7
  export const CollapsibleObjectFieldTemplateTitle = styled(ObjectFieldTemplateTitle) `
7
8
  display: flex;
@@ -23,6 +24,8 @@ export function getComponents(components) {
23
24
  return {
24
25
  Wrapper: components.CollapsibleObjectFieldTemplateWrapper ??
25
26
  components.ObjectFieldTemplateWrapper,
27
+ TitleInfoWrapper: components.CollapsibleObjectTitleInfoWrapper ??
28
+ components.ObjectFieldTitleInfoWrapper,
26
29
  Icon: components.CollapsibleObjectFieldTemplateIcon ?? components.Icon,
27
30
  Title: components.CollapsibleObjectFieldTemplateTitle ??
28
31
  components.ObjectFieldTemplateTitle,
@@ -3,11 +3,12 @@ import { useContext, useMemo } from "react";
3
3
  import { extractUiSchema, getDescription, getTitle } from "../../../utils";
4
4
  import { FormRegistry } from "../../FormRegistry";
5
5
  export const FieldTemplate = (props) => {
6
- const { components: { FieldWrapper, FieldTitle, FieldDescription, ErrorMessage, FieldHelp, RequiredIndicator, FieldInfo, }, } = useContext(FormRegistry);
6
+ const { components: { FieldWrapper, FieldTitleInfoWrapper, FieldTitle, FieldDescription, ErrorMessage, FieldHelp, RequiredIndicator, FieldInfo, }, } = useContext(FormRegistry);
7
7
  const { name, uiSchema, children, ...otherProps } = props;
8
8
  const title = getTitle(props);
9
9
  const description = getDescription(props);
10
- const { help, info, props: { wrapper: wrapperProps = {}, title: titleProps, description: descriptionProps, help: helpProps, error: errorProps, } = {}, } = useMemo(() => extractUiSchema(uiSchema), [uiSchema]);
10
+ const { help, info, disabled, props: { wrapper: wrapperProps = {}, title: titleProps, description: descriptionProps, help: helpProps, error: errorProps, disabled: isDisabled, } = {}, } = useMemo(() => extractUiSchema(uiSchema), [uiSchema]);
11
+ const isReadOnly = props.schema?.readOnly;
11
12
  const dataAttributes = Object.keys(otherProps)
12
13
  .filter((key) => key.startsWith("data-"))
13
14
  .reduce((acc, key) => {
@@ -19,5 +20,5 @@ export const FieldTemplate = (props) => {
19
20
  ...wrapperProps,
20
21
  ...dataAttributes, // This will only include data-* attributes
21
22
  };
22
- return (_jsxs(FieldWrapper, { ...mergedWrapperProps, children: [title && (_jsxs(FieldTitle, { ...titleProps, htmlFor: name, children: [title, props.required && _jsx(RequiredIndicator, {})] })), info && _jsx(FieldInfo, { ...info }), description && (_jsx(FieldDescription, { ...descriptionProps, children: description })), children, help && _jsx(FieldHelp, { ...helpProps, children: help }), _jsx(ErrorMessage, { ...errorProps, name: name })] }));
23
+ return (_jsxs(FieldWrapper, { ...mergedWrapperProps, "$isDisabled": isDisabled, children: [_jsxs(FieldTitleInfoWrapper, { children: [title && (_jsxs(FieldTitle, { ...titleProps, htmlFor: name, children: [title, props.required && _jsx(RequiredIndicator, {})] })), info && _jsx(FieldInfo, { ...info })] }), description && (_jsx(FieldDescription, { ...descriptionProps, children: description })), children, help && _jsx(FieldHelp, { ...helpProps, children: help }), _jsx(ErrorMessage, { ...errorProps, name: name })] }));
23
24
  };
@@ -5,7 +5,7 @@ import { FormRegistry } from "../../FormRegistry";
5
5
  import { getComponents } from "./styledComponents";
6
6
  export const ObjectFieldTemplate = (props) => {
7
7
  const { components } = useContext(FormRegistry);
8
- const { Wrapper, Title, Description, Help, Info, RequiredIndicator, ErrorMessage, } = getComponents(components);
8
+ const { Wrapper, Title, TitleInfoWrapper, Description, Help, Info, RequiredIndicator, ErrorMessage, } = getComponents(components);
9
9
  const { children, uiSchema, ...otherProps } = props;
10
10
  const title = getTitle(props);
11
11
  const description = getDescription(props);
@@ -24,5 +24,5 @@ export const ObjectFieldTemplate = (props) => {
24
24
  ...wrapperProps,
25
25
  ...dataAttributes,
26
26
  };
27
- return (_jsxs(Wrapper, { ...mergedWrapperProps, children: [title && (_jsxs(Title, { ...titleProps, children: [title, props?.required && _jsx(RequiredIndicator, {})] })), info && _jsx(Info, { ...info }), description && (_jsx(Description, { ...descriptionProps, children: description })), children, help && _jsx(Help, { ...helpProps, children: help })] }));
27
+ return (_jsxs(Wrapper, { ...mergedWrapperProps, children: [_jsxs(TitleInfoWrapper, { children: [title && (_jsxs(Title, { ...titleProps, children: [title, props?.required && _jsx(RequiredIndicator, {})] })), info && _jsx(Info, { ...info })] }), description && (_jsx(Description, { ...descriptionProps, children: description })), children, help && _jsx(Help, { ...helpProps, children: help })] }));
28
28
  };
@@ -1,15 +1,35 @@
1
+ import { lighten } from "polished";
1
2
  import { styled } from "styled-components";
2
3
  export const ObjectFieldTemplateWrapper = styled.fieldset `
4
+ display: flex;
5
+ flex-direction: column;
3
6
  color: ${(props) => props.theme.color.text.default};
4
7
  font-family: ${(props) => props.theme.typography.fontFamily.base};
5
8
  margin-inline: 0;
6
9
  margin-bottom: ${(props) => props.theme.spacing.xs};
7
10
 
11
+ &:has(input[disabled]), &:has(option[disabled]), &:has(select[disabled]), &:has(textarea[disabled]) {
12
+ border-color: ${(props) => lighten(0.4, props.theme.color.border.default)};
13
+
14
+ legend {
15
+ color: ${(props) => lighten(0.4, props.theme.color.text.default)};
16
+
17
+ & + p {
18
+ color: ${(props) => lighten(0.4, props.theme.color.text.default)};
19
+ }
20
+ }
21
+ }
22
+
8
23
  `;
9
24
  export const ObjectFieldTemplateTitle = styled.legend `
10
25
  color: ${(props) => props.theme.color.text.default};
11
26
  font-family: ${(props) => props.theme.typography.fontFamily.base};
12
27
  `;
28
+ export const ObjectFieldTitleInfoWrapper = styled.div `
29
+ display: flex;
30
+ flex-direction: row;
31
+ flex-wrap: wrap;
32
+ `;
13
33
  export const ObjectFieldTemplateDescription = undefined;
14
34
  export const ObjectFieldTemplateHelp = undefined;
15
35
  export const ObjectFieldTemplateInfo = undefined;
@@ -19,6 +39,7 @@ export function getComponents(components) {
19
39
  return {
20
40
  Wrapper: components.ObjectFieldTemplateWrapper,
21
41
  Title: components.ObjectFieldTemplateTitle,
42
+ TitleInfoWrapper: components.ObjectFieldTitleInfoWrapper,
22
43
  Description: components.ObjectFieldTemplateDescription ?? components.FieldDescription,
23
44
  Help: components.ObjectFieldTemplateHelp ?? components.FieldHelp,
24
45
  Info: components.ObjectFieldTemplateInfo ?? components.FieldInfo,
@@ -11,7 +11,7 @@ export const MultipleChoiceField = (props) => {
11
11
  const { values } = useFormikContext();
12
12
  const value = getIn(values, name);
13
13
  const selected = getSelectedEnum(value, enums);
14
- const notSelected = enums?.values?.filter((v) => Array.isArray(value) && !value.includes(v));
14
+ const notSelected = enums?.values?.filter((v) => Array.isArray(value) && !value.includes(v.const));
15
15
  const hideNotSelected = onlyShowSelected === true || selected === undefined;
16
16
  const SelectedFieldTemplate = (props.uiSchema?.["ui:template"] &&
17
17
  templates[props.uiSchema?.["ui:template"]]) ??
@@ -3,6 +3,8 @@ import { FieldInfoBoxElementProps, FieldInfoProps } from "../../common/types/Fie
3
3
  export declare const FieldInfoBoxElement: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components/dist/types").Substitute<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, FieldInfoBoxElementProps>> & string;
4
4
  export declare const FieldInfoBoxArrowElement: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components/dist/types").Substitute<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, FieldInfoBoxElementProps>> & string;
5
5
  export declare const FieldInfoBoxInnerElement: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, never>> & string;
6
+ export declare const InlineFieldInfoBoxInnerElement: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, never>> & string;
6
7
  export declare const FieldInfoContainer: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>, never>> & string;
7
8
  export declare const FieldInfoLabel: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLSpanElement>, HTMLSpanElement>, never>> & string;
9
+ export declare const InlineFieldInfoWrapper: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, never>> & string;
8
10
  export declare const FieldInfo: React.FC<FieldInfoProps>;
@@ -1,6 +1,9 @@
1
1
  import React from "react";
2
2
  import * as formik from "formik";
3
- export declare const FieldWrapper: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, never>> & string;
3
+ export declare const FieldWrapper: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components/dist/types").Substitute<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, {
4
+ $isDisabled?: boolean;
5
+ }>> & string;
6
+ export declare const FieldTitleInfoWrapper: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement>, never>> & string;
4
7
  export declare const FieldTitle: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.LabelHTMLAttributes<HTMLLabelElement>, HTMLLabelElement>, never>> & string;
5
8
  export declare const FieldDescription: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLParagraphElement>, HTMLParagraphElement>, never>> & string;
6
9
  export declare const FieldHelp: import("styled-components/dist/types").IStyledComponentBase<"web", import("styled-components").FastOmit<React.DetailedHTMLProps<React.HTMLAttributes<HTMLParagraphElement>, HTMLParagraphElement>, never>> & string;