So that I don't have to write a component for every single redux-form
.
-
Accept a
schema
prop to generate form. Not json schema but a self-invented one. :P -
The state of the form is mained by
redux-form
inredux
state. -
Predefined material-ui widget components so you don't have to write in every form.
- number
- text
- password
- date
- file
- checkbox
- select
- autocomplete
- autocomplete-async
- autocomplete-text
- array
- group
-
Also has a set of ant-design theme widgets.
-
You can add more widgets using
addType
.
//remember this component is just a wrapper around [redux-form](), so you have to add redux-form's reducer to make it work!
import {ReduxSchemaForm} from "redux-schema-form"
import "redux-schema-form/src/material"
const schema=[
{
key:"name",
label:"Company Name",
type:"text",
...others// other props are passed to underlying component, such as required and multiLine
},{
key:"password",
label:"Password"
type:"password"
}
]
function Form(){
return <ReduxSchemaForm
form="my-form"
schema={schema}
{...others}
/>
}
Material-ui's keyboard navigation is badly written, so it may not be suitable for forms with lots of fields.
All props are passed to the underlying redux-form
instance, except these props:
Form become not submittable if submit succeeded.
Hide submit and cancel buttons.
Children will be placed between form fields and buttons.
Accepts an array of type FormFieldSchema[]
:
import {ConfigProps} from "redux-form"
export type Options = {name:string,value:string|number}[]
export type AsyncOptions = ()=>Promise<Options>
export type RuntimeAsyncOptions = (value:any)=>(Promise<Options>|Options)
export type ChangeOfSchema = (Partial<FormFieldSchema>&{key:string})[];
export interface FormFieldSchema extends Partial<ConfigProps<any,any>>{
key:string,
type: string,
label:string,
hide?:boolean,
placeholder?:string,
required?:boolean,
disabled?:boolean,
multiple?:boolean,
children?:FormFieldSchema[]
options?:Options | AsyncOptions | RuntimeAsyncOptions,
sideEffect?:(newValue:any,previousValue?:any,formValue?:any)=>ChangeOfSchema|Promise<ChangeOfSchema>,
getChildren?:((childValue:any)=>FormFieldSchema[])
[reduxFormFieldProps:string]:any
[materialUIComponentProps:string]:any
/**
* other props are passes to the underlying Field component, which can be any valid redux-form Field props, e.g. validate, normalize, ...;
* if it is not a valid redux-form prop, it will passed to the underlying widget component, for example, you can add multiLine:true if the type of this field is 'text', which is a prop of material-ui's TextField component.
*/
}
-
key The key of the field in the data, e.g. 'email'
-
label The displayed name of this field. e.g. 'Your Email:'
-
type The type of this field. e.g. 'select' or "text" or "email"
-
options Only meaningful if the type is "select" or "autocomplete-xxx", it must be an array of the type {name:string,value:any}, it defines the options of the selection component.
-
placeholder The hint text.
-
required As the name suggest.
-
disabled As the name suggest.
-
children Only meaningful if the type is "group" or "array". The resulted date will have an object as a property value. e.g.
const schema = [
{
key:"g",
type:"group",
label:"group",
children:[
{
key:"name",
type:"text",
label:"Name"
}
]
}
]
//The value passed to onSubmit will be like: {g:{name:"john"}}
- sideEffect
Called when the value of this field is changed or initialized. If it returns anything, it should be an array of type Partial<FormFieldSchema>[]
, which will merged into existing schema
using the key
field.
- getChildren
Only meaningful if the type is "array", to provide a way to have dynamic children form per child specific. It will be called with the value of a child of the array field, and should return a FormFieldSchema[]
as the child form of this child. e.g.
const schema = [
{
key:"g",
type:"array",
label:"array",
getChildren:value=>[
{
key:"name",
type:"text",
label:value
}
]
}
]
//The label of the array child will be the same as its value.
- others
All other fields in
FormFieldSchema
are passed to the underlyingredux-form
'sField
component. See their docs.