diff --git a/api/current.txt b/api/current.txt
index a829bdf..1aa4d2a 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -4538,13 +4538,22 @@
     ctor public Notification.Action.Builder(android.app.Notification.Action);
     method public android.app.Notification.Action.Builder addExtras(android.os.Bundle);
     method public android.app.Notification.Action.Builder addRemoteInput(android.app.RemoteInput);
-    method public android.app.Notification.Action.Builder apply(android.app.Notification.Action.Builder.Extender);
     method public android.app.Notification.Action build();
+    method public android.app.Notification.Action.Builder extend(android.app.Notification.Action.Extender);
     method public android.os.Bundle getExtras();
   }
 
-  public static abstract interface Notification.Action.Builder.Extender {
-    method public abstract android.app.Notification.Action.Builder applyTo(android.app.Notification.Action.Builder);
+  public static abstract interface Notification.Action.Extender {
+    method public abstract android.app.Notification.Action.Builder extend(android.app.Notification.Action.Builder);
+  }
+
+  public static final class Notification.Action.WearableExtender implements android.app.Notification.Action.Extender {
+    ctor public Notification.Action.WearableExtender();
+    ctor public Notification.Action.WearableExtender(android.app.Notification.Action);
+    method public android.app.Notification.Action.WearableExtender clone();
+    method public android.app.Notification.Action.Builder extend(android.app.Notification.Action.Builder);
+    method public boolean isAvailableOffline();
+    method public android.app.Notification.Action.WearableExtender setAvailableOffline(boolean);
   }
 
   public static class Notification.BigPictureStyle extends android.app.Notification.Style {
@@ -4572,6 +4581,7 @@
     method public android.app.Notification.Builder addPerson(java.lang.String);
     method public android.app.Notification.Builder apply(android.app.Notification.Builder.Extender);
     method public android.app.Notification build();
+    method public android.app.Notification.Builder extend(android.app.Notification.Extender);
     method public android.os.Bundle getExtras();
     method public deprecated android.app.Notification getNotification();
     method public android.app.Notification.Builder setAutoCancel(boolean);
@@ -4613,8 +4623,8 @@
     method public android.app.Notification.Builder setWhen(long);
   }
 
-  public static abstract interface Notification.Builder.Extender {
-    method public abstract android.app.Notification.Builder applyTo(android.app.Notification.Builder);
+  public static abstract interface Notification.Extender {
+    method public abstract android.app.Notification.Builder extend(android.app.Notification.Builder);
   }
 
   public static class Notification.InboxStyle extends android.app.Notification.Style {
@@ -4644,6 +4654,51 @@
     field protected android.app.Notification.Builder mBuilder;
   }
 
+  public static final class Notification.WearableExtender implements android.app.Notification.Extender {
+    ctor public Notification.WearableExtender();
+    ctor public Notification.WearableExtender(android.app.Notification);
+    method public android.app.Notification.WearableExtender addAction(android.app.Notification.Action);
+    method public android.app.Notification.WearableExtender addActions(java.util.List<android.app.Notification.Action>);
+    method public android.app.Notification.WearableExtender addPage(android.app.Notification);
+    method public android.app.Notification.WearableExtender addPages(java.util.List<android.app.Notification>);
+    method public android.app.Notification.WearableExtender clearActions();
+    method public android.app.Notification.WearableExtender clearPages();
+    method public android.app.Notification.WearableExtender clone();
+    method public android.app.Notification.Builder extend(android.app.Notification.Builder);
+    method public java.util.List<android.app.Notification.Action> getActions();
+    method public android.graphics.Bitmap getBackground();
+    method public int getContentAction();
+    method public int getContentIcon();
+    method public int getContentIconGravity();
+    method public boolean getContentIntentAvailableOffline();
+    method public int getCustomContentHeight();
+    method public int getCustomSizePreset();
+    method public android.app.PendingIntent getDisplayIntent();
+    method public int getGravity();
+    method public boolean getHintHideIcon();
+    method public boolean getHintShowBackgroundOnly();
+    method public java.util.List<android.app.Notification> getPages();
+    method public boolean getStartScrollBottom();
+    method public android.app.Notification.WearableExtender setBackground(android.graphics.Bitmap);
+    method public android.app.Notification.WearableExtender setContentAction(int);
+    method public android.app.Notification.WearableExtender setContentIcon(int);
+    method public android.app.Notification.WearableExtender setContentIconGravity(int);
+    method public android.app.Notification.WearableExtender setContentIntentAvailableOffline(boolean);
+    method public android.app.Notification.WearableExtender setCustomContentHeight(int);
+    method public android.app.Notification.WearableExtender setCustomSizePreset(int);
+    method public android.app.Notification.WearableExtender setDisplayIntent(android.app.PendingIntent);
+    method public android.app.Notification.WearableExtender setGravity(int);
+    method public android.app.Notification.WearableExtender setHintHideIcon(boolean);
+    method public android.app.Notification.WearableExtender setHintShowBackgroundOnly(boolean);
+    method public android.app.Notification.WearableExtender setStartScrollBottom(boolean);
+    field public static final int SIZE_DEFAULT = 0; // 0x0
+    field public static final int SIZE_LARGE = 4; // 0x4
+    field public static final int SIZE_MEDIUM = 3; // 0x3
+    field public static final int SIZE_SMALL = 2; // 0x2
+    field public static final int SIZE_XSMALL = 1; // 0x1
+    field public static final int UNSET_ACTION_INDEX = -1; // 0xffffffff
+  }
+
   public class NotificationManager {
     method public void cancel(int);
     method public void cancel(java.lang.String, int);
diff --git a/core/java/android/app/Notification.java b/core/java/android/app/Notification.java
index dfd927f..6e23b11 100644
--- a/core/java/android/app/Notification.java
+++ b/core/java/android/app/Notification.java
@@ -35,6 +35,7 @@
 import android.text.TextUtils;
 import android.util.Log;
 import android.util.TypedValue;
+import android.view.Gravity;
 import android.view.View;
 import android.widget.ProgressBar;
 import android.widget.RemoteViews;
@@ -46,7 +47,9 @@
 import java.lang.annotation.RetentionPolicy;
 import java.text.NumberFormat;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collections;
+import java.util.List;
 
 /**
  * A class that represents how a persistent notification is to be presented to
@@ -767,7 +770,7 @@
      */
     public static class Action implements Parcelable {
         private final Bundle mExtras;
-        private RemoteInput[] mRemoteInputs;
+        private final RemoteInput[] mRemoteInputs;
 
         /**
          * Small icon representing the action.
@@ -910,25 +913,12 @@
              * Apply an extender to this action builder. Extenders may be used to add
              * metadata or change options on this builder.
              */
-            public Builder apply(Extender extender) {
-                extender.applyTo(this);
+            public Builder extend(Extender extender) {
+                extender.extend(this);
                 return this;
             }
 
             /**
-             * Extender interface for use with {@link #apply}. Extenders may be used to add
-             * metadata or change options on this builder.
-             */
-            public interface Extender {
-                /**
-                 * Apply this extender to a notification action builder.
-                 * @param builder the builder to be modified.
-                 * @return the build object for chaining.
-                 */
-                public Builder applyTo(Builder builder);
-            }
-
-            /**
              * Combine all of the options that have been set and return a new {@link Action}
              * object.
              * @return the built action
@@ -975,6 +965,121 @@
                 return new Action[size];
             }
         };
+
+        /**
+         * Extender interface for use with {@link Builder#extend}. Extenders may be used to add
+         * metadata or change options on an action builder.
+         */
+        public interface Extender {
+            /**
+             * Apply this extender to a notification action builder.
+             * @param builder the builder to be modified.
+             * @return the build object for chaining.
+             */
+            public Builder extend(Builder builder);
+        }
+
+        /**
+         * Wearable extender for notification actions. To add extensions to an action,
+         * create a new {@link android.app.Notification.Action.WearableExtender} object using
+         * the {@code WearableExtender()} constructor and apply it to a
+         * {@link android.app.Notification.Action.Builder} using
+         * {@link android.app.Notification.Action.Builder#extend}.
+         *
+         * <pre class="prettyprint">
+         * Notification.Action action = new Notification.Action.Builder(
+         *         R.drawable.archive_all, "Archive all", actionIntent)
+         *         .apply(new Notification.Action.WearableExtender()
+         *                 .setAvailableOffline(false))
+         *         .build();
+         * </pre>
+         */
+        public static final class WearableExtender implements Extender {
+            /** Notification action extra which contains wearable extensions */
+            private static final String EXTRA_WEARABLE_EXTENSIONS = "android.wearable.EXTENSIONS";
+
+            private static final String KEY_FLAGS = "flags";
+
+            // Flags bitwise-ored to mFlags
+            private static final int FLAG_AVAILABLE_OFFLINE = 0x1;
+
+            // Default value for flags integer
+            private static final int DEFAULT_FLAGS = FLAG_AVAILABLE_OFFLINE;
+
+            private int mFlags = DEFAULT_FLAGS;
+
+            /**
+             * Create a {@link android.app.Notification.Action.WearableExtender} with default
+             * options.
+             */
+            public WearableExtender() {
+            }
+
+            /**
+             * Create a {@link android.app.Notification.Action.WearableExtender} by reading
+             * wearable options present in an existing notification action.
+             * @param action the notification action to inspect.
+             */
+            public WearableExtender(Action action) {
+                Bundle wearableBundle = action.getExtras().getBundle(EXTRA_WEARABLE_EXTENSIONS);
+                if (wearableBundle != null) {
+                    mFlags = wearableBundle.getInt(KEY_FLAGS, DEFAULT_FLAGS);
+                }
+            }
+
+            /**
+             * Apply wearable extensions to a notification action that is being built. This is
+             * typically called by the {@link android.app.Notification.Action.Builder#extend}
+             * method of {@link android.app.Notification.Action.Builder}.
+             */
+            @Override
+            public Action.Builder extend(Action.Builder builder) {
+                Bundle wearableBundle = new Bundle();
+
+                if (mFlags != DEFAULT_FLAGS) {
+                    wearableBundle.putInt(KEY_FLAGS, mFlags);
+                }
+
+                builder.getExtras().putBundle(EXTRA_WEARABLE_EXTENSIONS, wearableBundle);
+                return builder;
+            }
+
+            @Override
+            public WearableExtender clone() {
+                WearableExtender that = new WearableExtender();
+                that.mFlags = this.mFlags;
+                return that;
+            }
+
+            /**
+             * Set whether this action is available when the wearable device is not connected to
+             * a companion device. The user can still trigger this action when the wearable device is
+             * offline, but a visual hint will indicate that the action may not be available.
+             * Defaults to true.
+             */
+            public WearableExtender setAvailableOffline(boolean availableOffline) {
+                setFlag(FLAG_AVAILABLE_OFFLINE, availableOffline);
+                return this;
+            }
+
+            /**
+             * Get whether this action is available when the wearable device is not connected to
+             * a companion device. The user can still trigger this action when the wearable device is
+             * offline, but a visual hint will indicate that the action may not be available.
+             * Defaults to true.
+             */
+            public boolean isAvailableOffline() {
+                return (mFlags & FLAG_AVAILABLE_OFFLINE) != 0;
+            }
+
+            private void setFlag(int mask, boolean value) {
+                if (value) {
+                    mFlags |= mask;
+                } else {
+                    mFlags &= ~mask;
+                }
+            }
+        }
     }
 
     /**
@@ -2169,24 +2274,11 @@
          * Apply an extender to this notification builder. Extenders may be used to add
          * metadata or change options on this builder.
          */
-        public Builder apply(Extender extender) {
-            extender.applyTo(this);
+        public Builder extend(Extender extender) {
+            extender.extend(this);
             return this;
         }
 
-        /**
-         * Extender interface for use with {@link #apply}. Extenders may be used to add
-         * metadata or change options on this builder.
-         */
-        public interface Extender {
-            /**
-             * Apply this extender to a notification builder.
-             * @param builder the builder to be modified.
-             * @return the build object for chaining.
-             */
-            public Builder applyTo(Builder builder);
-        }
-
         private void setFlag(int mask, boolean value) {
             if (value) {
                 mFlags |= mask;
@@ -3163,4 +3255,634 @@
             return big;
         }
     }
+
+    /**
+     * Extender interface for use with {@link Builder#extend}. Extenders may be used to add
+     * metadata or change options on a notification builder.
+     */
+    public interface Extender {
+        /**
+         * Apply this extender to a notification builder.
+         * @param builder the builder to be modified.
+         * @return the build object for chaining.
+         */
+        public Builder extend(Builder builder);
+    }
+
+    /**
+     * Helper class to add wearable extensions to notifications.
+     * <p class="note"> See
+     * <a href="{@docRoot}wear/notifications/creating.html">Creating Notifications
+     * for Android Wear</a> for more information on how to use this class.
+     * <p>
+     * To create a notification with wearable extensions:
+     * <ol>
+     *   <li>Create a {@link android.app.Notification.Builder}, setting any desired
+     *   properties.
+     *   <li>Create a {@link android.app.Notification.WearableExtender}.
+     *   <li>Set wearable-specific properties using the
+     *   {@code add} and {@code set} methods of {@link android.app.Notification.WearableExtender}.
+     *   <li>Call {@link android.app.Notification.Builder#extend} to apply the extensions to a
+     *   notification.
+     *   <li>Post the notification to the notification system with the
+     *   {@code NotificationManager.notify(...)} methods.
+     * </ol>
+     *
+     * <pre class="prettyprint">
+     * Notification notif = new Notification.Builder(mContext)
+     *         .setContentTitle(&quot;New mail from &quot; + sender.toString())
+     *         .setContentText(subject)
+     *         .setSmallIcon(R.drawable.new_mail)
+     *         .extend(new Notification.WearableExtender()
+     *                 .setContentIcon(R.drawable.new_mail))
+     *         .build();
+     * NotificationManager notificationManger =
+     *         (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
+     * notificationManger.notify(0, notif);</pre>
+     *
+     * <p>Wearable extensions can be accessed on an existing notification by using the
+     * {@code WearableExtender(Notification)} constructor,
+     * and then using the {@code get} methods to access values.
+     *
+     * <pre class="prettyprint">
+     * Notification.WearableExtender wearableExtender = new Notification.WearableExtender(
+     *         notification);
+     * List&lt;Notification&gt; pages = wearableExtender.getPages();
+     * </pre>
+     */
+    public static final class WearableExtender implements Extender {
+        /**
+         * Sentinel value for an action index that is unset.
+         */
+        public static final int UNSET_ACTION_INDEX = -1;
+
+        /**
+         * Size value for use with {@link #setCustomSizePreset} to show this notification with
+         * default sizing.
+         * <p>For custom display notifications created using {@link #setDisplayIntent},
+         * the default is {@link #SIZE_LARGE}. All other notifications size automatically based
+         * on their content.
+         */
+        public static final int SIZE_DEFAULT = 0;
+
+        /**
+         * Size value for use with {@link #setCustomSizePreset} to show this notification
+         * with an extra small size.
+         * <p>This value is only applicable for custom display notifications created using
+         * {@link #setDisplayIntent}.
+         */
+        public static final int SIZE_XSMALL = 1;
+
+        /**
+         * Size value for use with {@link #setCustomSizePreset} to show this notification
+         * with a small size.
+         * <p>This value is only applicable for custom display notifications created using
+         * {@link #setDisplayIntent}.
+         */
+        public static final int SIZE_SMALL = 2;
+
+        /**
+         * Size value for use with {@link #setCustomSizePreset} to show this notification
+         * with a medium size.
+         * <p>This value is only applicable for custom display notifications created using
+         * {@link #setDisplayIntent}.
+         */
+        public static final int SIZE_MEDIUM = 3;
+
+        /**
+         * Size value for use with {@link #setCustomSizePreset} to show this notification
+         * with a large size.
+         * <p>This value is only applicable for custom display notifications created using
+         * {@link #setDisplayIntent}.
+         */
+        public static final int SIZE_LARGE = 4;
+
+        /** Notification extra which contains wearable extensions */
+        private static final String EXTRA_WEARABLE_EXTENSIONS = "android.wearable.EXTENSIONS";
+
+        // Keys within EXTRA_WEARABLE_OPTIONS for wearable options.
+        private static final String KEY_ACTIONS = "actions";
+        private static final String KEY_FLAGS = "flags";
+        private static final String KEY_DISPLAY_INTENT = "displayIntent";
+        private static final String KEY_PAGES = "pages";
+        private static final String KEY_BACKGROUND = "background";
+        private static final String KEY_CONTENT_ICON = "contentIcon";
+        private static final String KEY_CONTENT_ICON_GRAVITY = "contentIconGravity";
+        private static final String KEY_CONTENT_ACTION_INDEX = "contentActionIndex";
+        private static final String KEY_CUSTOM_SIZE_PRESET = "customSizePreset";
+        private static final String KEY_CUSTOM_CONTENT_HEIGHT = "customContentHeight";
+        private static final String KEY_GRAVITY = "gravity";
+
+        // Flags bitwise-ored to mFlags
+        private static final int FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE = 0x1;
+        private static final int FLAG_HINT_HIDE_ICON = 1 << 1;
+        private static final int FLAG_HINT_SHOW_BACKGROUND_ONLY = 1 << 2;
+        private static final int FLAG_START_SCROLL_BOTTOM = 1 << 3;
+
+        // Default value for flags integer
+        private static final int DEFAULT_FLAGS = FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE;
+
+        private static final int DEFAULT_CONTENT_ICON_GRAVITY = Gravity.END;
+        private static final int DEFAULT_GRAVITY = Gravity.BOTTOM;
+
+        private ArrayList<Action> mActions = new ArrayList<Action>();
+        private int mFlags = DEFAULT_FLAGS;
+        private PendingIntent mDisplayIntent;
+        private ArrayList<Notification> mPages = new ArrayList<Notification>();
+        private Bitmap mBackground;
+        private int mContentIcon;
+        private int mContentIconGravity = DEFAULT_CONTENT_ICON_GRAVITY;
+        private int mContentActionIndex = UNSET_ACTION_INDEX;
+        private int mCustomSizePreset = SIZE_DEFAULT;
+        private int mCustomContentHeight;
+        private int mGravity = DEFAULT_GRAVITY;
+
+        /**
+         * Create a {@link android.app.Notification.WearableExtender} with default
+         * options.
+         */
+        public WearableExtender() {
+        }
+
+        public WearableExtender(Notification notif) {
+            Bundle wearableBundle = notif.extras.getBundle(EXTRA_WEARABLE_EXTENSIONS);
+            if (wearableBundle != null) {
+                List<Action> actions = wearableBundle.getParcelableArrayList(KEY_ACTIONS);
+                if (actions != null) {
+                    mActions.addAll(actions);
+                }
+
+                mFlags = wearableBundle.getInt(KEY_FLAGS, DEFAULT_FLAGS);
+                mDisplayIntent = wearableBundle.getParcelable(KEY_DISPLAY_INTENT);
+
+                Notification[] pages = getNotificationArrayFromBundle(
+                        wearableBundle, KEY_PAGES);
+                if (pages != null) {
+                    Collections.addAll(mPages, pages);
+                }
+
+                mBackground = wearableBundle.getParcelable(KEY_BACKGROUND);
+                mContentIcon = wearableBundle.getInt(KEY_CONTENT_ICON);
+                mContentIconGravity = wearableBundle.getInt(KEY_CONTENT_ICON_GRAVITY,
+                        DEFAULT_CONTENT_ICON_GRAVITY);
+                mContentActionIndex = wearableBundle.getInt(KEY_CONTENT_ACTION_INDEX,
+                        UNSET_ACTION_INDEX);
+                mCustomSizePreset = wearableBundle.getInt(KEY_CUSTOM_SIZE_PRESET,
+                        SIZE_DEFAULT);
+                mCustomContentHeight = wearableBundle.getInt(KEY_CUSTOM_CONTENT_HEIGHT);
+                mGravity = wearableBundle.getInt(KEY_GRAVITY, DEFAULT_GRAVITY);
+            }
+        }
+
+        /**
+         * Apply wearable extensions to a notification that is being built. This is typically
+         * called by the {@link android.app.Notification.Builder#extend} method of
+         * {@link android.app.Notification.Builder}.
+         */
+        @Override
+        public Notification.Builder extend(Notification.Builder builder) {
+            Bundle wearableBundle = new Bundle();
+
+            if (!mActions.isEmpty()) {
+                wearableBundle.putParcelableArrayList(KEY_ACTIONS, mActions);
+            }
+            if (mFlags != DEFAULT_FLAGS) {
+                wearableBundle.putInt(KEY_FLAGS, mFlags);
+            }
+            if (mDisplayIntent != null) {
+                wearableBundle.putParcelable(KEY_DISPLAY_INTENT, mDisplayIntent);
+            }
+            if (!mPages.isEmpty()) {
+                wearableBundle.putParcelableArray(KEY_PAGES, mPages.toArray(
+                        new Notification[mPages.size()]));
+            }
+            if (mBackground != null) {
+                wearableBundle.putParcelable(KEY_BACKGROUND, mBackground);
+            }
+            if (mContentIcon != 0) {
+                wearableBundle.putInt(KEY_CONTENT_ICON, mContentIcon);
+            }
+            if (mContentIconGravity != DEFAULT_CONTENT_ICON_GRAVITY) {
+                wearableBundle.putInt(KEY_CONTENT_ICON_GRAVITY, mContentIconGravity);
+            }
+            if (mContentActionIndex != UNSET_ACTION_INDEX) {
+                wearableBundle.putInt(KEY_CONTENT_ACTION_INDEX,
+                        mContentActionIndex);
+            }
+            if (mCustomSizePreset != SIZE_DEFAULT) {
+                wearableBundle.putInt(KEY_CUSTOM_SIZE_PRESET, mCustomSizePreset);
+            }
+            if (mCustomContentHeight != 0) {
+                wearableBundle.putInt(KEY_CUSTOM_CONTENT_HEIGHT, mCustomContentHeight);
+            }
+            if (mGravity != DEFAULT_GRAVITY) {
+                wearableBundle.putInt(KEY_GRAVITY, mGravity);
+            }
+
+            builder.getExtras().putBundle(EXTRA_WEARABLE_EXTENSIONS, wearableBundle);
+            return builder;
+        }
+
+        @Override
+        public WearableExtender clone() {
+            WearableExtender that = new WearableExtender();
+            that.mActions = new ArrayList<Action>(this.mActions);
+            that.mFlags = this.mFlags;
+            that.mDisplayIntent = this.mDisplayIntent;
+            that.mPages = new ArrayList<Notification>(this.mPages);
+            that.mBackground = this.mBackground;
+            that.mContentIcon = this.mContentIcon;
+            that.mContentIconGravity = this.mContentIconGravity;
+            that.mContentActionIndex = this.mContentActionIndex;
+            that.mCustomSizePreset = this.mCustomSizePreset;
+            that.mCustomContentHeight = this.mCustomContentHeight;
+            that.mGravity = this.mGravity;
+            return that;
+        }
+
+        /**
+         * Add a wearable action to this notification.
+         *
+         * <p>When wearable actions are added using this method, the set of actions that
+         * show on a wearable device splits from devices that only show actions added
+         * using {@link android.app.Notification.Builder#addAction}. This allows for customization
+         * of which actions display on different devices.
+         *
+         * @param action the action to add to this notification
+         * @return this object for method chaining
+         * @see android.app.Notification.Action
+         */
+        public WearableExtender addAction(Action action) {
+            mActions.add(action);
+            return this;
+        }
+
+        /**
+         * Adds wearable actions to this notification.
+         *
+         * <p>When wearable actions are added using this method, the set of actions that
+         * show on a wearable device splits from devices that only show actions added
+         * using {@link android.app.Notification.Builder#addAction}. This allows for customization
+         * of which actions display on different devices.
+         *
+         * @param actions the actions to add to this notification
+         * @return this object for method chaining
+         * @see android.app.Notification.Action
+         */
+        public WearableExtender addActions(List<Action> actions) {
+            mActions.addAll(actions);
+            return this;
+        }
+
+        /**
+         * Clear all wearable actions present on this builder.
+         * @return this object for method chaining.
+         * @see #addAction
+         */
+        public WearableExtender clearActions() {
+            mActions.clear();
+            return this;
+        }
+
+        /**
+         * Get the wearable actions present on this notification.
+         */
+        public List<Action> getActions() {
+            return mActions;
+        }
+
+        /**
+         * Set an intent to launch inside of an activity view when displaying
+         * this notification. This {@link PendingIntent} should be for an activity.
+         *
+         * @param intent the {@link PendingIntent} for an activity
+         * @return this object for method chaining
+         * @see android.app.Notification.WearableExtender#getDisplayIntent
+         */
+        public WearableExtender setDisplayIntent(PendingIntent intent) {
+            mDisplayIntent = intent;
+            return this;
+        }
+
+        /**
+         * Get the intent to launch inside of an activity view when displaying this
+         * notification. This {@code PendingIntent} should be for an activity.
+         */
+        public PendingIntent getDisplayIntent() {
+            return mDisplayIntent;
+        }
+
+        /**
+         * Add an additional page of content to display with this notification. The current
+         * notification forms the first page, and pages added using this function form
+         * subsequent pages. This field can be used to separate a notification into multiple
+         * sections.
+         *
+         * @param page the notification to add as another page
+         * @return this object for method chaining
+         * @see android.app.Notification.WearableExtender#getPages
+         */
+        public WearableExtender addPage(Notification page) {
+            mPages.add(page);
+            return this;
+        }
+
+        /**
+         * Add additional pages of content to display with this notification. The current
+         * notification forms the first page, and pages added using this function form
+         * subsequent pages. This field can be used to separate a notification into multiple
+         * sections.
+         *
+         * @param pages a list of notifications
+         * @return this object for method chaining
+         * @see android.app.Notification.WearableExtender#getPages
+         */
+        public WearableExtender addPages(List<Notification> pages) {
+            mPages.addAll(pages);
+            return this;
+        }
+
+        /**
+         * Clear all additional pages present on this builder.
+         * @return this object for method chaining.
+         * @see #addPage
+         */
+        public WearableExtender clearPages() {
+            mPages.clear();
+            return this;
+        }
+
+        /**
+         * Get the array of additional pages of content for displaying this notification. The
+         * current notification forms the first page, and elements within this array form
+         * subsequent pages. This field can be used to separate a notification into multiple
+         * sections.
+         * @return the pages for this notification
+         */
+        public List<Notification> getPages() {
+            return mPages;
+        }
+
+        /**
+         * Set a background image to be displayed behind the notification content.
+         * Contrary to the {@link android.app.Notification.BigPictureStyle}, this background
+         * will work with any notification style.
+         *
+         * @param background the background bitmap
+         * @return this object for method chaining
+         * @see android.app.Notification.WearableExtender#getBackground
+         */
+        public WearableExtender setBackground(Bitmap background) {
+            mBackground = background;
+            return this;
+        }
+
+        /**
+         * Get a background image to be displayed behind the notification content.
+         * Contrary to the {@link android.app.Notification.BigPictureStyle}, this background
+         * will work with any notification style.
+         *
+         * @return the background image
+         * @see android.app.Notification.WearableExtender#setBackground
+         */
+        public Bitmap getBackground() {
+            return mBackground;
+        }
+
+        /**
+         * Set an icon that goes with the content of this notification.
+         */
+        public WearableExtender setContentIcon(int icon) {
+            mContentIcon = icon;
+            return this;
+        }
+
+        /**
+         * Get an icon that goes with the content of this notification.
+         */
+        public int getContentIcon() {
+            return mContentIcon;
+        }
+
+        /**
+         * Set the gravity that the content icon should have within the notification display.
+         * Supported values include {@link android.view.Gravity#START} and
+         * {@link android.view.Gravity#END}. The default value is {@link android.view.Gravity#END}.
+         * @see #setContentIcon
+         */
+        public WearableExtender setContentIconGravity(int contentIconGravity) {
+            mContentIconGravity = contentIconGravity;
+            return this;
+        }
+
+        /**
+         * Get the gravity that the content icon should have within the notification display.
+         * Supported values include {@link android.view.Gravity#START} and
+         * {@link android.view.Gravity#END}. The default value is {@link android.view.Gravity#END}.
+         * @see #getContentIcon
+         */
+        public int getContentIconGravity() {
+            return mContentIconGravity;
+        }
+
+        /**
+         * Set an action from this notification's actions to be clickable with the content of
+         * this notification page. This action will no longer display separately from the
+         * notification content. This action's icon will display with optional subtext provided
+         * by the action's title.
+         * @param actionIndex The index of the action to hoist on the current notification page.
+         *                    If wearable actions are present, this index will apply to that list,
+         *                    otherwise it will apply to the main notification's actions list.
+         */
+        public WearableExtender setContentAction(int actionIndex) {
+            mContentActionIndex = actionIndex;
+            return this;
+        }
+
+        /**
+         * Get the action index of an action from this notification to show as clickable with
+         * the content of this notification page. When the user clicks this notification page,
+         * this action will trigger. This action will no longer display separately from the
+         * notification content. The action's icon will display with optional subtext provided
+         * by the action's title.
+         *
+         * <p>If wearable specific actions are present, this index will apply to that list,
+         * otherwise it will apply to the main notification's actions list.
+         */
+        public int getContentAction() {
+            return mContentActionIndex;
+        }
+
+        /**
+         * Set the gravity that this notification should have within the available viewport space.
+         * Supported values include {@link android.view.Gravity#TOP},
+         * {@link android.view.Gravity#CENTER_VERTICAL} and {@link android.view.Gravity#BOTTOM}.
+         * The default value is {@link android.view.Gravity#BOTTOM}.
+         */
+        public WearableExtender setGravity(int gravity) {
+            mGravity = gravity;
+            return this;
+        }
+
+        /**
+         * Get the gravity that this notification should have within the available viewport space.
+         * Supported values include {@link android.view.Gravity#TOP},
+         * {@link android.view.Gravity#CENTER_VERTICAL} and {@link android.view.Gravity#BOTTOM}.
+         * The default value is {@link android.view.Gravity#BOTTOM}.
+         */
+        public int getGravity() {
+            return mGravity;
+        }
+
+        /**
+         * Set the custom size preset for the display of this notification out of the available
+         * presets found in {@link android.app.Notification.WearableExtender}, e.g.
+         * {@link #SIZE_LARGE}.
+         * <p>Some custom size presets are only applicable for custom display notifications created
+         * using {@link android.app.Notification.WearableExtender#setDisplayIntent}. Check the
+         * documentation for the preset in question. See also
+         * {@link #setCustomContentHeight} and {@link #getCustomSizePreset}.
+         */
+        public WearableExtender setCustomSizePreset(int sizePreset) {
+            mCustomSizePreset = sizePreset;
+            return this;
+        }
+
+        /**
+         * Get the custom size preset for the display of this notification out of the available
+         * presets found in {@link android.app.Notification.WearableExtender}, e.g.
+         * {@link #SIZE_LARGE}.
+         * <p>Some custom size presets are only applicable for custom display notifications created
+         * using {@link #setDisplayIntent}. Check the documentation for the preset in question.
+         * See also {@link #setCustomContentHeight} and {@link #setCustomSizePreset}.
+         */
+        public int getCustomSizePreset() {
+            return mCustomSizePreset;
+        }
+
+        /**
+         * Set the custom height in pixels for the display of this notification's content.
+         * <p>This option is only available for custom display notifications created
+         * using {@link android.app.Notification.WearableExtender#setDisplayIntent}. See also
+         * {@link android.app.Notification.WearableExtender#setCustomSizePreset} and
+         * {@link #getCustomContentHeight}.
+         */
+        public WearableExtender setCustomContentHeight(int height) {
+            mCustomContentHeight = height;
+            return this;
+        }
+
+        /**
+         * Get the custom height in pixels for the display of this notification's content.
+         * <p>This option is only available for custom display notifications created
+         * using {@link #setDisplayIntent}. See also {@link #setCustomSizePreset} and
+         * {@link #setCustomContentHeight}.
+         */
+        public int getCustomContentHeight() {
+            return mCustomContentHeight;
+        }
+
+        /**
+         * Set whether the scrolling position for the contents of this notification should start
+         * at the bottom of the contents instead of the top when the contents are too long to
+         * display within the screen.  Default is false (start scroll at the top).
+         */
+        public WearableExtender setStartScrollBottom(boolean startScrollBottom) {
+            setFlag(FLAG_START_SCROLL_BOTTOM, startScrollBottom);
+            return this;
+        }
+
+        /**
+         * Get whether the scrolling position for the contents of this notification should start
+         * at the bottom of the contents instead of the top when the contents are too long to
+         * display within the screen. Default is false (start scroll at the top).
+         */
+        public boolean getStartScrollBottom() {
+            return (mFlags & FLAG_START_SCROLL_BOTTOM) != 0;
+        }
+
+        /**
+         * Set whether the content intent is available when the wearable device is not connected
+         * to a companion device.  The user can still trigger this intent when the wearable device
+         * is offline, but a visual hint will indicate that the content intent may not be available.
+         * Defaults to true.
+         */
+        public WearableExtender setContentIntentAvailableOffline(
+                boolean contentIntentAvailableOffline) {
+            setFlag(FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE, contentIntentAvailableOffline);
+            return this;
+        }
+
+        /**
+         * Get whether the content intent is available when the wearable device is not connected
+         * to a companion device.  The user can still trigger this intent when the wearable device
+         * is offline, but a visual hint will indicate that the content intent may not be available.
+         * Defaults to true.
+         */
+        public boolean getContentIntentAvailableOffline() {
+            return (mFlags & FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE) != 0;
+        }
+
+        /**
+         * Set a hint that this notification's icon should not be displayed.
+         * @param hintHideIcon {@code true} to hide the icon, {@code false} otherwise.
+         * @return this object for method chaining
+         */
+        public WearableExtender setHintHideIcon(boolean hintHideIcon) {
+            setFlag(FLAG_HINT_HIDE_ICON, hintHideIcon);
+            return this;
+        }
+
+        /**
+         * Get a hint that this notification's icon should not be displayed.
+         * @return {@code true} if this icon should not be displayed, false otherwise.
+         * The default value is {@code false} if this was never set.
+         */
+        public boolean getHintHideIcon() {
+            return (mFlags & FLAG_HINT_HIDE_ICON) != 0;
+        }
+
+        /**
+         * Set a visual hint that only the background image of this notification should be
+         * displayed, and other semantic content should be hidden. This hint is only applicable
+         * to sub-pages added using {@link #addPage}.
+         */
+        public WearableExtender setHintShowBackgroundOnly(boolean hintShowBackgroundOnly) {
+            setFlag(FLAG_HINT_SHOW_BACKGROUND_ONLY, hintShowBackgroundOnly);
+            return this;
+        }
+
+        /**
+         * Get a visual hint that only the background image of this notification should be
+         * displayed, and other semantic content should be hidden. This hint is only applicable
+         * to sub-pages added using {@link android.app.Notification.WearableExtender#addPage}.
+         */
+        public boolean getHintShowBackgroundOnly() {
+            return (mFlags & FLAG_HINT_SHOW_BACKGROUND_ONLY) != 0;
+        }
+
+        private void setFlag(int mask, boolean value) {
+            if (value) {
+                mFlags |= mask;
+            } else {
+                mFlags &= ~mask;
+            }
+        }
+    }
+
+    /**
+     * Get an array of Notification objects from a parcelable array bundle field.
+     * Update the bundle to have a typed array so fetches in the future don't need
+     * to do an array copy.
+     */
+    private static Notification[] getNotificationArrayFromBundle(Bundle bundle, String key) {
+        Parcelable[] array = bundle.getParcelableArray(key);
+        if (array instanceof Notification[] || array == null) {
+            return (Notification[]) array;
+        }
+        Notification[] typedArray = Arrays.copyOf(array, array.length,
+                Notification[].class);
+        bundle.putParcelableArray(key, typedArray);
+        return typedArray;
+    }
 }
diff --git a/core/java/android/app/RemoteInput.java b/core/java/android/app/RemoteInput.java
index 9cfc541..11420c5 100644
--- a/core/java/android/app/RemoteInput.java
+++ b/core/java/android/app/RemoteInput.java
@@ -64,18 +64,24 @@
     /** Extra added to a clip data intent object to hold the results bundle. */
     public static final String EXTRA_RESULTS_DATA = "android.remoteinput.resultsData";
 
+    // Flags bitwise-ored to mFlags
+    private static final int FLAG_ALLOW_FREE_FORM_INPUT = 0x1;
+
+    // Default value for flags integer
+    private static final int DEFAULT_FLAGS = FLAG_ALLOW_FREE_FORM_INPUT;
+
     private final String mResultKey;
     private final CharSequence mLabel;
     private final CharSequence[] mChoices;
-    private final boolean mAllowFreeFormInput;
+    private final int mFlags;
     private final Bundle mExtras;
 
     private RemoteInput(String resultKey, CharSequence label, CharSequence[] choices,
-            boolean allowFreeFormInput, Bundle extras) {
+            int flags, Bundle extras) {
         this.mResultKey = resultKey;
         this.mLabel = label;
         this.mChoices = choices;
-        this.mAllowFreeFormInput = allowFreeFormInput;
+        this.mFlags = flags;
         this.mExtras = extras;
     }
 
@@ -108,7 +114,7 @@
      * if you set this to false and {@link #getChoices} returns {@code null} or empty.
      */
     public boolean getAllowFreeFormInput() {
-        return mAllowFreeFormInput;
+        return (mFlags & FLAG_ALLOW_FREE_FORM_INPUT) != 0;
     }
 
     /**
@@ -125,7 +131,7 @@
         private final String mResultKey;
         private CharSequence mLabel;
         private CharSequence[] mChoices;
-        private boolean mAllowFreeFormInput = true;
+        private int mFlags = DEFAULT_FLAGS;
         private Bundle mExtras = new Bundle();
 
         /**
@@ -178,7 +184,7 @@
          * @return this object for method chaining
          */
         public Builder setAllowFreeFormInput(boolean allowFreeFormInput) {
-            mAllowFreeFormInput = allowFreeFormInput;
+            setFlag(mFlags, allowFreeFormInput);
             return this;
         }
 
@@ -205,12 +211,20 @@
             return mExtras;
         }
 
+        private void setFlag(int mask, boolean value) {
+            if (value) {
+                mFlags |= mask;
+            } else {
+                mFlags &= ~mask;
+            }
+        }
+
         /**
          * Combine all of the options that have been set and return a new {@link RemoteInput}
          * object.
          */
         public RemoteInput build() {
-            return new RemoteInput(mResultKey, mLabel, mChoices, mAllowFreeFormInput, mExtras);
+            return new RemoteInput(mResultKey, mLabel, mChoices, mFlags, mExtras);
         }
     }
 
@@ -218,7 +232,7 @@
         mResultKey = in.readString();
         mLabel = in.readCharSequence();
         mChoices = in.readCharSequenceArray();
-        mAllowFreeFormInput = in.readInt() != 0;
+        mFlags = in.readInt();
         mExtras = in.readBundle();
     }
 
@@ -279,7 +293,7 @@
         out.writeString(mResultKey);
         out.writeCharSequence(mLabel);
         out.writeCharSequenceArray(mChoices);
-        out.writeInt(mAllowFreeFormInput ? 1 : 0);
+        out.writeInt(mFlags);
         out.writeBundle(mExtras);
     }
 
diff --git a/core/java/android/app/wearable/WearableActionExtensions.java b/core/java/android/app/wearable/WearableActionExtensions.java
deleted file mode 100644
index c296ef2..0000000
--- a/core/java/android/app/wearable/WearableActionExtensions.java
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.app.wearable;
-
-import android.app.Notification;
-import android.os.Parcel;
-import android.os.Parcelable;
-
-/**
- * Wearable extensions to notification actions. To add extensions to an action,
- * create a new {@link WearableActionExtensions} object using
- * {@link WearableActionExtensions.Builder} and apply it to a
- * {@link android.app.Notification.Action.Builder}.
- *
- * <pre class="prettyprint">
- * Notification.Action action = new Notification.Action.Builder(
- *         R.drawable.archive_all, "Archive all", actionIntent)
- *         .apply(new WearableActionExtensions.Builder()
- *                 .setAvailableOffline(false)
- *                 .build())
- *         .build();
- * </pre>
- */
-public final class WearableActionExtensions implements Notification.Action.Builder.Extender,
-        Parcelable {
-    /** Notification action extra which contains wearable extensions */
-    private static final String EXTRA_WEARABLE_EXTENSIONS = "android.wearable.EXTENSIONS";
-
-    // Flags bitwise-ored to mFlags
-    private static final int FLAG_AVAILABLE_OFFLINE = 1 << 0;
-
-    // Default value for flags integer
-    private static final int DEFAULT_FLAGS = FLAG_AVAILABLE_OFFLINE;
-
-    private final int mFlags;
-
-    private WearableActionExtensions(int flags) {
-        mFlags = flags;
-    }
-
-    private WearableActionExtensions(Parcel in) {
-        mFlags = in.readInt();
-    }
-
-    /**
-     * Create a {@link WearableActionExtensions} by reading wearable extensions present on an
-     * existing notification action.
-     * @param action the notification action to inspect.
-     * @return a new {@link WearableActionExtensions} object.
-     */
-    public static WearableActionExtensions from(Notification.Action action) {
-        WearableActionExtensions extensions = action.getExtras().getParcelable(
-                EXTRA_WEARABLE_EXTENSIONS);
-        if (extensions != null) {
-            return extensions;
-        } else {
-            // Return a WearableActionExtensions with default values.
-            return new Builder().build();
-        }
-    }
-
-    /**
-     * Get whether this action is available when the wearable device is not connected to
-     * a companion device. The user can still trigger this action when the wearable device is
-     * offline, but a visual hint will indicate that the action may not be available.
-     * Defaults to true.
-     */
-    public boolean isAvailableOffline() {
-        return (mFlags & FLAG_AVAILABLE_OFFLINE) != 0;
-    }
-
-    @Override
-    public Notification.Action.Builder applyTo(Notification.Action.Builder builder) {
-        builder.getExtras().putParcelable(EXTRA_WEARABLE_EXTENSIONS, this);
-        return builder;
-    }
-
-    @Override
-    public int describeContents() {
-        return 0;
-    }
-
-    @Override
-    public void writeToParcel(Parcel out, int flags) {
-        out.writeInt(mFlags);
-    }
-
-    /**
-     * Builder for {@link WearableActionExtensions} objects, which adds wearable extensions to
-     * notification actions. To extend an action, create an instance of this class, call the set
-     * methods present, call {@link #build}, and finally apply the options to a
-     * {@link Notification.Action.Builder} using its
-     * {@link android.app.Notification.Action.Builder#apply} method.
-     */
-    public static final class Builder {
-        private int mFlags = DEFAULT_FLAGS;
-
-        /**
-         * Construct a builder to be used for adding wearable extensions to notification actions.
-         *
-         * <pre class="prettyprint">
-         * Notification.Action action = new Notification.Action.Builder(
-         *         R.drawable.archive_all, "Archive all", actionIntent)
-         *         .apply(new WearableActionExtensions.Builder()
-         *                 .setAvailableOffline(false)
-         *                 .build())
-         *         .build();</pre>
-         */
-        public Builder() {
-        }
-
-        /**
-         * Create a {@link Builder} by reading wearable extensions present on an
-         * existing {@code WearableActionExtensions} object.
-         * @param other the existing extensions to inspect.
-         */
-        public Builder(WearableActionExtensions other) {
-            mFlags = other.mFlags;
-        }
-
-        /**
-         * Set whether this action is available when the wearable device is not connected to
-         * a companion device. The user can still trigger this action when the wearable device is
-         * offline, but a visual hint will indicate that the action may not be available.
-         * Defaults to true.
-         */
-        public Builder setAvailableOffline(boolean availableOffline) {
-            setFlag(FLAG_AVAILABLE_OFFLINE, availableOffline);
-            return this;
-        }
-
-        /**
-         * Build a new {@link WearableActionExtensions} object with the extensions
-         * currently present on this builder.
-         * @return the extensions object.
-         */
-        public WearableActionExtensions build() {
-            return new WearableActionExtensions(mFlags);
-        }
-
-        private void setFlag(int mask, boolean value) {
-            if (value) {
-                mFlags |= mask;
-            } else {
-                mFlags &= ~mask;
-            }
-        }
-    }
-
-    public static final Creator<WearableActionExtensions> CREATOR =
-            new Creator<WearableActionExtensions>() {
-        @Override
-        public WearableActionExtensions createFromParcel(Parcel in) {
-            return new WearableActionExtensions(in);
-        }
-
-        @Override
-        public WearableActionExtensions[] newArray(int size) {
-            return new WearableActionExtensions[size];
-        }
-    };
-}
diff --git a/core/java/android/app/wearable/WearableNotificationExtensions.java b/core/java/android/app/wearable/WearableNotificationExtensions.java
deleted file mode 100644
index d433613..0000000
--- a/core/java/android/app/wearable/WearableNotificationExtensions.java
+++ /dev/null
@@ -1,702 +0,0 @@
-/*
- * Copyright (C) 2014 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.app.wearable;
-
-import android.app.Notification;
-import android.app.PendingIntent;
-import android.graphics.Bitmap;
-import android.os.Parcel;
-import android.os.Parcelable;
-import android.view.Gravity;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-
-/**
- * Helper class that contains wearable extensions for notifications.
- * <p class="note"> See
- * <a href="{@docRoot}wear/notifications/creating.html">Creating Notifications
- * for Android Wear</a> for more information on how to use this class.
- * <p>
- * To create a notification with wearable extensions:
- * <ol>
- *   <li>Create a {@link Notification.Builder}, setting any desired
- *   properties.
- *   <li>Create a {@link WearableNotificationExtensions.Builder}.
- *   <li>Set wearable-specific properties using the
- *   {@code add} and {@code set} methods of {@link WearableNotificationExtensions.Builder}.
- *   <li>Call {@link WearableNotificationExtensions.Builder#build} to build the extensions
- *   object.
- *   <li>Call {@link Notification.Builder#apply} to apply the extensions to a notification.
- *   <li>Post the notification to the notification system with the
- *   {@code NotificationManager.notify(...)} methods.
- * </ol>
- *
- * <pre class="prettyprint">
- * Notification notif = new Notification.Builder(mContext)
- *         .setContentTitle(&quot;New mail from &quot; + sender.toString())
- *         .setContentText(subject)
- *         .setSmallIcon(R.drawable.new_mail)
- *         .apply(new new WearableNotificationExtensions.Builder()
- *                 .setContentIcon(R.drawable.new_mail)
- *                 .build())
- *         .build();
- * NotificationManager notificationManger =
- *         (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
- * notificationManger.notify(0, notif);</pre>
- *
- * <p>Wearable extensions can be accessed on an existing notification by using the
- * {@link WearableNotificationExtensions#from} function.
- *
- * <pre class="prettyprint">
- * WearableNotificationExtensions wearableExtensions = WearableNotificationExtensions.from(
- *         notification);
- * Notification[] pages = wearableExtensions.getPages();
- * </pre>
- */
-public final class WearableNotificationExtensions implements Notification.Builder.Extender,
-        Parcelable {
-    /**
-     * Sentinel value for an action index that is unset.
-     */
-    public static final int UNSET_ACTION_INDEX = -1;
-
-    /**
-     * Size value for use with {@link Builder#setCustomSizePreset} to show this notification with
-     * default sizing.
-     * <p>For custom display notifications created using {@link Builder#setDisplayIntent},
-     * the default is {@link #SIZE_LARGE}. All other notifications size automatically based
-     * on their content.
-     */
-    public static final int SIZE_DEFAULT = 0;
-
-    /**
-     * Size value for use with {@link Builder#setCustomSizePreset} to show this notification
-     * with an extra small size.
-     * <p>This value is only applicable for custom display notifications created using
-     * {@link Builder#setDisplayIntent}.
-     */
-    public static final int SIZE_XSMALL = 1;
-
-    /**
-     * Size value for use with {@link Builder#setCustomSizePreset} to show this notification
-     * with a small size.
-     * <p>This value is only applicable for custom display notifications created using
-     * {@link Builder#setDisplayIntent}.
-     */
-    public static final int SIZE_SMALL = 2;
-
-    /**
-     * Size value for use with {@link Builder#setCustomSizePreset} to show this notification
-     * with a medium size.
-     * <p>This value is only applicable for custom display notifications created using
-     * {@link Builder#setDisplayIntent}.
-     */
-    public static final int SIZE_MEDIUM = 3;
-
-    /**
-     * Size value for use with {@link Builder#setCustomSizePreset} to show this notification
-     * with a large size.
-     * <p>This value is only applicable for custom display notifications created using
-     * {@link Builder#setDisplayIntent}.
-     */
-    public static final int SIZE_LARGE = 4;
-
-    /** Notification extra which contains wearable extensions */
-    static final String EXTRA_WEARABLE_EXTENSIONS = "android.wearable.EXTENSIONS";
-
-    // Flags bitwise-ored to mFlags
-    static final int FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE = 1 << 0;
-    static final int FLAG_HINT_HIDE_ICON = 1 << 1;
-    static final int FLAG_HINT_SHOW_BACKGROUND_ONLY = 1 << 2;
-    static final int FLAG_START_SCROLL_BOTTOM = 1 << 3;
-
-    // Default value for flags integer
-    static final int DEFAULT_FLAGS = FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE;
-
-    private final Notification.Action[] mActions;
-    private final int mFlags;
-    private final PendingIntent mDisplayIntent;
-    private final Notification[] mPages;
-    private final Bitmap mBackground;
-    private final int mContentIcon;
-    private final int mContentIconGravity;
-    private final int mContentActionIndex;
-    private final int mCustomSizePreset;
-    private final int mCustomContentHeight;
-    private final int mGravity;
-
-    private WearableNotificationExtensions(Notification.Action[] actions, int flags,
-            PendingIntent displayIntent, Notification[] pages, Bitmap background,
-            int contentIcon, int contentIconGravity, int contentActionIndex,
-            int customSizePreset, int customContentHeight, int gravity) {
-        mActions = actions;
-        mFlags = flags;
-        mDisplayIntent = displayIntent;
-        mPages = pages;
-        mBackground = background;
-        mContentIcon = contentIcon;
-        mContentIconGravity = contentIconGravity;
-        mContentActionIndex = contentActionIndex;
-        mCustomSizePreset = customSizePreset;
-        mCustomContentHeight = customContentHeight;
-        mGravity = gravity;
-    }
-
-    private WearableNotificationExtensions(Parcel in) {
-        mActions = in.createTypedArray(Notification.Action.CREATOR);
-        mFlags = in.readInt();
-        mDisplayIntent = in.readParcelable(PendingIntent.class.getClassLoader());
-        mPages = in.createTypedArray(Notification.CREATOR);
-        mBackground = in.readParcelable(Bitmap.class.getClassLoader());
-        mContentIcon = in.readInt();
-        mContentIconGravity = in.readInt();
-        mContentActionIndex = in.readInt();
-        mCustomSizePreset = in.readInt();
-        mCustomContentHeight = in.readInt();
-        mGravity = in.readInt();
-    }
-
-    /**
-     * Create a {@link WearableNotificationExtensions} by reading wearable extensions present on an
-     * existing notification.
-     * @param notif the notification to inspect.
-     * @return a new {@link WearableNotificationExtensions} object.
-     */
-    public static WearableNotificationExtensions from(Notification notif) {
-        WearableNotificationExtensions extensions = notif.extras.getParcelable(
-                EXTRA_WEARABLE_EXTENSIONS);
-        if (extensions != null) {
-            return extensions;
-        } else {
-            // Return a WearableNotificationExtensions with default values.
-            return new Builder().build();
-        }
-    }
-
-    /**
-     * Apply wearable extensions to a notification that is being built. This is typically
-     * called by {@link Notification.Builder#apply} method of {@link Notification.Builder}.
-     */
-    @Override
-    public Notification.Builder applyTo(Notification.Builder builder) {
-        builder.getExtras().putParcelable(EXTRA_WEARABLE_EXTENSIONS, this);
-        return builder;
-    }
-
-    /**
-     * Get the number of wearable actions present on this notification.
-     *
-     * @return the number of wearable actions for this notification
-     */
-    public int getActionCount() {
-        return mActions.length;
-    }
-
-    /**
-     * Get a {@link Notification.Action} for the wearable action at {@code actionIndex}.
-     * @param actionIndex the index of the desired wearable action
-     */
-    public Notification.Action getAction(int actionIndex) {
-        return mActions[actionIndex];
-    }
-
-    /**
-     * Get the wearable actions present on this notification.
-     */
-    public Notification.Action[] getActions() {
-        return mActions;
-    }
-
-    /**
-     * Get the intent to launch inside of an activity view when displaying this
-     * notification. This {@code PendingIntent} should be for an activity.
-     */
-    public PendingIntent getDisplayIntent() {
-        return mDisplayIntent;
-    }
-
-    /**
-     * Get the array of additional pages of content for displaying this notification. The
-     * current notification forms the first page, and elements within this array form
-     * subsequent pages. This field can be used to separate a notification into multiple
-     * sections.
-     * @return the pages for this notification
-     */
-    public Notification[] getPages() {
-        return mPages;
-    }
-
-    /**
-     * Get a background image to be displayed behind the notification content.
-     * Contrary to the {@link Notification.BigPictureStyle}, this background
-     * will work with any notification style.
-     *
-     * @return the background image
-     * @see Builder#setBackground
-     */
-    public Bitmap getBackground() {
-        return mBackground;
-    }
-
-    /**
-     * Get an icon that goes with the content of this notification.
-     */
-    public int getContentIcon() {
-        return mContentIcon;
-    }
-
-    /**
-     * Get the gravity that the content icon should have within the notification display.
-     * Supported values include {@link Gravity#START} and {@link Gravity#END}. The default
-     * value is {@link android.view.Gravity#END}.
-     * @see #getContentIcon
-     */
-    public int getContentIconGravity() {
-        return mContentIconGravity;
-    }
-
-    /**
-     * Get the action index of an action from this notification to show as clickable with
-     * the content of this notification page. When the user clicks this notification page,
-     * this action will trigger. This action will no longer display separately from the
-     * notification content. The action's icon will display with optional subtext provided
-     * by the action's title.
-     *
-     * <p>If wearable specific actions are present, this index will apply to that list,
-     * otherwise it will apply to the main notification's actions list.
-     */
-    public int getContentAction() {
-        return mContentActionIndex;
-    }
-
-    /**
-     * Get the gravity that this notification should have within the available viewport space.
-     * Supported values include {@link Gravity#TOP}, {@link Gravity#CENTER_VERTICAL} and
-     * {@link android.view.Gravity#BOTTOM}. The default value is
-     * {@link android.view.Gravity#BOTTOM}.
-     */
-    public int getGravity() {
-        return mGravity;
-    }
-
-    /**
-     * Get the custom size preset for the display of this notification out of the available
-     * presets found in {@link WearableNotificationExtensions}, e.g. {@link #SIZE_LARGE}.
-     * <p>Some custom size presets are only applicable for custom display notifications created
-     * using {@link Builder#setDisplayIntent}. Check the documentation for the preset in question.
-     * See also {@link Builder#setCustomContentHeight} and {@link Builder#setCustomSizePreset}.
-     */
-    public int getCustomSizePreset() {
-        return mCustomSizePreset;
-    }
-
-    /**
-     * Get the custom height in pixels for the display of this notification's content.
-     * <p>This option is only available for custom display notifications created
-     * using {@link Builder#setDisplayIntent}. See also {@link Builder#setCustomSizePreset} and
-     * {@link Builder#setCustomContentHeight}.
-     */
-    public int getCustomContentHeight() {
-        return mCustomContentHeight;
-    }
-
-    /**
-     * Get whether the scrolling position for the contents of this notification should start
-     * at the bottom of the contents instead of the top when the contents are too long to
-     * display within the screen. Default is false (start scroll at the top).
-     */
-    public boolean getStartScrollBottom() {
-        return (mFlags & FLAG_START_SCROLL_BOTTOM) != 0;
-    }
-
-    /**
-     * Get whether the content intent is available when the wearable device is not connected
-     * to a companion device.  The user can still trigger this intent when the wearable device is
-     * offline, but a visual hint will indicate that the content intent may not be available.
-     * Defaults to true.
-     */
-    public boolean getContentIntentAvailableOffline() {
-        return (mFlags & FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE) != 0;
-    }
-
-    /**
-     * Get a hint that this notification's icon should not be displayed.
-     * @return {@code true} if this icon should not be displayed, false otherwise.
-     * The default value is {@code false} if this was never set.
-     */
-    public boolean getHintHideIcon() {
-        return (mFlags & FLAG_HINT_HIDE_ICON) != 0;
-    }
-
-    /**
-     * Get a visual hint that only the background image of this notification should be
-     * displayed, and other semantic content should be hidden. This hint is only applicable
-     * to sub-pages added using {@link Builder#addPage}.
-     */
-    public boolean getHintShowBackgroundOnly() {
-        return (mFlags & FLAG_HINT_SHOW_BACKGROUND_ONLY) != 0;
-    }
-
-    @Override
-    public int describeContents() {
-        return 0;
-    }
-
-    @Override
-    public void writeToParcel(Parcel out, int flags) {
-        out.writeTypedArray(mActions, flags);
-        out.writeInt(mFlags);
-        out.writeParcelable(mDisplayIntent, flags);
-        out.writeTypedArray(mPages, flags);
-        out.writeParcelable(mBackground, flags);
-        out.writeInt(mContentIcon);
-        out.writeInt(mContentIconGravity);
-        out.writeInt(mContentActionIndex);
-        out.writeInt(mCustomSizePreset);
-        out.writeInt(mCustomContentHeight);
-        out.writeInt(mGravity);
-    }
-
-    /**
-     * Builder to apply wearable notification extensions to a {@link Notification.Builder}
-     * object.
-     *
-     * <p>You can chain the "set" methods for this builder in any order,
-     * but you must call the {@link #build} method and then the {@link Notification.Builder#apply}
-     * method to apply your extensions to a notification.
-     *
-     * <pre class="prettyprint">
-     * Notification notif = new Notification.Builder(mContext)
-     *         .setContentTitle(&quot;New mail from &quot; + sender.toString())
-     *         .setContentText(subject)
-     *         .setSmallIcon(R.drawable.new_mail);
-     *         .apply(new WearableNotificationExtensions.Builder()
-     *                 .setContentIcon(R.drawable.new_mail)
-     *                 .build())
-     *         .build();
-     * NotificationManager notificationManger =
-     *         (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
-     * notificationManager.notify(0, notif);</pre>
-     */
-    public static final class Builder {
-        private final List<Notification.Action> mActions =
-                new ArrayList<Notification.Action>();
-        private int mFlags = DEFAULT_FLAGS;
-        private PendingIntent mDisplayIntent;
-        private final List<Notification> mPages = new ArrayList<Notification>();
-        private Bitmap mBackground;
-        private int mContentIcon;
-        private int mContentIconGravity = Gravity.END;
-        private int mContentActionIndex = UNSET_ACTION_INDEX;
-        private int mCustomContentHeight;
-        private int mCustomSizePreset = SIZE_DEFAULT;
-        private int mGravity = Gravity.BOTTOM;
-
-        /**
-         * Construct a builder to be used for adding wearable extensions to notifications.
-         *
-         * <pre class="prettyprint">
-         * Notification notif = new Notification.Builder(mContext)
-         *         .setContentTitle(&quot;New mail from &quot; + sender.toString())
-         *         .setContentText(subject)
-         *         .setSmallIcon(R.drawable.new_mail);
-         *         .apply(new WearableNotificationExtensions.Builder()
-         *                 .setContentIcon(R.drawable.new_mail)
-         *                 .build())
-         *         .build();
-         * NotificationManager notificationManger =
-         *         (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
-         * notificationManager.notify(0, notif);</pre>
-         */
-        public Builder() {
-        }
-
-        /**
-         * Create a {@link Builder} by reading wearable extensions present on an
-         * existing {@code WearableNotificationExtensions} object.
-         * @param other the existing extensions to inspect.
-         */
-        public Builder(WearableNotificationExtensions other) {
-            Collections.addAll(mActions, other.mActions);
-            mFlags = other.mFlags;
-            mDisplayIntent = other.mDisplayIntent;
-            Collections.addAll(mPages, other.mPages);
-            mBackground = other.mBackground;
-            mContentIcon = other.mContentIcon;
-            mContentIconGravity = other.mContentIconGravity;
-            mContentActionIndex = other.mContentActionIndex;
-            mCustomContentHeight = other.mCustomContentHeight;
-            mCustomSizePreset = other.mCustomSizePreset;
-            mGravity = other.mGravity;
-        }
-
-        /**
-         * Add a wearable action to this notification.
-         *
-         * <p>When wearable actions are added using this method, the set of actions that
-         * show on a wearable device splits from devices that only show actions added
-         * using {@link android.app.Notification.Builder#addAction}. This allows for customization
-         * of which actions display on different devices.
-         *
-         * @param action the action to add to this notification
-         * @return this object for method chaining
-         * @see Notification.Action
-         */
-        public Builder addAction(Notification.Action action) {
-            mActions.add(action);
-            return this;
-        }
-
-        /**
-         * Adds wearable actions to this notification.
-         *
-         * <p>When wearable actions are added using this method, the set of actions that
-         * show on a wearable device splits from devices that only show actions added
-         * using {@link android.app.Notification.Builder#addAction}. This allows for customization
-         * of which actions display on different devices.
-         *
-         * @param actions the actions to add to this notification
-         * @return this object for method chaining
-         * @see Notification.Action
-         */
-        public Builder addActions(List<Notification.Action> actions) {
-            mActions.addAll(actions);
-            return this;
-        }
-
-        /**
-         * Clear all wearable actions present on this builder.
-         * @return this object for method chaining.
-         * @see #addAction
-         */
-        public Builder clearActions() {
-            mActions.clear();
-            return this;
-        }
-
-        /**
-         * Set an intent to launch inside of an activity view when displaying
-         * this notification. This {@link android.app.PendingIntent} should be for an activity.
-         *
-         * @param intent the {@link android.app.PendingIntent} for an activity
-         * @return this object for method chaining
-         * @see WearableNotificationExtensions#getDisplayIntent
-         */
-        public Builder setDisplayIntent(PendingIntent intent) {
-            mDisplayIntent = intent;
-            return this;
-        }
-
-        /**
-         * Add an additional page of content to display with this notification. The current
-         * notification forms the first page, and pages added using this function form
-         * subsequent pages. This field can be used to separate a notification into multiple
-         * sections.
-         *
-         * @param page the notification to add as another page
-         * @return this object for method chaining
-         * @see WearableNotificationExtensions#getPages
-         */
-        public Builder addPage(Notification page) {
-            mPages.add(page);
-            return this;
-        }
-
-        /**
-         * Add additional pages of content to display with this notification. The current
-         * notification forms the first page, and pages added using this function form
-         * subsequent pages. This field can be used to separate a notification into multiple
-         * sections.
-         *
-         * @param pages a list of notifications
-         * @return this object for method chaining
-         * @see WearableNotificationExtensions#getPages
-         */
-        public Builder addPages(List<Notification> pages) {
-            mPages.addAll(pages);
-            return this;
-        }
-
-        /**
-         * Clear all additional pages present on this builder.
-         * @return this object for method chaining.
-         * @see #addPage
-         */
-        public Builder clearPages() {
-            mPages.clear();
-            return this;
-        }
-
-        /**
-         * Set a background image to be displayed behind the notification content.
-         * Contrary to the {@link Notification.BigPictureStyle}, this background
-         * will work with any notification style.
-         *
-         * @param background the background bitmap
-         * @return this object for method chaining
-         * @see WearableNotificationExtensions#getBackground
-         */
-        public Builder setBackground(Bitmap background) {
-            mBackground = background;
-            return this;
-        }
-
-        /**
-         * Set an icon that goes with the content of this notification.
-         */
-        public Builder setContentIcon(int icon) {
-            mContentIcon = icon;
-            return this;
-        }
-
-        /**
-         * Set the gravity that the content icon should have within the notification display.
-         * Supported values include {@link Gravity#START} and {@link Gravity#END}. The default
-         * value is {@link android.view.Gravity#END}.
-         * @see #setContentIcon
-         */
-        public Builder setContentIconGravity(int contentIconGravity) {
-            mContentIconGravity = contentIconGravity;
-            return this;
-        }
-
-        /**
-         * Set an action from this notification's actions to be clickable with the content of
-         * this notification page. This action will no longer display separately from the
-         * notification content. This action's icon will display with optional subtext provided
-         * by the action's title.
-         * @param actionIndex The index of the action to hoist on the current notification page.
-         *                    If wearable actions are present, this index will apply to that list,
-         *                    otherwise it will apply to the main notification's actions list.
-         */
-        public Builder setContentAction(int actionIndex) {
-            mContentActionIndex = actionIndex;
-            return this;
-        }
-
-        /**
-         * Set the gravity that this notification should have within the available viewport space.
-         * Supported values include {@link Gravity#TOP}, {@link Gravity#CENTER_VERTICAL} and
-         * {@link Gravity#BOTTOM}. The default value is {@link Gravity#BOTTOM}.
-         */
-        public Builder setGravity(int gravity) {
-            mGravity = gravity;
-            return this;
-        }
-
-        /**
-         * Set the custom size preset for the display of this notification out of the available
-         * presets found in {@link WearableNotificationExtensions}, e.g. {@link #SIZE_LARGE}.
-         * <p>Some custom size presets are only applicable for custom display notifications created
-         * using {@link Builder#setDisplayIntent}. Check the documentation for the preset in
-         * question. See also {@link Builder#setCustomContentHeight} and
-         * {@link #getCustomSizePreset}.
-         */
-        public Builder setCustomSizePreset(int sizePreset) {
-            mCustomSizePreset = sizePreset;
-            return this;
-        }
-
-        /**
-         * Set the custom height in pixels for the display of this notification's content.
-         * <p>This option is only available for custom display notifications created
-         * using {@link Builder#setDisplayIntent}. See also {@link Builder#setCustomSizePreset} and
-         * {@link #getCustomContentHeight}.
-         */
-        public Builder setCustomContentHeight(int height) {
-            mCustomContentHeight = height;
-            return this;
-        }
-
-        /**
-         * Set whether the scrolling position for the contents of this notification should start
-         * at the bottom of the contents instead of the top when the contents are too long to
-         * display within the screen.  Default is false (start scroll at the top).
-         */
-        public Builder setStartScrollBottom(boolean startScrollBottom) {
-            setFlag(FLAG_START_SCROLL_BOTTOM, startScrollBottom);
-            return this;
-        }
-
-        /**
-         * Set whether the content intent is available when the wearable device is not connected
-         * to a companion device.  The user can still trigger this intent when the wearable device
-         * is offline, but a visual hint will indicate that the content intent may not be available.
-         * Defaults to true.
-         */
-        public Builder setContentIntentAvailableOffline(boolean contentIntentAvailableOffline) {
-            setFlag(FLAG_CONTENT_INTENT_AVAILABLE_OFFLINE, contentIntentAvailableOffline);
-            return this;
-        }
-
-        /**
-         * Set a hint that this notification's icon should not be displayed.
-         * @param hintHideIcon {@code true} to hide the icon, {@code false} otherwise.
-         * @return this object for method chaining
-         */
-        public Builder setHintHideIcon(boolean hintHideIcon) {
-            setFlag(FLAG_HINT_HIDE_ICON, hintHideIcon);
-            return this;
-        }
-
-        /**
-         * Set a visual hint that only the background image of this notification should be
-         * displayed, and other semantic content should be hidden. This hint is only applicable
-         * to sub-pages added using {@link #addPage}.
-         */
-        public Builder setHintShowBackgroundOnly(boolean hintShowBackgroundOnly) {
-            setFlag(FLAG_HINT_SHOW_BACKGROUND_ONLY, hintShowBackgroundOnly);
-            return this;
-        }
-
-        /**
-         * Build a new {@link WearableNotificationExtensions} object with the extensions
-         * currently present on this builder.
-         * @return the extensions object.
-         */
-        public WearableNotificationExtensions build() {
-            return new WearableNotificationExtensions(
-                    mActions.toArray(new Notification.Action[mActions.size()]), mFlags,
-                    mDisplayIntent, mPages.toArray(new Notification[mPages.size()]),
-                    mBackground, mContentIcon, mContentIconGravity, mContentActionIndex,
-                    mCustomSizePreset, mCustomContentHeight, mGravity);
-        }
-
-        private void setFlag(int mask, boolean value) {
-            if (value) {
-                mFlags |= mask;
-            } else {
-                mFlags &= ~mask;
-            }
-        }
-    }
-
-    public static final Creator<WearableNotificationExtensions> CREATOR =
-            new Creator<WearableNotificationExtensions>() {
-        @Override
-        public WearableNotificationExtensions createFromParcel(Parcel in) {
-            return new WearableNotificationExtensions(in);
-        }
-
-        @Override
-        public WearableNotificationExtensions[] newArray(int size) {
-            return new WearableNotificationExtensions[size];
-        }
-    };
-}
