<commit_before>---
title:  "App Bar"
layout: detail
section: documentation
---
# App Bar

The App Bar is a flexible navigation bar designed to provide a typical Material navigation
experience.
<!--{: .intro :}-->

### Material Design Specifications

<ul class="icon-list">
  <li class="icon-link"><a href="https://www.google.com/design/spec/layout/structure.html#structure-app-bar">App Bar Structure</a></li>
  <li class="icon-link"><a href="https://www.google.com/design/spec/patterns/scrolling-techniques.html">Scrolling Techniques</a></li>
</ul>

### API Documentation

<ul class="icon-list">
  <li class="icon-link"><a href="/apidocs/AppBar/Classes/MDCAppBarContainerViewController.html">MDCAppBarContainerViewController</a></li>
  <li class="icon-link"><a href="/apidocs/AppBar/Protocols/MDCAppBarParenting.html">MDCAppBarParenting</a></li>
</ul>

- - -

## Installation

### Requirements

- Xcode 7.0 or higher.
- iOS SDK version 7.0 or higher.

### Installation with CocoaPods

To add this component to your Xcode project using CocoaPods, add the following to your `Podfile`:

~~~ bash
$ pod 'MaterialComponents/AppBar'
~~~

Then, run the following command:

~~~ bash
$ pod install
~~~

- - -

## Overview

The App Bar is a composite component that initializes and provides access to instances of the
following components:

- [Flexible Header](../FlexibleHeader)
- [Header Stack View](../HeaderStackView)
- [Navigation Bar](../NavigationBar)

The provided view hierarchy looks like so:

    <MDCFlexibleHeaderView>
       | <CALayer>
       |    | <MDCShadowLayer>
       | <UIView> <- headerView.contentView
       |    | <MDCHeaderStackView>
       |    |    | <MDCNavigationBar>

This view hierarchy will be added to your view controller hierarchy using the convenience methods
outlined in the Usage docs below.

Note that it is possible to create each of the above components yourself, though we only encourage
doing so if the App Bar is limiting your ability to build something. In such a case we recommend
also [filing an issue](https://github.com/google/material-components-ios/issues/new) so that we can
identify whether your use case is something we can directly support.



- - -

## Usage

### Add the App Bar to a view controller

Each view controller in your app that intends to use an App Bar will follow these instructions.
You'll typically add the App Bar to the same view controllers that you'd push onto a
UINavigationController, hiding the UINavigationController's `navigationBar` accordingly.

The result of following these steps will be that:

1. an App Bar is registered as a child view controller of your view controller,
2. you have access to the App Bar's Flexible Header view via the headerViewController property, and
   that
3. you have access to the Navigation Bar and Header Stack View views via the corresponding
   properties.

Step 1: **Make your view controller conform to MDCAppBarParenting**.

Conforming to this protocol allows your view controller to hold a strong reference to the App Bar
properties. As we'll see in a moment, this allows the App Bar to configure your view controller with
helper methods.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C

~~~ objc
@interface MyViewController () <MDCAppBarParenting>
@end
~~~

#### Swift
~~~ swift
class MyViewController: UITableViewController, MDCAppBarParenting
~~~
<!--</div>-->

Step 2: **Synthesize the required properties of the MDCAppBarParenting protocol**.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C

~~~ objc
@implementation MyViewController

@synthesize navigationBar;
@synthesize headerStackView;
@synthesize headerViewController;
~~~

#### Swift
~~~ swift
var headerStackView: MDCHeaderStackView?
var navigationBar: MDCNavigationBar?
var headerViewController: MDCFlexibleHeaderViewController?
~~~
<!--</div>-->

Step 3: **Initialize your view controller's App Bar**.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C

~~~ objc
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
  self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
  if (self) {
    MDCAppBarPrepareParent(self);
  }
  return self;
}
~~~

