Components

Ionic apps are made of high-level building blocks called components. Components allow you to quickly construct an interface for your app. Ionic comes with a number of components, including modals, popups, and cards. Although components are primarily HTML and CSS, some components also include JavaScript functionality. Check out the examples below to see what each component looks like and to learn how to use each one. Once you’re familiar with the basics, head over to the API docs for ideas on how to customize each component.

Action Sheets

Improve this Doc

Action Sheets slide up from the bottom edge of the device screen, and display a set of options with the ability to confirm or cancel an action. Action Sheets can sometimes be used as an alternative to menus, however, they should not be used for navigation.

The Action Sheet always appears above any other components on the page, and must be dismissed in order to interact with the underlying content. When it is triggered, the rest of the page darkens to give more focus to the Action Sheet options.

Basic Usage

Demo Source

presentActionSheet() {
  let actionSheet = ActionSheet.create({
    title: 'Modify your album',
    buttons: [
      {
        text: 'Destructive',
        role: 'destructive',
        handler: () => {
          console.log('Destructive clicked');
        }
      },{
        text: 'Archive',
        handler: () => {
          console.log('Archive clicked');
        }
      },{
        text: 'Cancel',
        role: 'cancel',
        handler: () => {
          console.log('Cancel clicked');
        }
      }
    ]
  });
  this.nav.present(actionSheet);
  }

Alerts

Improve this Doc

Alerts are a great way to offer the user the ability to choose a specific action or list of actions. They also can provide the user with important information, or require them to make a decision (or multiple decisions).

From a UI perspective, you can think of Alerts as a type of “floating” modal, that covers only a portion of the screen. This means Alerts should only be used for quick actions like password verification, small app notifications, or quick options. More in depth user flows should be reserved for full screen ​Modals​.

Alerts are quite flexible, and can easily be customized. Check out the API docs for more information.

Basic Usage:

Demo Source

Basic Alerts are generally used to notify the user about new information (a change in the app, a new feature), an urgent situation that requires acknowledgement, or as a confirmation to the user that an action was successful or not.

  doAlert() {
    let alert = Alert.create({
      title: 'New Friend!',
      subTitle: 'Your friend, Obi wan Kenobi, just accepted your friend request!',
      buttons: ['OK']
    });
    this.nav.present(alert);
  }

Prompt Alerts

Demo Source

Prompts offer the user a way to input data or information. For example, often times Prompt Alerts will be used to ask the user for password confirmation as a means of security before moving forward in an app’s ux flow.

    let prompt = Alert.create({
      title: 'Login',
      message: "Enter a name for this new album you're so keen on adding",
      inputs: [
        {
          name: 'title',
          placeholder: 'Title'
        },
      ],
      buttons: [
        {
          text: 'Cancel',
          handler: data => {
            console.log('Cancel clicked');
          }
        },
        {
          text: 'Save',
          handler: data => {
            console.log('Saved clicked');
          }
        }
      ]
    });

Confirmation Alerts

Demo Source

Confirmation Alerts are used when it is required that the user explicitly confirms a particular choice before progressing forward in the app. A common example of the Confirmation Alert is checking to make sure a user wants to delete or remove a contact from their address book.

    let confirm = Alert.create({
      title: 'Use this lightsaber?',
      message: 'Do you agree to use this lightsaber to do good across the intergalactic galaxy?',
      buttons: [
        {
          text: 'Disagree',
          handler: () => {
            console.log('Disagree clicked');
          }
        },
        {
          text: 'Agree',
          handler: () => {
            console.log('Agree clicked');
          }
        }
      ]
    });

Radio

Demo Source

