TaskStackBuilder.java revision 56a1f598b89d0e65dbd2a2678b66a43f5b7638c2
1c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell/*
2c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * Copyright (C) 2012 The Android Open Source Project
3c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
4c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * Licensed under the Apache License, Version 2.0 (the "License");
5c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * you may not use this file except in compliance with the License.
6c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * You may obtain a copy of the License at
7c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
8c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *      http://www.apache.org/licenses/LICENSE-2.0
9c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
10c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * Unless required by applicable law or agreed to in writing, software
11c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * distributed under the License is distributed on an "AS IS" BASIS,
12c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * See the License for the specific language governing permissions and
14c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * limitations under the License.
15c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell */
16c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
17c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellpackage android.support.v4.app;
18c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
19c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.app.Activity;
20c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.app.PendingIntent;
21c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.content.Context;
22c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.content.Intent;
23c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.content.pm.PackageManager.NameNotFoundException;
24c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.os.Build;
25c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.support.v4.content.IntentCompat;
26c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport android.util.Log;
27c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
28c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport java.util.ArrayList;
29c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellimport java.util.Iterator;
30c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
31c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell/**
32c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * Utility class for constructing synthetic back stacks for cross-task navigation
33c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * on Android 3.0 and newer.
34c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
35c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * <p>In API level 11 (Android 3.0/Honeycomb) the recommended conventions for
36c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * app navigation using the back key changed. The back key's behavior is local
37c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * to the current task and does not capture navigation across different tasks.
38c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * Navigating across tasks and easily reaching the previous task is accomplished
39c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * through the "recents" UI, accessible through the software-provided Recents key
40c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * on the navigation or system bar. On devices with the older hardware button configuration
41c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * the recents UI can be accessed with a long press on the Home key.</p>
42c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
43c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * <p>When crossing from one task stack to another post-Android 3.0,
44c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * the application should synthesize a back stack/history for the new task so that
45c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * the user may navigate out of the new task and back to the Launcher by repeated
46c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * presses of the back key. Back key presses should not navigate across task stacks.</p>
47c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
48c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * <p>TaskStackBuilder provides a backward-compatible way to obey the correct conventions
49c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * around cross-task navigation on the device's version of the platform. On devices running
50c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * Android 3.0 or newer, calls to the {@link #startActivities()} method or sending the
51c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * {@link PendingIntent} generated by {@link #getPendingIntent(int, int)} will construct
52c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * the synthetic back stack as prescribed. On devices running older versions of the platform,
53c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * these same calls will invoke the topmost activity in the supplied stack, ignoring
54c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * the rest of the synthetic stack and allowing the back key to navigate back to the previous
55c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * task.</p>
56c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell *
57c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * <div class="special reference">
58c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * <h3>About Navigation</h3>
59c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * For more detailed information about tasks, the back stack, and navigation design guidelines,
60c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * please read
61c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * <a href="{@docRoot}guide/topics/fundamentals/tasks-and-back-stack.html">Tasks and Back Stack</a>
62c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * from the developer guide and <a href="{@docRoot}design/patterns/navigation.html">Navigation</a>
63c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * from the design guide.
64c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell * </div>
65c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell */
66c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powellpublic class TaskStackBuilder implements Iterable<Intent> {
67c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    private static final String TAG = "TaskStackBuilder";
68c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
69c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    interface TaskStackBuilderImpl {
70c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        PendingIntent getPendingIntent(Context context, Intent[] intents, int requestCode,
71c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                int flags);
72c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
73c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
74c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    static class TaskStackBuilderImplBase implements TaskStackBuilderImpl {
75c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        public PendingIntent getPendingIntent(Context context, Intent[] intents, int requestCode,
76c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                int flags) {
77c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            Intent topIntent = intents[intents.length - 1];
78c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            topIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
79c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            return PendingIntent.getActivity(context, requestCode, topIntent, flags);
80c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
81c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
82c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
83c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    static class TaskStackBuilderImplHoneycomb implements TaskStackBuilderImpl {
84c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        public PendingIntent getPendingIntent(Context context, Intent[] intents, int requestCode,
85c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                int flags) {
86c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            intents[0].addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
87c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                    IntentCompat.FLAG_ACTIVITY_CLEAR_TASK);
88c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            return TaskStackBuilderHoneycomb.getActivitiesPendingIntent(context, requestCode,
89c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                    intents, flags);
90c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
91c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
92c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
93c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    private static final TaskStackBuilderImpl IMPL;
94c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
95c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    static {
96c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        if (Build.VERSION.SDK_INT >= 11) {
97c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            IMPL = new TaskStackBuilderImplHoneycomb();
98c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        } else {
99c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            IMPL = new TaskStackBuilderImplBase();
100c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
101c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
102c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
103c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    private final ArrayList<Intent> mIntents = new ArrayList<Intent>();
104c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    private final Context mSourceContext;
105c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
106c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    private TaskStackBuilder(Context a) {
107c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        mSourceContext = a;
108c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
109c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
110c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
111c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Return a new TaskStackBuilder for launching a fresh task stack consisting
112c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * of a series of activities.
113c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
114c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param context The context that will launch the new task stack or generate a PendingIntent
115c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return A new TaskStackBuilder
116c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
117c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public static TaskStackBuilder from(Context context) {
118c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return new TaskStackBuilder(context);
119c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
120c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
121c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
122c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Add a new Intent to the task stack. The most recently added Intent will invoke
123c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * the Activity at the top of the final task stack.
124c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
125c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param nextIntent Intent for the next Activity in the synthesized task stack
126c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return This TaskStackBuilder for method chaining
127c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
128c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public TaskStackBuilder addNextIntent(Intent nextIntent) {
129c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        mIntents.add(nextIntent);
130c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return this;
131c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
132c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
133c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
134c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Add the activity parent chain as specified by manifest &lt;meta-data&gt; elements
135c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * to the task stack builder.
136c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
137c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param sourceActivity All parents of this activity will be added
138c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return This TaskStackBuilder for method chaining
139c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
140c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public TaskStackBuilder addParentStack(Activity sourceActivity) {
141c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        final int insertAt = mIntents.size();
142c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        Intent parent = NavUtils.getParentActivityIntent(sourceActivity);
143c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        while (parent != null) {
144c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            mIntents.add(insertAt, parent);
145c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            try {
146c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                parent = NavUtils.getParentActivityIntent(sourceActivity, parent.getComponent());
147c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            } catch (NameNotFoundException e) {
148c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                Log.e(TAG, "Bad ComponentName while traversing activity parent metadata");
149c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                throw new IllegalArgumentException(e);
150c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            }
151c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
152c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return this;
153c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
154c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
155c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
156c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Add the activity parent chain as specified by manifest &lt;meta-data&gt; elements
157c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * to the task stack builder.
158c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
159c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param sourceActivityClass All parents of this activity will be added
160c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return This TaskStackBuilder for method chaining
161c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
162c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public TaskStackBuilder addParentStack(Class<?> sourceActivityClass) {
163c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        final int insertAt = mIntents.size();
164c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        try {
165c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            Intent parent = NavUtils.getParentActivityIntent(mSourceContext, sourceActivityClass);
166c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            while (parent != null) {
167c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                mIntents.add(insertAt, parent);
168c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                parent = NavUtils.getParentActivityIntent(mSourceContext, parent.getComponent());
169c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            }
170c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        } catch (NameNotFoundException e) {
171c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            Log.e(TAG, "Bad ComponentName while traversing activity parent metadata");
172c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            throw new IllegalArgumentException(e);
173c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
174c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return this;
175c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
176c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
177c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
178c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return the number of intents added so far.
179c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
180c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public int getIntentCount() {
181c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return mIntents.size();
182c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
183c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
184c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
185c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Get the intent at the specified index.
186c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Useful if you need to modify the flags or extras of an intent that was previously added,
187c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * for example with {@link #addParentStack(Activity)}.
188c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
189c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param index Index from 0-getIntentCount()
190c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return the intent at position index
191c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
192c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public Intent getIntent(int index) {
193c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return mIntents.get(index);
194c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
195c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
196c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public Iterator<Intent> iterator() {
197c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return mIntents.iterator();
198c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
199c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
200c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
201c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Start the task stack constructed by this builder. The Context used to obtain
202c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * this builder must be an Activity.
203c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
204c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * <p>On devices that do not support API level 11 or higher the topmost activity
205c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * will be started as a new task. On devices that do support API level 11 or higher
206c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * the new task stack will be created in its entirety.</p>
207c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
208c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public void startActivities() {
209c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        if (mIntents.isEmpty()) {
210c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            throw new IllegalStateException(
211c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                    "No intents added to TaskStackBuilder; cannot startActivities");
212c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
213c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
214c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        Intent[] intents = mIntents.toArray(new Intent[mIntents.size()]);
215c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        intents[0].addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
216c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                IntentCompat.FLAG_ACTIVITY_CLEAR_TASK |
217c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell                IntentCompat.FLAG_ACTIVITY_TASK_ON_HOME);
218c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        if (!ActivityCompat.startActivities((Activity) mSourceContext, intents)) {
219c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            Intent topIntent = intents[intents.length - 1];
220c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            topIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
221c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell            mSourceContext.startActivity(topIntent);
222c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        }
223c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
224c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell
225c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    /**
226c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * Obtain a {@link PendingIntent} for launching the task constructed by this builder so far.
227c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *
228c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param requestCode Private request code for the sender
229c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @param flags May be {@link PendingIntent#FLAG_ONE_SHOT},
230c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *              {@link PendingIntent#FLAG_NO_CREATE}, {@link PendingIntent#FLAG_CANCEL_CURRENT},
231c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *              {@link PendingIntent#FLAG_UPDATE_CURRENT}, or any of the flags supported by
232c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *              {@link Intent#fillIn(Intent, int)} to control which unspecified parts of the
233c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     *              intent that can be supplied when the actual send happens.
234c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     * @return The obtained PendingIntent
235c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell     */
236c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    public PendingIntent getPendingIntent(int requestCode, int flags) {
23756a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell        if (mIntents.isEmpty()) {
23856a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell            throw new IllegalStateException(
23956a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell                    "No intents added to TaskStackBuilder; cannot getPendingIntent");
24056a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell        }
24156a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell
242c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        Intent[] intents = mIntents.toArray(new Intent[mIntents.size()]);
24356a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell        intents[0].addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
24456a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell                IntentCompat.FLAG_ACTIVITY_CLEAR_TASK |
24556a1f598b89d0e65dbd2a2678b66a43f5b7638c2Adam Powell                IntentCompat.FLAG_ACTIVITY_TASK_ON_HOME);
246c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell        return IMPL.getPendingIntent(mSourceContext, intents, requestCode, flags);
247c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell    }
248c9cf2eb0a9b6694d0fda3dbc313844955db60820Adam Powell}
249