#### Swift
~~~ swift
override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: NSBundle?) {
  super.init(nibName: nibNameOrNil, bundle: nibBundleOrNil)

  MDCAppBarPrepareParent(self)
~~~
<!--</div>-->

Step 4: **Inform the App Bar that your view controller's view has loaded**.

Ideally you will do this after all views have been added to your controller's view in order to
ensure that the App Bar's view is above all of your other views.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C
~~~ objc
- (void)viewDidLoad {
  [super viewDidLoad];

  ...

  // After all other views have been registered.
  MDCAppBarAddViews(self);
}
~~~

#### Swift
~~~ swift
override func viewDidLoad() {
  super.viewDidLoad()

  // After all other views have been registered.
  MDCAppBarAddViews(self)
}
~~~
<!--</div>-->

### App Bar & UINavigationController

A view controller with an App Bar pushed onto a UINavigationController will look odd due to the
presence of two navigation bars: one provided by App Bar and another provided by
UINavigationController. The Flexible Header section on
[interacting with UINavigationController](../FlexibleHeader/#interacting-with-uinavigationcontroller)
provides recommendations for hiding the navigation bar appropriately in this situation.

### Status bar style

The Flexible Header component provides facilities for inferring the status bar style based on the
Flexible Header view's background color. Learn more by reading the section on
[Status bar style](../FlexibleHeader/#status-bar-style).

### UINavigationItem and the App Bar

The App Bar begins mirroring the state of your view controller's `navigationItem` in the provided
`navigationBar` once you call `MDCAppBarAddViews`.

Learn more by reading the Navigation Bar section on
[Observing UINavigationItem instances](../NavigationBar/#observing-uinavigationitem-instances).
Notably: read the section on "Exceptions" to understand which UINavigationItem are **not**
supported.

### Background images

Showcase photography and imagery in your App Bar by adding image views to the App Bar's Flexible
Header.

Learn more by reading the Flexible Header section on
[Background images](../FlexibleHeader/#background-images).

### Touch forwarding

The App Bar enables touch forwarding for the headerStackView and the navigationBar instances. Touch
events made to those views (not their subviews) will be forwarded to the tracking scroll view.

Learn more by reading the Flexible Header section on
[Touch forwarding](../FlexibleHeader/#touch-forwarding).

TODO: Discuss known limitiations. Discuss interactive background image (behind the stack view).<commit_msg>[AppBar] Add README section on interacting with background views.<commit_after>---
title:  "App Bar"
layout: detail
section: documentation
---
# App Bar

The App Bar is a flexible navigation bar designed to provide a typical Material navigation
experience.
<!--{: .intro :}-->

### Material Design Specifications

<ul class="icon-list">
  <li class="icon-link"><a href="https://www.google.com/design/spec/layout/structure.html#structure-app-bar">App Bar Structure</a></li>
  <li class="icon-link"><a href="https://www.google.com/design/spec/patterns/scrolling-techniques.html">Scrolling Techniques</a></li>
</ul>

### API Documentation

<ul class="icon-list">
  <li class="icon-link"><a href="/apidocs/AppBar/Classes/MDCAppBarContainerViewController.html">MDCAppBarContainerViewController</a></li>
  <li class="icon-link"><a href="/apidocs/AppBar/Protocols/MDCAppBarParenting.html">MDCAppBarParenting</a></li>
</ul>

- - -

## Installation

### Requirements

- Xcode 7.0 or higher.
- iOS SDK version 7.0 or higher.

### Installation with CocoaPods

To add this component to your Xcode project using CocoaPods, add the following to your `Podfile`:

~~~ bash
$ pod 'MaterialComponents/AppBar'
~~~

Then, run the following command:

~~~ bash
$ pod install
~~~

- - -

## Overview

The App Bar is a composite component that initializes and provides access to instances of the
following components:

- [Flexible Header](../FlexibleHeader)
- [Header Stack View](../HeaderStackView)
- [Navigation Bar](../NavigationBar)

The provided view hierarchy looks like so:

    <MDCFlexibleHeaderView>
       | <CALayer>
       |    | <MDCShadowLayer>
       | <UIView> <- headerView.contentView
       |    | <MDCHeaderStackView>
       |    |    | <MDCNavigationBar>

This view hierarchy will be added to your view controller hierarchy using the convenience methods
outlined in the Usage docs below.

Note that it is possible to create each of the above components yourself, though we only encourage
doing so if the App Bar is limiting your ability to build something. In such a case we recommend
also [filing an issue](https://github.com/google/material-components-ios/issues/new) so that we can
identify whether your use case is something we can directly support.



- - -

## Usage

### Add the App Bar to a view controller

Each view controller in your app that intends to use an App Bar will follow these instructions.
You'll typically add the App Bar to the same view controllers that you'd push onto a
UINavigationController, hiding the UINavigationController's `navigationBar` accordingly.

The result of following these steps will be that:

1. an App Bar is registered as a child view controller of your view controller,
2. you have access to the App Bar's Flexible Header view via the headerViewController property, and
   that
3. you have access to the Navigation Bar and Header Stack View views via the corresponding
   properties.

Step 1: **Make your view controller conform to MDCAppBarParenting**.

Conforming to this protocol allows your view controller to hold a strong reference to the App Bar
properties. As we'll see in a moment, this allows the App Bar to configure your view controller with
helper methods.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C

~~~ objc
@interface MyViewController () <MDCAppBarParenting>
@end
~~~

#### Swift
~~~ swift
class MyViewController: UITableViewController, MDCAppBarParenting
~~~
<!--</div>-->

Step 2: **Synthesize the required properties of the MDCAppBarParenting protocol**.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C

~~~ objc
@implementation MyViewController

@synthesize navigationBar;
@synthesize headerStackView;
@synthesize headerViewController;
~~~

#### Swift
~~~ swift
var headerStackView: MDCHeaderStackView?
var navigationBar: MDCNavigationBar?
var headerViewController: MDCFlexibleHeaderViewController?
~~~
<!--</div>-->

Step 3: **Initialize your view controller's App Bar**.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C

~~~ objc
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
  self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
  if (self) {
    MDCAppBarPrepareParent(self);
  }
  return self;
}
~~~

#### Swift
~~~ swift
override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: NSBundle?) {
  super.init(nibName: nibNameOrNil, bundle: nibBundleOrNil)

  MDCAppBarPrepareParent(self)
~~~
<!--</div>-->

Step 4: **Inform the App Bar that your view controller's view has loaded**.

Ideally you will do this after all views have been added to your controller's view in order to
ensure that the App Bar's view is above all of your other views.

<!--<div class="material-code-render" markdown="1">-->
#### Objective-C
~~~ objc
- (void)viewDidLoad {
  [super viewDidLoad];

  ...

  // After all other views have been registered.
  MDCAppBarAddViews(self);
}
~~~

#### Swift
~~~ swift
override func viewDidLoad() {
  super.viewDidLoad()

  // After all other views have been registered.
  MDCAppBarAddViews(self)
}
~~~
<!--</div>-->

### App Bar & UINavigationController

A view controller with an App Bar pushed onto a UINavigationController will look odd due to the
presence of two navigation bars: one provided by App Bar and another provided by
UINavigationController. The Flexible Header section on
[interacting with UINavigationController](../FlexibleHeader/#interacting-with-uinavigationcontroller)
provides recommendations for hiding the navigation bar appropriately in this situation.

### Status bar style

The Flexible Header component provides facilities for inferring the status bar style based on the
Flexible Header view's background color. Learn more by reading the section on
[Status bar style](../FlexibleHeader/#status-bar-style).

### UINavigationItem and the App Bar

The App Bar begins mirroring the state of your view controller's `navigationItem` in the provided
`navigationBar` once you call `MDCAppBarAddViews`.

Learn more by reading the Navigation Bar section on
[Observing UINavigationItem instances](../NavigationBar/#observing-uinavigationitem-instances).
Notably: read the section on "Exceptions" to understand which UINavigationItem are **not**
supported.

### Background images

Showcase photography and imagery in your App Bar by adding image views to the App Bar's Flexible
Header.

Learn more by reading the Flexible Header section on
[Background images](../FlexibleHeader/#background-images).

### Touch forwarding

The App Bar enables touch forwarding for the headerStackView and the navigationBar instances. Touch
events made to those views (not their subviews) will be forwarded to the tracking scroll view.

Learn more by reading the Flexible Header section on
[Touch forwarding](../FlexibleHeader/#touch-forwarding).

### Interacting with background views

Scenario: you've added a background image to your App Bar and you'd now like to be able to tap the
background image.

This is not trivial to do with the App Bar APIs due to considerations being discussed in
[Issue #184](https://github.com/google/material-components-ios/issues/184).

The heart of the limitation is that we're using a view (`headerStackView) to lay out the Navigation
Bar. If you add a background view behind the `headerStackView` instance then `headerStackView` will
end up eating all of your touch events.

Until [Issue #184](https://github.com/google/material-components-ios/issues/184) is resolved, our
recommendation for building interactive background views is the following:

1. Do not use the App Bar component.
2. Create your own Flexible Header. Learn more by reading the Flexible Header
   [Usage](../FlexibleHeader/#usage) docs.
3. Add your views to this flexible header instance.
4. Create a Navigation Bar if you need one. Treat it like any other custom view.
{'fraction_non_alphanumeric': 0.1009657594381036, 'fraction_numerical': 0.0031066387519416492, 'mean_word_length': 4.638994668697639, 'pattern_counts': {'":': 0, '<': 93, '<?xml version=': 0, '>': 91, 'https://': 8, 'lorem ipsum': 0, 'www.': 4, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5419769', 'n_tokens_mistral': 4316, 'n_tokens_neox': 4011, 'n_words': 1648}