In this post, we will learn How to use Forms in AngularJS to take user input, validate it, send to server or process it. We will make a complete AngularJS CRUD application. You will get insight into several AngularJS built-in directives used in day-to-day usage. We will start from ground zero and will build upon peace by peace. By the end of this post, you will be able to make your own Stunning AngularJS Forms for your application.
Just to show, Our final form [An AngularJS CRUD application] will look like this. Don’t worry. We will start from scratch and will build up step by step while learning the deep details.
This very first example shows a really simple form without any validation or styling. It is intentional because our goal is to first understand some basics of form handling in AngularJS here. Later in this post, we will make some exotic forms with validation, error handling and styling with bootstrap.
<html ng-app="myApp"> <head> <title>Form Demo</title> <style>body{font-family:"Arial";background-color:#E2E2DC}</style> </head> <body ng-controller="AppController as ctrl"> <form ng-submit="ctrl.submit()"> <input type="text" ng-model="ctrl.user.username" placeholder="Enter your name"/><br/><br/> <input type="text" ng-model="ctrl.user.address" placeholder="Enter your Address"/><br/><br/> <input type="text" ng-model="ctrl.user.email" placeholder="Enter your Email"/><br/><br/> <input type="submit" value="Submit"> </form> <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.4/angular.js"> </script> <script> angular.module('myApp', []) .controller('AppController', [function() { var self = this; self.submit = function() { console.log('Form is submitted with following user', self.user); }; }]); </script> </body> </html>
This form takes user input and simply logs user in console. Check your browser console output to see the result.
Main Highlights
In this simplistic example, 3 text field and a button is wrapped inside a form.
ng-model
, AngularJS automatically creates the objects and it’s properties on the fly if it does not exist. In this case, until the user types something into the username or any other field, there is no user object. As the user types in the first letter, it causes the user object to be created, and the typed-in value to be assigned to the respective field.ng-submit
directive on form here instead of using ng-click on submit button. This is because a form can be submitted by clicking the Submit button, or hitting Enter on a text field. The ng-submit gets triggered on all those events, whereas the ng-click will only be triggered when the user clicks the button.This example is build upon previous example, and shows how to show validation error message to user to inform what went wrong.
In order to take advantage of AngularJS’s form bindings to be able to fetch errors for individual field, we can use name attribute on that field and on form. When we add a name to any input field, it creates a model on the form for that particular input, with the error state.
<html ng-app="myApp"> <head> <title>Form Demo</title> <style>body{font-family:"Arial";background-color:#E2E2DC}</style> </head> <body ng-controller="AppController as ctrl"> <form ng-submit="ctrl.submit()" name="myForm"> <input type="text" ng-model="ctrl.user.username" name="uname" placeholder="Enter your name" required ng-minlength="3"/> <span ng-show="myForm.$dirty && myForm.uname.$error.required">This is a required field</span> <span ng-show="myForm.$dirty && myForm.uname.$error.minlength">Minimum length required is 4</span> <span ng-show="myForm.$dirty && myForm.uname.$invalid">This field is invalid </span><br/><br/> <input type="text" ng-model="ctrl.user.address" placeholder="Enter your Address"/><br/><br/> <input type="email" ng-model="ctrl.user.email" name="email" placeholder="Enter your Email" required/> <span ng-show="myForm.$dirty && myForm.email.$error.required">This is a required field</span> <span ng-show="myForm.$dirty && myForm.email.$invalid">This field is invalid </span><br/><br/> <input type="submit" value="Submit" ng-disabled="myForm.$invalid"> </form> <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.4/angular.js"> </script> <script> angular.module('myApp', []) .controller('AppController', [function() { var self = this; self.submit = function() { console.log('Form is submitted with following user', self.user); }; }]); </script> </body> </html>
Again, Check your browser console output to see the result.
Main Highlights
We have included some error messages on individual field level.
name
attribute. For instance, we don’t want address field to be validated, hence no name attribute on that field. required
validator as well as AngularJS ng-minlength
and type="email"
validators. Each of the validators exposes a key on the $error object, so that we can pick it up and display the error message for that particular error to the userng-show
and ng-hide
are two directives in AngularJS that deal with hiding and showing HTML elements. They inspect a variable and, depending on the truthiness of its value, show or hide elements in the UI, respectively. AngularJS treats true, nonempty strings, nonzero numbers, and nonnull JS objects as truthy. myForm.$dirty
condition. it will be true only if something was typed in/edited in form. It will avoid showing errors on form load. Different form states are shown further in post.myForm.email.$invalid
], which can again be used with ng-show to display further error to user. ng-disabled
to disable the submit button if the form is invalid [ng-disabled="myForm.$invalid"
].$invalid
: AngularJS sets this state when any of the validations (required, ng-minlength, and others) mark any of the fields within the form as invalid.$valid
: The inverse of the previous state, which states that all the validations in the form are currently evaluating to correct.$pristine
: All forms in AngularJS start with this state. This allows you to figure out if a user has started typing in and modifying any of the form elements. Possible usage: disabling the reset button if a form is pristine.$dirty
: The inverse of $pristine, which states that the user made some changes (he can revert it, but the $dirty bit is set).$error
: This field on the form houses all the individual fields and the errors on each form element.On each validation step, AngularJS adds/removes certain CSS classes to/from form and individual fields. It means highlighting error fields are just matter of providing your own styles to these classes.
<html ng-app="myApp"> <head> <title>Form Demo</title> <style>body{font-family:"Arial";background-color:#E2E2DC}</style> <style> .username.ng-valid { background-color: lightgreen; } .username.ng-dirty.ng-invalid-required { background-color: red; } .username.ng-dirty.ng-invalid-minlength { background-color: yellow; } .email.ng-valid { background-color: lightgreen; } .email.ng-dirty.ng-invalid-required { background-color: red; } .email.ng-dirty.ng-invalid-email { background-color: yellow; } </style> </head> <body ng-controller="AppController as ctrl"> <form ng-submit="ctrl.submit()" name="myForm"> <input type="text" ng-model="ctrl.user.username" name="uname" class="username" placeholder="Enter your name" required ng-minlength="3"/> <span ng-show="myForm.$dirty && myForm.uname.$error.required">This is a required field</span> <span ng-show="myForm.$dirty && myForm.uname.$error.minlength">Minimum length required is 4</span> <span ng-show="myForm.$dirty && myForm.uname.$invalid">This field is invalid </span><br/><br/> <input type="text" ng-model="ctrl.user.address" placeholder="Enter your Address"/><br/><br/> <input type="email" ng-model="ctrl.user.email" name="email" class="email" placeholder="Enter your Email" required/> <span ng-show="myForm.$dirty && myForm.email.$error.required">This is a required field</span> <span ng-show="myForm.$dirty && myForm.email.$invalid">This field is invalid </span><br/><br/> <input type="submit" value="Submit" ng-disabled="myForm.$invalid"> </form> <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.4/angular.js"> </script> <script> angular.module('myApp', []) .controller('AppController', [function() { var self = this; self.submit = function() { console.log('Form is submitted with following user', self.user); }; }]); </script> </body> </html>
In above example, first we added two placeholder classes in username and email field, so that we can further refer to them in our stylesheet.Then we took those classes and added specific validation classes from AngularJS which will be added/removed on specific steps in validation cycle.
Try filling these fields to see them in action.
Shown below are the form states and respective AngularJS classes being added/removed on form and individual fields.
Similarly , for each validation failure, following CSS classes are added/removed from individual fields.
Below example is a full blown AngularJS based CRUD application. In this final example, we are using Bootstrap CSS to stylify our form. In order to show a list of all users of application, we are using another very popular AngularJS directive ng-repeat
, which is the standard choice to iterate over list of Items [can also iterate over keys of a given object]. For the moment, we are not communicating with Server, data is local, but in next post on AngularJS Service, we will fetch the data from [and update it in] real server.
<html>
<head>
<title>Form Demo</title>
<style>
.username.ng-valid {
background-color: lightgreen;
}
.username.ng-dirty.ng-invalid-required {
background-color: red;
}
.username.ng-dirty.ng-invalid-minlength {
background-color: yellow;
}
.email.ng-valid {
background-color: lightgreen;
}
.email.ng-dirty.ng-invalid-required {
background-color: red;
}
.email.ng-dirty.ng-invalid-email {
background-color: yellow;
}
</style>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css">
<link rel="stylesheet" href="app.css">
</head>
<body ng-app="myApp">
<div class="generic-container" ng-controller="AppController as ctrl">
<div class="panel panel-default">
<div class="panel-heading"><span class="lead">User Registration Form </span></div>
<div class="formcontainer">
<form ng-submit="ctrl.submit()" name="myForm" class="form-horizontal">
<input type="hidden" ng-model="ctrl.user.id" />
<div class="row">
<div class="form-group col-md-12">
<label class="col-md-2 control-lable" >Live Demo
This example is build upon previous example.
Main Highlights
ng-repeat
directive. $scope
explicitly, (which was heavily used in previous releases of AngularJS and created lots of confusion among new to AngularJS). This link is a must to know more about AngularJS scopes.$scope
dependency in our controller, this time just to get a handle on something from view [form] in controller. Every controller has an associated $scope object, which inherits from $rootScope
. Every application has a single root scope. All other scopes inherit from rootScope. Scope is the glue between application controller and the view. In this example, we used $scope to get the handle on form from view, into our controller , in order to reset it.$scope.myForm.$setPristine();
to make the form pristine. In other words , we set the form as a Blank Slate where nothing has been written yet. It cleans out any previous validation state change effects. We also reset the user object used in form.That’s it. In next post we will discuss about AngularJS services and will extend our example to communicate with server using AngularJS built-in service $http. Stay tune.
If you like tutorials on this site, why not take a step further and connect me on Facebook , Google Plus & Twitter as well? I would love to hear your thoughts on these articles, it will help improve further our learning process.
In this post we will be developing a full-blown CRUD application using Spring Boot, AngularJS, Spring Data, JPA/Hibernate and MySQL,…
Spring Boot complements Spring REST support by providing default dependencies/converters out of the box. Writing RESTful services in Spring Boot…
Being able to start the application as standalone jar is great, but sometimes it might not be possible to run…
Spring framework has taken the software development industry by storm. Dependency Injection, rock solid MVC framework, Transaction management, messaging support,…
Let's secure our Spring REST API using OAuth2 this time, a simple guide showing what is required to secure a…
This post shows how an AngularJS application can consume a REST API which is secured with Basic authentication using Spring…
View Comments
Very Good tutorial Point. I am very happy and solve my problem.Thanks post this tutorial.
Where do I find the file for app.css which contains all of the styles for the final app?
Hi, you can get it from the download of SpringMVC+AngularJS post.
Great tutorial! Thx!
But I think there are some typos in last code example:
Address
should be "control-label" the same for others labels in ....
For submit and reset buttons i think some tags were lost/ I think better to put there this:
Reset Form
Cheers,
Boris
Awesome post!!.. Most of my doubts are clarified..
The following code :
=====================================================
Name
This is a required field
Minimum length required is 3
This field is invalid
Address
Email
This is a required field
This field is invalid
========================
This works only OK when I replace
name="uname" instead of id="uname"
name="address" instead of id="address"
name="email" instead of id="email"
the last tutorial is cool, but it's so complicated..
nice post for angularjs, but need some correction in case of email validation.
BESTpost I ever found for AngularJS.
I am Happy with Explanation . Got everything very clearly .
Please keep it up posting such material on advance topics of AngularJS ... Amazing.. :) great Work !!!!
Glad you liked it. Have a look on other detailed posts on AngularJS topics, your comments are much appreciated.