Essential AngularJS Extensions

One of the most popular and highly supported AngularJS plugins is the AngularUI framework.

AngularUI

AngularJS itself is packed full of out-of-the-box features that we can use to build an expressive AngularJS app without relying on separate libraries; however, the very active AngularJS community has built some great libraries that we can take advantage of to maximize the power of our apps.

In this section, we’re covering several different and most commonly used components of the AngularUI library.

The AngularUI library has been broken out into several modules so that, rather than including the entire suite, we can pick and choose the components that we’re interested in using.

As we walk through the different components, we’ll need to ensure that we install each of the different components with which we are going to work.

Installation

For each component, we can either download the individual JavaScript library and place it in our application path or we can use Bower to complete our installation. We at ng-newsletter.com recommend using Bower. For the purposes of this chapter, we’ll cover installing each module only with Bower.

ui-router

One of the most useful libraries that the AngularUI library gives us is the ui-router. It’s a routing framework that allows us to organize our interface by a state machine, rather than a simple URL route.

Installation

To install the ui-router library, we can either download the release or use Bower to install the library.

Make sure you have Bower installed globally:

$ npm install bower -g

Use Bower to install the angular-ui library:

$ bower install angular-ui-router --save

We’ll need to make sure we link the library to our view:

<script type="text/javascript" 
  src="app/bower_components/angular-ui-router/release/angular-ui-router.js">
</script>

And we’ll need to inject the ui.router as a dependency in our app:

angular.module('myApp', ['ui.router'])

Now, unlike the built-in ngRoute service, the ui-router can nest views as it works based off states, rather than simply a url.

Instead of using the ng-view directive as we do with the ngRoute service, we’ll use the ui-view directive with ngRoute.

When dealing with routes and states inside of ui-router, we’re mainly concerned with in which state the application and at which route the web app currently stands.

<div ng-controller="DemoController">
  <div ui-view></div>
</div>

Just like ngRoute, the templates we define at any given state are placed inside of the <div ui-view></div> element. Each of these templates can include its own ui-view, as well. This fact allows us to have nested views inside our routes.

To define a route, we use the .config method, just like normal, but instead of setting our routes on $routeProvider, we set our states on the $stateProvider.

.config(function($stateProvider, $urlRouterProvider) {
  $stateProvider
    .state('start', {
      url: '/start',
      templateUrl: 'partials/start.html'
    })
});

This step assigns the state named start to the state configuration object. The state configuration object, or the stateConfig, has similar options to the route configuration object, which gives us the ability to configure the states of our application.

template, templateUrl, templateProvider

These are the three ways to set up templates on each of the views:

For instance:

$stateProvider.state('home', {
  template: '<h1>Hello {{ name }}</h1>'
});

controller

Just like in ngRoute, we can either associate an already-registered controller with a URL (via a string) or we can create a controller function that operates as the controller for the state.

If there is no template defined (in one of the previous options), the controller will not be created.

resolve

We can resolve a list of dependencies that we will inject into our controller using the resolve functionality. In ngRoute, the resolve option allows us to resolve promises before the route is actually rendered. Inside ui-router, we have a bit more freedom as to how we can use this option.

The resolve option takes an object where the keys are the names of the dependencies to inject into the controller and the values are the factories that are to be resolved.

If a string is passed, then ui-router tries to match an existing registered service. If a function is passed, the function is injected, and the return value of the function is the dependency. If the function returns a promise, it is resolved before the controller is instantiated and the value (just like ngRoute) is injected into the controller.

$stateProvider.state('home', {
  resolve: {
    // This will return immediately as the 
    // result is not a promise
    person: function() {
      return {
        name: "Ari",
        email: "[email protected]"
      }
    },
    // This function returns a promise, therefore
    // it will be resolved before the controller
    // is instantiated
    currentDetails: function($http) {
      return $http({
        method: 'JSONP',
        url: '/current_details'
      });
    },
    // We can use the resulting promise in another
    // resolution
    facebookId: function($http, currentDetails) {
      return $http({
        method: 'GET',
        url: 'http://facebook.com/api/current_user',
        params: {
          email: currentDetails.data.emails[0]
        }
      })
    }
  },
  controller: function($scope, person, 
                currentDetails, facebookId) {
      $scope.person = person;
  }
})

url

The url option assigns a unique URL for the state of the application. The url options gives us the same features of deep linking, while navigating around the app by state, rather than simply by URL.

This option is similar to the ngRoute URL, but can be considered a major upgrade, as we’ll see in a moment.

The basic route can be specified like so:

$stateProvider
  .state('inbox', {
    url: '/inbox',
    template: '<h1>Welcome to your inbox</h1>'
  });

When the user navigates to /inbox, the app transitions into the inbox state, and we fill the main ui-view directive with the contents of the template (<h1>Welcome to your inbox</h1>).

The URL can take several different options and we can set the basic parameters in the url like in ngRoute:

$stateProvider
  .state('inbox', {
    url: '/inbox/:inboxId',
    template: '<h1>Welcome to your inbox</h1>',
    controller: function($scope, $stateParams) {
      $scope.inboxId = $stateParams.inboxId;
    }
  });
 
This page is a preview of ng-book.
Get the rest of this chapter plus 600 pages of the best Angular content on the web.

 

Ready to master AngularJS?

  • What if you could master the entire framework – with solid foundations – in less time without beating your head against a wall? Imagine how quickly you could work if you knew the best practices and the best tools?
  • Stop wasting your time searching and have everything you need to be productive in one, well-organized place, with complete examples to get your project up without needing to resort to endless hours of research.
  • You will learn what you need to know to work professionally with ng-book: The Complete Book on AngularJS or get your money back.
Get it now