PreferenceActivity.java revision 327fbd2c8fa294b919475feb4c74a74ee1981e02
1518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian/*
2518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * Copyright (C) 2007 The Android Open Source Project
3518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
4518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * Licensed under the Apache License, Version 2.0 (the "License");
5518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * you may not use this file except in compliance with the License.
6518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * You may obtain a copy of the License at
7518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
8518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *      http://www.apache.org/licenses/LICENSE-2.0
9518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
10518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * Unless required by applicable law or agreed to in writing, software
11518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * distributed under the License is distributed on an "AS IS" BASIS,
12518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * See the License for the specific language governing permissions and
14518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * limitations under the License.
15518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian */
16518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
171c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennispackage android.preference;
181c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis
19518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport com.android.internal.util.XmlUtils;
20518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
21518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport org.xmlpull.v1.XmlPullParser;
22518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport org.xmlpull.v1.XmlPullParserException;
23518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
24518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.app.ActionBar;
25518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.app.Fragment;
26518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.app.FragmentBreadCrumbs;
27518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.app.FragmentManager;
28518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.app.FragmentTransaction;
29518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.app.ListActivity;
30518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.content.Context;
31518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.content.Intent;
32518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.content.res.Configuration;
337db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopianimport android.content.res.Resources;
34518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.content.res.TypedArray;
35518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.content.res.XmlResourceParser;
36518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.os.Bundle;
37518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.os.Handler;
38518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.os.Message;
39518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.os.Parcel;
401c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennisimport android.os.Parcelable;
41518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.text.TextUtils;
42518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.util.AttributeSet;
43518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.util.TypedValue;
440469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamyimport android.util.Xml;
45518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.view.LayoutInflater;
46518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.view.View;
47518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.view.View.OnClickListener;
48518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.view.ViewGroup;
49518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.widget.AbsListView;
50518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.widget.ArrayAdapter;
51ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopianimport android.widget.Button;
52518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.widget.FrameLayout;
53518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.widget.ImageView;
54518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.widget.ListView;
55518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport android.widget.TextView;
56518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
57bc2d79ed7ada6243f3690f94ab512c0ddcdbed12Mathias Agopianimport java.io.IOException;
58bc2d79ed7ada6243f3690f94ab512c0ddcdbed12Mathias Agopianimport java.util.ArrayList;
59518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianimport java.util.List;
60518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
61518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian/**
62518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * This is the base class for an activity to show a hierarchy of preferences
63518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * to the user.  Prior to {@link android.os.Build.VERSION_CODES#HONEYCOMB}
64518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * this class only allowed the display of a single set of preference; this
65518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * functionality should now be found in the new {@link PreferenceFragment}
66518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * class.  If you are using PreferenceActivity in its old mode, the documentation
67518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * there applies to the deprecated APIs here.
68518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
69518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>This activity shows one or more headers of preferences, each of with
70518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * is associated with a {@link PreferenceFragment} to display the preferences
71518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * of that header.  The actual layout and display of these associations can
72518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * however vary; currently there are two major approaches it may take:
731c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang *
741c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang * <ul>
751c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang * <li>On a small screen it may display only the headers as a single list
761c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang * when first launched.  Selecting one of the header items will re-launch
77518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * the activity with it only showing the PreferenceFragment of that header.
78518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <li>On a large screen in may display both the headers and current
79518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * PreferenceFragment together as panes.  Selecting a header item switches
80518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * to showing the correct PreferenceFragment for that item.
81518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * </ul>
82518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
83518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>Subclasses of PreferenceActivity should implement
84518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * {@link #onBuildHeaders} to populate the header list with the desired
85518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * items.  Doing this implicitly switches the class into its new "headers
86518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * + fragments" mode rather than the old style of just showing a single
87518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * preferences list.
88518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
89518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <a name="SampleCode"></a>
90518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <h3>Sample Code</h3>
91518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
92518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>The following sample code shows a simple preference activity that
93518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * has two different sets of preferences.  The implementation, consisting
94518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * of the activity itself as well as its two preference fragments is:</p>
95518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
96518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * {@sample development/samples/ApiDemos/src/com/example/android/apis/preference/PreferenceWithHeaders.java
97518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *      activity}
98518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
99518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>The preference_headers resource describes the headers to be displayed
100518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * and the fragments associated with them.  It is:
101518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
102518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * {@sample development/samples/ApiDemos/res/xml/preference_headers.xml headers}
103518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
104518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>The first header is shown by Prefs1Fragment, which populates itself
105518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * from the following XML resource:</p>
106518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
107518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * {@sample development/samples/ApiDemos/res/xml/fragmented_preferences.xml preferences}
108518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
109518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>Note that this XML resource contains a preference screen holding another
110518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * fragment, the Prefs1FragmentInner implemented here.  This allows the user
111518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * to traverse down a hierarchy of preferences; pressing back will pop each
112518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * fragment off the stack to return to the previous preferences.
113518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian *
114518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * <p>See {@link PreferenceFragment} for information on implementing the
115518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian * fragments themselves.
116518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian */
117518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopianpublic abstract class PreferenceActivity extends ListActivity implements
118518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        PreferenceManager.OnPreferenceTreeClickListener,
119518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        PreferenceFragment.OnPreferenceStartFragmentCallback {
120518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String TAG = "PreferenceActivity";
121518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
122518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // Constants for state save/restore
123518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String HEADERS_TAG = ":android:headers";
124518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String CUR_HEADER_TAG = ":android:cur_header";
125518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String PREFERENCES_TAG = ":android:preferences";
126518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
127518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
128518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * When starting this activity, the invoking Intent can contain this extra
129518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * string to specify which fragment should be initially displayed.
130518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
131518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public static final String EXTRA_SHOW_FRAGMENT = ":android:show_fragment";
132518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
133518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
134518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * When starting this activity and using {@link #EXTRA_SHOW_FRAGMENT},
135518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * this extra can also be specify to supply a Bundle of arguments to pass
136b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall     * to that fragment when it is instantiated during the initial creation
137518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * of PreferenceActivity.
138518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
139518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public static final String EXTRA_SHOW_FRAGMENT_ARGUMENTS = ":android:show_fragment_args";
140518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
141518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
142518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * When starting this activity, the invoking Intent can contain this extra
143518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * boolean that the header list should not be displayed.  This is most often
144518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * used in conjunction with {@link #EXTRA_SHOW_FRAGMENT} to launch
145518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * the activity to display a specific fragment that the user has navigated
146518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * to.
147518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
148518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public static final String EXTRA_NO_HEADERS = ":android:no_headers";
149518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
150518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String BACK_STACK_PREFS = ":android:prefs";
151518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
152b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    // extras that allow any preference activity to be launched as part of a wizard
153518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
154518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // show Back and Next buttons? takes boolean parameter
155518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // Back will then return RESULT_CANCELED and Next RESULT_OK
156518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String EXTRA_PREFS_SHOW_BUTTON_BAR = "extra_prefs_show_button_bar";
157518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
158518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // add a Skip button?
159518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String EXTRA_PREFS_SHOW_SKIP = "extra_prefs_show_skip";
160518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
161518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // specify custom text for the Back or Next buttons, or cause a button to not appear
162518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // at all by setting it to null
163518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String EXTRA_PREFS_SET_NEXT_TEXT = "extra_prefs_set_next_text";
164518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final String EXTRA_PREFS_SET_BACK_TEXT = "extra_prefs_set_back_text";
165518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
166518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // --- State for new mode when showing a list of headers + prefs fragment
167518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
168518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private final ArrayList<Header> mHeaders = new ArrayList<Header>();
169518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
170b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    private HeaderAdapter mAdapter;
171518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
172518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private FrameLayout mListFooter;
1737773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian
1747773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    private ViewGroup mPrefsContainer;
175518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
176518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private FragmentBreadCrumbs mFragmentBreadCrumbs;
1777773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian
1787773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    private boolean mSinglePane;
1797773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian
1807773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    private Header mCurHeader;
1817773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian
1827773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    // --- State for old mode when showing a single preference list
1837773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian
184518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private PreferenceManager mPreferenceManager;
1857773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian
1867773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    private Bundle mSavedInstanceState;
187518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
188518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    // --- Common state
189518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
190518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private Button mNextButton;
191518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
192518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
193518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * The starting request code given out to preference framework.
194518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
195b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    private static final int FIRST_REQUEST_CODE = 100;
196518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
197518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final int MSG_BIND_PREFERENCES = 1;
198518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static final int MSG_BUILD_HEADERS = 2;
199518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private Handler mHandler = new Handler() {
200518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        @Override
201518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public void handleMessage(Message msg) {
202518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            switch (msg.what) {
203518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                case MSG_BIND_PREFERENCES: {
204518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    bindPreferences();
205ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                } break;
206ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                case MSG_BUILD_HEADERS: {
2077773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                    ArrayList<Header> oldHeaders = new ArrayList<Header>(mHeaders);
2087773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                    mHeaders.clear();
209518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    onBuildHeaders(mHeaders);
210518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    if (mAdapter != null) {
211518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        mAdapter.notifyDataSetChanged();
212518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    }
213518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    Header header = onGetNewHeader();
214518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    if (header != null && header.fragment != null) {
215518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        Header mappedHeader = findBestMatchingHeader(header, oldHeaders);
216518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        if (mappedHeader == null || mCurHeader != mappedHeader) {
217518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            switchToHeader(header);
218b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                        }
219b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                    } else if (mCurHeader != null) {
220b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                        Header mappedHeader = findBestMatchingHeader(mCurHeader, mHeaders);
221518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        if (mappedHeader != null) {
222518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            setSelectedHeader(mappedHeader);
2237773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                        }
224518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    }
225518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                } break;
226518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
227518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
228518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    };
229518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
230518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private static class HeaderAdapter extends ArrayAdapter<Header> {
231518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        private static class HeaderViewHolder {
232518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            ImageView icon;
233518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            TextView title;
234518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            TextView summary;
235518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
236b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
237b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        private LayoutInflater mInflater;
238b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
239ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        public HeaderAdapter(Context context, List<Header> objects) {
240518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            super(context, 0, objects);
241518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mInflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
24281a63350527cafce6929309533c58586878f10b5Mathias Agopian        }
243e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block
24481a63350527cafce6929309533c58586878f10b5Mathias Agopian        @Override
24581a63350527cafce6929309533c58586878f10b5Mathias Agopian        public View getView(int position, View convertView, ViewGroup parent) {
24681a63350527cafce6929309533c58586878f10b5Mathias Agopian            HeaderViewHolder holder;
24781a63350527cafce6929309533c58586878f10b5Mathias Agopian            View view;
248518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
249518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (convertView == null) {
2507773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                view = mInflater.inflate(com.android.internal.R.layout.preference_header_item,
251518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        parent, false);
252bee205fd58a27c10a0895de5339e76025d429d2bJamie Gennis                holder = new HeaderViewHolder();
253bee205fd58a27c10a0895de5339e76025d429d2bJamie Gennis                holder.icon = (ImageView) view.findViewById(com.android.internal.R.id.icon);
254e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block                holder.title = (TextView) view.findViewById(com.android.internal.R.id.title);
255bee205fd58a27c10a0895de5339e76025d429d2bJamie Gennis                holder.summary = (TextView) view.findViewById(com.android.internal.R.id.summary);
25681a63350527cafce6929309533c58586878f10b5Mathias Agopian                view.setTag(holder);
257bee205fd58a27c10a0895de5339e76025d429d2bJamie Gennis            } else {
258bee205fd58a27c10a0895de5339e76025d429d2bJamie Gennis                view = convertView;
259518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                holder = (HeaderViewHolder) view.getTag();
260518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
261518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
26259769469e4b9b2d8b12c020eb44b030b3927a50bJamie Gennis            // All view fields must be updated every time, because the view may be recycled
26359769469e4b9b2d8b12c020eb44b030b3927a50bJamie Gennis            Header header = getItem(position);
26459769469e4b9b2d8b12c020eb44b030b3927a50bJamie Gennis            holder.icon.setImageResource(header.iconRes);
26559769469e4b9b2d8b12c020eb44b030b3927a50bJamie Gennis            holder.title.setText(header.getTitle(getContext().getResources()));
26659769469e4b9b2d8b12c020eb44b030b3927a50bJamie Gennis            CharSequence summary = header.getSummary(getContext().getResources());
267518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (!TextUtils.isEmpty(summary)) {
2687773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                holder.summary.setVisibility(View.VISIBLE);
269518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                holder.summary.setText(summary);
270b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            } else {
271b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                holder.summary.setVisibility(View.GONE);
272518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
273518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
27481a63350527cafce6929309533c58586878f10b5Mathias Agopian            return view;
27581a63350527cafce6929309533c58586878f10b5Mathias Agopian        }
27681a63350527cafce6929309533c58586878f10b5Mathias Agopian    }
27781a63350527cafce6929309533c58586878f10b5Mathias Agopian
278518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
279518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Default value for {@link Header#id Header.id} indicating that no
280518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * identifier value is set.  All other values (including those below -1)
281518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * are valid.
282518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
283518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public static final long HEADER_ID_UNDEFINED = -1;
284518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
285518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
286518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Description of a single Header item that the user can select.
287518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
288b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    public static final class Header implements Parcelable {
289b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        /**
290b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall         * Identifier for this header, to correlate with a new list when
291518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * it is updated.  The default value is
2927773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian         * {@link PreferenceActivity#HEADER_ID_UNDEFINED}, meaning no id.
293518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_id
294b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall         */
295b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        public long id = HEADER_ID_UNDEFINED;
296518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
297518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
298518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Resource ID of title of the header that is shown to the user.
299518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_title
300518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
301518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public int titleRes;
302518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
303518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
304518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Title of the header that is shown to the user.
305518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_title
306518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
307b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        public CharSequence title;
308b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
309b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        /**
310518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Resource ID of optional summary describing what this header controls.
3117773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_summary
312518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
313b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        public int summaryRes;
314b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
315518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
316518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Optional summary describing what this header controls.
317518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_summary
318518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
319518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence summary;
320518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
321518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
322518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Resource ID of optional text to show as the title in the bread crumb.
323518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_breadCrumbTitle
324518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
325b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        public int breadCrumbTitleRes;
326518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
327518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
328b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall         * Optional text to show as the title in the bread crumb.
3295b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_breadCrumbTitle
3305b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian         */
331518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence breadCrumbTitle;
332518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
333ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        /**
334518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Resource ID of optional text to show as the short title in the bread crumb.
335518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_breadCrumbShortTitle
336518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
337518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public int breadCrumbShortTitleRes;
338518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
339518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
340518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Optional text to show as the short title in the bread crumb.
341518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_breadCrumbShortTitle
342518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
343518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence breadCrumbShortTitle;
344518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
345b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        /**
346518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Optional icon resource to show for this header.
347518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_icon
348b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall         */
3495b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        public int iconRes;
3505b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian
351518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
352518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Full class name of the fragment to display when this header is
3537773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian         * selected.
3547773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian         * @attr ref android.R.styleable#PreferenceHeader_fragment
355518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
356518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public String fragment;
357e8696a40e09b24b634214684d18526187b316a2fJamie Gennis
3581c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis        /**
359e8696a40e09b24b634214684d18526187b316a2fJamie Gennis         * Optional arguments to supply to the fragment when it is
360e8696a40e09b24b634214684d18526187b316a2fJamie Gennis         * instantiated.
361b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall         */
362e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        public Bundle fragmentArguments;
363e8696a40e09b24b634214684d18526187b316a2fJamie Gennis
364e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        /**
365e8696a40e09b24b634214684d18526187b316a2fJamie Gennis         * Intent to launch when the preference is selected.
366b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall         */
367e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        public Intent intent;
368e8696a40e09b24b634214684d18526187b316a2fJamie Gennis
369e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        /**
370e8696a40e09b24b634214684d18526187b316a2fJamie Gennis         * Optional additional data for use by subclasses of PreferenceActivity.
371e8696a40e09b24b634214684d18526187b316a2fJamie Gennis         */
372e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        public Bundle extras;
373e8696a40e09b24b634214684d18526187b316a2fJamie Gennis
374e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        public Header() {
375e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        }
376e8696a40e09b24b634214684d18526187b316a2fJamie Gennis
377e8696a40e09b24b634214684d18526187b316a2fJamie Gennis        /**
378518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Return the currently set title.  If {@link #titleRes} is set,
379518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * this resource is loaded from <var>res</var> and returned.  Otherwise
380518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * {@link #title} is returned.
381518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
382518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence getTitle(Resources res) {
383518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (titleRes != 0) {
384518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                return res.getText(titleRes);
385518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
386518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            return title;
387b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        }
388b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
389b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        /**
390518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Return the currently set summary.  If {@link #summaryRes} is set,
391518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * this resource is loaded from <var>res</var> and returned.  Otherwise
392518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * {@link #summary} is returned.
393518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
394518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence getSummary(Resources res) {
3957773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian            if (summaryRes != 0) {
396518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                return res.getText(summaryRes);
397518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
398518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            return summary;
399518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
400518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
401518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        /**
402518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * Return the currently set bread crumb title.  If {@link #breadCrumbTitleRes} is set,
403518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * this resource is loaded from <var>res</var> and returned.  Otherwise
404518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         * {@link #breadCrumbTitle} is returned.
4057773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian         */
406518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence getBreadCrumbTitle(Resources res) {
4077773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian            if (breadCrumbTitleRes != 0) {
408518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                return res.getText(breadCrumbTitleRes);
409518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
410518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            return breadCrumbTitle;
411518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
412b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
413b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        /**
4140469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy         * Return the currently set bread crumb short title.  If
4150469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy         * {@link #breadCrumbShortTitleRes} is set,
4160469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy         * this resource is loaded from <var>res</var> and returned.  Otherwise
4170469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy         * {@link #breadCrumbShortTitle} is returned.
418518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian         */
419518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public CharSequence getBreadCrumbShortTitle(Resources res) {
420518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (breadCrumbShortTitleRes != 0) {
421518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                return res.getText(breadCrumbShortTitleRes);
422518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
423518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            return breadCrumbShortTitle;
424518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
425518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
426518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        @Override
427518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public int describeContents() {
428b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            return 0;
4295b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        }
4305b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian
431518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        @Override
432b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        public void writeToParcel(Parcel dest, int flags) {
4335b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            dest.writeLong(id);
4345b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            dest.writeInt(titleRes);
435518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            TextUtils.writeToParcel(title, dest, flags);
436518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeInt(summaryRes);
437ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            TextUtils.writeToParcel(summary, dest, flags);
438518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeInt(breadCrumbTitleRes);
439518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            TextUtils.writeToParcel(breadCrumbTitle, dest, flags);
440518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeInt(breadCrumbShortTitleRes);
441518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            TextUtils.writeToParcel(breadCrumbShortTitle, dest, flags);
442518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeInt(iconRes);
443518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeString(fragment);
444518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeBundle(fragmentArguments);
445518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (intent != null) {
446518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                dest.writeInt(1);
447518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                intent.writeToParcel(dest, flags);
448518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            } else {
449b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                dest.writeInt(0);
450518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
451518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            dest.writeBundle(extras);
4525b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        }
4535b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian
4545b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        public void readFromParcel(Parcel in) {
455518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            id = in.readLong();
456518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            titleRes = in.readInt();
457518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            title = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
458518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            summaryRes = in.readInt();
459518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            summary = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
460518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            breadCrumbTitleRes = in.readInt();
461b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            breadCrumbTitle = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
462b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            breadCrumbShortTitleRes = in.readInt();
463b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            breadCrumbShortTitle = TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
464518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            iconRes = in.readInt();
465518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            fragment = in.readString();
4665b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            fragmentArguments = in.readBundle();
467518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (in.readInt() != 0) {
468518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                intent = Intent.CREATOR.createFromParcel(in);
469518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
470518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            extras = in.readBundle();
471518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
472518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
473518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        Header(Parcel in) {
474518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            readFromParcel(in);
475518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
476518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
477518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        public static final Creator<Header> CREATOR = new Creator<Header>() {
478518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            public Header createFromParcel(Parcel source) {
479518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                return new Header(source);
480518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
481518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            public Header[] newArray(int size) {
482518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                return new Header[size];
483518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
484518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        };
485518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
486518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
487518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
488518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    protected void onCreate(Bundle savedInstanceState) {
489518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        super.onCreate(savedInstanceState);
490518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
491518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        setContentView(com.android.internal.R.layout.preference_list_content);
492518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
493518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mListFooter = (FrameLayout)findViewById(com.android.internal.R.id.list_footer);
494518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mPrefsContainer = (ViewGroup) findViewById(com.android.internal.R.id.prefs_frame);
495518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        boolean hidingHeaders = onIsHidingHeaders();
496518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mSinglePane = hidingHeaders || !onIsMultiPane();
497518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        String initialFragment = getIntent().getStringExtra(EXTRA_SHOW_FRAGMENT);
498518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        Bundle initialArguments = getIntent().getBundleExtra(EXTRA_SHOW_FRAGMENT_ARGUMENTS);
499518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
500518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (savedInstanceState != null) {
501518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // We are restarting from a previous saved state; used that to
502518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // initialize, instead of starting fresh.
503518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            ArrayList<Header> headers = savedInstanceState.getParcelableArrayList(HEADERS_TAG);
504518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (headers != null) {
505518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                mHeaders.addAll(headers);
506518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                int curHeader = savedInstanceState.getInt(CUR_HEADER_TAG,
507518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        (int)HEADER_ID_UNDEFINED);
508518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (curHeader >= 0 && curHeader < mHeaders.size()) {
509518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    setSelectedHeader(mHeaders.get(curHeader));
510518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
511518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
512518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
513b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        } else {
514fb87e54a9af8bc5063ca4deebe81d90126992480Mathias Agopian            if (initialFragment != null && mSinglePane) {
515fb87e54a9af8bc5063ca4deebe81d90126992480Mathias Agopian                // If we are just showing a fragment, we want to run in
516518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                // new fragment mode, but don't need to compute and show
517518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                // the headers.
518fb87e54a9af8bc5063ca4deebe81d90126992480Mathias Agopian                switchToHeader(initialFragment, initialArguments);
519518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
520518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            } else {
5210469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                // We need to try to build the headers.
5220469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                onBuildHeaders(mHeaders);
52393a826f78f6313db791e6fc880439189897651b3Siva Velusamy
5240469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                // If there are headers, then at this point we need to show
525518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                // them and, depending on the screen, we may also show in-line
526518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                // the currently selected preference fragment.
527518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (mHeaders.size() > 0) {
528518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    if (!mSinglePane) {
529518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        if (initialFragment == null) {
530518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            Header h = onGetInitialHeader();
531518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            switchToHeader(h);
5325fecea776a5f093c21ac1a0ad3552b847d4be23eMathias Agopian                        } else {
533e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block                            switchToHeader(initialFragment, initialArguments);
5345fecea776a5f093c21ac1a0ad3552b847d4be23eMathias Agopian                        }
535518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    }
536518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
537518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
538518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
539518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
540518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        // The default configuration is to only show the list view.  Adjust
541518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        // visibility for other configurations.
542518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (initialFragment != null && mSinglePane) {
543518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // Single pane, showing just a prefs fragment.
544518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            findViewById(com.android.internal.R.id.headers).setVisibility(View.GONE);
545b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            mPrefsContainer.setVisibility(View.VISIBLE);
546518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        } else if (mHeaders.size() > 0) {
547518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mAdapter = new HeaderAdapter(this, mHeaders);
548b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            setListAdapter(mAdapter);
549518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (!mSinglePane) {
550518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                // Multi-pane.
551518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                getListView().setChoiceMode(AbsListView.CHOICE_MODE_SINGLE);
5527773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                if (mCurHeader != null) {
5537773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian                    setSelectedHeader(mCurHeader);
554518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
555518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                mPrefsContainer.setVisibility(View.VISIBLE);
556518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
557518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        } else {
558518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // If there are no headers, we are in the old "just show a screen
559518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // of preferences" mode.
560518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            setContentView(com.android.internal.R.layout.preference_list_content_single);
561518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mListFooter = (FrameLayout) findViewById(com.android.internal.R.id.list_footer);
562518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mPrefsContainer = (ViewGroup) findViewById(com.android.internal.R.id.prefs);
563518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mPreferenceManager = new PreferenceManager(this, FIRST_REQUEST_CODE);
564518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mPreferenceManager.setOnPreferenceTreeClickListener(this);
565518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
566518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
567518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        getListView().setScrollBarStyle(View.SCROLLBARS_INSIDE_OVERLAY);
568518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
569518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        // see if we should show Back/Next buttons
570518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        Intent intent = getIntent();
571518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (intent.getBooleanExtra(EXTRA_PREFS_SHOW_BUTTON_BAR, false)) {
572518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
573518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            findViewById(com.android.internal.R.id.button_bar).setVisibility(View.VISIBLE);
574518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
575518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            Button backButton = (Button)findViewById(com.android.internal.R.id.back_button);
576518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            backButton.setOnClickListener(new OnClickListener() {
577518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                public void onClick(View v) {
578518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    setResult(RESULT_CANCELED);
579518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    finish();
580518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
581518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            });
582518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            Button skipButton = (Button)findViewById(com.android.internal.R.id.skip_button);
583518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            skipButton.setOnClickListener(new OnClickListener() {
584518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                public void onClick(View v) {
585518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    setResult(RESULT_OK);
586518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    finish();
587518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
588518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            });
589518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mNextButton = (Button)findViewById(com.android.internal.R.id.next_button);
590518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mNextButton.setOnClickListener(new OnClickListener() {
591518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                public void onClick(View v) {
592518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    setResult(RESULT_OK);
593518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    finish();
594518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
595518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            });
596518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
597518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // set our various button parameters
598518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (intent.hasExtra(EXTRA_PREFS_SET_NEXT_TEXT)) {
599518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                String buttonText = intent.getStringExtra(EXTRA_PREFS_SET_NEXT_TEXT);
600518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (TextUtils.isEmpty(buttonText)) {
601518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    mNextButton.setVisibility(View.GONE);
602518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
603518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                else {
604518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    mNextButton.setText(buttonText);
605518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
606518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
607518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (intent.hasExtra(EXTRA_PREFS_SET_BACK_TEXT)) {
608ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                String buttonText = intent.getStringExtra(EXTRA_PREFS_SET_BACK_TEXT);
609ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                if (TextUtils.isEmpty(buttonText)) {
610ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                    backButton.setVisibility(View.GONE);
611ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                }
612ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                else {
613518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    backButton.setText(buttonText);
614518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
615518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
616518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (intent.getBooleanExtra(EXTRA_PREFS_SHOW_SKIP, false)) {
617518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                skipButton.setVisibility(View.VISIBLE);
618518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
619ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        }
620ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    }
621ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian
622ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    /**
623ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Returns true if this activity is currently showing the header list.
624518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
625518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public boolean hasHeaders() {
626518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        return getListView().getVisibility() == View.VISIBLE
627518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                && mPreferenceManager == null;
628ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    }
629ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian
630ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    /**
631ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Returns true if this activity is showing multiple panes -- the headers
632518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * and a preference fragment.
633ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     */
634ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    public boolean isMultiPane() {
635ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        return hasHeaders() && mPrefsContainer.getVisibility() == View.VISIBLE;
636ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    }
637518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
638518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
639518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Called to determine if the activity should run in multi-pane mode.
640518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * The default implementation returns true if the screen is large
641518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * enough.
642518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
643518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public boolean onIsMultiPane() {
644518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        Configuration config = getResources().getConfiguration();
645518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if ((config.screenLayout&Configuration.SCREENLAYOUT_SIZE_MASK)
646518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                == Configuration.SCREENLAYOUT_SIZE_XLARGE) {
647518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            return true;
648518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
649518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if ((config.screenLayout&Configuration.SCREENLAYOUT_SIZE_MASK)
650518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                == Configuration.SCREENLAYOUT_SIZE_LARGE
651518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                && config.orientation == Configuration.ORIENTATION_LANDSCAPE) {
652aca51c06f38155f1435fbc6944d7fc0a9bf1e4e9Jamie Gennis            return true;
653aca51c06f38155f1435fbc6944d7fc0a9bf1e4e9Jamie Gennis        }
654c42fcf05ce253d5342993b28c412be16e61efffbJamie Gennis        return false;
655aca51c06f38155f1435fbc6944d7fc0a9bf1e4e9Jamie Gennis    }
656aca51c06f38155f1435fbc6944d7fc0a9bf1e4e9Jamie Gennis
657aca51c06f38155f1435fbc6944d7fc0a9bf1e4e9Jamie Gennis    /**
658518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Called to determine whether the header list should be hidden.
659518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * The default implementation returns the
660518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * value given in {@link #EXTRA_NO_HEADERS} or false if it is not supplied.
661518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * This is set to false, for example, when the activity is being re-launched
662aca51c06f38155f1435fbc6944d7fc0a9bf1e4e9Jamie Gennis     * to show a particular preference activity.
663518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
664518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public boolean onIsHidingHeaders() {
665518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        return getIntent().getBooleanExtra(EXTRA_NO_HEADERS, false);
666518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
667518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
668518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
669518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Called to determine the initial header to be shown.  The default
670518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * implementation simply returns the fragment of the first header.  Note
671518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * that the returned Header object does not actually need to exist in
672518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * your header list -- whatever its fragment is will simply be used to
673518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * show for the initial UI.
674518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
675518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public Header onGetInitialHeader() {
676518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        return mHeaders.get(0);
677518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
678518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
679518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
680518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Called after the header list has been updated ({@link #onBuildHeaders}
681518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * has been called and returned due to {@link #invalidateHeaders()}) to
682518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * specify the header that should now be selected.  The default implementation
683518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * returns null to keep whatever header is currently selected.
684518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
685518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public Header onGetNewHeader() {
686518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        return null;
687e6f43ddce78d6846af12550ff9193c5c6fe5844bSteve Block    }
688518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
689518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
690518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Called when the activity needs its list of headers build.  By
6910469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy     * implementing this and adding at least one item to the list, you
6920469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy     * will cause the activity to run in its modern fragment mode.  Note
6930469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy     * that this function may not always be called; for example, if the
6940469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy     * activity has been asked to display a particular fragment without
695518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * the header list, there is no need to build the headers.
696518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     *
697ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * <p>Typical implementations will use {@link #loadHeadersFromResource}
698ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * to fill in the list from a resource.
699ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     *
700ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * @param target The list in which to place the headers.
701ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     */
7027773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    public void onBuildHeaders(List<Header> target) {
7037773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian    }
704518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
705ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    /**
706ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Call when you need to change the headers being displayed.  Will result
707518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * in onBuildHeaders() later being called to retrieve the new list.
708ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     */
709518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void invalidateHeaders() {
710ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        if (!mHandler.hasMessages(MSG_BUILD_HEADERS)) {
711518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mHandler.sendEmptyMessage(MSG_BUILD_HEADERS);
712518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
713518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
714518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
715518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
716518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Parse the given XML file as a header description, adding each
717518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * parsed Header into the target list.
718518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     *
719518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param resid The XML resource to load and parse.
720518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param target The list in which the parsed headers should be placed.
721518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
72228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis    public void loadHeadersFromResource(int resid, List<Header> target) {
72328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis        XmlResourceParser parser = null;
72428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis        try {
72528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            parser = getResources().getXml(resid);
72628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            AttributeSet attrs = Xml.asAttributeSet(parser);
72728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
72828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            int type;
72928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
73028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    && type != XmlPullParser.START_TAG) {
73128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            }
73228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
73328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            String nodeName = parser.getName();
73428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            if (!"preference-headers".equals(nodeName)) {
73528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                throw new RuntimeException(
73628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        "XML document must start with <preference-headers> tag; found"
73728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        + nodeName + " at " + parser.getPositionDescription());
73828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            }
73928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
74028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            Bundle curBundle = null;
74128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
74228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            final int outerDepth = parser.getDepth();
74328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis            while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
74428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                   && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
74528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
74628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    continue;
74728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                }
74828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
74928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                nodeName = parser.getName();
75028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                if ("header".equals(nodeName)) {
75128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    Header header = new Header();
75228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
75328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    TypedArray sa = getResources().obtainAttributes(attrs,
75428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            com.android.internal.R.styleable.PreferenceHeader);
75528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    header.id = sa.getResourceId(
75628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            com.android.internal.R.styleable.PreferenceHeader_id,
75728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            (int)HEADER_ID_UNDEFINED);
75828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    TypedValue tv = sa.peekValue(
75928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            com.android.internal.R.styleable.PreferenceHeader_title);
76028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    if (tv != null && tv.type == TypedValue.TYPE_STRING) {
76128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        if (tv.resourceId != 0) {
76228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.titleRes = tv.resourceId;
76328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        } else {
76428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.title = tv.string;
76528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        }
76628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    }
76728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    tv = sa.peekValue(
76828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            com.android.internal.R.styleable.PreferenceHeader_summary);
76928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    if (tv != null && tv.type == TypedValue.TYPE_STRING) {
77028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        if (tv.resourceId != 0) {
77128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.summaryRes = tv.resourceId;
77228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        } else {
77328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.summary = tv.string;
77428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        }
77528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    }
77628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    tv = sa.peekValue(
77728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            com.android.internal.R.styleable.PreferenceHeader_breadCrumbTitle);
77828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    if (tv != null && tv.type == TypedValue.TYPE_STRING) {
77928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        if (tv.resourceId != 0) {
78028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.breadCrumbTitleRes = tv.resourceId;
78128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        } else {
78228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.breadCrumbTitle = tv.string;
78328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        }
78428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    }
785518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    tv = sa.peekValue(
786518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            com.android.internal.R.styleable.PreferenceHeader_breadCrumbShortTitle);
7871c8e95cf86f2182986385bc1ee85f13f425f3a3aJamie Gennis                    if (tv != null && tv.type == TypedValue.TYPE_STRING) {
788518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        if (tv.resourceId != 0) {
789518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            header.breadCrumbShortTitleRes = tv.resourceId;
790b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                        } else {
791518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                            header.breadCrumbShortTitle = tv.string;
792518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        }
793b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                    }
7945b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian                    header.iconRes = sa.getResourceId(
7955b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian                            com.android.internal.R.styleable.PreferenceHeader_icon, 0);
796518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    header.fragment = sa.getString(
7970469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                            com.android.internal.R.styleable.PreferenceHeader_fragment);
7980469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                    sa.recycle();
7990469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy
8000469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                    if (curBundle == null) {
8010469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy                        curBundle = new Bundle();
802518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    }
8037db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian
8047db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                    final int innerDepth = parser.getDepth();
8057db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                    while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
8067db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                           && (type != XmlPullParser.END_TAG || parser.getDepth() > innerDepth)) {
8077db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                        if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
8087db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                            continue;
8097db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                        }
8107db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian
8117db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                        String innerNodeName = parser.getName();
8127db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                        if (innerNodeName.equals("extra")) {
8137db993a98b9239bd4e384cc4aa128262fe3cf52cMathias Agopian                            getResources().parseBundleExtra("extra", attrs, curBundle);
81428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            XmlUtils.skipCurrentTag(parser);
81528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
81628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        } else if (innerNodeName.equals("intent")) {
81728ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            header.intent = Intent.parseIntent(getResources(), parser, attrs);
81828ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
81928ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        } else {
82028ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                            XmlUtils.skipCurrentTag(parser);
82128ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        }
82228ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    }
82328ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis
82428ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                    if (curBundle.size() > 0) {
82528ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        header.fragmentArguments = curBundle;
82628ef8d7911dbfd1bf8256fb43acba894d87fc07aJamie Gennis                        curBundle = null;
827518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    }
828518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
829518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    target.add(header);
830518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                } else {
831518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    XmlUtils.skipCurrentTag(parser);
832518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
833518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
834b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
835518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        } catch (XmlPullParserException e) {
836518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            throw new RuntimeException("Error parsing headers", e);
837b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        } catch (IOException e) {
8385b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            throw new RuntimeException("Error parsing headers", e);
8395b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        } finally {
840518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (parser != null) parser.close();
841518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
842ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian
843518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
844518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
845518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
846518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Set a footer that should be shown at the bottom of the header list.
847518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
848518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void setListFooter(View view) {
849b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        mListFooter.removeAllViews();
850518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mListFooter.addView(view, new FrameLayout.LayoutParams(
851518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                FrameLayout.LayoutParams.MATCH_PARENT,
852518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                FrameLayout.LayoutParams.WRAP_CONTENT));
853518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
8544b9511c16195a646242eff833b0af212933b6ecaMathias Agopian
855518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
8564b9511c16195a646242eff833b0af212933b6ecaMathias Agopian    protected void onStop() {
857518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        super.onStop();
8584b9511c16195a646242eff833b0af212933b6ecaMathias Agopian
859518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mPreferenceManager != null) {
8604b9511c16195a646242eff833b0af212933b6ecaMathias Agopian            mPreferenceManager.dispatchActivityStop();
861ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        }
862ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    }
863518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
864518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
865518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    protected void onDestroy() {
866518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        super.onDestroy();
867518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
868518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mPreferenceManager != null) {
869518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mPreferenceManager.dispatchActivityDestroy();
870518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
871518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
872518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
873518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
874518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    protected void onSaveInstanceState(Bundle outState) {
875518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        super.onSaveInstanceState(outState);
876518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
877b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        if (mHeaders.size() > 0) {
878518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            outState.putParcelableArrayList(HEADERS_TAG, mHeaders);
879518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (mCurHeader != null) {
880b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                int index = mHeaders.indexOf(mCurHeader);
8815b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian                if (index >= 0) {
8825b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian                    outState.putInt(CUR_HEADER_TAG, index);
883518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
884518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
885518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
886518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
887ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        if (mPreferenceManager != null) {
888518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            final PreferenceScreen preferenceScreen = getPreferenceScreen();
889518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (preferenceScreen != null) {
890518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                Bundle container = new Bundle();
891518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                preferenceScreen.saveHierarchyState(container);
892518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                outState.putBundle(PREFERENCES_TAG, container);
893518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
894518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
895518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
896518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
897b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    @Override
898518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    protected void onRestoreInstanceState(Bundle state) {
899518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mPreferenceManager != null) {
900b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            Bundle container = state.getBundle(PREFERENCES_TAG);
9015b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            if (container != null) {
9025b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian                final PreferenceScreen preferenceScreen = getPreferenceScreen();
903518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (preferenceScreen != null) {
904518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    preferenceScreen.restoreHierarchyState(container);
905518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    mSavedInstanceState = state;
906518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    return;
907ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                }
908518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
909518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
910518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
911518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        // Only call this if we didn't save the instance state for later.
912518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        // If we did save it, it will be restored when we bind the adapter.
913518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        super.onRestoreInstanceState(state);
914518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
915518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
916518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
917b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
918518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        super.onActivityResult(requestCode, resultCode, data);
919518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
920b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        if (mPreferenceManager != null) {
9215b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            mPreferenceManager.dispatchActivityResult(requestCode, resultCode, data);
9225b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        }
923518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
924518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
925518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
926518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void onContentChanged() {
927ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        super.onContentChanged();
928518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
929518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mPreferenceManager != null) {
930518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            postBindPreferences();
931518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
932518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
933518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
934518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    @Override
935518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    protected void onListItemClick(ListView l, View v, int position, long id) {
936b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        super.onListItemClick(l, v, position, id);
937518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
938518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mAdapter != null) {
939518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            onHeaderClick(mHeaders.get(position), position);
940ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        }
941ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    }
942ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian
943518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
944ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Called when the user selects an item in the header list.  The default
945518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * implementation will call either {@link #startWithFragment(String, Bundle, Fragment, int)}
946518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * or {@link #switchToHeader(Header)} as appropriate.
947518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     *
948518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param header The header that was selected.
949518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param position The header's position in the list.
950518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
951518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void onHeaderClick(Header header, int position) {
952518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (header.fragment != null) {
953518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (mSinglePane) {
954518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                startWithFragment(header.fragment, header.fragmentArguments, null, 0);
955518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            } else {
956518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                switchToHeader(header);
957ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            }
958ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        } else if (header.intent != null) {
959ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            startActivity(header.intent);
960ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        }
961ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    }
962ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian
963ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    /**
964ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Start a new instance of this activity, showing only the given
965ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * preference fragment.  When launched in this mode, the header list
966518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * will be hidden and the given preference fragment will be instantiated
967518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * and fill the entire activity.
968518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     *
969518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param fragmentName The name of the fragment to display.
970518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param args Optional arguments to supply to the fragment.
971518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
972518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void startWithFragment(String fragmentName, Bundle args,
973518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            Fragment resultTo, int resultRequestCode) {
974518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        Intent intent = new Intent(Intent.ACTION_MAIN);
975518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        intent.setClass(this, getClass());
976518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        intent.putExtra(EXTRA_SHOW_FRAGMENT, fragmentName);
977518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        intent.putExtra(EXTRA_SHOW_FRAGMENT_ARGUMENTS, args);
978518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        intent.putExtra(EXTRA_NO_HEADERS, true);
979518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (resultTo == null) {
980ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            startActivity(intent);
981ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        } else {
982ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            resultTo.startActivityForResult(intent, resultRequestCode);
983518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
984518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
985518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
986518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
987518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Change the base title of the bread crumbs for the current preferences.
988518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * This will normally be called for you.  See
989518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * {@link android.app.FragmentBreadCrumbs} for more information.
990518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
991518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void showBreadCrumbs(CharSequence title, CharSequence shortTitle) {
992518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mFragmentBreadCrumbs == null) {
993518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            View crumbs = findViewById(android.R.id.title);
994518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // For screens with a different kind of title, don't create breadcrumbs.
995ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            if (!(crumbs instanceof FragmentBreadCrumbs)) return;
996ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            mFragmentBreadCrumbs = (FragmentBreadCrumbs) findViewById(android.R.id.title);
997ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            if (mFragmentBreadCrumbs == null) {
998518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                mFragmentBreadCrumbs = new FragmentBreadCrumbs(this);
999ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                ActionBar actionBar = getActionBar();
1000518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (actionBar != null) {
1001518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    actionBar.setCustomNavigationMode(mFragmentBreadCrumbs);
1002518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
1003518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
1004518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mFragmentBreadCrumbs.setMaxVisible(2);
1005518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mFragmentBreadCrumbs.setActivity(this);
1006518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1007518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mFragmentBreadCrumbs.setTitle(title, shortTitle);
1008518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mFragmentBreadCrumbs.setParentTitle(null, null, null);
1009fb87e54a9af8bc5063ca4deebe81d90126992480Mathias Agopian    }
1010518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1011ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    /**
1012ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Should be called after onCreate to ensure that the breadcrumbs, if any, were created.
1013ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * This prepends a title to the fragment breadcrumbs and attaches a listener to any clicks
1014518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * on the parent entry.
1015ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * @param title the title for the breadcrumb
1016518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param shortTitle the short title for the breadcrumb
10170469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy     */
10180469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy    public void setParentTitle(CharSequence title, CharSequence shortTitle,
10190469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy            OnClickListener listener) {
10200469dd6d55fa331bfd7de9431da98b6340d82271Siva Velusamy        if (mFragmentBreadCrumbs != null) {
1021518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            mFragmentBreadCrumbs.setParentTitle(title, shortTitle, listener);
1022518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1023518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
1024518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1025518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    void setSelectedHeader(Header header) {
1026518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        mCurHeader = header;
1027518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        int index = mHeaders.indexOf(header);
1028518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (index >= 0) {
1029518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            getListView().setItemChecked(index, true);
1030b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        } else {
1031b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            getListView().clearChoices();
1032b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        }
1033518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (header != null) {
1034518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            CharSequence title = header.getBreadCrumbTitle(getResources());
10357773c435bc5da8217433e1b242d3a6712a17b5f7Mathias Agopian            if (title == null) title = header.getTitle(getResources());
1036518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (title == null) title = getTitle();
1037518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            showBreadCrumbs(title, header.getBreadCrumbShortTitle(getResources()));
1038518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        } else {
1039518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            showBreadCrumbs(getTitle(), null);
1040518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1041518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
1042518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1043518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    private void switchToHeaderInner(String fragmentName, Bundle args, int direction) {
1044518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        getFragmentManager().popBackStack(BACK_STACK_PREFS,
1045518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                FragmentManager.POP_BACK_STACK_INCLUSIVE);
1046518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        Fragment f = Fragment.instantiate(this, fragmentName, args);
1047518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        FragmentTransaction transaction = getFragmentManager().beginTransaction();
1048518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
1049b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        transaction.replace(com.android.internal.R.id.prefs, f);
1050518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        transaction.commit();
1051518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
1052b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall
10535b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian    /**
10545b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian     * When in two-pane mode, switch the fragment pane to show the given
1055518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * preference fragment.
1056518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     *
1057518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param fragmentName The name of the fragment to display.
1058518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param args Optional arguments to supply to the fragment.
1059ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     */
1060518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void switchToHeader(String fragmentName, Bundle args) {
1061518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        setSelectedHeader(null);
1062518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        switchToHeaderInner(fragmentName, args, 0);
1063518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
1064518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1065518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
1066518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * When in two-pane mode, switch to the fragment pane to show the given
1067518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * preference fragment.
1068b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall     *
1069518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param header The new header to display.
1070518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
1071b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    public void switchToHeader(Header header) {
10725b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian        if (mCurHeader == header) {
10735b287a6ea8dfac7ab3e03ae1e98f9e2214cbae09Mathias Agopian            // This is the header we are currently displaying.  Just make sure
1074518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            // to pop the stack up to its root state.
1075518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            getFragmentManager().popBackStack(BACK_STACK_PREFS,
1076518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    FragmentManager.POP_BACK_STACK_INCLUSIVE);
1077ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        } else {
1078518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            int direction = mHeaders.indexOf(header) - mHeaders.indexOf(mCurHeader);
1079518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            switchToHeaderInner(header.fragment, header.fragmentArguments, direction);
1080518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            setSelectedHeader(header);
1081518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1082518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
1083518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1084518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    Header findBestMatchingHeader(Header cur, ArrayList<Header> from) {
1085518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        ArrayList<Header> matches = new ArrayList<Header>();
1086518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        for (int j=0; j<from.size(); j++) {
1087b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            Header oh = from.get(j);
1088518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (cur == oh || (cur.id != HEADER_ID_UNDEFINED && cur.id == oh.id)) {
1089518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                // Must be this one.
1090b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall                matches.clear();
10917c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                matches.add(oh);
1092518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                break;
10937c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            }
10947c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            if (cur.fragment != null) {
10957c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                if (cur.fragment.equals(oh.fragment)) {
10967c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                    matches.add(oh);
10977c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                }
10987c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            } else if (cur.intent != null) {
10997c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                if (cur.intent.equals(oh.intent)) {
1100518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    matches.add(oh);
11017c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                }
1102518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            } else if (cur.title != null) {
1103518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (cur.title.equals(oh.title)) {
1104518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    matches.add(oh);
1105518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
1106518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
1107518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1108b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        final int NM = matches.size();
1109518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (NM == 1) {
1110518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            return matches.get(0);
1111ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian        } else if (NM > 1) {
11127c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            for (int j=0; j<NM; j++) {
11137c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                Header oh = matches.get(j);
1114518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (cur.fragmentArguments != null &&
1115518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                        cur.fragmentArguments.equals(oh.fragmentArguments)) {
1116518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    return oh;
1117518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
1118518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (cur.extras != null && cur.extras.equals(oh.extras)) {
1119518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    return oh;
1120518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
1121518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                if (cur.title != null && cur.title.equals(oh.title)) {
1122518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                    return oh;
1123518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                }
1124518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            }
1125518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1126518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        return null;
1127b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall    }
1128518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1129518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
1130518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Start a new fragment.
11317c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     *
11327c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * @param fragment The fragment to start
11337c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * @param push If true, the current fragment will be pushed onto the back stack.  If false,
1134518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * the current fragment will be replaced.
11357c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     */
1136518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    public void startPreferenceFragment(Fragment fragment, boolean push) {
1137518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        FragmentTransaction transaction = getFragmentManager().beginTransaction();
1138518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        transaction.replace(com.android.internal.R.id.prefs, fragment);
1139518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (push) {
1140518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
1141518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            transaction.addToBackStack(BACK_STACK_PREFS);
1142b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall        } else {
1143518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
1144518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1145518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        transaction.commit();
11467c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian    }
11477c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian
11487c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian    /**
1149518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Start a new fragment containing a preference panel.  If the prefences
1150518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * are being displayed in multi-pane mode, the given fragment class will
1151518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * be instantiated and placed in the appropriate pane.  If running in
1152518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * single-pane mode, a new activity will be launched in which to show the
11537c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * fragment.
11547c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     *
1155518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param fragmentClass Full name of the class implementing the fragment.
1156518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param args Any desired arguments to supply to the fragment.
1157518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param titleRes Optional resource identifier of the title of this
1158b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall     * fragment.
1159518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param titleText Optional text of the title of this fragment.
1160518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * @param resultTo Optional fragment that result data should be sent to.
11617c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * If non-null, resultTo.onActivityResult() will be called when this
11627c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * preference panel is done.  The launched panel must use
11637c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * {@link #finishPreferencePanel(Fragment, int, Intent)} when done.
11647c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * @param resultRequestCode If resultTo is non-null, this is the caller's
11657c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian     * request code to be received with the resut.
1166518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     */
11677c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian    public void startPreferencePanel(String fragmentClass, Bundle args, int titleRes,
1168518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            CharSequence titleText, Fragment resultTo, int resultRequestCode) {
1169518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        if (mSinglePane) {
11707c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            startWithFragment(fragmentClass, args, resultTo, resultRequestCode);
11717c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian        } else {
1172518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            Fragment f = Fragment.instantiate(this, fragmentClass, args);
1173518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            if (resultTo != null) {
1174518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian                f.setTargetFragment(resultTo, resultRequestCode);
1175b29e5e8c2682ae145e8c56d9afb061f8da7f854cJesse Hall            }
1176518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            FragmentTransaction transaction = getFragmentManager().beginTransaction();
1177518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            transaction.replace(com.android.internal.R.id.prefs, f);
11787c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            if (titleRes != 0) {
11797c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                transaction.setBreadCrumbTitle(titleRes);
11807c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            } else if (titleText != null) {
11817c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian                transaction.setBreadCrumbTitle(titleText);
11827c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            }
1183518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
11847c0441ac271f4e00a2d63eb3048c037ebffa90b9Mathias Agopian            transaction.addToBackStack(BACK_STACK_PREFS);
1185518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian            transaction.commit();
1186518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian        }
1187518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    }
1188518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian
1189518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian    /**
1190518ec112f468eb67bf681b3eec896d7bfb4ff98dMathias Agopian     * Called by a preference panel fragment to finish itself.
11914b9511c16195a646242eff833b0af212933b6ecaMathias Agopian     *
11921c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * @param caller The fragment that is asking to be finished.
11931c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * @param resultCode Optional result code to send back to the original
11941c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * launching fragment.
11951c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * @param resultData Optional result data to send back to the original
11961c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * launching fragment.
11971c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     */
11981c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang    public void finishPreferencePanel(Fragment caller, int resultCode, Intent resultData) {
11991c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang        if (mSinglePane) {
12001c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang            setResult(resultCode, resultData);
12011c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang            finish();
12021c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang        } else {
12031c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang            // XXX be smarter about popping the stack.
12041c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang            onBackPressed();
1205ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian            if (caller != null) {
12061c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang                if (caller.getTargetFragment() != null) {
1207ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                    caller.getTargetFragment().onActivityResult(caller.getTargetRequestCode(),
1208ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian                            resultCode, resultData);
12091c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang                }
12101c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang            }
12110e8bbee5775d81c7bbc479b995496cac9238559fMathias Agopian        }
12121c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang    }
12131c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang
12141c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang    @Override
12151c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang    public boolean onPreferenceStartFragment(PreferenceFragment caller, Preference pref) {
12161c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang        startPreferencePanel(pref.getFragment(), pref.getExtras(), 0, pref.getTitle(), null, 0);
12171c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang        return true;
12181c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang    }
12191c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang
12201c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang    /**
12211c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * Posts a message to bind the preferences to the list view.
12221c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * <p>
1223ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     * Binding late is preferred as any custom preference types created in
12241c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang     * {@link #onCreate(Bundle)} are able to have their views recycled.
1225ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian     */
1226ada798b7ca7cabc255aa159964b64975e7fdb2dfMathias Agopian    private void postBindPreferences() {
12271c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang        if (mHandler.hasMessages(MSG_BIND_PREFERENCES)) return;
12281c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang        mHandler.obtainMessage(MSG_BIND_PREFERENCES).sendToTarget();
12290e8bbee5775d81c7bbc479b995496cac9238559fMathias Agopian    }
12301c3d72a2291827fb15e2ef311a571c860e0dba41Jonas Yang
1231    private void bindPreferences() {
1232        final PreferenceScreen preferenceScreen = getPreferenceScreen();
1233        if (preferenceScreen != null) {
1234            preferenceScreen.bind(getListView());
1235            if (mSavedInstanceState != null) {
1236                super.onRestoreInstanceState(mSavedInstanceState);
1237                mSavedInstanceState = null;
1238            }
1239        }
1240    }
1241
1242    /**
1243     * Returns the {@link PreferenceManager} used by this activity.
1244     * @return The {@link PreferenceManager}.
1245     *
1246     * @deprecated This function is not relevant for a modern fragment-based
1247     * PreferenceActivity.
1248     */
1249    @Deprecated
1250    public PreferenceManager getPreferenceManager() {
1251        return mPreferenceManager;
1252    }
1253
1254    private void requirePreferenceManager() {
1255        if (mPreferenceManager == null) {
1256            if (mAdapter == null) {
1257                throw new RuntimeException("This should be called after super.onCreate.");
1258            }
1259            throw new RuntimeException(
1260                    "Modern two-pane PreferenceActivity requires use of a PreferenceFragment");
1261        }
1262    }
1263
1264    /**
1265     * Sets the root of the preference hierarchy that this activity is showing.
1266     *
1267     * @param preferenceScreen The root {@link PreferenceScreen} of the preference hierarchy.
1268     *
1269     * @deprecated This function is not relevant for a modern fragment-based
1270     * PreferenceActivity.
1271     */
1272    @Deprecated
1273    public void setPreferenceScreen(PreferenceScreen preferenceScreen) {
1274        requirePreferenceManager();
1275
1276        if (mPreferenceManager.setPreferences(preferenceScreen) && preferenceScreen != null) {
1277            postBindPreferences();
1278            CharSequence title = getPreferenceScreen().getTitle();
1279            // Set the title of the activity
1280            if (title != null) {
1281                setTitle(title);
1282            }
1283        }
1284    }
1285
1286    /**
1287     * Gets the root of the preference hierarchy that this activity is showing.
1288     *
1289     * @return The {@link PreferenceScreen} that is the root of the preference
1290     *         hierarchy.
1291     *
1292     * @deprecated This function is not relevant for a modern fragment-based
1293     * PreferenceActivity.
1294     */
1295    @Deprecated
1296    public PreferenceScreen getPreferenceScreen() {
1297        if (mPreferenceManager != null) {
1298            return mPreferenceManager.getPreferenceScreen();
1299        }
1300        return null;
1301    }
1302
1303    /**
1304     * Adds preferences from activities that match the given {@link Intent}.
1305     *
1306     * @param intent The {@link Intent} to query activities.
1307     *
1308     * @deprecated This function is not relevant for a modern fragment-based
1309     * PreferenceActivity.
1310     */
1311    @Deprecated
1312    public void addPreferencesFromIntent(Intent intent) {
1313        requirePreferenceManager();
1314
1315        setPreferenceScreen(mPreferenceManager.inflateFromIntent(intent, getPreferenceScreen()));
1316    }
1317
1318    /**
1319     * Inflates the given XML resource and adds the preference hierarchy to the current
1320     * preference hierarchy.
1321     *
1322     * @param preferencesResId The XML resource ID to inflate.
1323     *
1324     * @deprecated This function is not relevant for a modern fragment-based
1325     * PreferenceActivity.
1326     */
1327    @Deprecated
1328    public void addPreferencesFromResource(int preferencesResId) {
1329        requirePreferenceManager();
1330
1331        setPreferenceScreen(mPreferenceManager.inflateFromResource(this, preferencesResId,
1332                getPreferenceScreen()));
1333    }
1334
1335    /**
1336     * {@inheritDoc}
1337     *
1338     * @deprecated This function is not relevant for a modern fragment-based
1339     * PreferenceActivity.
1340     */
1341    @Deprecated
1342    public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen, Preference preference) {
1343        return false;
1344    }
1345
1346    /**
1347     * Finds a {@link Preference} based on its key.
1348     *
1349     * @param key The key of the preference to retrieve.
1350     * @return The {@link Preference} with the key, or null.
1351     * @see PreferenceGroup#findPreference(CharSequence)
1352     *
1353     * @deprecated This function is not relevant for a modern fragment-based
1354     * PreferenceActivity.
1355     */
1356    @Deprecated
1357    public Preference findPreference(CharSequence key) {
1358
1359        if (mPreferenceManager == null) {
1360            return null;
1361        }
1362
1363        return mPreferenceManager.findPreference(key);
1364    }
1365
1366    @Override
1367    protected void onNewIntent(Intent intent) {
1368        if (mPreferenceManager != null) {
1369            mPreferenceManager.dispatchNewIntent(intent);
1370        }
1371    }
1372
1373    // give subclasses access to the Next button
1374    /** @hide */
1375    protected boolean hasNextButton() {
1376        return mNextButton != null;
1377    }
1378    /** @hide */
1379    protected Button getNextButton() {
1380        return mNextButton;
1381    }
1382}
1383