143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani/* 243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * Copyright (C) 2008 The Android Open Source Project 343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * Licensed under the Apache License, Version 2.0 (the "License"); 543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * you may not use this file except in compliance with the License. 643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * You may obtain a copy of the License at 743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * http://www.apache.org/licenses/LICENSE-2.0 943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 1043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * Unless required by applicable law or agreed to in writing, software 1143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * distributed under the License is distributed on an "AS IS" BASIS, 1243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * See the License for the specific language governing permissions and 1443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * limitations under the License. 1543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani */ 1643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 1743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasanipackage com.android.settings.accounts; 1843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 1943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.accounts.AccountManager; 2043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.accounts.AccountManagerCallback; 2143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.accounts.AccountManagerFuture; 2243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.accounts.AuthenticatorException; 2343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.accounts.OperationCanceledException; 2443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.app.Activity; 25b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolacheimport android.app.PendingIntent; 2643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.content.Intent; 2743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.os.Bundle; 2843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport android.util.Log; 2943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 30eb71f2689785bd43560afb04f8b2281c3f67f695Amith Yamasaniimport com.android.settings.Utils; 31eb71f2689785bd43560afb04f8b2281c3f67f695Amith Yamasani 3243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasaniimport java.io.IOException; 3343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 3443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani/** 3543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * Entry point Actiivty for account setup. Works as follows 3621c2904ba32b33e5a43d33b9c46abc3ce9d6bbb0Amith Yamasani * 3743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 1) When the other Activities launch this Activity, it launches {@link ChooseAccountActivity} 3843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * without showing anything. 3943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 2) After receiving an account type from ChooseAccountActivity, this Activity launches the 4043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * account setup specified by AccountManager. 4143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 3) After the account setup, this Activity finishes without showing anything. 4243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * 4343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * Note: 4443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * Previously this Activity did what {@link ChooseAccountActivity} does right now, but we 4543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * currently delegate the work to the other Activity. When we let this Activity do that work, users 4643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * would see the list of account types when leaving this Activity, since the UI is already ready 4743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani * when returning from each account setup, which doesn't look good. 4843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani */ 4943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasanipublic class AddAccountSettings extends Activity { 50b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache /** 5184d04c20531c94a52d20098ee675ad55df9acf8fRussell Brenner * 52b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache */ 53b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache private static final String KEY_ADD_CALLED = "AddAccountCalled"; 54b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 55b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache /** 56b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache * Extra parameter to identify the caller. Applications may display a 57b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache * different UI if the calls is made from Settings or from a specific 58b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache * application. 59b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache */ 60b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache private static final String KEY_CALLER_IDENTITY = "pendingIntent"; 61b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 6243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani private static final String TAG = "AccountSettings"; 6343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 6443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani /* package */ static final String EXTRA_SELECTED_ACCOUNT = "selected_account"; 6543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 6684d04c20531c94a52d20098ee675ad55df9acf8fRussell Brenner // show additional info regarding the use of a device with multiple users 6784d04c20531c94a52d20098ee675ad55df9acf8fRussell Brenner static final String EXTRA_HAS_MULTIPLE_USERS = "hasMultipleUsers"; 6884d04c20531c94a52d20098ee675ad55df9acf8fRussell Brenner 6943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani private static final int CHOOSE_ACCOUNT_REQUEST = 1; 70cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani private static final int ADD_ACCOUNT_REQUEST = 2; 7143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 72b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache private PendingIntent mPendingIntent; 73b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 7443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani private AccountManagerCallback<Bundle> mCallback = new AccountManagerCallback<Bundle>() { 7543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani public void run(AccountManagerFuture<Bundle> future) { 76cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani boolean done = true; 7743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani try { 7843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani Bundle bundle = future.getResult(); 79cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani //bundle.keySet(); 80cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani Intent intent = (Intent) bundle.get(AccountManager.KEY_INTENT); 81cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani if (intent != null) { 82cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani done = false; 83cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani Bundle addAccountOptions = new Bundle(); 84cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani addAccountOptions.putParcelable(KEY_CALLER_IDENTITY, mPendingIntent); 85cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani addAccountOptions.putBoolean(EXTRA_HAS_MULTIPLE_USERS, 86cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani Utils.hasMultipleUsers(AddAccountSettings.this)); 87cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani intent.putExtras(addAccountOptions); 88cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani startActivityForResult(intent, ADD_ACCOUNT_REQUEST); 89cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani } else { 90cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani setResult(RESULT_OK); 91cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani if (mPendingIntent != null) { 92cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani mPendingIntent.cancel(); 93cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani mPendingIntent = null; 94cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani } 95b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache } 96b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 9743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (Log.isLoggable(TAG, Log.VERBOSE)) Log.v(TAG, "account added: " + bundle); 9843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } catch (OperationCanceledException e) { 9943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (Log.isLoggable(TAG, Log.VERBOSE)) Log.v(TAG, "addAccount was canceled"); 10043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } catch (IOException e) { 10143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (Log.isLoggable(TAG, Log.VERBOSE)) Log.v(TAG, "addAccount failed: " + e); 10243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } catch (AuthenticatorException e) { 10343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (Log.isLoggable(TAG, Log.VERBOSE)) Log.v(TAG, "addAccount failed: " + e); 10443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } finally { 105cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani if (done) { 106cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani finish(); 107cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani } 10843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 10943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 11043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani }; 11143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 112b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache private boolean mAddAccountCalled = false; 113b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 11443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani @Override 11543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani public void onCreate(Bundle savedInstanceState) { 11643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani super.onCreate(savedInstanceState); 1177bb8f7288eaad7f6cedaea3b5c8dc48e4baa0a7fAmith Yamasani 118b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache if (savedInstanceState != null) { 119b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache mAddAccountCalled = savedInstanceState.getBoolean(KEY_ADD_CALLED); 120b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache if (Log.isLoggable(TAG, Log.VERBOSE)) Log.v(TAG, "restored"); 121b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache } 122b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 12321c2904ba32b33e5a43d33b9c46abc3ce9d6bbb0Amith Yamasani if (mAddAccountCalled) { 12421c2904ba32b33e5a43d33b9c46abc3ce9d6bbb0Amith Yamasani // We already called add account - maybe the callback was lost. 12521c2904ba32b33e5a43d33b9c46abc3ce9d6bbb0Amith Yamasani finish(); 12621c2904ba32b33e5a43d33b9c46abc3ce9d6bbb0Amith Yamasani return; 127eb71f2689785bd43560afb04f8b2281c3f67f695Amith Yamasani } 12843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani final String[] authorities = 12943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani getIntent().getStringArrayExtra(AccountPreferenceBase.AUTHORITIES_FILTER_KEY); 13043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani final String[] accountTypes = 13143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani getIntent().getStringArrayExtra(AccountPreferenceBase.ACCOUNT_TYPES_FILTER_KEY); 13243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani final Intent intent = new Intent(this, ChooseAccountActivity.class); 13343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (authorities != null) { 13443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani intent.putExtra(AccountPreferenceBase.AUTHORITIES_FILTER_KEY, authorities); 13543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 13643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (accountTypes != null) { 13743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani intent.putExtra(AccountPreferenceBase.ACCOUNT_TYPES_FILTER_KEY, accountTypes); 13843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 13943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani startActivityForResult(intent, CHOOSE_ACCOUNT_REQUEST); 14043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 14143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 14243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani @Override 14343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani public void onActivityResult(int requestCode, int resultCode, Intent data) { 14443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani switch (requestCode) { 14543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani case CHOOSE_ACCOUNT_REQUEST: 14643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani if (resultCode == RESULT_CANCELED) { 14743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani setResult(resultCode); 14843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani finish(); 14943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani return; 15043c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 15143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani // Go to account setup screen. finish() is called inside mCallback. 15243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani addAccount(data.getStringExtra(EXTRA_SELECTED_ACCOUNT)); 15343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani break; 154cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani case ADD_ACCOUNT_REQUEST: 155cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani setResult(resultCode); 156cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani if (mPendingIntent != null) { 157cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani mPendingIntent.cancel(); 158cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani mPendingIntent = null; 159cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani } 160cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani finish(); 161cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani break; 16243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 16343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 16443c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani 165b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache protected void onSaveInstanceState(Bundle outState) { 166b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache super.onSaveInstanceState(outState); 167b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache outState.putBoolean(KEY_ADD_CALLED, mAddAccountCalled); 168b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache if (Log.isLoggable(TAG, Log.VERBOSE)) Log.v(TAG, "saved"); 169b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache } 170b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache 17143c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani private void addAccount(String accountType) { 172b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache Bundle addAccountOptions = new Bundle(); 173b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache mPendingIntent = PendingIntent.getBroadcast(this, 0, new Intent(), 0); 174b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache addAccountOptions.putParcelable(KEY_CALLER_IDENTITY, mPendingIntent); 17584d04c20531c94a52d20098ee675ad55df9acf8fRussell Brenner addAccountOptions.putBoolean(EXTRA_HAS_MULTIPLE_USERS, Utils.hasMultipleUsers(this)); 17643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani AccountManager.get(this).addAccount( 17743c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani accountType, 17843c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani null, /* authTokenType */ 17943c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani null, /* requiredFeatures */ 180b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache addAccountOptions, 181cbabf19cbb85a21da3a4325f5ef925895ac16040Amith Yamasani null, 18243c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani mCallback, 18343c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani null /* handler */); 184b22a242e0e87caf214d9a6139df09bbb2975990aCostin Manolache mAddAccountCalled = true; 18543c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani } 18643c697854c7e373fbc1dae8b7a5259a32de346b4Amith Yamasani} 187