Skip to content

Commit 2cae601

Browse files
authored
Improvements (#82)
* Changed div to a generic container with prop "as" that can use a custom tag instead of default "div" * Div exists now, but may be removed in the future in favour of the new Html component * Html component should be used from now on * Added new field renderer "inner-text" that shows value set in the values object or default value. * Used for general HTML text instead of a specific field * For read-only values * Fixed incorrect export * Added prop "wrapAs" to define a wrapper or set React.Fragement when "wrapAs" is null * Wrapper doesn't need to be 'div' everytime * Setting null removes the wrapper entirely * Avoid passing "wrapAs" to the field and thus avoid triggering invalid dom attribute attribute * Added bootstrap input-group demo
2 parents f0de89a + 16feaa2 commit 2cae601

File tree

9 files changed

+114
-26
lines changed

9 files changed

+114
-26
lines changed

demo/src/schema/all-available-fields.js

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,58 @@ export default {
2828
fieldType: "text",
2929
comment: "This is a field comment. You can add your text here."
3030
},
31+
inputGroup: {
32+
type: 'container',
33+
renderer: 'div',
34+
htmlClass: 'input-group',
35+
elements: {
36+
prepend: {
37+
type: 'container',
38+
renderer: 'div',
39+
htmlClass: 'input-group-prepend',
40+
elements: {
41+
innerText: {
42+
type: 'field',
43+
renderer: 'inner-text',
44+
name: 'prependInnerText',
45+
htmlClass: 'input-group-text',
46+
defaultValue: '@',
47+
wrapAs: null
48+
}
49+
}
50+
},
51+
text: {
52+
name: "text",
53+
type: "field",
54+
renderer: "text",
55+
fieldType: "text",
56+
wrapAs: null
57+
},
58+
append: {
59+
type: 'container',
60+
renderer: 'div',
61+
htmlClass: 'input-group-append',
62+
elements: {
63+
innerText: {
64+
type: 'field',
65+
renderer: 'inner-text',
66+
name: 'appendInnerText',
67+
htmlClass: 'input-group-text',
68+
defaultValue: 'pixels',
69+
wrapAs: null
70+
}
71+
}
72+
}
73+
}
74+
},
75+
innerText: {
76+
type: 'field',
77+
renderer: 'inner-text',
78+
name: 'innerText',
79+
as: 'small',
80+
htmlClass: 'text-muted d-block mb-3 mt-1',
81+
defaultValue: 'This is a field comment. You can add your text here'
82+
},
3183
autocomplete: {
3284
name: "autocomplete",
3385
label: "Autocomplete",

package-lock.json

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@flipbyte/formik-json",
3-
"version": "0.4.8",
3+
"version": "0.5.0",
44
"description": "formik-json is a wrapper for Formik to easily create forms using JSON / Javascript Object for defining the elements",
55
"main": "lib/index.js",
66
"module": "es/index.js",
Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,26 +4,33 @@ import Element from '../Element';
44
import PropTypes from 'prop-types';
55
import { joinNames } from '../utils';
66

7-
const Div = ({
8-
config: { name: containerName = '', elements, htmlClass, comment, commentClass = 'text-muted d-block mb-3' }
7+
const HtmlTag = ({
8+
config: {
9+
name: containerName = '',
10+
as: Component = 'div',
11+
elements,
12+
htmlClass,
13+
comment,
14+
commentClass = 'text-muted d-block mb-3'
15+
}
916
}) => (
10-
<div className={ htmlClass }>
17+
<Component className={ htmlClass }>
1118
{ comment && <small className={ commentClass }>{ comment }</small> }
1219
{ _.map(elements, ({ name, ...rest }, key) => (
1320
<Element
1421
key={ key }
1522
config={{ ...rest, name: joinNames(containerName, name) }}
1623
/>
1724
))}
18-
</div>
25+
</Component>
1926
);
2027

21-
Div.propTypes = {
28+
HtmlTag.propTypes = {
2229
config: PropTypes.shape({
2330
name: PropTypes.string,
2431
elements: PropTypes.object.isRequired,
2532
htmlClass: PropTypes.string
2633
})
2734
}
2835

29-
export default Div;
36+
export default HtmlTag;

src/Container/index.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,14 @@
11
import { registerContainer } from '../registry';
22

3-
import Div from './Div';
3+
import HtmlTag from './HtmlTag';
44
import Form from './Form';
55
import Tabs from './Tabs';
66
import Fieldset from './Fieldset';
77
import ButtonGroup from './ButtonGroup';
88
import EditableGrid from './EditableGrid';
99

10-
registerContainer('div', Div);
10+
registerContainer('div', HtmlTag);
11+
registerContainer('html-tag', HtmlTag);
1112
registerContainer('form', Form);
1213
registerContainer('tabs', Tabs);
1314
registerContainer('fieldset', Fieldset);

src/Field/InnerText.js

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
import React from 'react';
2+
3+
const InnerText = ({ config, formik, value, error }) => {
4+
const {
5+
name,
6+
as: Component = 'span',
7+
htmlClass,
8+
defaultValue = '',
9+
...attributes
10+
} = config;
11+
12+
return (
13+
<Component className={ htmlClass } { ...attributes }>
14+
{ value || defaultValue }
15+
</Component>
16+
);
17+
};
18+
19+
export default React.memo(InnerText);

src/Field/index.js

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import Switch from './Switch';
77
import Wysiwyg from './Wysiwyg';
88
import Textarea from './Textarea';
99
import Checkbox from './Checkbox';
10+
import InnerText from './InnerText';
1011
import CodeEditor from './CodeEditor';
1112
import ReactSelect from './ReactSelect';
1213
import FileUploader from './FileUploader';
@@ -27,6 +28,7 @@ registerField('switch', Switch);
2728
registerField('wysiwyg', Wysiwyg);
2829
registerField('textarea', Textarea);
2930
registerField('checkbox', Checkbox);
31+
registerField('inner-text', InnerText);
3032
registerField('code-editor', CodeEditor);
3133
registerField('react-select', ReactSelect);
3234
registerField('autocomplete', Autocomplete);

src/Renderer.js

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,12 @@ import ErrorManager from './ErrorManager';
1313
* @param {object} props
1414
* @return {Component}
1515
*/
16-
const renderElement = ( props ) => {
17-
const {
18-
config: { type, renderer }
19-
} = props;
16+
const renderElement = ({ config, formik, value, error }) => {
17+
const { type, renderer, wrapAs, ...rest } = config;
2018
const registry = type === FIELD ? fields : containers;
2119
const Renderer = typeof renderer === 'string' ? registry.get(renderer) : renderer;
2220

23-
return <Renderer { ...props } />
21+
return <Renderer config={{ type, ...rest }} formik={ formik } value={ value } error={ error } />
2422
}
2523

2624
/**
@@ -44,7 +42,7 @@ const ElementRenderer = ({
4442
name,
4543
showWhen,
4644
enabledWhen,
47-
template,
45+
template
4846
} = config;
4947
const { values } = formik;
5048
const [ canShow, setCanShow ] = useState(showWhen ? false : true);

src/Template/Default.js

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import React from 'react';
1+
import React, { Fragment } from 'react';
22
import Label from '../Field/Label';
33
import ErrorMessage from '../Field/ErrorMessage';
44

@@ -11,16 +11,25 @@ const Default = ({
1111
comment,
1212
error,
1313
labelClass = '',
14-
formGroupClass = 'form-group',
14+
wrapAs = 'div',
15+
htmlClass = 'form-group',
1516
commentClass = 'text-muted',
1617
children
17-
}) => (
18-
<div className={ formGroupClass } style={ styles(disabled) }>
19-
{ label && <Label htmlFor={ name } className={ labelClass }>{ label }</Label> }
20-
{ children }
21-
{ comment && <small className={ commentClass }>{ comment }</small> }
22-
<ErrorMessage name={ name } error={ error } />
23-
</div>
24-
);
18+
}) => {
19+
const Component = !wrapAs ? Fragment : wrapAs;
20+
const componentProps = !wrapAs ? {} : {
21+
className: htmlClass,
22+
style: styles(disabled)
23+
};
24+
25+
return (
26+
<Component { ...componentProps }>
27+
{ label && <Label htmlFor={ name } className={ labelClass }>{ label }</Label> }
28+
{ children }
29+
{ comment && <small className={ commentClass }>{ comment }</small> }
30+
<ErrorMessage name={ name } error={ error } />
31+
</Component>
32+
);
33+
};
2534

2635
export default Default;

0 commit comments

Comments
 (0)