TaskStackBuilder.java revision ea7e91514ee1968d15713e82a5cca745e2c46a05
1dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell/*
2dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * Copyright (C) 2012 The Android Open Source Project
3dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
4dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * Licensed under the Apache License, Version 2.0 (the "License");
5dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * you may not use this file except in compliance with the License.
6dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * You may obtain a copy of the License at
7dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
8dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *      http://www.apache.org/licenses/LICENSE-2.0
9dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
10dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * Unless required by applicable law or agreed to in writing, software
11dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * distributed under the License is distributed on an "AS IS" BASIS,
12dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * See the License for the specific language governing permissions and
14dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * limitations under the License.
15dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell */
16dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
17dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellpackage android.app;
18dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
19dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.content.ComponentName;
20dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.content.Context;
21dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.content.Intent;
22dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.content.pm.ActivityInfo;
23dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.content.pm.PackageManager;
24dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.content.pm.PackageManager.NameNotFoundException;
25f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powellimport android.os.Bundle;
26ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasaniimport android.os.UserHandle;
27dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport android.util.Log;
28dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
29dd8fab2629131b09367df747afd9a61e42dd1992Adam Powellimport java.util.ArrayList;
30dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
31dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell/**
32dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * Utility class for constructing synthetic back stacks for cross-task navigation
33dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * on Android 3.0 and newer.
34dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
35dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * <p>In API level 11 (Android 3.0/Honeycomb) the recommended conventions for
36dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * app navigation using the back key changed. The back key's behavior is local
37dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * to the current task and does not capture navigation across different tasks.
38dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * Navigating across tasks and easily reaching the previous task is accomplished
39dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * through the "recents" UI, accessible through the software-provided Recents key
40dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * on the navigation or system bar. On devices with the older hardware button configuration
41dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * the recents UI can be accessed with a long press on the Home key.</p>
42dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
43dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * <p>When crossing from one task stack to another post-Android 3.0,
44dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * the application should synthesize a back stack/history for the new task so that
45dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * the user may navigate out of the new task and back to the Launcher by repeated
46dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * presses of the back key. Back key presses should not navigate across task stacks.</p>
47dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
48dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * <p>TaskStackBuilder provides a way to obey the correct conventions
49dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * around cross-task navigation.</p>
50dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell *
51dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * <div class="special reference">
52dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * <h3>About Navigation</h3>
53dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * For more detailed information about tasks, the back stack, and navigation design guidelines,
54dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * please read
55dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * <a href="{@docRoot}guide/topics/fundamentals/tasks-and-back-stack.html">Tasks and Back Stack</a>
56dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * from the developer guide and <a href="{@docRoot}design/patterns/navigation.html">Navigation</a>
57dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * from the design guide.
58dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell * </div>
59dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell */
60f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powellpublic class TaskStackBuilder {
61dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    private static final String TAG = "TaskStackBuilder";
62dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
63dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    private final ArrayList<Intent> mIntents = new ArrayList<Intent>();
64dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    private final Context mSourceContext;
65dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
66dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    private TaskStackBuilder(Context a) {
67dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        mSourceContext = a;
68dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
69dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
70dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
71dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Return a new TaskStackBuilder for launching a fresh task stack consisting
72dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * of a series of activities.
73dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *
74dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param context The context that will launch the new task stack or generate a PendingIntent
75dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return A new TaskStackBuilder
76dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
77f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    public static TaskStackBuilder create(Context context) {
78dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        return new TaskStackBuilder(context);
79dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
80dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
81dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
82dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Add a new Intent to the task stack. The most recently added Intent will invoke
83dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * the Activity at the top of the final task stack.
84dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *
85dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param nextIntent Intent for the next Activity in the synthesized task stack
86dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return This TaskStackBuilder for method chaining
87dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
88dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    public TaskStackBuilder addNextIntent(Intent nextIntent) {
89dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        mIntents.add(nextIntent);
90dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        return this;
91dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
92dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
93dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
94f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * Add a new Intent with the resolved chain of parents for the target activity to
95f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * the task stack.
96f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *
97f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * <p>This is equivalent to calling {@link #addParentStack(ComponentName) addParentStack}
98f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * with the resolved ComponentName of nextIntent (if it can be resolved), followed by
99f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * {@link #addNextIntent(Intent) addNextIntent} with nextIntent.</p>
100f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *
101f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @param nextIntent Intent for the topmost Activity in the synthesized task stack.
102f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *                   Its chain of parents as specified in the manifest will be added.
103f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @return This TaskStackBuilder for method chaining.
104f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     */
105f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    public TaskStackBuilder addNextIntentWithParentStack(Intent nextIntent) {
106f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        ComponentName target = nextIntent.getComponent();
107f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        if (target == null) {
108f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell            target = nextIntent.resolveActivity(mSourceContext.getPackageManager());
109f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        }
110f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        if (target != null) {
111f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell            addParentStack(target);
112f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        }
113f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        addNextIntent(nextIntent);
114f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        return this;
115f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    }
116f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell
117f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    /**
118dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Add the activity parent chain as specified by the
1193c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * {@link Activity#getParentActivityIntent() getParentActivityIntent()} method of the activity
1203c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * specified and the {@link android.R.attr#parentActivityName parentActivityName} attributes
1213c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * of each successive activity (or activity-alias) element in the application's manifest
1223c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * to the task stack builder.
123dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *
124dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param sourceActivity All parents of this activity will be added
125dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return This TaskStackBuilder for method chaining
126dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
127dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    public TaskStackBuilder addParentStack(Activity sourceActivity) {
1285a4010c054a4449156df885ad0f46f8db3263d87Adam Powell        final Intent parent = sourceActivity.getParentActivityIntent();
1295a4010c054a4449156df885ad0f46f8db3263d87Adam Powell        if (parent != null) {
1305a4010c054a4449156df885ad0f46f8db3263d87Adam Powell            // We have the actual parent intent, build the rest from static metadata
1315a4010c054a4449156df885ad0f46f8db3263d87Adam Powell            // then add the direct parent intent to the end.
1325a4010c054a4449156df885ad0f46f8db3263d87Adam Powell            addParentStack(parent.getComponent());
1335a4010c054a4449156df885ad0f46f8db3263d87Adam Powell            addNextIntent(parent);
134dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        }
135dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        return this;
136dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
137dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
138dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
139dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Add the activity parent chain as specified by the
140dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * {@link android.R.attr#parentActivityName parentActivityName} attribute of the activity
141dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * (or activity-alias) element in the application's manifest to the task stack builder.
142dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *
143dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param sourceActivityClass All parents of this activity will be added
144dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return This TaskStackBuilder for method chaining
145dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
146dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    public TaskStackBuilder addParentStack(Class<?> sourceActivityClass) {
1475a4010c054a4449156df885ad0f46f8db3263d87Adam Powell        return addParentStack(new ComponentName(mSourceContext, sourceActivityClass));
148dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
149dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
150dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
1513c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * Add the activity parent chain as specified by the
1523c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * {@link android.R.attr#parentActivityName parentActivityName} attribute of the activity
1533c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * (or activity-alias) element in the application's manifest to the task stack builder.
1543c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     *
1553c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * @param sourceActivityName Must specify an Activity component. All parents of
1563c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     *                           this activity will be added
1573c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     * @return This TaskStackBuilder for method chaining
1583c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell     */
1593c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell    public TaskStackBuilder addParentStack(ComponentName sourceActivityName) {
1603c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell        final int insertAt = mIntents.size();
1613c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell        PackageManager pm = mSourceContext.getPackageManager();
1623c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell        try {
1633c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell            ActivityInfo info = pm.getActivityInfo(sourceActivityName, 0);
1643c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell            String parentActivity = info.parentActivityName;
1655c43ec9328ba98fa88acc452b140f2d682a3042cAdam Powell            while (parentActivity != null) {
1666b6c90523ed8779aa962ff4f5ef8c368a96269e2Adam Powell                final ComponentName target = new ComponentName(info.packageName, parentActivity);
1675a4010c054a4449156df885ad0f46f8db3263d87Adam Powell                info = pm.getActivityInfo(target, 0);
1683c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell                parentActivity = info.parentActivityName;
1695a4010c054a4449156df885ad0f46f8db3263d87Adam Powell                final Intent parent = parentActivity == null && insertAt == 0
1705a4010c054a4449156df885ad0f46f8db3263d87Adam Powell                        ? Intent.makeMainActivity(target)
1715a4010c054a4449156df885ad0f46f8db3263d87Adam Powell                        : new Intent().setComponent(target);
1725a4010c054a4449156df885ad0f46f8db3263d87Adam Powell                mIntents.add(insertAt, parent);
1733c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell            }
1743c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell        } catch (NameNotFoundException e) {
1753c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell            Log.e(TAG, "Bad ComponentName while traversing activity parent metadata");
1763c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell            throw new IllegalArgumentException(e);
1773c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell        }
1783c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell        return this;
1793c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell    }
1803c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell
1813c464bdefe37f75153e8a8c978c3457ae4d1f37eAdam Powell    /**
182dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return the number of intents added so far.
183dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
184dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    public int getIntentCount() {
185dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        return mIntents.size();
186dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
187dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
188dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
189f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * Return the intent at the specified index for modification.
190dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Useful if you need to modify the flags or extras of an intent that was previously added,
191dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * for example with {@link #addParentStack(Activity)}.
192dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *
193dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param index Index from 0-getIntentCount()
194dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return the intent at position index
195dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
196f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    public Intent editIntentAt(int index) {
197dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        return mIntents.get(index);
198dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
199dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
200f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    /**
201f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * Start the task stack constructed by this builder.
202f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     */
203f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    public void startActivities() {
204f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        startActivities(null);
205dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
206dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
207dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
208dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Start the task stack constructed by this builder.
209ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     * @hide
210dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
211ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani    public void startActivities(Bundle options, UserHandle userHandle) {
212dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        if (mIntents.isEmpty()) {
213dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell            throw new IllegalStateException(
214dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell                    "No intents added to TaskStackBuilder; cannot startActivities");
215dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell        }
216dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
217ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani        mSourceContext.startActivitiesAsUser(getIntents(), options, userHandle);
218ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani    }
219ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani
220ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani    /**
221ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     * Start the task stack constructed by this builder.
222ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     *
223ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     * @param options Additional options for how the Activity should be started.
224ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     * See {@link android.content.Context#startActivity(Intent, Bundle)
225ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     * Context.startActivity(Intent, Bundle)} for more details.
226ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani     */
227ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani    public void startActivities(Bundle options) {
228ea7e91514ee1968d15713e82a5cca745e2c46a05Amith Yamasani        startActivities(options, new UserHandle(UserHandle.myUserId()));
229dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
230dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell
231dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    /**
232dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * Obtain a {@link PendingIntent} for launching the task constructed by this builder so far.
233dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *
234dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param requestCode Private request code for the sender
235dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @param flags May be {@link PendingIntent#FLAG_ONE_SHOT},
236dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *              {@link PendingIntent#FLAG_NO_CREATE}, {@link PendingIntent#FLAG_CANCEL_CURRENT},
237dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *              {@link PendingIntent#FLAG_UPDATE_CURRENT}, or any of the flags supported by
238dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *              {@link Intent#fillIn(Intent, int)} to control which unspecified parts of the
239dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     *              intent that can be supplied when the actual send happens.
240f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *
241dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     * @return The obtained PendingIntent
242dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell     */
243dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    public PendingIntent getPendingIntent(int requestCode, int flags) {
244f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell        return getPendingIntent(requestCode, flags, null);
245f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    }
246f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell
247f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    /**
248f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * Obtain a {@link PendingIntent} for launching the task constructed by this builder so far.
249f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *
250f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @param requestCode Private request code for the sender
251f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @param flags May be {@link PendingIntent#FLAG_ONE_SHOT},
252f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *              {@link PendingIntent#FLAG_NO_CREATE}, {@link PendingIntent#FLAG_CANCEL_CURRENT},
253f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *              {@link PendingIntent#FLAG_UPDATE_CURRENT}, or any of the flags supported by
254f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *              {@link Intent#fillIn(Intent, int)} to control which unspecified parts of the
255f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *              intent that can be supplied when the actual send happens.
256f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @param options Additional options for how the Activity should be started.
257f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * See {@link android.content.Context#startActivity(Intent, Bundle)
258f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * Context.startActivity(Intent, Bundle)} for more details.
259f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *
260f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @return The obtained PendingIntent
261f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     */
262f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    public PendingIntent getPendingIntent(int requestCode, int flags, Bundle options) {
2638ab700cbbab60f7a01a86cbf16496e1f34236dd6Adam Powell        if (mIntents.isEmpty()) {
2648ab700cbbab60f7a01a86cbf16496e1f34236dd6Adam Powell            throw new IllegalStateException(
2658ab700cbbab60f7a01a86cbf16496e1f34236dd6Adam Powell                    "No intents added to TaskStackBuilder; cannot getPendingIntent");
2668ab700cbbab60f7a01a86cbf16496e1f34236dd6Adam Powell        }
2678ab700cbbab60f7a01a86cbf16496e1f34236dd6Adam Powell
26875e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        return PendingIntent.getActivities(mSourceContext, requestCode, getIntents(),
26975e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell                flags, options);
270f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    }
271f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell
272f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    /**
273f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * Return an array containing the intents added to this builder. The intent at the
274f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * root of the task stack will appear as the first item in the array and the
275f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * intent at the top of the stack will appear as the last item.
276f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     *
277f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     * @return An array containing the intents added to this builder.
278f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell     */
279f78a8444a9b21b0d1daca8667d580dd0ec04a310Adam Powell    public Intent[] getIntents() {
28075e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        Intent[] intents = new Intent[mIntents.size()];
28175e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        if (intents.length == 0) return intents;
28275e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell
28375e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        intents[0] = new Intent(mIntents.get(0)).addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
28475e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell                Intent.FLAG_ACTIVITY_CLEAR_TASK |
28575e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell                Intent.FLAG_ACTIVITY_TASK_ON_HOME);
28675e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        for (int i = 1; i < intents.length; i++) {
28775e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell            intents[i] = new Intent(mIntents.get(i));
28875e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        }
28975e0af8982cd29cfe8a01c18d1e82d7abcfd1711Adam Powell        return intents;
290dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell    }
291dd8fab2629131b09367df747afd9a61e42dd1992Adam Powell}
292