Using the Ionic Framework

Wednesday Sep 17th 2014 by Chad Campbell

Creating apps across the fragmented mobile landscape of Android and iOS has been a challenge. Ionic helps developers create beautiful, high performing apps that work across platforms with the help of Cordova. This article will give you a taste of what you can do with the Ionic framework.

The previous article, "Developing Hybrid Apps with the Ionic Framework," discussed building hybrid apps with Ionic. That article focused on the Ionic command-line tools. This article will focus more on the Ionic Framework itself. After reading this article, you'll have a better feel for what Ionic provides. To be comfortable with the contents of this article, you should have a basic understanding of AngularJS, CSS, and HTML. To show some of Ionic's capabilities, we will build a todo app. The app will look like the following:

Figure 1: The completed todo list

This app is based on an MIT-licensed app that you can get for yourself on GitHub. The purpose of this article is to talk about Ionic, not re-write the wheel :). The app itself is very basic. It lets you simply add todo items. Editing and deleting items are out of scope for this article. That's because is we want to stay focused on the unique piece: the Ionic framework. To jump start the process, run the following commands in an empty directory from your command line:

ionic start todo blank
cd todo
npm install
ionic serve

Code Segment A

The four commands in Code Segment A will initialize a new app. This basic app should be open in your web browser. The commands in Code Segment A were discussed in the previous article. With the tooling in your belt, we can change focus to actually develop an app. To make an app that looks like the one in Figure 1, we'll start by adding some tabs for navigational purposes.

Adding Tabs to Your App

The first thing we'll do is add two tabs to our app. If you would like to follow along, open www/index.html in your favorite text editor. Replace the code that says <ion-content></ion-content> with the following:

<ion-tabs class="tabs-background-positive tabs-icon-top">
   <ion-tab title="Items" icon="ion-document-text">
         Tasks go here

   <ion-tab title="Details" icon="ion-information-circled">
         Details go here

Code Segment B

The code in Code Segment B creates two tabs within the app. The ion-tabs element is an AngularJS directive used to allow multiple items to share the same real estate on the screen. By default, the tabs will position themselves against the bottom of the screen. However, you can choose to add the tabs-top class to position the tabs against the top of the screen. The other two classes used in the snippet above, tabs-background-positive and tabs-icon-top, are just as interesting.

Setting Tab Icon Position

The colors used in the tabs can be customized with the help of two separate classes: tab-background-{color} and tab-{color}. The former class specifies the tab's background color. The latter class identifies the class to use in the foreground. In the example above, you may have noticed the word positive is used for the color. This is pulled from the list of predefined colors specified here. You can define your own colors if you so choose.

The other class used above, tabs-icon-top, was used to specify the use of icons in the tabs. By default, tabs will only show their text. If you want to actually show an icon, you need to specify the icon's location in relation to the text. This can be set with one of the pre-packaged CSS classes. Those classes and a brief description are shown in Table 1:

Name Description Example
(unset) Displays only the tabs text Table1
tabs-icon-only Shows only the tab icons. Each tab's title will not be shown. Table2
tabs-icon-top Places icons on top of each tab's title. Table3
tabs-icon-left Adds an icon to the left of each tab's title. Table4

Table 1

Table 1 shows the options for positioning tabs. There are also options to set the tab colors.

Setting Tab Colors

Tabs in a single app usually have a shared look-and-feel. The Ionic framework makes it easy to customize the colors used. You can quickly set the colors by using the tab-{color} class. This class will let you set the color of the tab bar. The {color} piece is one of the predefined colors mentioned before. There are ways use your own custom colors by using class CSS skills.

Setting tab colors is a great way to make your app stand out. Using icons is a great way to make your app more approachable. To understand the other customization options at the tab strip level, I would recommend reviewing the documentation available here. For now, it's time to narrow our focus and look at individual tabs.

Working with Individual Tabs

Each tab represents a selectable item within a tab strip. This selectable item is created by the ion-tab directive seen in Code Segment B. When selected, the content associated with the tab will appear. We'll get into creating some content a little later. For now, let's discuss the title, icon, and badge options available for an ion-tab at design time.

The title attribute lets you set the name of a tab. This name will be shown as long as the tab-icon-only class is not added in the parent ion-tabs directive. It's recommended to keep the title attribute value to a single, short word. Be brief and be bright.

The icon for a tab can be set through the icon property. This property relies on a string that identifies a CSS class to set the image. Typically, this will rely on an icon font. One called Ionicons, which has over 500 icons, comes with the Ionic framework. That's why the use of ion-document-text in Code Segment B just worked. You also have the option of choosing icons for the selected and unselected states with the icon-on and icon-off attributes.

Finally, let's talk about badges. A badge draws attention to something. For instance, it may be a number showing how many unread emails you have. In the Ionic framework, you can use a number or something else. You just set the badge attribute on the ion-tab element. You can set the color by using one of the previously mentioned color classes with the badge-style attribute.

At this point, we've seen how to set up our app's navigation with the ion-tabs element. The content for our app will reside within individual ion-tab elements. With that in mind, let's go deeper into our app and start adding content to our tabs.

Adding Content to a Tab

Content in an ion-tab is added through the ion-content element. This child element serves as a container for the meat of a tab. The ion-content element itself mainly deals with the scrolling behavior. You can customize that behavior with the attributes described here. For our demo, we'll talk about adding basic content. Then, we'll add a list to an ion-content element.

Adding Basic Content

To demonstrate adding basic content to a tab, we'll display the number of items to do. In fact, we'll start in the view (index.html) and replace the Details go here from Code Segment B with the following:

<div class="content padding">
   You have {{items.length}} items outstanding

Code Segment C

If you open your browser, you'll see something that looks like Figure 2:

Figure 2: Showing the outstanding items

