summaryrefslogtreecommitdiffstats
path: root/policy
diff options
context:
space:
mode:
authorDaniel Sandler <dsandler@android.com>2013-10-11 14:27:53 -0400
committerDaniel Sandler <dsandler@android.com>2013-10-13 15:28:19 -0400
commita953b6d968beba01baad095b9ed2e40dbb97f189 (patch)
tree5c21f49bac4c1137b2d2869aeb3dff84d8a33d1f /policy
parentd38b1302b7506ae7eef6c6680228c0f07f6e1895 (diff)
downloadframeworks_base-a953b6d968beba01baad095b9ed2e40dbb97f189.zip
frameworks_base-a953b6d968beba01baad095b9ed2e40dbb97f189.tar.gz
frameworks_base-a953b6d968beba01baad095b9ed2e40dbb97f189.tar.bz2
New window cling for immersive mode.
Bug: 11077915 Change-Id: I6858259b31301b76dee81d3e6fbc534c1cdea661
Diffstat (limited to 'policy')
-rw-r--r--policy/src/com/android/internal/policy/impl/TransientNavigationConfirmation.java132
1 files changed, 120 insertions, 12 deletions
diff --git a/policy/src/com/android/internal/policy/impl/TransientNavigationConfirmation.java b/policy/src/com/android/internal/policy/impl/TransientNavigationConfirmation.java
index 8613088..a6381a7 100644
--- a/policy/src/com/android/internal/policy/impl/TransientNavigationConfirmation.java
+++ b/policy/src/com/android/internal/policy/impl/TransientNavigationConfirmation.java
@@ -16,18 +16,31 @@
package com.android.internal.policy.impl;
+import android.animation.Animator;
+import android.animation.ArgbEvaluator;
+import android.animation.ValueAnimator;
+import android.app.ActivityManager;
import android.content.Context;
+import android.graphics.PixelFormat;
+import android.graphics.drawable.ColorDrawable;
import android.os.Handler;
import android.os.Message;
import android.os.UserHandle;
import android.provider.Settings;
import android.text.TextUtils;
import android.util.ArraySet;
+import android.util.DisplayMetrics;
import android.util.Slog;
+import android.view.Gravity;
+import android.view.MotionEvent;
import android.view.View;
+import android.view.ViewGroup;
+import android.view.WindowManager;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;
-import android.widget.Toast;
+import android.view.animation.DecelerateInterpolator;
+import android.widget.Button;
+import android.widget.FrameLayout;
import com.android.internal.R;
@@ -40,6 +53,7 @@ import java.util.Arrays;
public class TransientNavigationConfirmation {
private static final String TAG = "TransientNavigationConfirmation";
private static final boolean DEBUG = false;
+ private static final boolean DEBUG_SHOW_EVERY_TIME = false; // super annoying, use with caution
private final Context mContext;
private final H mHandler;
@@ -47,11 +61,12 @@ public class TransientNavigationConfirmation {
private final long mShowDelayMs;
private final long mPanicThresholdMs;
- private Toast mToast;
+ private ClingWindowView mClingWindow;
private String mLastPackage;
private String mPromptPackage;
private long mPanicTime;
private String mPanicPackage;
+ private WindowManager mWindowManager;
public TransientNavigationConfirmation(Context context) {
mContext = context;
@@ -59,6 +74,8 @@ public class TransientNavigationConfirmation {
mShowDelayMs = getNavBarExitDuration() * 3;
mPanicThresholdMs = context.getResources()
.getInteger(R.integer.config_transient_navigation_confirmation_panic);
+ mWindowManager = (WindowManager)
+ mContext.getSystemService(Context.WINDOW_SERVICE);
}
private long getNavBarExitDuration() {
@@ -104,7 +121,7 @@ public class TransientNavigationConfirmation {
mHandler.removeMessages(H.SHOW);
if (isNavTransient) {
mLastPackage = pkg;
- if (!mConfirmedPackages.contains(pkg)) {
+ if (DEBUG_SHOW_EVERY_TIME || !mConfirmedPackages.contains(pkg)) {
mHandler.sendMessageDelayed(mHandler.obtainMessage(H.SHOW, pkg), mShowDelayMs);
}
} else {
@@ -141,11 +158,90 @@ public class TransientNavigationConfirmation {
}
private void handleHide() {
- if (mToast != null) {
+ if (mClingWindow != null) {
if (DEBUG) Slog.d(TAG,
"Hiding transient navigation confirmation for " + mPromptPackage);
- mToast.cancel();
- mToast = null;
+ mWindowManager.removeView(mClingWindow);
+ mClingWindow = null;
+ }
+ }
+
+ private class ClingWindowView extends FrameLayout {
+ private static final int BGCOLOR = 0x80000000;
+ private static final int OFFSET_DP = 48;
+
+ private final ColorDrawable mColor = new ColorDrawable(0);
+ private ValueAnimator mColorAnim;
+
+ public ClingWindowView(Context context) {
+ super(context);
+ setClickable(true);
+ setBackground(mColor);
+ }
+
+ @Override
+ public void onAttachedToWindow() {
+ super.onAttachedToWindow();
+
+ DisplayMetrics metrics = new DisplayMetrics();
+ mWindowManager.getDefaultDisplay().getMetrics(metrics);
+ float density = metrics.density;
+
+ // create the confirmation cling
+ final ViewGroup clingLayout = (ViewGroup)
+ View.inflate(getContext(), R.layout.transient_navigation_cling, null);
+
+ final Button ok = (Button) clingLayout.findViewById(R.id.ok);
+ ok.setOnClickListener(new OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ handleHide();
+ }
+ });
+ addView(clingLayout, new FrameLayout.LayoutParams(
+ FrameLayout.LayoutParams.MATCH_PARENT,
+ FrameLayout.LayoutParams.WRAP_CONTENT
+ ));
+
+ if (ActivityManager.isHighEndGfx()) {
+ final View bubble = clingLayout.findViewById(R.id.text);
+ bubble.setAlpha(0f);
+ bubble.setTranslationY(-OFFSET_DP*density);
+ bubble.animate()
+ .alpha(1f)
+ .translationY(0)
+ .setDuration(300)
+ .setInterpolator(new DecelerateInterpolator())
+ .start();
+
+ ok.setAlpha(0f);
+ ok.setTranslationY(-OFFSET_DP*density);
+ ok.animate().alpha(1f)
+ .translationY(0)
+ .setDuration(300)
+ .setStartDelay(200)
+ .setInterpolator(new DecelerateInterpolator())
+ .start();
+
+ mColorAnim = ValueAnimator.ofObject(new ArgbEvaluator(), 0, BGCOLOR);
+ mColorAnim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
+ @Override
+ public void onAnimationUpdate(ValueAnimator animation) {
+ final int c = (Integer) animation.getAnimatedValue();
+ mColor.setColor(c);
+ }
+ });
+ mColorAnim.setDuration(1000);
+ mColorAnim.start();
+ } else {
+ mColor.setColor(BGCOLOR);
+ }
+ }
+
+ @Override
+ public boolean onTouchEvent(MotionEvent motion) {
+ Slog.v(TAG, "ClingWindowView.onTouchEvent");
+ return true;
}
}
@@ -153,16 +249,28 @@ public class TransientNavigationConfirmation {
mPromptPackage = pkg;
if (DEBUG) Slog.d(TAG, "Showing transient navigation confirmation for " + pkg);
- // create the confirmation toast bar
- final int msg = R.string.transient_navigation_confirmation;
- mToast = Toast.makeBar(mContext, msg, Toast.LENGTH_INFINITE);
- mToast.setAction(R.string.ok, confirmAction(pkg));
+ mClingWindow = new ClingWindowView(mContext);
// we will be hiding the nav bar, so layout as if it's already hidden
- mToast.getView().setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION);
+ mClingWindow.setSystemUiVisibility(
+ View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
+ | View.SYSTEM_UI_FLAG_LAYOUT_STABLE);
// show the confirmation
- mToast.show();
+ WindowManager.LayoutParams lp = new WindowManager.LayoutParams(
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ WindowManager.LayoutParams.TYPE_TOAST,
+ 0
+ | WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
+ | WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
+ | WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED
+ ,
+ PixelFormat.TRANSLUCENT);
+ lp.setTitle("TransientNavigationConfirmation");
+ lp.windowAnimations = com.android.internal.R.style.Animation_RecentApplications;
+ lp.gravity = Gravity.FILL;
+ mWindowManager.addView(mClingWindow, lp);
}
private Runnable confirmAction(final String pkg) {