From 39f1e04079976d3d10fdd8e5dd36c833bab8a371 Mon Sep 17 00:00:00 2001 From: Jason parks Date: Thu, 20 Jan 2011 23:29:28 -0600 Subject: [PATCH] More UI tweaks and fixes. * Actually post the correct message every 5 second for the progress bar. * Update the text for the settings to a more finalish version. * Check the battery status before allowing encryption to proceed. * Display a place holder message if no password is set for the device. Change-Id: I2734300c9a81467dbd0401427d8b656922ab4819 --- res/values/strings.xml | 4 +- src/com/android/settings/CryptKeeper.java | 26 ++-- .../android/settings/CryptKeeperSettings.java | 115 +++++++++++------- 3 files changed, 86 insertions(+), 59 deletions(-) diff --git a/res/values/strings.xml b/res/values/strings.xml index 6131eb7fdb3..9724e6088c2 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -587,12 +587,12 @@ Requires you to set a device unlock pin or password Confirm encrypt - Device encryption will convert user data to an ecrypted state, including your accounts, system data, downloaded applications and data, photos, movies, musics, etc.\n\nEncyrption cannot be undone without performing a factory data reset, which would then erase all data.\n\nYou must set up a device lock pin or password to proceed.\n\nThis operation may take up to an hour and may not be interrupted. You must have a fully charged battery and plug in the device to initiate encryption. Running out of power during encryption will cause data loss. + You can encrypt your accounts, settings, downloaded applications and their data, media, and other files. Once you encrypt your tablet, you can\'t unencrypt it except by performing a factory data reset, erasing all the data on your tablet.\n\nEncryption takes up to an hour. You must start with a charged battery and keep your tablet plugged in until encryption is complete. If you interrupt the encryption process, you will lose some or all of your data. Encrypt tablet Encrypt phone - Encrypt user data? This operation is not reversible and may not be interrupted without loos of data! Encryption may take up to an hour. + Encrypt user data? This operation is not reversible and may not be interrupted without loss of data! Encryption may take up to an hour. Encrypting diff --git a/src/com/android/settings/CryptKeeper.java b/src/com/android/settings/CryptKeeper.java index 25bb242b81e..222e954f140 100644 --- a/src/com/android/settings/CryptKeeper.java +++ b/src/com/android/settings/CryptKeeper.java @@ -75,9 +75,9 @@ public class CryptKeeper extends Activity implements TextView.OnEditorActionList } catch (Exception e) { Log.w(TAG, "Error parsing progress: " + e.toString()); } - - // Check the status every 1 second - sendEmptyMessageDelayed(0, 1000); + + // Check the status every 5 second + sendEmptyMessageDelayed(UPDATE_PROGRESS, 5000); break; case COOLDOWN: @@ -128,6 +128,12 @@ public class CryptKeeper extends Activity implements TextView.OnEditorActionList setContentView(R.layout.crypt_keeper_password_entry); passwordEntryInit(); } + + // Disable the status bar + StatusBarManager sbm = (StatusBarManager) getSystemService(Context.STATUS_BAR_SERVICE); + sbm.disable(StatusBarManager.DISABLE_EXPAND | StatusBarManager.DISABLE_NOTIFICATION_ICONS + | StatusBarManager.DISABLE_NOTIFICATION_ALERTS + | StatusBarManager.DISABLE_SYSTEM_INFO | StatusBarManager.DISABLE_NAVIGATION); } private void encryptionProgressInit() { @@ -151,12 +157,6 @@ public class CryptKeeper extends Activity implements TextView.OnEditorActionList String dateFormatString = getString(com.android.internal.R.string.full_wday_month_day_no_year); TextView date = (TextView) findViewById(R.id.date); date.setText(DateFormat.format(dateFormatString, new Date())); - - // Disable the status bar - StatusBarManager sbm = (StatusBarManager) getSystemService(Context.STATUS_BAR_SERVICE); - sbm.disable(StatusBarManager.DISABLE_EXPAND | StatusBarManager.DISABLE_NOTIFICATION_ICONS - | StatusBarManager.DISABLE_NOTIFICATION_ALERTS - | StatusBarManager.DISABLE_SYSTEM_INFO | StatusBarManager.DISABLE_NAVIGATION); } private IMountService getMountService() { @@ -184,12 +184,10 @@ public class CryptKeeper extends Activity implements TextView.OnEditorActionList try { service.decryptStorage(password); - // For now the only way to get here is for the password to be - // wrong. + if (mFailedAttempts == 0) { + // Success. Do something here within 2 seconds - mFailedAttempts++; - - if (mFailedAttempts == MAX_FAILED_ATTEMPTS) { + } else if (mFailedAttempts == MAX_FAILED_ATTEMPTS) { // Factory reset the device. sendBroadcast(new Intent("android.intent.action.MASTER_CLEAR")); } else if ((mFailedAttempts % COOL_DOWN_ATTEMPTS) == 0) { diff --git a/src/com/android/settings/CryptKeeperSettings.java b/src/com/android/settings/CryptKeeperSettings.java index 8b60ca7b21d..26483ec37f4 100644 --- a/src/com/android/settings/CryptKeeperSettings.java +++ b/src/com/android/settings/CryptKeeperSettings.java @@ -17,9 +17,14 @@ package com.android.settings; import android.app.Activity; +import android.app.AlertDialog; import android.app.Fragment; +import android.content.BroadcastReceiver; +import android.content.Context; import android.content.Intent; +import android.content.IntentFilter; import android.content.res.Resources; +import android.os.BatteryManager; import android.os.Bundle; import android.preference.Preference; import android.preference.PreferenceActivity; @@ -45,6 +50,72 @@ public class CryptKeeperSettings extends Fragment { private View mContentView; private Button mInitiateButton; + private IntentFilter mIntentFilter; + + private BroadcastReceiver mIntentReceiver = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + String action = intent.getAction(); + if (action.equals(Intent.ACTION_BATTERY_CHANGED)) { + int level = intent.getIntExtra("level", 0); + int status = intent.getIntExtra("status", BatteryManager.BATTERY_STATUS_UNKNOWN); + + if (status == BatteryManager.BATTERY_STATUS_CHARGING && level >= 80) { + mInitiateButton.setEnabled(true); + } else { + mInitiateButton.setEnabled(false); + } + } + } + }; + + /** + * If the user clicks to begin the reset sequence, we next require a + * keyguard confirmation if the user has currently enabled one. If there + * is no keyguard available, we prompt the user to set a password. + */ + private Button.OnClickListener mInitiateListener = new Button.OnClickListener() { + + public void onClick(View v) { + if (!runKeyguardConfirmation(KEYGUARD_REQUEST)) { + // TODO remove with proper flow + new AlertDialog.Builder(getActivity()) + .setTitle("No password set") + .setIcon(android.R.drawable.ic_dialog_alert) + .setMessage("Before you enable encryption you must set a device password.") + .setPositiveButton(android.R.string.ok, null) + .create() + .show(); + } + } + }; + + + @Override + public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedState) { + mContentView = inflater.inflate(R.layout.crypt_keeper_settings, null); + + mIntentFilter = new IntentFilter(); + mIntentFilter.addAction(Intent.ACTION_BATTERY_CHANGED); + + mInitiateButton = (Button) mContentView.findViewById(R.id.initiate_encrypt); + mInitiateButton.setOnClickListener(mInitiateListener); + mInitiateButton.setEnabled(false); + + return mContentView; + } + + @Override + public void onResume() { + super.onResume(); + getActivity().registerReceiver(mIntentReceiver, mIntentFilter); + } + + @Override + public void onPause() { + super.onPause(); + getActivity().unregisterReceiver(mIntentReceiver); + } /** * Keyguard validation is run using the standard {@link ConfirmLockPattern} @@ -67,14 +138,12 @@ public class CryptKeeperSettings extends Fragment { if (requestCode != KEYGUARD_REQUEST) { return; } - + // If the user entered a valid keyguard trace, present the final // confirmation prompt; otherwise, go back to the initial state. if (resultCode == Activity.RESULT_OK) { String password = data.getStringExtra("password"); showFinalConfirmation(password); - } else { - establishInitialState(); } } @@ -85,45 +154,5 @@ public class CryptKeeperSettings extends Fragment { preference.getExtras().putString("password", password); ((PreferenceActivity) getActivity()).onPreferenceStartFragment(null, preference); } - - /** - * If the user clicks to begin the reset sequence, we next require a - * keyguard confirmation if the user has currently enabled one. If there - * is no keyguard available, we simply go to the final confirmation prompt. - */ - private Button.OnClickListener mInitiateListener = new Button.OnClickListener() { - - public void onClick(View v) { - if (!runKeyguardConfirmation(KEYGUARD_REQUEST)) { - // TODO: Need to request a password - // showFinalConfirmation(); - } - } - }; - - /** - * In its initial state, the activity presents a button for the user to - * click in order to initiate a confirmation sequence. This method is - * called from various other points in the code to reset the activity to - * this base state. - * - *

Reinflating views from resources is expensive and prevents us from - * caching widget pointers, so we use a single-inflate pattern: we lazy- - * inflate each view, caching all of the widget pointers we'll need at the - * time, then simply reuse the inflated views directly whenever we need - * to change contents. - */ - private void establishInitialState() { - mInitiateButton = (Button) mContentView.findViewById(R.id.initiate_encrypt); - mInitiateButton.setOnClickListener(mInitiateListener); - } - - @Override - public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedState) { - mContentView = inflater.inflate(R.layout.crypt_keeper_settings, null); - - establishInitialState(); - return mContentView; - } }