diff options
author | Michael Jurka <mikejurka@google.com> | 2012-11-01 18:26:01 -0700 |
---|---|---|
committer | Michael Jurka <mikejurka@google.com> | 2012-11-01 18:50:21 -0700 |
commit | 67a871d85732e582c70a2a1d85ef4419eb658a12 (patch) | |
tree | effd9037568ce6a2fd73afa3150ce5646881f9a3 | |
parent | 9767597a74bd9a5a265ff72aa5f77dd7efb93b53 (diff) | |
download | frameworks_base-67a871d85732e582c70a2a1d85ef4419eb658a12.zip frameworks_base-67a871d85732e582c70a2a1d85ef4419eb658a12.tar.gz frameworks_base-67a871d85732e582c70a2a1d85ef4419eb658a12.tar.bz2 |
Use clock's widget as the default keyguard widget
Also, if we have no widgets in lockscreen,
reinflate the default widget. If that fails,
inflate the built-in clock (KeyguardStatusView)
Change-Id: I2e90ab0893c993a755700e075e4a8ac5a685e0f2
7 files changed, 90 insertions, 76 deletions
diff --git a/core/java/com/android/internal/widget/LockPatternUtils.java b/core/java/com/android/internal/widget/LockPatternUtils.java index 3ee3c8c..e5e1a2b 100644 --- a/core/java/com/android/internal/widget/LockPatternUtils.java +++ b/core/java/com/android/internal/widget/LockPatternUtils.java @@ -1073,11 +1073,7 @@ public class LockPatternUtils { } return appWidgetIds; } - if (appWidgetIdString == null) { - return new int[] { LockPatternUtils.ID_DEFAULT_STATUS_WIDGET }; - } else { - return new int[0]; - } + return new int[0]; } private static String combineStrings(int[] list, String separator) { diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml index 0890a18..4861c57 100755 --- a/core/res/res/values/config.xml +++ b/core/res/res/values/config.xml @@ -404,6 +404,12 @@ --> <integer name="config_longPressOnPowerBehavior">1</integer> + <!-- Package name for default keyguard appwidget [DO NOT TRANSLATE] --> + <string name="widget_default_package_name"></string> + + <!-- Class name for default keyguard appwidget [DO NOT TRANSLATE] --> + <string name="widget_default_class_name"></string> + <!-- Indicate whether the SD card is accessible without removing the battery. --> <bool name="config_batterySdCardAccessibility">false</bool> diff --git a/core/res/res/values/strings.xml b/core/res/res/values/strings.xml index 51d6429..4a4f1c4 100755 --- a/core/res/res/values/strings.xml +++ b/core/res/res/values/strings.xml @@ -2065,15 +2065,6 @@ <!-- This can be used in any application wanting to disable the text "Emergency number" --> <string name="emergency_call_dialog_number_for_display">Emergency number</string> - <!-- String to display if the clock status widget is selected (it is the default) [CHAR LIMIT=22] --> - <string name="widget_default" msgid="8269383575996003796">Clock</string> - - <!-- Package name for default widget [DO NOT TRANSLATE] --> - <string name="widget_default_package_name">com.android.deskclock</string> - - <!-- Class name for default widget [DO NOT TRANSLATE] --> - <string name="widget_default_class_name">com.android.deskclock.DeskClock</string> - <!-- *** touch based lock / unlock *** --> <skip /> diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml index 05b3068..d28f139 100644 --- a/core/res/res/values/symbols.xml +++ b/core/res/res/values/symbols.xml @@ -479,7 +479,6 @@ <java-symbol type="string" name="emailTypeOther" /> <java-symbol type="string" name="emailTypeWork" /> <java-symbol type="string" name="emergency_call_dialog_number_for_display" /> - <java-symbol type="string" name="widget_default" /> <java-symbol type="string" name="widget_default_package_name" /> <java-symbol type="string" name="widget_default_class_name" /> <java-symbol type="string" name="emergency_calls_only" /> diff --git a/policy/src/com/android/internal/policy/impl/keyguard/KeyguardHostView.java b/policy/src/com/android/internal/policy/impl/keyguard/KeyguardHostView.java index ca3d0a2..18f8b0c 100644 --- a/policy/src/com/android/internal/policy/impl/keyguard/KeyguardHostView.java +++ b/policy/src/com/android/internal/policy/impl/keyguard/KeyguardHostView.java @@ -29,8 +29,6 @@ import android.content.ComponentName; import android.content.Context; import android.content.Intent; import android.content.IntentSender; -import android.content.pm.ActivityInfo; -import android.content.pm.PackageManager; import android.content.pm.UserInfo; import android.content.res.Resources; import android.graphics.Canvas; @@ -50,7 +48,6 @@ import android.view.LayoutInflater; import android.view.MotionEvent; import android.view.View; import android.view.WindowManager; -import android.view.accessibility.AccessibilityNodeInfo; import android.view.animation.AnimationUtils; import android.widget.RemoteViews.OnClickHandler; @@ -59,7 +56,6 @@ import com.android.internal.policy.impl.keyguard.KeyguardSecurityModel.SecurityM import com.android.internal.widget.LockPatternUtils; import java.io.File; -import java.util.ArrayList; import java.util.List; public class KeyguardHostView extends KeyguardViewBase { @@ -68,10 +64,10 @@ public class KeyguardHostView extends KeyguardViewBase { // Use this to debug all of keyguard public static boolean DEBUG = KeyguardViewMediator.DEBUG; - // also referenced in SecuritySettings.java static final int APPWIDGET_HOST_ID = 0x4B455947; private AppWidgetHost mAppWidgetHost; + private AppWidgetManager mAppWidgetManager; private KeyguardWidgetPager mAppWidgetContainer; private KeyguardSecurityViewFlipper mSecurityViewContainer; private KeyguardSelectorView mKeyguardSelectorView; @@ -113,6 +109,7 @@ public class KeyguardHostView extends KeyguardViewBase { mLockPatternUtils = new LockPatternUtils(context); mAppWidgetHost = new AppWidgetHost( context, APPWIDGET_HOST_ID, mOnClickHandler, Looper.myLooper()); + mAppWidgetManager = AppWidgetManager.getInstance(mContext); mSecurityModel = new KeyguardSecurityModel(context); // The following enables the MENU key to work for testing automation @@ -158,10 +155,6 @@ public class KeyguardHostView extends KeyguardViewBase { mAppWidgetContainer.setCallbacks(mWidgetCallbacks); mAppWidgetContainer.setMinScale(0.5f); - addDefaultWidgets(); - addWidgetsFromSettings(); - mSwitchPageRunnable.run(); - SlidingChallengeLayout slider = (SlidingChallengeLayout) findViewById(R.id.sliding_layout); if (slider != null) { @@ -183,8 +176,11 @@ public class KeyguardHostView extends KeyguardViewBase { setSystemUiVisibility(getSystemUiVisibility() | View.STATUS_BAR_DISABLE_BACK); } - showPrimarySecurityScreen(false); + addDefaultWidgets(); + addWidgetsFromSettings(); + mSwitchPageRunnable.run(); + showPrimarySecurityScreen(false); updateSecurityViews(); } @@ -549,8 +545,6 @@ public class KeyguardHostView extends KeyguardViewBase { }; }; - private KeyguardStatusViewManager mKeyguardStatusViewManager; - // Used to ignore callbacks from methods that are no longer current (e.g. face unlock). // This avoids unwanted asynchronous events from messing with the state. private KeyguardSecurityCallback mNullCallback = new KeyguardSecurityCallback() { @@ -715,6 +709,7 @@ public class KeyguardHostView extends KeyguardViewBase { // biometric unlock to start next time keyguard is shown. KeyguardUpdateMonitor.getInstance(mContext).setAlternateUnlockEnabled(true); saveStickyWidgetIndex(); + checkAppWidgetConsistency(); showPrimarySecurityScreen(true); getSecurityView(mCurrentSecuritySelection).onPause(); CameraWidgetFrame cameraPage = findCameraPage(); @@ -812,15 +807,16 @@ public class KeyguardHostView extends KeyguardViewBase { } } - private void addWidget(int appId, int pageIndex) { - AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(mContext); - AppWidgetProviderInfo appWidgetInfo = appWidgetManager.getAppWidgetInfo(appId); + private boolean addWidget(int appId, int pageIndex) { + AppWidgetProviderInfo appWidgetInfo = mAppWidgetManager.getAppWidgetInfo(appId); if (appWidgetInfo != null) { AppWidgetHostView view = getAppWidgetHost().createView(mContext, appId, appWidgetInfo); addWidget(view, pageIndex); + return true; } else { Log.w(TAG, "AppWidgetInfo for app widget id " + appId + " was null, deleting"); mLockPatternUtils.removeAppWidget(appId); + return false; } } @@ -890,22 +886,7 @@ public class KeyguardHostView extends KeyguardViewBase { @Override public void run() { - int defaultIconId = 0; - Resources res = KeyguardHostView.this.getContext().getResources(); - ComponentName clock = new ComponentName( - res.getString(R.string.widget_default_package_name), - res.getString(R.string.widget_default_class_name)); - try { - ActivityInfo activityInfo = - mContext.getPackageManager().getActivityInfo(clock, 0); - if (activityInfo != null) { - defaultIconId = activityInfo.icon; - } - } catch (PackageManager.NameNotFoundException e) { - defaultIconId = 0; - } - launchPickActivityIntent(R.string.widget_default, defaultIconId, clock, - LockPatternUtils.EXTRA_DEFAULT_WIDGET); + launchPickActivityIntent(); } }); mCallback.dismiss(false); @@ -916,8 +897,7 @@ public class KeyguardHostView extends KeyguardViewBase { initializeTransportControl(); } - private void launchPickActivityIntent(int defaultLabelId, int defaultIconId, - ComponentName defaultComponentName, String defaultTag) { + private void launchPickActivityIntent() { // Create intent to pick widget Intent pickIntent = new Intent(AppWidgetManager.ACTION_KEYGUARD_APPWIDGET_PICK); @@ -928,22 +908,6 @@ public class KeyguardHostView extends KeyguardViewBase { pickIntent.putExtra(AppWidgetManager.EXTRA_CATEGORY_FILTER, AppWidgetProviderInfo.WIDGET_CATEGORY_KEYGUARD); - // Add an custom entry for the default - AppWidgetProviderInfo defaultInfo = new AppWidgetProviderInfo(); - ArrayList<AppWidgetProviderInfo> extraInfos = new ArrayList<AppWidgetProviderInfo>(); - defaultInfo.label = getResources().getString(defaultLabelId); - defaultInfo.icon = defaultIconId; - defaultInfo.provider = defaultComponentName; - extraInfos.add(defaultInfo); - - ArrayList<Bundle> extraExtras = new ArrayList<Bundle>(); - Bundle b = new Bundle(); - b.putBoolean(defaultTag, true); - extraExtras.add(b); - - // Launch the widget picker - pickIntent.putExtra(AppWidgetManager.EXTRA_CUSTOM_INFO, extraInfos); - pickIntent.putExtra(AppWidgetManager.EXTRA_CUSTOM_EXTRAS, extraExtras); pickIntent.putExtra(Intent.EXTRA_INTENT, getBaseIntent()); pickIntent.addFlags( Intent.FLAG_ACTIVITY_NEW_TASK @@ -1024,6 +988,22 @@ public class KeyguardHostView extends KeyguardViewBase { } } + private int getAddPageIndex() { + View addWidget = mAppWidgetContainer.findViewById(R.id.keyguard_add_widget); + int addPageIndex = mAppWidgetContainer.indexOfChild(addWidget); + // This shouldn't happen, but just to be safe! + if (addPageIndex < 0) { + addPageIndex = 0; + } + return addPageIndex; + } + + private void addDefaultStatusWidget(int index) { + LayoutInflater inflater = LayoutInflater.from(mContext); + View statusWidget = inflater.inflate(R.layout.keyguard_status_view, null, true); + mAppWidgetContainer.addWidget(statusWidget, index); + } + private void addWidgetsFromSettings() { DevicePolicyManager dpm = (DevicePolicyManager) mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); @@ -1036,23 +1016,17 @@ public class KeyguardHostView extends KeyguardViewBase { } } - View addWidget = mAppWidgetContainer.findViewById(R.id.keyguard_add_widget); - int addPageIndex = mAppWidgetContainer.indexOfChild(addWidget); - // This shouldn't happen, but just to be safe! - if (addPageIndex < 0) { - addPageIndex = 0; - } + int addPageIndex = getAddPageIndex(); // Add user-selected widget final int[] widgets = mLockPatternUtils.getAppWidgets(); + if (widgets == null) { Log.d(TAG, "Problem reading widgets"); } else { for (int i = widgets.length -1; i >= 0; i--) { if (widgets[i] == LockPatternUtils.ID_DEFAULT_STATUS_WIDGET) { - LayoutInflater inflater = LayoutInflater.from(mContext); - View statusWidget = inflater.inflate(R.layout.keyguard_status_view, null, true); - mAppWidgetContainer.addWidget(statusWidget, addPageIndex + 1); + addDefaultStatusWidget(addPageIndex + 1); } else { // We add the widgets from left to right, starting after the first page after // the add page. We count down, since the order will be persisted from right @@ -1061,6 +1035,42 @@ public class KeyguardHostView extends KeyguardViewBase { } } } + checkAppWidgetConsistency(); + } + + public void checkAppWidgetConsistency() { + final int childCount = mAppWidgetContainer.getChildCount(); + boolean widgetPageExists = false; + for (int i = 0; i < childCount; i++) { + if (isWidgetPage(i)) { + widgetPageExists = true; + break; + } + } + if (!widgetPageExists) { + final int addPageIndex = getAddPageIndex(); + + Resources res = getContext().getResources(); + ComponentName defaultAppWidget = new ComponentName( + res.getString(R.string.widget_default_package_name), + res.getString(R.string.widget_default_class_name)); + + // Note: we don't support configuring the widget + int appWidgetId = mAppWidgetHost.allocateAppWidgetId(); + boolean bindSuccessful = false; + try { + mAppWidgetManager.bindAppWidgetId(appWidgetId, defaultAppWidget); + bindSuccessful = true; + } catch (IllegalArgumentException e) { + Log.e(TAG, "Error when trying to bind default AppWidget: " + e); + } + // Use the built-in status/clock view if we can't inflate the default widget + if (!(bindSuccessful && addWidget(appWidgetId, addPageIndex + 1))) { + addDefaultStatusWidget(addPageIndex + 1); + } + mAppWidgetContainer.onAddView( + mAppWidgetContainer.getChildAt(addPageIndex + 1), addPageIndex + 1); + } } Runnable mSwitchPageRunnable = new Runnable() { @@ -1155,6 +1165,15 @@ public class KeyguardHostView extends KeyguardViewBase { return null; } + private boolean isWidgetPage(int pageIndex) { + View v = mAppWidgetContainer.getChildAt(pageIndex); + if (v != null && v instanceof KeyguardWidgetFrame) { + KeyguardWidgetFrame kwf = (KeyguardWidgetFrame) v; + return kwf.getContentAppWidgetId() != AppWidgetManager.INVALID_APPWIDGET_ID; + } + return false; + } + private boolean isCameraPage(int pageIndex) { View v = mAppWidgetContainer.getChildAt(pageIndex); return v != null && v instanceof CameraWidgetFrame; diff --git a/policy/src/com/android/internal/policy/impl/keyguard/KeyguardWidgetFrame.java b/policy/src/com/android/internal/policy/impl/keyguard/KeyguardWidgetFrame.java index b1ff049..bb4272c 100644 --- a/policy/src/com/android/internal/policy/impl/keyguard/KeyguardWidgetFrame.java +++ b/policy/src/com/android/internal/policy/impl/keyguard/KeyguardWidgetFrame.java @@ -20,6 +20,7 @@ import android.animation.Animator; import android.animation.ObjectAnimator; import android.animation.PropertyValuesHolder; import android.appwidget.AppWidgetHostView; +import android.appwidget.AppWidgetManager; import android.content.Context; import android.content.res.Resources; import android.graphics.Canvas; @@ -220,8 +221,10 @@ public class KeyguardWidgetFrame extends FrameLayout { View content = getContent(); if (content instanceof AppWidgetHostView) { return ((AppWidgetHostView) content).getAppWidgetId(); - } else { + } else if (content instanceof KeyguardStatusView) { return ((KeyguardStatusView) content).getAppWidgetId(); + } else { + return AppWidgetManager.INVALID_APPWIDGET_ID; } } diff --git a/services/java/com/android/server/AppWidgetServiceImpl.java b/services/java/com/android/server/AppWidgetServiceImpl.java index d0dd9cf..daa82f2 100644 --- a/services/java/com/android/server/AppWidgetServiceImpl.java +++ b/services/java/com/android/server/AppWidgetServiceImpl.java @@ -599,7 +599,7 @@ class AppWidgetServiceImpl { } public void bindAppWidgetId(int appWidgetId, ComponentName provider, Bundle options) { - mContext.enforceCallingPermission(android.Manifest.permission.BIND_APPWIDGET, + mContext.enforceCallingOrSelfPermission(android.Manifest.permission.BIND_APPWIDGET, "bindAppWidgetId appWidgetId=" + appWidgetId + " provider=" + provider); bindAppWidgetIdImpl(appWidgetId, provider, options); } @@ -607,7 +607,7 @@ class AppWidgetServiceImpl { public boolean bindAppWidgetIdIfAllowed( String packageName, int appWidgetId, ComponentName provider, Bundle options) { try { - mContext.enforceCallingPermission(android.Manifest.permission.BIND_APPWIDGET, null); + mContext.enforceCallingOrSelfPermission(android.Manifest.permission.BIND_APPWIDGET, null); } catch (SecurityException se) { if (!callerHasBindAppWidgetPermission(packageName)) { return false; |