Form
In this example, we use UIKernel.Form
to create a simple form for editing grid records.
To initialize a form, we use initForm
function and pass it a settings object with fields
and model
props as an argument.
A settings object can also have other props .
To update field values, you can use either updateField
or validateField
.
validateField
not only updates a field, but also validates it.
getValidationError
returns validation errors for a specific field.
getData
returns form data.
submit
is used to submit a form.
FormComponent.js
class Form extends React . Component {
constructor ( props ) {
super ( props );
this . form = new UIKernel . Form ();
this . onFormChange = this . onFormChange . bind ( this );
}
componentDidMount () {
this . form . init ({
fields : [ 'name' , 'age' ], // Fields we need
model : new UIKernel . Adapters . Grid . ToFormUpdate ( model , 2 ), // We're going to change record with ID = 2
});
this . form . addChangeListener ( this . onFormChange );
}
componentWillUnmount () {
this . form . removeChangeListener ( this . onFormChange );
}
onFormChange ( newFormState ) {
if ( ! _ . isEqual ( this . props . state . fields , newFormState . fields )) {
this . form . submit ()
. catch (( err ) => {
if ( err && ! ( err instanceof UIKernel . ValidationErrors )) { // If error is not a validation one
alert ( 'Error' );
}
});
}
this . props . onChange ( newFormState );
}
render () {
if ( ! this . props . state . isLoaded ) {
return < span > Loading ... < /span> ;
}
return (
< div className = "form" >
< div className = "header panel-heading" >
< h4 className = "title" > Edit record number 2 < /h4 >
< /div >
< div className = "body" >
< form className = "form-horizontal change-second-field-form" >
< div className = { 'form-group' + ( this . props . state . fields . name . errors ? ' error' : '' )} >
< label className = "col-sm-2 control-label" > Name < /label >
< div className = "col-sm-6" >
< input
type = "text"
className = "form-control"
onChange = { this . form . updateField . bind ( this . form , 'name' )}
value = { this . props . state . fields . name . value }
/ >
< /div >
< div className = "col-sm-3" >
< div className = "validation-error" > { this . props . state . fields . name . errors } < /div >
< /div >
< /div >
< div className = { 'form-group' + ( this . props . state . fields . age . errors ? ' error' : '' )} >
< label className = "col-sm-2 control-label" > Age < /label >
< div className = "col-sm-6" >
{ /* we use UIKernel.Editors.Number instead of <input type =" number "/> */ }
{ /* because UIKernel.Editors.Number returns a numeric value instead of a string. */ }
< UIKernel . Editors . Number
className = "form-control"
onChange = { this . form . updateField . bind ( this . form , 'age' )}
value = { this . props . state . fields . age . value }
/ >
< /div >
< div className = "col-sm-3" >
< div className = "validation-error" > { this . props . state . fields . age . errors } < /div >
< /div >
< /div >
< /form >
< /div >
< /div >
);
}
}
We use UIKernel.createValidator
to create a validator and call field
function to define validation rules for our form.
validation.js
const Validator = UIKernel . createValidator ()
. field ( 'name' , UIKernel . Validators . regExp . notNull ( /^ \w{2,30} $/ , 'Invalid first name.' ))
. field ( 'age' , UIKernel . Validators . number . notNull ( 15 , 90 , 'Age must be between 15 and 90' ));
We pass validation to the grid model.
model.js
const model = new UIKernel . Models . Grid . Collection ({
data : [
[ 1 , { 'id' : 1 , 'name' : 'Stacey' , 'age' : 22 }],
[ 2 , { 'id' : 2 , 'name' : 'Adam' , 'age' : 43 }],
[ 3 , { 'id' : 3 , 'name' : 'Deanna' , 'age' : 21 }]
],
validator
});
columns.js
const columns = {
id : {
name : 'ID' ,
width : '40' ,
sortCycle : [ 'asc' , 'desc' ],
editor : function () {
return < input type = "text" {... this . props } /> ;
},
render : [ 'id' , record => record . id ]
},
name : {
name : 'Name' , // columns title
sortCycle : [ 'asc' , 'desc' , 'default' ], // sort cycle
editor : function () {
return < input type = "text" {... this . props } /> ;
},
render : [ 'name' , record => record . name ]
},
age : {
name : 'Age' ,
sortCycle : [ 'asc' , 'desc' , 'default' ],
editor : function () {
return < input type = "text" {... this . props } /> ;
},
render : [ 'age' , record => record . age ]
}
};
MainComponent.js
class MainComponent extends React . Component {
constructor ( props ) {
super ( props );
this . state = {
form : {}
};
this . updateFormState = this . updateFormState . bind ( this );
}
updateFormState ( newFormState ) {
this . setState ({ form : newFormState });
}
render () {
return (
< div className = "container" >
< div className = "row" >
< div className = "col-sm-12" >
< div className = "panel panel-info" >
< div className = "panel-heading" >
< h3 className = "panel-title" > Records < /h3 >
< /div >
< div className = "panel-body padding0" >
< UIKernel . Grid
ref = {( grid ) => this . grid = grid }
model = { model }
cols = { columns }
autoSubmit = { true }
/ >
< Form
state = { this . state . form }
onChange = { this . updateFormState }
/ >
< /div >
< /div >
< /div >
< /div >
< /div >
);
}
}
main.js
:
React . render ( < MainComponent /> , document . getElementById ( "example" ));