About Sencha Touch Form Field Validation…

One of the questions that comes up fairly often during my Sencha Touch instructor-led classes is how to visually highlight form fields that contain invalid input or require some form of data entry:

requiredfields

Unlike Ext-JS, which contains very strong form field validation options, Sencha Touch prefers that you to validate input by transferring data from a from into a data model and then calling the model.validate() method as illustrated below:

A sample model that contains two validation rules for each field:

Ext.define('MyApp.model.Person', {
    extend: 'Ext.data.Model',
    config: {
        fields: ['fname','lname'],
        validations: [
            { type: 'presence', field: 'fname' },
            { type: 'presence', field: 'lname' },
            { type: 'length', field: 'fname', max: 20 },
            { type: 'length', field: 'lname', max: 20 }
        ]
    }
});

And here’s a sample data entry form to go along with it:

Ext.define('MyApp.view.Demo', {
 extend: 'Ext.form.Panel',
 config: {
  fieldDefaults: {
   labelWidth: 80
  },
  items: [
   {
    xtype: 'titlebar',
    docked: 'top',
    title: 'Form Validation Example'
   },
   {
    xtype: 'fieldset',
    title: 'Enter Your Name',
    items: [
      {
        xtype: 'textfield',
        label: 'First Name',
        name: 'fname',
        required: true
      },
      {
        xtype: 'textfield',
        label: 'Last Name',
        name: 'lname',
        required: true
      }
    ]
   },
   {
     xtype: 'toolbar',
     docked: 'bottom',
     layout: {
        pack: 'center',
        type: 'hbox'
     },
     items: [
       {
        xtype: 'button',
        handler: function(button, event) {
          /* validate fields here */
        }
        text: 'Submit'
       }
     ]
   }
 ]
 }
});

Validating the data requires you to transfer the data from the form into a model instance, call model.validate() and then generate a response to the user as illustrated below:

{
  xtype: 'button',
  handler: function(button,event) {
     var errorString = '',
         form = button.up('formpanel'),
         fields = form.query("field");

     // dump form fields into new model instance
     var model = Ext.create("MyApp.model.Person", form.getValues());

     // validate form fields
     var errors = model.validate();

     if (!errors.isValid()) {
      // loop through validation errors and generate a message to the user
      errors.each(function (errorObj){
        errorString += errorObj.getField() + " " + errorObj.getMessage() + "
";
        var s = Ext.String.format('field[name={0}]',errorObj.getField());
        form.down(s).addCls('invalidField');
      });
      Ext.Msg.alert('Errors in your input',errorString);
     } else {
      Ext.Msg.alert("Data is valid","Success");
     }
  },
  text: 'Submit'
}

But what if you wanted to actually highlight the invalid fields by changing their background color? Well, it turns out this is actually quite simple — just programmatically add/remove a CSS style class!

Here’s a sample CSS file:


// file: resources/css/extra.css

.invalidField .x-form-field {
  background-color: red !important;
}

And here’s the modification to our submit handler code that adds and removes the CSS class from the controls:

{
 xtype: 'button',
 handler: function(button, event) {
   var errorString = '',
       form = button.up('formpanel'),
       fields = form.query("field");

   // remove the style class from all fields
   for (var i=0; i<fields.length; i++) {
       fields[i].removeCls('invalidField');
   }

   var model = Ext.create("MyApp.model.Person", form.getValues());

   var errors = model.validate();

   if (!errors.isValid()) {
      errors.each(function (errorObj){
        errorString += errorObj.getField() + " " + errorObj.getMessage() + "
";

        // build a string to select the appropriate field
        var s = Ext.String.format('field[name={0}]',errorObj.getField());

        // apply the style class
        form.down(s).addCls('invalidField');
      });
      Ext.Msg.alert('Errors in your input',errorString);
   } else {
      Ext.Msg.alert("Data is valid","Success");
   }
 },
 text: 'Submit'
}

So what are you waiting for?

3 thoughts on “About Sencha Touch Form Field Validation…

  1. Wouter Vos

    The class does not get added for me.

    var totalField = lines[i].down(‘textfield[name=amountTotal]’);
    totalField.addCls(‘invalidField’);

    After this the class is still missing. And of course the red background does not work either.

    Reply

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s