Radio Alerts are simply another type of Confirmation Alert, but use the Radio component to offer several choices. They offer the user a set of options to choose from, but are allowed to only make one final selection before continuing forward.

  doRadio() {
    let alert = Alert.create();
    alert.setTitle('Lightsaber color');

    alert.addInput({
      type: 'radio',
      label: 'Blue',
      value: 'blue',
      checked: true
    });

    alert.addButton('Cancel');
    alert.addButton({
      text: 'OK',
      handler: data => {
        this.testRadioOpen = false;
        this.testRadioResult = data;
      }
    });

Checkbox

Demo Source

Checkbox Alerts are simply another type of Confirmation Alert, but use the Checkbox component to offer several choices. They offer the user a set of options to choose from.

  doCheckbox() {
    let alert = Alert.create();
    alert.setTitle('Which planets have you visited?');

    alert.addInput({
      type: 'checkbox',
      label: 'Alderaan',
      value: 'value1',
      checked: true
    });

    alert.addInput({
      type: 'checkbox',
      label: 'Bespin',
      value: 'value2'
    });

    alert.addButton('Cancel');
    alert.addButton({
      text: 'Okay',
      handler: data => {
        console.log('Checkbox data:', data);
        this.testCheckboxOpen = false;
        this.testCheckboxResult = data;
      }
    });
  }

Badges

Improve this Doc

Badges are small components that typically communicate a numerical value to the user. They are typically used within an item.

Basic Usage

Demo Source

<ion-item>
  <ion-icon name="logo-twitter" item-left></ion-icon>
  Followers
  <ion-badge item-right>260k</ion-badge>
</ion-item>

Badges can also be given any color attribute:

<ion-badge secondary></ion-badge>

Buttons

Improve this Doc

Buttons are an essential way to interact with and navigate through an app, and should clearly communicate what action will occur after the user taps them. Buttons are simple components in Ionic, can consist of text, an icon, or both, and can be enhanced with a wide range of attributes.

Basic Usage

Demo Source

<button>Button</button>

The primary property sets the color of the button. Ionic includes a number of default colors which can be easily overridden:

<button light>Light</button>
<button>Primary</button>
<button secondary>Secondary</button>
<button danger>Danger</button>
<button dark>Dark</button>

Outline Style

Demo Source

To use the outline style for a button, just add the outline property:

<button light outline>Light Outline</button>
<button outline>Primary Outline</button>
<button secondary outline>Secondary Outline</button>
<button danger outline>Danger Outline</button>
<button dark outline>Dark Outline</button>

Clear Style

Demo Source

To use the clear style for a button, just add the clear property:

<button light clear>Light Clear</button>
<button clear>Primary Clear</button>
<button secondary clear>Secondary Clear</button>
<button danger clear>Danger Clear</button>
<button dark clear>Dark Clear</button>

Round Buttons

Demo Source

To create a button with rounded corners, just add the round property:

<button light round>Light Round</button>
<button round>Primary Round</button>
<button secondary round>Secondary Round</button>
<button danger round>Danger Round</button>
<button dark round>Dark Round</button>

Block Buttons

Demo Source

Adding block to a button will make the button take 100% of its parent’s width. It will also add display: block to the button:

<button block>Block Button</button>

Full Buttons

Demo Source

Adding full to a button will also make the button take 100% of its parent’s width. However, it will also remove the button’s left and right borders. This style is useful when the button should stretch across the entire width of the display.

<button full>Full Button</button>

Button Sizes

Demo Source

Add the large attribute to make a button larger, or small to make it smaller:

<button small>Small</button>
<button>Default</button>
<button large>Large</button>

Icon Buttons

Demo Source

To add icons to a button, add an icon component inside of it:

<!-- Float the icon left -->
<button>
  <ion-icon name="home"></ion-icon>
  Left Icon
</button>

<!-- Float the icon right -->
<button>
  Right Icon
  <ion-icon name="home"></ion-icon>
</button>

<!-- Only icon (no text) -->
<button>
  <ion-icon name="home"></ion-icon>
</button>

Floating Action Buttons

Demo Source

Adding fab to a button will turn it into a floating action button. This is a material design styled button that is meant to draw the user to take a specific action. Fab buttons are positioned absolutely, and their placement can be controlled by adding attributes like fab-top and fab-left. See the button API spec for a full list of attributes.

<button fab>FAB</button>

Buttons In Components

Demo Source

Although buttons can be used on their own, they can easily be used within other components. For example, buttons can be added to a list item or a navbar.

<ion-navbar>
  <ion-buttons start>
    <button>
      <ion-icon name="contact"></ion-icon>
    </button>
  </ion-buttons>

  <ion-buttons end>
    <button>
      <ion-icon name="search"></ion-icon>
    </button>
  </ion-buttons>
</ion-navbar>

<ion-list>
  <ion-item>
    Left Icon Button
    <button outline item-right>
      <ion-icon name="star"></ion-icon>
      Left Icon
    </button>
  </ion-item>
</ion-list>

Cards

Improve this Doc

Cards are a great way to display important pieces of content, and are quickly emerging as a core design pattern for apps. They're are a great way to contain and organize information, while also setting up predictable expectations for the user. With so much content to display at once, and often so little screen realestate, cards have fast become the design pattern of choice for many companies, including the likes of Google, Twitter, and Spotify.

For mobile experiences, Cards make it easy to display the same information visually across many different screen sizes. They allow for more control, are flexible, and can even be animated. Cards are usually placed on top of one another, but they can also be used like a "page" and swiped between, left and right.

Basic Usage:

Demo Source

Cards are primarily a CSS component. To use add a basic card, follow this structure:

<ion-card>

  <ion-card-header>
    Card Header
  </ion-card-header>

  <ion-card-content>
    <!-- Add card content here! -->
  </ion-card-content>

</ion-card>

Card Headers

Just like a normal page, cards can be customized to include headers. To add use add a card header, add the <ion-card-header> component inside of your card:

<ion-card>
  <ion-card-header>
    Header
  </ion-card-header>
  <ion-card-content>
    The British use the term "header", but the American term "head-shot" the English simply refuse to adopt.
  </ion-card-content>
</ion-card>

Lists In Cards

Demo Source

A card can contain a list of items. To create a card list, add elements with the ion-item attribute inside of an ion-list in your card:

<ion-card>
  <ion-card-header>
    Explore Nearby
  </ion-card-header>

  <ion-list>
    <button ion-item>
      <ion-icon name="cart" item-left></ion-icon>
      Shopping
    </button>

    <button ion-item>
      <ion-icon name="medical" item-left></ion-icon>
      Hospital
    </button>

    <button ion-item>
      <ion-icon name="cafe" item-left></ion-icon>
      Cafe
    </button>

    <button ion-item>
      <ion-icon name="paw" item-left></ion-icon>
      Dog Park
    </button>

    <button ion-item>
      <ion-icon name="beer" item-left></ion-icon>
      Pub
    </button>

    <button ion-item>
      <ion-icon name="planet" item-left></ion-icon>
      Space
    </button>

  </ion-list>
</ion-card>

Images In Cards

Demo Source

Images often vary in size, so it is important that they adopt a consistent style throughout your app. Images can easily be added to cards. Adding an image to a card will give the image a constant width, and a variable height. Lists, headers, and other card components can easily be combined with image cards. To add an image to a card, use the following markup:

<ion-card>
  <img src="img/nin-live.png"/>
  <ion-card-content>
    <ion-card-title>
      Nine Inch Nails Live
      </ion-card-title>
    <p>
      The most popular industrial group ever, and largely
      responsible for bringing the music to a mass audience.
    </p>
  </ion-card-content>
</ion-card>

Background Images

Demo Source

Coming soon.

Advanced Cards

The styles from different types of cards can be combined to create advanced cards. Cards can also receive custom CSS. Below are a few advanced cards that have been built by combining various card attributes with a small amount of custom CSS.

Social Cards

Demo Source

It’s often necessary to create social cards within an application. Using a combination of different items in a card you can achieve this.

<ion-card>

  <ion-item>
    <ion-avatar item-left>
      <img src="img/marty-avatar.png">
    </ion-avatar>
    <h2>Marty McFly</h2>
    <p>November 5, 1955</p>
  </ion-item>

  <img src="img/advance-card-bttf.png">

  <ion-card-content>
  <p>Wait a minute. Wait a minute, Doc. Uhhh... Are you telling me that you built a time machine... out of a DeLorean?! Whoa. This is heavy.</p>
  </ion-card-content>

  <ion-item>
    <button primary clear item-left>
      <ion-icon name="thumbs-up"></ion-icon>
      <div>12 Likes</div>
    </button>
    <button primary clear item-left>
      <ion-icon name="text"></ion-icon>
      <div>4 Comments</div>
    </button>
    <ion-note item-right>
      11h ago
    </ion-note>
  </ion-item>

</ion-card>

Map Cards

Demo Source

A combination of Ionic components can be used to create a card that appears as a map.

<ion-card>

  <img src="img/advance-card-map-madison.png">
  <button fab fab-right fab-top>
    <ion-icon name="pin"></ion-icon>
  </button>

  <ion-item>
    <ion-icon name="football" item-left large></ion-icon>
    <h2>Museum of Football</h2>
    <p>11 N. Way St, Madison, WI 53703</p>
  </ion-item>

  <ion-item>
    <ion-icon name="wine" item-left large ></ion-icon>
    <h2>Institute of Fine Cocktails</h2>
    <p>14 S. Hop Avenue, Madison, WI 53703</p>
  </ion-item>

  <ion-item>
    <span item-left>18 min</span>
    <span item-left>(2.6 mi)</span>
    <button primary clear item-right>
      <ion-icon name="navigate"></ion-icon>
      Start
    </button>
  </ion-item>

</ion-card>

Checkbox

Improve this Doc

A checkbox is an input component that holds a boolean value. Checkboxes are no different than HTML checkbox inputs. However, like other Ionic components, checkboxes are styled differently on each platform. Use the checked attribute to set the default value, and the disabled attribute to disable the user from changing the value.

Basic Usage

Demo Source

<ion-item>
  <ion-label>Daenerys Targaryen</ion-label>
  <ion-checkbox dark checked="true"></ion-checkbox>
</ion-item>

<ion-item>
  <ion-label>Arya Stark</ion-label>
  <ion-checkbox disabled="true"></ion-checkbox>
</ion-item>

Events

Improve this Doc

You can target specific events to trigger specific functionality. Built on top of Hammer.js, you can bind to tap, press, pan, swipe, rotate, and pinch. These events are listened for the same way as DOM events such as click.

Basic Usage

Demo Source

  <ion-card (tap)="tapEvent($event)">
    <ion-item>
      Tapped:  times
    </ion-item>
  </ion-card>

Grid

Improve this Doc

Ionic’s grid system is based on flexbox, a CSS feature supported by all devices that Ionic supports. The grid is composed of two units — rows and columns. Columns will expand to fill their row, and will resize to fit additional columns.

In order to set width use width attribute on ion-col tag.

Demo Source

<ion-row>
  <ion-col width-10>This column will take 10% of space</ion-col>
</ion-row>
Explicit Column Percentage Attributes
width-10 10%
width-20 20%
width-25 25%
width-33 33.3333%
width-50 50%
width-67 66.6666%
width-75 75%
width-80 80%
width-90 90%

Use the offset attribute on a column to set its percent offset from the left (eg: offset-25). To change how columns in a row align vertically, add the center or baseline attribute to an <ion-row>.

Use the wrap attribute on an <ion-row> element to allow items in that row to wrap. This applies the flex-wrap: wrap; style to the <ion-row> element.

Icons

Improve this Doc

Ionic comes with the same 700+ Ionicons icons we’ve all come to know and love.

Basic Usage:

Demo Source

To use an icon, just add the Icon’s CSS class to your element:

<ion-icon name="heart"></ion-icon>

Active / Inactive Icons:

All icons have both active and inactive states. Active icons are typically full and thick, where as inactive icons are outlined and thin. Set the is-active attribute to true or false to change the state of the icon. Icons will default to active if a value is not specified.

<ion-icon name="heart"></ion-icon>                    <!-- active -->
<ion-icon name="heart" isActive="false"></ion-icon>  <!-- inactive -->

Platform Specific Icons:

Many icons have both Material Design and iOS versions. Ionic will automatically use the correct version based on the platform.

However, if you want more control, you can explicitly set the icon to use for each platform. Use the md (material design) and ios attributes to specify a platform specific icon:

<ion-icon ios="logo-apple" md="logo-android"></ion-icon>

Variable Icons:

To set an icon using a variable:

<ion-icon [name]="myIcon"></ion-icon>
export class MyFirstPage {
  constructor(nav: NavController) {
    // use the home icon
    this.myIcon = "home";
  }
}

Explore the full icon set

Inputs

Improve this Doc

Inputs are essential for collecting and handling user input in a secure way. They should follow styling and interaction guidelines for each platform, so that they are intuitive for users to interact with. Ionic uses Angular 2’s form library, which can be thought of as two dependent pieces, Controls, and Control Groups.

Each input field in a form has a Control, a function that binds to the value in the field, and performs validation. A Control Group is a collection of Controls. Control Groups handle form submission, and provide a high level API that can be used to determine whether the entire form is valid.

A number of attributes that can be used to style forms and their various input fields are listed below. For more info on form logic, check out the Inputs API docs.

Fixed Labels

Demo Source

Use fixed to place a label to the left of the input element. When the user enters text, the label does not hide. The user’s input will align on the same position, regardless of the length of the label. Note that there’s nothing stopping you from also using a placeholder label too.

<ion-list>

  <ion-item>
    <ion-label fixed>Username</ion-label>
    <ion-input type="text" value=""></ion-input>
  </ion-item>

  <ion-item>
    <ion-label fixed>Password</ion-label>
    <ion-input type="password"></ion-input>
  </ion-item>

</ion-list>

Floating Labels

Demo Source

Floating labels are just like Stacked Labels, except that their labels animate, or “float” up when text is entered in the input. Each <ion-label> should have the floating attribute assigned.

Enter text in the example to the right to see the floating labels in action.

<ion-list>

  <ion-item>
    <ion-label floating>Username</ion-label>
    <ion-input type="text"></ion-input>
  </ion-item>

  <ion-item>
    <ion-label floating>Password</ion-label>
    <ion-input type="password"></ion-input>
  </ion-item>

</ion-list>

Inline Labels

Demo Source

If a label attribute is not provided, an <ion-label> component will default to using an inline label. When the user enters text, the label does not hide. Note that there’s nothing stopping you from also using a placeholder as well.

<ion-list>

  <ion-item>
    <ion-label>Username</ion-label>
    <ion-input type="text"></ion-input>
  </ion-item>

  <ion-item>
    <ion-label>Password</ion-label>
    <ion-input type="password"></ion-input>
  </ion-item>

</ion-list>

<div padding>
  <button block>Sign In</button>
</div>

Inset Labels

Demo Source

By default each input item will fill 100% of the width of its parent element (the list). However, you can inset the list by adding the inset attribute.

<ion-list inset>

  <ion-item>
    <ion-label>Username</ion-label>
    <ion-input type="text"></ion-input>
  </ion-item>

  <ion-item>
    <ion-label>Password</ion-label>
    <ion-input type="password"></ion-input>
  </ion-item>

</ion-list>

Placeholder Labels

Demo Source

Add the placeholder attribute to an <input> element to simulate the input’s label. When the user begins to enter text into the input, the placeholder label will be hidden.

<ion-list>

  <ion-item>
    <ion-input type="text" placeholder="Username"></ion-input>
  </ion-item>

  <ion-item>
    <ion-input type="password" placeholder="Password"></ion-input>
  </ion-item>

</ion-list>

Stacked Labels

Demo Source

A stacked label will always appear on top of the input. Each <ion-label> should have the stacked attribute. You can also add a placeholder so that users have a hint of what type of text the input is looking for.

<ion-list>

  <ion-item>
    <ion-label stacked>Username</ion-label>
    <ion-input type="text"></ion-input>
  </ion-item>

  <ion-item>
    <ion-label stacked>Password</ion-label>
    <ion-input type="password"></ion-input>
  </ion-item>

</ion-list>

Lists

Improve this Doc

Lists are used to display rows of information, such as a contact list, playlist, or menu. Or maybe something crazy we don’t even know exists yet!

Basic Usage (Default)

Demo Source

By default, all lists will be styled with divider lines:

<ion-list>
  <ion-item *ngFor="#item of items" (click)="itemSelected(item)">
    {{item.title}}
  </ion-item>
</ion-list>

Basic Usage (No Lines)

Demo Source

Adding the no-lines attribute will hide the dividers between list items:

<ion-list no-lines>
  <ion-item *ngFor="#item of items" (click)="itemSelected(item)">
    {{item.title}}
  </ion-item>
</ion-list>

Inset List

Demo Source

By default, lists have no outside margin, to add one, add the inset property to the list component.

<ion-list inset>
  <ion-item *ngFor="#item of items" (click)="itemSelected(item)">
    {{item.title}}
  </ion-item>
</ion-list>

List Dividers

Demo Source

To divide groups of items, use <ion-item-group> instead of <ion-list>. Use <ion-item-divider> components to divide the group in to multiple sections:

<ion-content>
    <ion-item-group>

      <ion-item-divider light>A</ion-item-divider>
      <ion-item>Angola</ion-item>
      <ion-item>Argentina</ion-item>

      <ion-item-divider light>B</ion-item-divider>

    </ion-item-group>
</ion-content>

List Headers

Demo Source

Each list can include a header at the top of the list:

<ion-list>
  <ion-list-header>
    Action
  </ion-list-header>
  <ion-item>Terminator II</ion-item>
  <ion-item>The Empire Strikes Back</ion-item>
  <ion-item>Blade Runner</ion-item>
</ion-list>

Icon List

Demo Source

Adding icons to list items is a great way to hint about the contents of each item. The position of the icon can be set using the item-left and item-right attributes:

<ion-list>
  <ion-item>
    <ion-icon name="leaf" item-left></ion-icon>
      Herbology
    <ion-icon name="rose" item-right></ion-icon>
  </ion-item>
</ion-list>

Avatar List

Demo Source

Item avatars showcase an image larger than an icon, but smaller than a thumbnail. To use an avatar, add an <ion-avatar> component inside of an item. The position of the avatar can be set using the item-left and item-right attributes:

<ion-list>
  <ion-item>
    <ion-avatar item-left>
      <img src="img/avatar-cher.png">
    </ion-avatar>
    <h2>Cher</h2>
    <p>Ugh. As if.</p>
  </ion-item>
</ion-list>

Multiline List

Demo Source

Multiline lists are identical to regular lists, except they can multiple lines of text. When multiple header or paragraph tags are added to an <ion-item>, the item will automatically adjust its height to fit the new lines. Below is an example with three lines of text:

<ion-list>
  <ion-item>
    <ion-avatar item-left>
      <img src="img/avatar-finn.png">
    </ion-avatar>
    <h2>Finn</h2>
    <h3>Don't Know What To Do!</h3>
    <p>I've had a pretty messed up day. If we just...</p>
  </ion-item>
</ion-list>

Sliding List

Demo Source

Sliding items can be swiped to the left to reveal a set of buttons. To use a sliding item, add a <ion-item-sliding> component inside of a list. Next, add a <ion-item-options> component inside of the sliding item to contain the buttons:

<ion-list>
  <ion-item-sliding>
    <ion-item>
      <ion-avatar item-left>
        <img src="img/slimer.png">
      </ion-avatar>
      <h2>Slimer</h2>
    </ion-item>
    <ion-item-options>
      <button primary>
        <ion-icon name="text"></ion-icon>
        Text
      </button>
      <button secondary>
        <ion-icon name="call"></ion-icon>
        Call
      </button>
    </ion-item-options>
  </ion-item-sliding>
</ion-list>

Thumbnail List

Demo Source

Item thumbnails showcase an image that takes up the entire height of an item. To use a thumbnail, add an <ion-thumbnail> component inside of an item. The position of the thumbnail can be set using the item-left and item-right attributes:

<ion-list>
  <ion-item>
    <ion-thumbnail item-left>
      <img src="img/thumbnail-totoro.png">
    </ion-thumbnail>
    <h2>My Neighbor Totoro</h2>
    <p>Hayao Miyazaki • 1988</p>
    <button clear item-right>View</button>
  </ion-item>
</ion-list>

Loading

Improve this Doc

The Loading component is an overlay that prevents user interaction while indicating activity. By default, it shows a spinner based on the mode. It can also be passed any HTML content to display with the spinner. You can hide or change the spinner to any of our predefined spinners. The loading indicator is styled to display on top of other content even during navigation.

Check out the API docs for more information.

Basic Usage

Demo Source

presentLoading() {
  let loading = Loading.create({
    content: "Please wait...",
    duration: 3000
  });
  this.nav.present(loading);
}

Improve this Doc

For more in depth information on Menus, see the Menu API reference.

Menu is a side-menu navigation that can be dragged out or toggled to show. Menu supports two display styles currently: overlay, and reveal. Overlay is the tradtional Android drawer style, and Reveal is the traditional iOS style. By default, Menu will adjust to the correct style for the platform.

Along with Tabs, Menus are a common way to navigate through an app if you have several “root” or “top-level” pages. For the basics of navigating through an Ionic app, see the Navigation section.

For UX reasons, we first recommend using Tabs. However, for situations where using Tabs might not be desirable, for example if you have a large number of root pages (making a TabBar impractical), a menu might be a better solution.

Menus also allow you to return to root pages at any point. This can be helpful if you have particularly deep navigation by allowing you to return to the top level of your app quickly.

However, because Menus are not always and immediately visible on screen, they require more work for the user than Tabs. Make sure to weigh your priorities when designing the navigational structure of your app.

To use a Menu add an <ion-menu> to your markup next to your root <ion-nav>.

Basic Usage

Demo Source

@App({
  template: `
    <ion-menu [content]="content">
      <ion-toolbar>
        <ion-title>Pages</ion-title>
      </ion-toolbar>
      <ion-content>
        <ion-list>
          <button ion-item (click)="openPage(loginPage)">
            Login
          </button>
          <button ion-item (click)="openPage(signupPage)">
            Signup
          </button>
        </ion-list>
      </ion-content>
    </ion-menu>

    <ion-nav id="nav" #content [root]="rootPage"></ion-nav>`
})
class MyApp {}

The <ion-menu>s bound [content] property gets a reference to the <ion-nav> in order to listen for drag events on the main content so it knows when to open/close.

Then in our @App component we have two buttons with click handlers that navigate to a new root page:

import {MenuController, IonicApp} from 'ionic/ionic';
import {LoginPage} from 'login';
import {SignupPage} from 'signup';

@App({
...
})
class MyApp {

  constructor(app: IonicApp, menu: MenuController) {
    this.app = app;
    this.menu = menu;
    this.rootPage = LoginPage;
    this.loginPage = LoginPage;
    this.signupPage = SignupPage;
  }

  openPage(page) {
    // Reset the nav controller to have just this page
    // we wouldn't want the back button to show in this scenario
    this.rootPage = page;
  
    // close the menu when clicking a link from the menu
    this.menu.close();
  }
}

We inject the MenuController provider so we can close the opened menu. We then use the NavController’s setRoot function to clear the navigation stack and set the selected page as the new navigation root.

Menus can be a little more complicated, but they allow for many different configuration options. For example, the Google Maps app uses a drawer style Menu that exposes a list of items that open Modals over the main map content area and toggle settings on and off.

For more information on Menus, check out the Menu API reference.

Modals

Improve this Doc

Modals slide in off screen to display a temporary UI, often used for login or signup pages, message composition, and option selection.

Basic Usage

Demo Source

Next, we need to create the class that will control our modal. Let’s import Modal, NavController and ViewController:

import {Modal, NavController, ViewController} from 'ionic-angular';

Next, let’s create our modal and define add its template:

@Page({
  template: `
  <ion-content padding>
    <h2>I'm a modal!</h2>
    <button (click)="close()">Close</button>
  </ion-content>`
})
class MyModal {
  constructor(viewCtrl: ViewController) {
    this.viewCtrl = viewCtrl;
  }
  
  close() {
    this.viewCtrl.dismiss();
  }
}

Finally, let’s add the code that will open our Modal:

import {Modal, NavController} from 'ionic/ionic'
class MyPage {
  constructor(nav: NavController){
    this.nav = nav;
  }
  showModal() {
    let modal = Modal.create(MyModal);
    this.nav.present(modal)
  }
}

The Modal.create() function can also receive an object as the second argument that will be passed to the modal. See the Modal API docs for more information.

Improve this Doc

For more in depth information on navigation, see the Nav API reference.

Navigation is how users move between different pages in your app. Ionic’s navigation follows standard native animation concepts, like those in iOS.

Like native apps, URLs are not required for navigation. Instead, pages are pushed and popped on and off a navigation controller’s page stack. URLs can be used to link back to unique, important parts of your app (“deeplinking”) but don’t define navigation as your app runs.

There are several ways to navigate throughout an Ionic app:

Basic Navigation

Demo Source

The simplest way to navigate throughout your app is to create and initialize a new navigation controller, using <ion-nav>:

  import {StartPage} from 'start'

  @App({
    template: '<ion-nav [root]="rootPage"></ion-nav>'
  })
  class MyApp {
    constructor(){
      // First page to push onto the stack
      this.rootPage = StartPage;
    }
  }

You can access the navigation controller you create by injecting it into any of your Pages:

@Page({
  template: `
    <ion-navbar *navbar>
      <ion-title>Login</ion-title>
    </ion-navbar>

    <ion-content>Hello World</ion-content>`
})
export class StartPage {
  constructor(nav: NavController){
    this.nav = nav;
  }
}

To navigate from one page to another simply push or pop a new page onto the stack:

@Page({
  template: `
    <ion-navbar *navbar>
      <ion-title>Login</ion-title>
    </ion-navbar>

    <ion-content>
      <button (click)="goToOtherPage()">
        Go to OtherPage
      </button>
    </ion-content>`
})
export class StartPage {
  constructor(nav: NavController) {
    this.nav = nav;
  }

  goToOtherPage(){
    //push another page onto the history stack
    //causing the nav controller to animate the new page in
    this.nav.push(OtherPage);
  }
}

@Page({
  template: `
    <ion-navbar *navbar>
      <ion-title>Other Page</ion-title>
    </ion-navbar>

    <ion-content>I'm the other page!</ion-content>`
})
class OtherPage {}

If your page has an <ion-navbar>, a back button will automatically be added to it if it is not a root page.

Alternatively, if you want to go back, but don’t have a NavBar, you can pop the current page off the stack:

@Page({
  template: `
    <ion-content>
      <button (click)="goBack()">
        There's no place like home
      </button>
    </ion-content>`
})
class OtherPage {
  constructor(nav: NavController) {
    this.nav = nav;
  }
  goBack() {
    this.nav.pop();
  }
}

For more information on basic navigation, check out the Nav API reference.

What if you want to control navigation from your root app component (the one decorated with @App, not @Page)? You can’t inject NavController because any components that are navigation controllers are children of the root component so they aren’t available to be injected.

By adding an id to ion-nav, you can use the IonicApp service to get a reference to the Nav component, which is a navigation controller (it extends NavController):

@App({
  template: '<ion-nav id="my-nav" [root]="rootPage"></ion-nav>'
})
export class MyApp {
  constructor(app: IonicApp) {
    this.rootPage = TabsPage;
    this.app = app;
  }

  // Wait for the components in MyApp's template to be initialized
  // In this case, we are waiting for the Nav with id="my-nav"
  ngAfterViewInit() {
    var nav = this.app.getComponent('my-nav');
    // Let's navigate from TabsPage to Page1
    nav.push(Page1);
  }
}

Advanced Navigation

What if you have several “root” or “top-level” pages that don’t have a parent-child relationship, but rather are siblings? You have two options: Tabs and Menu.

Radio

Improve this Doc

Like the checkbox, a radio is an input component that holds a boolean value. Under the hood, radios are no different than HTML radio inputs. However, like other Ionic components, radios are styled differently on each platform. Unlike checkboxes, radio components form a group, where only one radio can be selected at a time. Use the checked attribute to set the default value, and the disabled attribute to disable the user from changing to that value.

Basic Usage

Demo Source

<ion-list radio-group>
  <ion-list-header>
    Language
  </ion-list-header>

  <ion-item>
    <ion-label>Go</ion-label>
    <ion-radio checked="true" value="go"></ion-radio>
  </ion-item>

  <ion-item>
    <ion-label>Rust</ion-label>
    <ion-radio value="rust"></ion-radio>
  </ion-item>

  <ion-item>
    <ion-label>Python</ion-label>
    <ion-radio value="python" disabled="true"></ion-radio>
  </ion-item>
</ion-list>

Improve this Doc

A Searchbar binds to a model, and emits an input event when the model is changed.

Basic Usage

Demo Source

<ion-searchbar [(ngModel)]="searchQuery" (input)="getItems($event)"></ion-searchbar>
<ion-list>
  <ion-item *ngFor="#item of items">
    {{ item }}
  </ion-item>
</ion-list>

Note that in this example, the Searchbar binds to the searchQuery variable. The getItems() function is called when the input changes, which updates the cities that are displayed. Although this example filters the list based on the search input, Searchbar can be used in many different scenarios:

@Page({
  templateUrl: 'search/template.html',
})
class SearchPage {
  constructor() {
    this.searchQuery = '';
    this.initializeItems();
  }

  initializeItems() {
    this.items = [
      'Amsterdam',
      'Bogota',
      ...
    ];
  }

  getItems(searchbar) {
    // Reset items back to all of the items
    this.initializeItems();

    // set q to the value of the searchbar
    var q = searchbar.value;

    // if the value is an empty string don't filter the items
    if (q.trim() == '') {
      return;
    }

    this.items = this.items.filter((v) => {
      if (v.toLowerCase().indexOf(q.toLowerCase()) > -1) {
        return true;
      }
      return false;
    })
  }
}

The Searchbar takes a number of configuration options on the <ion-searchbar> element, such as cancelButtonText and hideCancelButton. Check out the Searchbar API reference for more information on configuring a Searchbar.

Segment

Improve this Doc

Use the segment to control radio selections.

Basic Usage

Demo Source

<div padding>
  <ion-segment [(ngModel)]="pet">
    <ion-segment-button value="kittens">
      Kittens
    </ion-segment-button>
    <ion-segment-button value="puppies">
      Puppies
    </ion-segment-button>
  </ion-segment>
</div>

<div [ngSwitch]="pet">
  <ion-list *ngSwitchWhen="'puppies'">
    <ion-item>
      <ion-thumbnail item-left>
        <img src="img/thumbnail-puppy-1.jpg">
      </ion-thumbnail>
      <h2>Ruby</h2>
    </ion-item>
    ...
  </ion-list>

  <ion-list *ngSwitchWhen="'kittens'">
    <ion-item>
      <ion-thumbnail item-left>
        <img src="img/thumbnail-kitten-1.jpg">
      </ion-thumbnail>
      <h2>Luna</h2>
    </ion-item>
    ...
  </ion-list>
</div>

Select

Improve this Doc

Basic Usage

Demo Source

The ion-select component is similar to an HTML <select> element, however, Ionic’s select component makes it easier for users to sort through and select the preferred option or options. When users tap the select component, a dialog will appear with all of the options in a large, easy to select list for users.


<ion-list>
  <ion-item>
    <ion-label>Gaming</ion-label>
    <ion-select [(ngModel)]="gaming">
      <ion-option value="nes">NES</ion-option>
      <ion-option value="n64">Nintendo64</ion-option>
      <ion-option value="ps">PlayStation</ion-option>
      <ion-option value="genesis">Sega Genesis</ion-option>
      <ion-option value="saturn">Sega Saturn</ion-option>
      <ion-option value="snes">SNES</ion-option>
      </ion-select>
      </ion-item>
</ion-list>

You can make multiple selection with <ion-select> by adding multiple="true" to the element

<ion-list>
  <ion-item>
    <ion-label>Toppings</ion-label>
    <ion-select [(ngModel)]="toppings" multiple="true" cancelText="Nah" okText="Okay!">
      <ion-option value="bacon" checked="true">Bacon</ion-option>
      <ion-option value="olives">Black Olives</ion-option>
      <ion-option value="xcheese" checked="true">Extra Cheese</ion-option>
      <ion-option value="peppers">Green Peppers</ion-option>
      <ion-option value="mushrooms">Mushrooms</ion-option>
      <ion-option value="onions">Onions</ion-option>
      <ion-option value="pepperoni">Pepperoni</ion-option>
      <ion-option value="pineapple">Pineapple</ion-option>
      <ion-option value="sausage">Sausage</ion-option>
      <ion-option value="Spinach">Spinach</ion-option>
    </ion-select>
  </ion-item>
</ion-list>

Slides

Improve this Doc

Slides make it easy to create galleries, tutorials, and page-based layouts.

Basic Usage

Demo Source

<ion-slides pager>

  <ion-slide style="background-color: green">
    <h2>Slide 1</h2>
  </ion-slide>

  <ion-slide style="background-color: blue">
    <h2>Slide 2</h2>
  </ion-slide>

  <ion-slide style="background-color: red">
    <h2>Slide 3</h2>
  </ion-slide>

</ion-slides>

Slides take a number of configuration options on the <ion-slides> element. Check out the Slides API reference for more information on configuring slides.

Tabs

Improve this Doc

For more details on the Tabs component, see the Tabs API reference, and the Tab API reference for information on configuring the individual Tab components it contains.

Tabs powers a multi-tabbed interface with a Tab Bar and a set of “pages” that can be tabbed through.

For iOS, tabs will appear at the bottom of the screen. For Android, tabs will be at the top of the screen, below the nav-bar. This follows each platform’s design specification, but can be configured with Config.

Tabs are useful if you have a few “root” or “top-level” pages. They are obvious to the user and quickly accessed, since they are always on the screen. However if screen space is limited, or you have a large number of root pages, a Menu may be a better option.

Basic Usage

Demo Source

To initialize Tabs, use <ion-tabs>, with a child <ion-tab> for each tab:

@App({
  template: `
    <ion-tabs>
      <ion-tab tabIcon="heart" [root]="tab1"></ion-tab>
      <ion-tab tabIcon="star" [root]="tab2"></ion-tab>
    </ion-tabs>`
})
class MyApp {
  constructor() {
    this.tab1 = Tab1;
    this.tab2 = Tab2;
  }
}

Individual tabs are just @Pages:

@Page({
  template: `
    <ion-navbar *navbar>
      <ion-title>Heart</ion-title>
    </ion-navbar>
    <ion-content>Tab 1</ion-content>`
})
class Tab1 {}

@Page({
  template: `
    <ion-navbar *navbar>
      <ion-title>Star</ion-title>
    </ion-navbar>
    <ion-content>Tab 2</ion-content>`
})
class Tab2 {}

Notice that each <ion-tab> binds to a [root] property, just like <ion-nav> in the Navigation section above. That is because each <ion-tab> is really just a navigation controller. This means that each tab has its own history stack, and NavController instances injected into children @Pages of each tab will be unique to each tab:

@Page({
...
})
class Tab1 {
  constructor(nav: NavController) {
    // Id is 1, nav refers to Tab1
    console.log(nav.id)
  }
}

@Page({
...
})
class Tab2 {
  constructor(nav: NavController) {
    // Id is 2, nav refers to Tab2
    console.log(nav.id)
  }
}

Icon Tabs

Demo Source

To add an icon inside of a tab, use the tab-icon attribute. This attribute can be passed the name of any icon:

@Page({
  template: `
  <ion-navbar *navbar>
    <ion-title>Tabs</ion-title>
  </ion-navbar>
  <ion-content>
  </ion-content>`,
})
class TabContentPage {
  constructor() {
  }
}

@Page({
  template: `
  <ion-tabs>
    <ion-tab tabIcon="contact" [root]="tab1"></ion-tab>
    <ion-tab tabIcon="compass" [root]="tab2"></ion-tab>
    <ion-tab tabIcon="analytics" [root]="tab3"></ion-tab>
    <ion-tab tabIcon="settings" [root]="tab4"></ion-tab>
  </ion-tabs>`
})
export class TabsIconPage {
  constructor() {
    this.tab1 = TabContentPage;
    this.tab2 = TabContentPage;
    ...
  }
}

Icon and Text

Demo Source

To add text and an icon inside of a tab, use the tab-icon and tab-title attributes:

@Page({
  template: `
  <ion-navbar *navbar>
    <ion-title>Tabs</ion-title>
  </ion-navbar>
  <ion-content>
  </ion-content>`
})
class TabsTextContentPage {
  constructor() {
  }
}

@Page({
  template: `
  <ion-tabs>
    <ion-tab tabIcon="water" tabTitle="Water" [root]="tab1"></ion-tab>
    <ion-tab tabIcon="leaf" tabTitle="Life" [root]="tab2"></ion-tab>
    <ion-tab tabIcon="flame" tabTitle="Fire" [root]="tab3"></ion-tab>
    <ion-tab tabIcon="magnet" tabTitle="Force" [root]="tab4"></ion-tab>
  </ion-tabs>`
})
export class TabsTextPage {
  constructor() {
    this.tab1 = TabsTextContentPage;
    this.tab2 = TabsTextContentPage;
    ...
  }
}

Badges

Demo Source

To add a badge to a tab, use the tabBadge and tabBadgeStyle attributes. The tabBadgeStyle attribute can be passed the name of any color:

@Page({
  template: `
  <ion-navbar *navbar>
    <ion-title>Tabs</ion-title>
  </ion-navbar>
  <ion-content>
  </ion-content>`,
})
class TabBadgePage {
  constructor() {
  }
}

@Page({
  template:
    '<ion-tabs>' +
      '<ion-tab tabIcon="call" [root]="tabOne" tabBadge="3" tabBadgeStyle="danger"></ion-tab>' +
      '<ion-tab tabIcon="chatbubbles" [root]="tabTwo" tabBadge="14" tabBadgeStyle="danger"></ion-tab>' +
      '<ion-tab tabIcon="musical-notes" [root]="tabThree"></ion-tab>' +
    '</ion-tabs>',
})
export class BadgesPage {
  constructor() {
    this.tabOne = TabBadgePage;
    this.tabTwo = TabBadgePage;
  }
}

For more information on tabs, check out the Tabs API reference.

Toggle

Improve this Doc

A toggle is an input component that holds a boolean value. Like the checkbox, toggles are often used to allow the user to switch a setting on or off. Attributes like value, disabled, and checked can be applied to the toggle to control its behavior. Check out the Toggle API Reference for more information.

Basic Usage

Demo Source

<ion-item>
  <ion-label> Sam</ion-label>
  <ion-toggle disabled checked="false"></ion-toggle>
</ion-item>

Toolbar

Improve this Doc

A toolbar is a generic bar that can be used in an app as a header, sub-header, footer, or even sub-footer. Since ion-toolbar is based on flexbox, no matter how many toolbars you have in your page, they will be displayed correctly and ion-content will adjust accordingly.

Basic Usage

Demo Source

Add the property position="bottom" to place the tool bar below the content:

<ion-toolbar>
  <ion-title>Toolbar</ion-title>
</ion-toolbar>

<ion-content></ion-content>

<ion-toolbar position="bottom">
  <ion-title>Footer</ion-title>
</ion-toolbar>

Header

One of the best uses of the toolbar is as a header.

<ion-toolbar primary>
  <ion-buttons start>
    <icon name="content"></icon>
  </ion-buttons>

  <ion-title>Header</ion-title>

  <ion-buttons end>
    <icon name="search"></icon>
  </ion-buttons>

</ion-toolbar>

<ion-content>
  <p>There is a header above me!</p>
</ion-content>

Buttons in Toolbars

Improve this Doc

Buttons can be added to both header and footer toolbars. To add a button to a toolbar, we need to first add an ion-buttons component. This component wraps one or more buttons, and can be given the start or end attributes to control the placement of the buttons it contains:

<ion-toolbar>
  <ion-buttons start>
    <button royal>
      <ion-icon name="search"></ion-icon>
    </button>
  </ion-buttons>
  <ion-title>Send To...</ion-title>
  <ion-buttons end>
    <button royal>
      <ion-icon name="person-add"></ion-icon>
    </button>
  </ion-buttons>
</ion-toolbar>

<ion-content></ion-content>

<ion-toolbar position="bottom">
  <p>Ash, Misty, Brock</p>
  <ion-buttons end>
    <button royal>
      Send
      <ion-icon name="send"></ion-icon>
    </button>
  </ion-buttons>
</ion-toolbar>

Segment in Toolbars

Improve this Doc

Segments are a great way to allow users to switch between different sets of data. Use the following markup to add a segment to a toolbar:

<ion-toolbar>
  <ion-buttons start>
    <button>
      <ion-icon name="create"></ion-icon>
    </button>
  </ion-buttons>
  <ion-segment>
    <ion-segment-button value="new">
      New
    </ion-segment-button>
    <ion-segment-button value="hot">
      Hot
    </ion-segment-button>
  </ion-segment>
  <ion-buttons end>
    <button>
      <ion-icon name="more"></ion-icon>
    </button>
  </ion-buttons>
</ion-toolbar>

Another common design paradigm is to include a searchbar inside your toolbar.

<ion-toolbar primary>
  <ion-searchbar [(ngModel)]="searchQuery" (input)="getItems($event)"></ion-searchbar>
</ion-toolbar>

<ion-content>
  <ion-list>
    <ion-item *ngFor="#item of items">
      {{ item }}
    </ion-item>
  </ion-list>
</ion-content>
@Page({
  templateUrl: 'search/template.html',
})
class SearchPage {
  constructor() {
    this.searchQuery = '';
    this.initializeItems();
  }

  initializeItems() {
    this.items = [
      'Angular 1.x',
      'Angular 2',
      'ReactJS',
      'EmberJS',
      'Meteor',
      'Typescript',
      'Dart',
      'CoffeeScript'
    ];
  }

  getItems(searchbar) {
    // Reset items back to all of the items
    this.initializeItems();

    // set q to the value of the searchbar
    var q = searchbar.value;

    // if the value is an empty string don't filter the items
    if (q.trim() == '') {
      return;
    }

    this.items = this.items.filter((v) => {
      if (v.toLowerCase().indexOf(q.toLowerCase()) > -1) {
        return true;
      }
      return false;
    })
  }
}

Changing the Color

You can change the toolbars color by changing the property on the element.


@Page({
  template: `
    <ion-toolbar primary>
      <ion-title>Toolbar</ion-title>
    </ion-toolbar>


    <ion-toolbar secondary>
      <ion-title>Toolbar</ion-title>
    </ion-toolbar>

    <ion-toolbar danger>
      <ion-title>Toolbar</ion-title>
    </ion-toolbar>


    <ion-toolbar dark>
      <ion-title>Toolbar</ion-title>
    </ion-toolbar>
  `
  })

You can also change the navbar’s color the same way. This will allow you to have a different color navbar per page in your app.

<ion-navbar *navbar dark>
  <ion-title>Dark</ion-title>
</ion-navbar>


<ion-navbar *navbar danger>
  <ion-title>Danger</ion-title>
</ion-navbar>

<ion-navbar *navbar secondary>
  <ion-title>Secondary</ion-title>
</ion-navbar>

API

Native

General