If you look at Figure 2, you'll notice that the text seems off. The actual count is missing. The code in Code Segment C is trying to bind to the length property of an array named items. Although items does not exist yet, this code did not cause our app to crash or even throw an error. To get our desired behavior, we need to add a controller.

In AngularJS, a controller is a JavaScript constructor function associated with a specific scope. To add a controller, add a new file called controller.js to the www/js directory. Inside of this file, add the code shown in the Code Segment D.

angular.module('todo.controllers', [])
   .controller('IndexCtrl', function($scope) {
      $scope.items = [];

Code Segment D

This snippet adds a single controller called IndexCtrl to a module named todo.controllers. If you look at the app, you'll notice that it is not working as desired yet. The reason why is because of two things: first, the module that contains IndexCtrl has not been loaded yet; and second, IndexCtrl has not been bound to the view.

To load the todo.controllers module, there are a couple of things that need to be done. First, the controller code needs to be referenced. To do this, add the line <script src="js/controllers.js"></script> above <script src="js/app.js"></script> in the www/index.html file. Then, in www/js/app.js, change the line that says angular.module('starter', ['ionic']) to angular.module('starter', ['ionic', 'todo.controllers']). These two changes will add the todo.controllers module to our app.

To bind IndexCtrl to the view, there is only one change that needs to be made. The change is to alter the line that says <ion-pane> to <ion-pane ng-controller="IndexCtrl">. This change leverages the ngController directive to bind our controller to our view. If you run the app now, you should see the following:

Figure 3: Binding the controller to our view

Although it may not look like much, we're really getting somewhere now. We've gotten some of the app structure put in place. This will allow us to build out the rest of the app fairly quickly. Considering the app is about listing todo items, we will now change our focus to adding a list to a view.

Adding a List

In the Ionic framework, a list is a way of displaying a collection of items. These items are displayed with help from the ion-list and ion-item elements. We'll dive deeper into the capabilities of each of these elements after we update our code. For now, replace the code from Code Segment B that said Tasks go here with the following code:

   <ion-item ng-repeat="item in items">
      <p style="white-space:normal;">{{item.description}}</p>

Code Segment E

If you look at the Items tab in the app now, you will see ... nothing. This is to be expected. This is because the code in Code Segment E uses the ngRepeat directive to render each todo item in ion-list. The items property on our scope (set up in Code Segment D) is empty. We need to create a way for a user to add a todo item to the array of items. In our app, we'll use a dialog.

Adding a Dialog to Your App

The Ionic framework provides a service called $ionicModal to deliver dialogs in your user interface. This service belongs to the ionic module, which is automatically included when you use the Ionic tools to start an app (discussed in the previous article). To add this service, open the www/js/controllers.js file created along with Code Segment D. Then, replace the line that says

.controller('IndexCtrl', function($scope) {


.controller('IndexCtrl', function($scope, $ionicModal) {

This injects the $ionicModal service as a dependency to IndexCtrl. This empowers us to initialize, show, and hide dialog windows. To demonstrate how to initialize a dialog window, add the following line below $scope.items = []; from Code Segment D.

$ionicModal.fromTemplateUrl('task-prompt.html', {
   scope: $scope,
   animation: 'slide-in-up'
}).then(function(modal) {
   $scope.modal = modal;

Code Segment F

This snippet initializes a dialog. The dialog will share scope with our current view. When opened, the dialog will slide up from the bottom of the screen. The content itself resides in task-prompt.html.

When creating the task-prompt view, there are several options. We could create a new .html file with our content. Alternatively, we can use inline HTML. To use inline HTML, open www/index.html and add the following code just above the closing </body> tag:

<script id="task-prompt.html" type="text/ng-template">
      <ion-header-bar class="bar-calm">
         <h1 class="title">Add New Task</h1>
         <div class="list">
            <label class="item item-input">
               <input type="text" placeholder="task title" ng-model="newTask.title">
            <label class="item item-input">
               <textarea placeholder="task description"

         <div class="row">
            <div class="col"><button ng-click="saveTask()"
               class="button button-full
               icon-left ion-checkmark-circled button-balanced">Save Task</button></div>
            <div class="col"><button ng-click="cancelTask()"
               class="button button-full icon-left ion-close-circled button-assertive">

Code Segment G

This code defines the body of our dialog. To actually open this dialog, we need to make two modifications. We need to update the header of our app. First, let's quickly add some color. Replace the line in www/index.html that says <ion-header-bar class="bar-stable"> with <ion-header-bar class="bar-energized">. This will give the app header some orange. Next, let's add a button to open the dialog we created in Code Segment G.

The Ionic framework lets you add buttons in ion-header-bar. For our needs, add the following code after the h1 element in ion-header-bar.

<button ng-click="showTaskPrompt();"
   class="button button-icon icon ion-plus-round"></button>

Code Segment H

The code in Code Segment H relies on a function called showTaskPrompt to open the dialog created in Code Segment G. We still need to create that function. To do that, open www/js/controllers.js. Add the following code below the code added in Code Segment F.

$scope.showTaskPrompt = function() {
   var newTask = {
      title: '',
      description: '',
      isComplete: null

   $scope.newTask = newTask;

Code Segment I

This snippet is the heart of the dialog opening. In Code Segment I, we initialize a new task. Then, we show the dialog. The dialog empowers the user to enter the task details. However, it doesn't actually do anything with those details. To get the task back into our list, add the following code underneath the code from Code Segment I.

$scope.saveTask = function() {

$scope.cancelTask = function() {

Code Segment J

After adding the code in Code Segment J, you'll have a fully functioning app. There's a lot more functionality that could be added. Still, this article provided a brief whirlwind example of the Ionic framework in action.

Mobile Site | Full Site
Copyright 2017 © QuinStreet Inc. All Rights Reserved