TabletStatusBar.java revision 536c58fbe51a53d0e6e78c360c9f6069ae0fd465
1808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato/* 2808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * Copyright (C) 2010 The Android Open Source Project 3808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * 4808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * Licensed under the Apache License, Version 2.0 (the "License"); 5808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * you may not use this file except in compliance with the License. 6808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * You may obtain a copy of the License at 7808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * 8808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * http://www.apache.org/licenses/LICENSE-2.0 9808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * 10808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * Unless required by applicable law or agreed to in writing, software 11808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * distributed under the License is distributed on an "AS IS" BASIS, 12808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * See the License for the specific language governing permissions and 14808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato * limitations under the License. 15808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato */ 16808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 17808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratopackage com.android.systemui.statusbar.tablet; 18808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 19f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onoratoimport java.io.FileDescriptor; 20f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onoratoimport java.io.PrintWriter; 21b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandlerimport java.util.ArrayList; 22b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandlerimport java.util.Map; 23b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandlerimport java.util.IdentityHashMap; 24f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato 25b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandlerimport android.animation.LayoutTransition; 26b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandlerimport android.animation.ObjectAnimator; 27b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandlerimport android.animation.AnimatorSet; 28dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.app.ActivityManagerNative; 29dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.app.PendingIntent; 30ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onoratoimport android.app.Notification; 31dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.app.StatusBarManager; 32808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.content.Context; 33808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.content.Intent; 34808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.content.res.Resources; 359120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandlerimport android.graphics.PixelFormat; 36dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.graphics.Rect; 374daaeafd278d22ec9013d1cdaade562044ee907eJoe Onoratoimport android.graphics.drawable.Drawable; 384daaeafd278d22ec9013d1cdaade562044ee907eJoe Onoratoimport android.graphics.drawable.LayerDrawable; 399120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandlerimport android.os.Handler; 40808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.os.IBinder; 413eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandlerimport android.os.Message; 42dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.os.RemoteException; 43ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onoratoimport android.text.TextUtils; 443eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandlerimport android.util.Slog; 4555d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onoratoimport android.view.animation.Animation; 46ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandlerimport android.view.animation.AnimationUtils; 47808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.view.Gravity; 483eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandlerimport android.view.LayoutInflater; 49b62ac127824e9723534a197189eca58d30f15d3dJoe Onoratoimport android.view.MotionEvent; 508304da460f95c0883eca0d97fcdc4eb42c10f7c2Daniel Sandlerimport android.view.VelocityTracker; 51808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.view.View; 52b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandlerimport android.view.ViewConfiguration; 539120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandlerimport android.view.ViewGroup; 549120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandlerimport android.view.WindowManager; 559120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandlerimport android.view.WindowManagerImpl; 56ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onoratoimport android.widget.FrameLayout; 573eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandlerimport android.widget.ImageView; 58808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport android.widget.LinearLayout; 59dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.widget.RemoteViews; 60dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.widget.ScrollView; 61dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandlerimport android.widget.TextSwitcher; 629120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandlerimport android.widget.TextView; 63808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 64808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport com.android.internal.statusbar.StatusBarIcon; 65808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport com.android.internal.statusbar.StatusBarNotification; 66808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 67fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onoratoimport com.android.systemui.R; 68808182dc874e93582da38d013a4a790d6bc08fc9Joe Onoratoimport com.android.systemui.statusbar.*; 69fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onoratoimport com.android.systemui.statusbar.policy.BatteryController; 70fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onoratoimport com.android.systemui.statusbar.policy.NetworkController; 71013cfc1116e3382981aa0da903d97fc4fdb2c791Joe Onoratoimport com.android.systemui.recent.RecentApplicationsActivity; 72808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 73fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onoratopublic class TabletStatusBar extends StatusBar { 74fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler public static final boolean DEBUG = false; 75fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato public static final String TAG = "TabletStatusBar"; 76808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 77b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato public static final int MSG_OPEN_NOTIFICATION_PANEL = 1000; 78b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato public static final int MSG_CLOSE_NOTIFICATION_PANEL = 1001; 79b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler public static final int MSG_OPEN_NOTIFICATION_PEEK = 1002; 80b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler public static final int MSG_CLOSE_NOTIFICATION_PEEK = 1003; 8144c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller public static final int MSG_OPEN_RECENTS_PANEL = 1020; 8244c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller public static final int MSG_CLOSE_RECENTS_PANEL = 1021; 83b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public static final int MSG_HIDE_SHADOWS = 1030; 84b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public static final int MSG_SHOW_SHADOWS = 1031; 85e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler public static final int MSG_RESTORE_SHADOWS = 1032; 8644c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller 87d39e388e6d7f19d6e8d620e449af4124efab1d0dDaniel Sandler private static final int MAX_IMAGE_LEVEL = 10000; 8844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller private static final boolean USE_2D_RECENTS = true; 89d39e388e6d7f19d6e8d620e449af4124efab1d0dDaniel Sandler 90b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public static final int LIGHTS_ON_DELAY = 5000; 91b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 92808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato int mIconSize; 939120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 949120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler H mHandler = new H(); 959120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 96dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // tracking all current notifications 97dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler private NotificationData mNotns = new NotificationData(); 9844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller 99b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato TabletStatusBarView mStatusBarView; 100fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato View mNotificationArea; 101fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato View mNotificationTrigger; 102dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler NotificationIconArea mNotificationIconArea; 103091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato View mNavigationArea; 104b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 105536c58fbe51a53d0e6e78c360c9f6069ae0fd465Joe Onorato ImageView mBackButton; 106b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler View mHomeButton; 107e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler View mMenuButton; 108f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato View mRecentButton; 109dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 110cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok InputMethodButton mInputMethodSwitchButton; 111cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok InputMethodButton mInputMethodShortcutButton; 11206487a58be22b100daf3f950b9a1d25c3ea42aa2satok 113ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato NotificationPanel mNotificationPanel; 1148a576713e255eb822558cef840d170d4477f47f0Joe Onorato NotificationPeekPanel mNotificationPeekWindow; 115b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ViewGroup mNotificationPeekRow; 116b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler int mNotificationPeekIndex; 117b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler LayoutTransition mNotificationPeekScrubLeft, mNotificationPeekScrubRight; 118b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 119b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler int mNotificationPeekTapDuration; 120b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler int mNotificationFlingVelocity; 1213eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 1220f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler ViewGroup mPile; 1233eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 124fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato BatteryController mBatteryController; 125fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato NetworkController mNetworkController; 1261e3ed8fc9537209920eea6adf5e576058f81d587Daniel Sandler 127ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler View mBarContents; 128b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 129b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler // lights out support 130b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler View mBackShadow, mHomeShadow, mRecentShadow, mMenuShadow, mNotificationShadow; 131b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler ShadowController mShadowController; 132ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler 1330f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler NotificationIconArea.IconLayout mIconLayout; 1340f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler 135ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onorato TabletTicker mTicker; 136dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 137dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // for disabling the status bar 138dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler int mDisabled = 0; 139dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 14055d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato boolean mNotificationsOn = true; 14144c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller private RecentAppsPanel mRecentsPanel; 14255d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato 1439120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler protected void addPanelWindows() { 144f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato final Context context = mContext; 145f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato 146f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato final Resources res = context.getResources(); 1479120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler final int barHeight= res.getDimensionPixelSize( 148755cc74e4cebdf67d21a2477512a4ac9b01e8323Joe Onorato com.android.internal.R.dimen.status_bar_height); 1499120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 15044c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller // Notification Panel 151f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato mNotificationPanel = (NotificationPanel)View.inflate(context, 152755cc74e4cebdf67d21a2477512a4ac9b01e8323Joe Onorato R.layout.status_bar_notification_panel, null); 153d39e388e6d7f19d6e8d620e449af4124efab1d0dDaniel Sandler mNotificationPanel.setVisibility(View.GONE); 154b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mNotificationPanel.setOnTouchListener( 155ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato new TouchOutsideListener(MSG_CLOSE_NOTIFICATION_PANEL, mNotificationPanel)); 156b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato 157fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato // the battery and network icons 158fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mBatteryController.addIconView((ImageView)mNotificationPanel.findViewById(R.id.battery)); 159fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mBatteryController.addLabelView( 160fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato (TextView)mNotificationPanel.findViewById(R.id.battery_text)); 161ddbba42b812ab397a75db78aba6b48fecf0e31f6Joe Onorato mNetworkController.addCombinedSignalIconView( 162fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato (ImageView)mNotificationPanel.findViewById(R.id.network)); 163fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mNetworkController.addLabelView( 164fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato (TextView)mNotificationPanel.findViewById(R.id.network_text)); 165fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato 16655d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato mStatusBarView.setIgnoreChildren(0, mNotificationTrigger, mNotificationPanel); 167d39e388e6d7f19d6e8d620e449af4124efab1d0dDaniel Sandler 1689120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler WindowManager.LayoutParams lp = new WindowManager.LayoutParams( 1694cddc98a4b63961e3528c5a70cd5c55a67a0c60aJoe Onorato ViewGroup.LayoutParams.MATCH_PARENT, 170cf2b199e98de71dcac042484800c07366363a734Joe Onorato ViewGroup.LayoutParams.MATCH_PARENT, 1719120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL, 1729120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN 17346e75294d540fe807d78aec2582ae02cc38c7d42Jeff Brown | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM 17446e75294d540fe807d78aec2582ae02cc38c7d42Jeff Brown | WindowManager.LayoutParams.FLAG_SPLIT_TOUCH, 1759120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler PixelFormat.TRANSLUCENT); 176ea70e63c0dcd09ec5790f4dca6ddd76284a6a23dJoe Onorato lp.gravity = Gravity.BOTTOM | Gravity.RIGHT; 1779120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler lp.setTitle("NotificationPanel"); 1789120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 1799120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler WindowManagerImpl.getDefault().addView(mNotificationPanel, lp); 1809120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 181b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // Notification preview window 1828a576713e255eb822558cef840d170d4477f47f0Joe Onorato mNotificationPeekWindow = (NotificationPeekPanel) View.inflate(context, 183755cc74e4cebdf67d21a2477512a4ac9b01e8323Joe Onorato R.layout.status_bar_notification_peek, null); 184b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekRow = (ViewGroup) mNotificationPeekWindow.findViewById(R.id.content); 185b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekWindow.setVisibility(View.GONE); 186b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekWindow.setOnTouchListener( 1875e759460dcb91ba96758c2ac6d354ff8563b78a4Joe Onorato new TouchOutsideListener(MSG_CLOSE_NOTIFICATION_PEEK, mNotificationPeekWindow)); 188b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubRight = new LayoutTransition(); 189b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubRight.setAnimator(LayoutTransition.APPEARING, 190b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ObjectAnimator.ofInt(null, "left", -512, 0)); 191b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubRight.setAnimator(LayoutTransition.DISAPPEARING, 192b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ObjectAnimator.ofInt(null, "left", -512, 0)); 193b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubRight.setDuration(500); 194b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 195b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubLeft = new LayoutTransition(); 196b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubLeft.setAnimator(LayoutTransition.APPEARING, 197b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ObjectAnimator.ofInt(null, "left", 512, 0)); 198b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubLeft.setAnimator(LayoutTransition.DISAPPEARING, 199b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ObjectAnimator.ofInt(null, "left", 512, 0)); 200b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekScrubLeft.setDuration(500); 201b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 202b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // XXX: setIgnoreChildren? 203b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler lp = new WindowManager.LayoutParams( 204b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 512, // ViewGroup.LayoutParams.WRAP_CONTENT, 205b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ViewGroup.LayoutParams.WRAP_CONTENT, 206b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL, 207b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN 20846e75294d540fe807d78aec2582ae02cc38c7d42Jeff Brown | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM 20946e75294d540fe807d78aec2582ae02cc38c7d42Jeff Brown | WindowManager.LayoutParams.FLAG_SPLIT_TOUCH, 210b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler PixelFormat.TRANSLUCENT); 211b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler lp.gravity = Gravity.BOTTOM | Gravity.RIGHT; 212b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler lp.setTitle("NotificationPeekWindow"); 213b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler lp.windowAnimations = com.android.internal.R.style.Animation_Toast; 214b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 215b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler WindowManagerImpl.getDefault().addView(mNotificationPeekWindow, lp); 216b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 21744c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller // Recents Panel 21844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if (USE_2D_RECENTS) { 219755cc74e4cebdf67d21a2477512a4ac9b01e8323Joe Onorato mRecentsPanel = (RecentAppsPanel) View.inflate(context, 220755cc74e4cebdf67d21a2477512a4ac9b01e8323Joe Onorato R.layout.status_bar_recent_panel, null); 22144c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mRecentsPanel.setVisibility(View.GONE); 22244c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mRecentsPanel.setOnTouchListener(new TouchOutsideListener(MSG_CLOSE_RECENTS_PANEL, 22344c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mRecentsPanel)); 22444c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mStatusBarView.setIgnoreChildren(2, mRecentButton, mRecentsPanel); 22544c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller 22644c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller lp = new WindowManager.LayoutParams( 22744c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller ViewGroup.LayoutParams.WRAP_CONTENT, 22844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller ViewGroup.LayoutParams.WRAP_CONTENT, 22944c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL, 23044c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN 23146e75294d540fe807d78aec2582ae02cc38c7d42Jeff Brown | WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM 23246e75294d540fe807d78aec2582ae02cc38c7d42Jeff Brown | WindowManager.LayoutParams.FLAG_SPLIT_TOUCH, 23344c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller PixelFormat.TRANSLUCENT); 23444c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller lp.gravity = Gravity.BOTTOM | Gravity.LEFT; 23544c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller lp.setTitle("RecentsPanel"); 236fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato lp.windowAnimations = R.style.Animation_RecentPanel; 23744c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller 23844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller WindowManagerImpl.getDefault().addView(mRecentsPanel, lp); 23944c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mRecentsPanel.setBar(this); 24044c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller } 2419120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler } 242808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 243808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato @Override 244f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato public void start() { 245f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato super.start(); // will add the main bar view 246808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 247808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 248808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato protected View makeStatusBarView() { 249f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato final Context context = mContext; 250f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato final Resources res = context.getResources(); 251808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 252808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato mIconSize = res.getDimensionPixelSize(com.android.internal.R.dimen.status_bar_icon_size); 253808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 254b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato final TabletStatusBarView sb = (TabletStatusBarView)View.inflate( 255f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato context, R.layout.status_bar, null); 256808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato mStatusBarView = sb; 257808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 258b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato sb.setHandler(mHandler); 259b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato 260ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler mBarContents = sb.findViewById(R.id.bar_contents); 261f63b0f44eb53f535a65bd83dbc1d8b95abc501daJoe Onorato 262fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato // the whole right-hand side of the bar 263fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mNotificationArea = sb.findViewById(R.id.notificationArea); 264fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato 26555d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato // the button to open the notification area 266fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mNotificationTrigger = sb.findViewById(R.id.notificationTrigger); 267f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato mNotificationTrigger.setOnClickListener(mOnClickListener); 26855d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato 269808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato // the more notifications icon 270808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato mNotificationIconArea = (NotificationIconArea)sb.findViewById(R.id.notificationIcons); 271808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 2723eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // where the icons go 2733eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler mIconLayout = (NotificationIconArea.IconLayout) sb.findViewById(R.id.icons); 274b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mIconLayout.setOnTouchListener(new NotificationIconTouchListener()); 275b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 276b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ViewConfiguration vc = ViewConfiguration.get(context); 277b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekTapDuration = vc.getTapTimeout(); 278b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationFlingVelocity = 300; // px/s 2793eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 28052f80cd36f406725e85a1825741a45c69de3d898Joe Onorato mTicker = new TabletTicker(context); 281dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 282fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato // The icons 283fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mBatteryController = new BatteryController(mContext); 284fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mBatteryController.addIconView((ImageView)sb.findViewById(R.id.battery)); 285fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mNetworkController = new NetworkController(mContext); 286ddbba42b812ab397a75db78aba6b48fecf0e31f6Joe Onorato mNetworkController.addCombinedSignalIconView((ImageView)sb.findViewById(R.id.network)); 2871e3ed8fc9537209920eea6adf5e576058f81d587Daniel Sandler 288091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato // The navigation buttons 289091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato mNavigationArea = sb.findViewById(R.id.navigationArea); 290536c58fbe51a53d0e6e78c360c9f6069ae0fd465Joe Onorato mBackButton = (ImageView)mNavigationArea.findViewById(R.id.back); 291b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mHomeButton = mNavigationArea.findViewById(R.id.home); 292e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler mMenuButton = mNavigationArea.findViewById(R.id.menu); 293b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mRecentButton = mNavigationArea.findViewById(R.id.recent_apps); 294b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler Slog.d(TAG, "rec=" + mRecentButton + ", listener=" + mOnClickListener); 295b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mRecentButton.setOnClickListener(mOnClickListener); 296091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato 29706487a58be22b100daf3f950b9a1d25c3ea42aa2satok // The bar contents buttons 298cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok mInputMethodSwitchButton = (InputMethodButton) sb.findViewById(R.id.imeSwitchButton); 299cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok mInputMethodShortcutButton = (InputMethodButton) sb.findViewById(R.id.imeShortcutButton); 30006487a58be22b100daf3f950b9a1d25c3ea42aa2satok 301b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // "shadows" of the status bar features, for lights-out mode 302b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mBackShadow = sb.findViewById(R.id.back_shadow); 303b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mHomeShadow = sb.findViewById(R.id.home_shadow); 304b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mRecentShadow = sb.findViewById(R.id.recent_shadow); 305b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mMenuShadow = sb.findViewById(R.id.menu_shadow); 306b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mNotificationShadow = sb.findViewById(R.id.notification_shadow); 307b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 308b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController = new ShadowController(false); 309b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.add(mBackButton, mBackShadow); 310b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.add(mHomeButton, mHomeShadow); 311b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.add(mRecentButton, mRecentShadow); 312b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.add(mMenuButton, mMenuShadow); 313b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.add(mNotificationArea, mNotificationShadow); 314b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 3155dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato // set the initial view visibility 3165dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato setAreThereNotifications(); 317271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler refreshNotificationTrigger(); 3185dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 319dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // Add the windows 320dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler addPanelWindows(); 321dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 322dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler mPile = (ViewGroup)mNotificationPanel.findViewById(R.id.content); 323dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler mPile.removeAllViews(); 32444c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller 325dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler ScrollView scroller = (ScrollView)mPile.getParent(); 326dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler scroller.setFillViewport(true); 327dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 328808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato return sb; 329808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 330808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 331808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato protected int getStatusBarGravity() { 332808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato return Gravity.BOTTOM | Gravity.FILL_HORIZONTAL; 333808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 334808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 3359120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler private class H extends Handler { 3369120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler public void handleMessage(Message m) { 3379120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler switch (m.what) { 338b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MSG_OPEN_NOTIFICATION_PEEK: 339b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (DEBUG) Slog.d(TAG, "opening notification peek window; arg=" + m.arg1); 340b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (m.arg1 >= 0) { 341b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler final int N = mNotns.size(); 342b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (mNotificationPeekIndex < N) { 343b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler NotificationData.Entry entry = mNotns.get(N-1-mNotificationPeekIndex); 344b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler entry.icon.setBackgroundColor(0); 345b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 346b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 347b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler final int peekIndex = m.arg1; 348b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (peekIndex < N) { 349b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler Slog.d(TAG, "loading peek: " + peekIndex); 350b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler NotificationData.Entry entry = mNotns.get(N-1-peekIndex); 351b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler NotificationData.Entry copy = new NotificationData.Entry( 352b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler entry.key, 353b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler entry.notification, 354b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler entry.icon); 355b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler inflateViews(copy, mNotificationPeekRow); 356b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 357b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler entry.icon.setBackgroundColor(0x20FFFFFF); 358b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 359b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler// mNotificationPeekRow.setLayoutTransition( 360b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler// peekIndex < mNotificationPeekIndex 361b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler// ? mNotificationPeekScrubLeft 362b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler// : mNotificationPeekScrubRight); 363b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 364b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekRow.removeAllViews(); 365b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekRow.addView(copy.row); 366b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 367b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekWindow.setVisibility(View.VISIBLE); 368b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPanel.setVisibility(View.GONE); 369b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 370b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekIndex = peekIndex; 371b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 372b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 373b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler break; 374b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MSG_CLOSE_NOTIFICATION_PEEK: 375b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (DEBUG) Slog.d(TAG, "closing notification peek window"); 376b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekWindow.setVisibility(View.GONE); 377b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekRow.removeAllViews(); 378b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler final int N = mNotns.size(); 379b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (mNotificationPeekIndex < N) { 380b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler NotificationData.Entry entry = mNotns.get(N-1-mNotificationPeekIndex); 381b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler entry.icon.setBackgroundColor(0); 382b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 383b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler break; 3849120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler case MSG_OPEN_NOTIFICATION_PANEL: 3859120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler if (DEBUG) Slog.d(TAG, "opening notifications panel"); 386091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato if (mNotificationPanel.getVisibility() == View.GONE) { 387b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mNotificationPeekWindow.setVisibility(View.GONE); 388091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato mNotificationPanel.setVisibility(View.VISIBLE); 389b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // synchronize with current shadow state 390b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.hideElement(mNotificationArea); 39150ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato mTicker.halt(); 392091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato } 3939120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler break; 3949120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler case MSG_CLOSE_NOTIFICATION_PANEL: 3959120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler if (DEBUG) Slog.d(TAG, "closing notifications panel"); 396091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato if (mNotificationPanel.getVisibility() == View.VISIBLE) { 397091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato mNotificationPanel.setVisibility(View.GONE); 398b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // synchronize with current shadow state 399b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.showElement(mNotificationArea); 400091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato } 4019120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler break; 40244c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller case MSG_OPEN_RECENTS_PANEL: 40344c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if (DEBUG) Slog.d(TAG, "opening recents panel"); 40444c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if (mRecentsPanel != null) mRecentsPanel.setVisibility(View.VISIBLE); 40544c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller break; 40644c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller case MSG_CLOSE_RECENTS_PANEL: 40744c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if (DEBUG) Slog.d(TAG, "closing recents panel"); 40844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if (mRecentsPanel != null) mRecentsPanel.setVisibility(View.GONE); 4099120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler break; 410b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler case MSG_HIDE_SHADOWS: 411e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler if (DEBUG) Slog.d(TAG, "hiding shadows (lights on)"); 412b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mShadowController.hideAllShadows(); 41306e6630a462b6a5c04c319d781d64896778d351fDaniel Sandler break; 414b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler case MSG_SHOW_SHADOWS: 415e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler if (DEBUG) Slog.d(TAG, "showing shadows (lights out)"); 41606e6630a462b6a5c04c319d781d64896778d351fDaniel Sandler animateCollapse(); 417b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mShadowController.showAllShadows(); 41806e6630a462b6a5c04c319d781d64896778d351fDaniel Sandler break; 419e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler case MSG_RESTORE_SHADOWS: 420e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler if (DEBUG) Slog.d(TAG, "quickly re-showing shadows if appropriate"); 421e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler mShadowController.refresh(); 422e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler break; 4239120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler } 4249120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler } 4259120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler } 426271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler 427271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler public void refreshNotificationTrigger() { 428fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato /* 429cf3c7cf3c986526398e2bc79a39227d751202822Daniel Sandler if (mNotificationTrigger == null) return; 430cf3c7cf3c986526398e2bc79a39227d751202822Daniel Sandler 431271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler int resId; 432271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler boolean panel = (mNotificationPanel != null 433271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler && mNotificationPanel.getVisibility() == View.VISIBLE); 434271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler if (!mNotificationsOn) { 435271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler resId = R.drawable.ic_sysbar_noti_dnd; 436271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler } else if (mNotns.size() > 0) { 437271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler resId = panel ? R.drawable.ic_sysbar_noti_avail_open : R.drawable.ic_sysbar_noti_avail; 438271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler } else { 439271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler resId = panel ? R.drawable.ic_sysbar_noti_none_open : R.drawable.ic_sysbar_noti_none; 440271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler } 441fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato //mNotificationTrigger.setImageResource(resId); 442fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato */ 4431e3ed8fc9537209920eea6adf5e576058f81d587Daniel Sandler } 4449120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 445808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void addIcon(String slot, int index, int viewIndex, StatusBarIcon icon) { 4461e3ed8fc9537209920eea6adf5e576058f81d587Daniel Sandler if (DEBUG) Slog.d(TAG, "addIcon(" + slot + ") -> " + icon); 447808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 448808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 449808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void updateIcon(String slot, int index, int viewIndex, 450808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato StatusBarIcon old, StatusBarIcon icon) { 4511e3ed8fc9537209920eea6adf5e576058f81d587Daniel Sandler if (DEBUG) Slog.d(TAG, "updateIcon(" + slot + ") -> " + icon); 452808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 453808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 454808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void removeIcon(String slot, int index, int viewIndex) { 4551e3ed8fc9537209920eea6adf5e576058f81d587Daniel Sandler if (DEBUG) Slog.d(TAG, "removeIcon(" + slot + ")"); 456808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 457808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 458808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void addNotification(IBinder key, StatusBarNotification notification) { 4593eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (DEBUG) Slog.d(TAG, "addNotification(" + key + " -> " + notification + ")"); 4603eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler addNotificationViews(key, notification); 461fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler 46250ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato final boolean immersive = isImmersive(); 463cf2b199e98de71dcac042484800c07366363a734Joe Onorato if (false && immersive) { 464fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler // TODO: immersive mode popups for tablet 465fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler } else if (notification.notification.fullScreenIntent != null) { 466fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler // not immersive & a full-screen alert should be shown 467fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler Slog.d(TAG, "Notification has fullScreenIntent and activity is not immersive;" 468fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler + " sending fullScreenIntent"); 469fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler try { 470fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler notification.notification.fullScreenIntent.send(); 471fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler } catch (PendingIntent.CanceledException e) { 472fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler } 473fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler } else { 47450ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato tick(key, notification); 475fb970e920413e7f3a6159056fa698bb9c6b04056Daniel Sandler } 4765dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 4775dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato setAreThereNotifications(); 478808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 479808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 480808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void updateNotification(IBinder key, StatusBarNotification notification) { 4813eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (DEBUG) Slog.d(TAG, "updateNotification(" + key + " -> " + notification + ") // TODO"); 48244c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller 4830f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler final NotificationData.Entry oldEntry = mNotns.findByKey(key); 484379020aec619c66d3e040de01f0726687fd2ad85Daniel Sandler if (oldEntry == null) { 4853eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.w(TAG, "updateNotification for unknown key: " + key); 4863eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return; 4873eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 4883eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 4893eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler final StatusBarNotification oldNotification = oldEntry.notification; 4903eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler final RemoteViews oldContentView = oldNotification.notification.contentView; 4913eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 4923eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler final RemoteViews contentView = notification.notification.contentView; 4933eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 4943eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (false) { 4953eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.d(TAG, "old notification: when=" + oldNotification.notification.when 4963eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler + " ongoing=" + oldNotification.isOngoing() 4973eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler + " expanded=" + oldEntry.expanded 4983eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler + " contentView=" + oldContentView); 4993eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.d(TAG, "new notification: when=" + notification.notification.when 5003eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler + " ongoing=" + oldNotification.isOngoing() 5013eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler + " contentView=" + contentView); 5023eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 5033eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 5043eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Can we just reapply the RemoteViews in place? If when didn't change, the order 5053eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // didn't change. 5063eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (notification.notification.when == oldNotification.notification.when 5073eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && notification.isOngoing() == oldNotification.isOngoing() 5083eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && oldEntry.expanded != null 5093eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && contentView != null 5103eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && oldContentView != null 5113eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && contentView.getPackage() != null 5123eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && oldContentView.getPackage() != null 5133eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && oldContentView.getPackage().equals(contentView.getPackage()) 5143eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler && oldContentView.getLayoutId() == contentView.getLayoutId()) { 5153eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (DEBUG) Slog.d(TAG, "reusing notification for key: " + key); 5163eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler oldEntry.notification = notification; 5173eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler try { 5183eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Reapply the RemoteViews 519f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato contentView.reapply(mContext, oldEntry.content); 5203eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // update the contentIntent 5213eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler final PendingIntent contentIntent = notification.notification.contentIntent; 5223eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (contentIntent != null) { 5233eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler oldEntry.content.setOnClickListener(new NotificationClicker(contentIntent, 5243eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.pkg, notification.tag, notification.id)); 525184498ce5a8d77e1d9c45693363829daaeef9611Joe Onorato } else { 526184498ce5a8d77e1d9c45693363829daaeef9611Joe Onorato oldEntry.content.setOnClickListener(null); 5273eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 5283eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Update the icon. 5293eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler final StatusBarIcon ic = new StatusBarIcon(notification.pkg, 5303eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.notification.icon, notification.notification.iconLevel, 5313eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.notification.number); 5323eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (!oldEntry.icon.set(ic)) { 5333eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler handleNotificationError(key, notification, "Couldn't update icon: " + ic); 5343eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return; 5353eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 5363eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 5373eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler catch (RuntimeException e) { 5383eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // It failed to add cleanly. Log, and remove the view from the panel. 5393eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.w(TAG, "Couldn't reapply views for package " + contentView.getPackage(), e); 5403eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler removeNotificationViews(key); 5413eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler addNotificationViews(key, notification); 5423eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 5433eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } else { 5443eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (DEBUG) Slog.d(TAG, "not reusing notification for key: " + key); 5453eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler removeNotificationViews(key); 5463eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler addNotificationViews(key, notification); 5473eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 54850ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato // fullScreenIntent doesn't happen on updates. You need to clear & repost a new 54950ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato // notification. 55050ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato final boolean immersive = isImmersive(); 55150ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato if (false && immersive) { 55250ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato // TODO: immersive mode 55350ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato } else { 55450ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato tick(key, notification); 55550ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato } 5565dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 5575dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato setAreThereNotifications(); 558808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 559808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 560808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void removeNotification(IBinder key) { 5613eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (DEBUG) Slog.d(TAG, "removeNotification(" + key + ") // TODO"); 5623eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler removeNotificationViews(key); 56350ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato mTicker.remove(key); 5645dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato setAreThereNotifications(); 565808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 566808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 567808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void disable(int state) { 568091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato int old = mDisabled; 569091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato int diff = state ^ old; 570dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler mDisabled = state; 571dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 572091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato // act accordingly 573dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if ((diff & StatusBarManager.DISABLE_EXPAND) != 0) { 574dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if ((state & StatusBarManager.DISABLE_EXPAND) != 0) { 575dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler Slog.d(TAG, "DISABLE_EXPAND: yes"); 576dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler animateCollapse(); 577dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 578dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 579dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if ((diff & StatusBarManager.DISABLE_NOTIFICATION_ICONS) != 0) { 580dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if ((state & StatusBarManager.DISABLE_NOTIFICATION_ICONS) != 0) { 581dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler Slog.d(TAG, "DISABLE_NOTIFICATION_ICONS: yes"); 582b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // synchronize with current shadow state 583b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.hideElement(mNotificationArea); 584091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato mTicker.halt(); 585dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } else { 586dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler Slog.d(TAG, "DISABLE_NOTIFICATION_ICONS: no"); 587b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // synchronize with current shadow state 588b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowController.showElement(mNotificationArea); 589dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 590dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } else if ((diff & StatusBarManager.DISABLE_NOTIFICATION_TICKER) != 0) { 591091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato if ((state & StatusBarManager.DISABLE_NOTIFICATION_TICKER) != 0) { 592ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onorato mTicker.halt(); 593dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 594dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 595091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato if ((diff & StatusBarManager.DISABLE_NAVIGATION) != 0) { 596091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato if ((state & StatusBarManager.DISABLE_NAVIGATION) != 0) { 597091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato Slog.d(TAG, "DISABLE_NAVIGATION: yes"); 598fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mNavigationArea.setVisibility(View.GONE); 599dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } else { 600091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato Slog.d(TAG, "DISABLE_NAVIGATION: no"); 601fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato mNavigationArea.setVisibility(View.VISIBLE); 602dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 603dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 604dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 605dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 606ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onorato private boolean hasTicker(Notification n) { 60746439cec0eb0da4d0f853f2d8712d0c00c98475bJoe Onorato return n.tickerView != null || !TextUtils.isEmpty(n.tickerText); 608ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onorato } 609ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onorato 61050ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato private void tick(IBinder key, StatusBarNotification n) { 61155d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato // Don't show the ticker when the windowshade is open. 61255d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato if (mNotificationPanel.getVisibility() == View.VISIBLE) { 61355d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato return; 61455d2d7646bf13bb5406bf01fd1bb96e58588570cJoe Onorato } 615dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // Show the ticker if one is requested. Also don't do this 616dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // until status bar window is attached to the window manager, 617dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // because... well, what's the point otherwise? And trying to 618dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler // run a ticker without being attached will crash! 619ef1e7763c2dc5b9bac69cc747efe05c81d9fd9fcJoe Onorato if (hasTicker(n.notification) && mStatusBarView.getWindowToken() != null) { 620dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if (0 == (mDisabled & (StatusBarManager.DISABLE_NOTIFICATION_ICONS 621dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler | StatusBarManager.DISABLE_NOTIFICATION_TICKER))) { 62250ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato mTicker.add(key, n); 623dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 624dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 625dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 626dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 627808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void animateExpand() { 628b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mHandler.removeMessages(MSG_OPEN_NOTIFICATION_PANEL); 629b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mHandler.sendEmptyMessage(MSG_OPEN_NOTIFICATION_PANEL); 630808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato } 631808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato 632808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato public void animateCollapse() { 633b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mHandler.removeMessages(MSG_CLOSE_NOTIFICATION_PANEL); 634b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mHandler.sendEmptyMessage(MSG_CLOSE_NOTIFICATION_PANEL); 63544c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mHandler.removeMessages(MSG_CLOSE_RECENTS_PANEL); 63644c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mHandler.sendEmptyMessage(MSG_CLOSE_RECENTS_PANEL); 6379120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler } 6389120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 639fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato // called by StatusBar 64006e6630a462b6a5c04c319d781d64896778d351fDaniel Sandler @Override 6419305647eb61bb60a1f42481a0c0d208dc9bbe965Joe Onorato public void setLightsOn(boolean on) { 642b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mHandler.removeMessages(MSG_SHOW_SHADOWS); 643b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mHandler.removeMessages(MSG_HIDE_SHADOWS); 644b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mHandler.sendEmptyMessage(on ? MSG_HIDE_SHADOWS : MSG_SHOW_SHADOWS); 6459305647eb61bb60a1f42481a0c0d208dc9bbe965Joe Onorato } 6469305647eb61bb60a1f42481a0c0d208dc9bbe965Joe Onorato 647e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler public void setMenuKeyVisible(boolean visible) { 648e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler if (DEBUG) { 649e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler Slog.d(TAG, (visible?"showing":"hiding") + " the MENU button"); 650e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler } 651b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mMenuButton.setVisibility(visible ? View.VISIBLE : View.GONE); 652e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler } 653e02d808abf370965c3c4e4d38af11bc69110fde2Daniel Sandler 654cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok public void setIMEButtonVisible(IBinder token, boolean visible) { 65506487a58be22b100daf3f950b9a1d25c3ea42aa2satok if (DEBUG) { 65606487a58be22b100daf3f950b9a1d25c3ea42aa2satok Slog.d(TAG, (visible?"showing":"hiding") + " the IME button"); 65706487a58be22b100daf3f950b9a1d25c3ea42aa2satok } 658cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok mInputMethodSwitchButton.setIMEButtonVisible(token, visible); 659cd7cd2969f545ad061a9b4ecd0044f15eb1b4abbsatok mInputMethodShortcutButton.setIMEButtonVisible(token, visible); 660536c58fbe51a53d0e6e78c360c9f6069ae0fd465Joe Onorato mBackButton.setImageResource( 661536c58fbe51a53d0e6e78c360c9f6069ae0fd465Joe Onorato visible ? R.drawable.ic_sysbar_back_ime : R.drawable.ic_sysbar_back); 66206487a58be22b100daf3f950b9a1d25c3ea42aa2satok } 66306487a58be22b100daf3f950b9a1d25c3ea42aa2satok 66450ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato private boolean isImmersive() { 66550ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato try { 66650ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato return ActivityManagerNative.getDefault().isTopActivityImmersive(); 66750ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato //Slog.d(TAG, "Top activity is " + (immersive?"immersive":"not immersive")); 66850ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato } catch (RemoteException ex) { 66950ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato // the end is nigh 67050ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato return false; 67150ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato } 67250ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato } 67350ec5ec0b8b3ab9cf697c8e3925e3fdd837f5e7dJoe Onorato 6745dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato private void setAreThereNotifications() { 6755dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato final boolean hasClearable = mNotns.hasClearableItems(); 6765dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 6775dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato //Slog.d(TAG, "setAreThereNotifications hasClerable=" + hasClearable); 6785dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 6795dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato /* 6805dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato mOngoingTitle.setVisibility(ongoing ? View.VISIBLE : View.GONE); 6815dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato mLatestTitle.setVisibility(latest ? View.VISIBLE : View.GONE); 6825dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 6835dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato if (ongoing || latest) { 6845dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato mNoNotificationsTitle.setVisibility(View.GONE); 6855dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato } else { 6865dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato mNoNotificationsTitle.setVisibility(View.VISIBLE); 6875dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato } 6885dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato */ 6895dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato } 6905dd1169ae95162383acf00d1e9a1886e0ac99a70Joe Onorato 691f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato /** 692f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato * Cancel this notification and tell the status bar service about the failure. Hold no locks. 693f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato */ 694f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato void handleNotificationError(IBinder key, StatusBarNotification n, String message) { 695f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato removeNotification(key); 696f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato try { 697f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato mBarService.onNotificationError(n.pkg, n.tag, n.id, n.uid, n.initialPid, message); 698f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } catch (RemoteException ex) { 699f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato // The end is nigh. 700f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } 701f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } 702f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato 703f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato private View.OnClickListener mOnClickListener = new View.OnClickListener() { 704f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato public void onClick(View v) { 705fd52b18d9bf3cd62c7a07058536e9f97db65beeaJoe Onorato if (v == mNotificationTrigger) { 706f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato onClickNotificationTrigger(); 707f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } else if (v == mRecentButton) { 708f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato onClickRecentButton(); 709f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } 710f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } 711f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato }; 712f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato 713f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato public void onClickNotificationTrigger() { 714b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (DEBUG) Slog.d(TAG, "clicked notification icons; disabled=" + mDisabled); 715091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato if ((mDisabled & StatusBarManager.DISABLE_EXPAND) == 0) { 716271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler if (!mNotificationsOn) { 717271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler mNotificationsOn = true; 718cf3c7cf3c986526398e2bc79a39227d751202822Daniel Sandler mIconLayout.setVisibility(View.VISIBLE); // TODO: animation 719271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler refreshNotificationTrigger(); 720271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler } else { 72144c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller int msg = (mNotificationPanel.getVisibility() == View.GONE) 722271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler ? MSG_OPEN_NOTIFICATION_PANEL 723271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler : MSG_CLOSE_NOTIFICATION_PANEL; 724271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler mHandler.removeMessages(msg); 725271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler mHandler.sendEmptyMessage(msg); 726271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler } 727091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato } 7289120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler } 7299120d55b806aec981ce7c1af20b7aa3d303ccca5Daniel Sandler 730f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato public void onClickRecentButton() { 731b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (DEBUG) Slog.d(TAG, "clicked recent apps; disabled=" + mDisabled); 73244c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if (mRecentsPanel == null) { 73344c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller Intent intent = new Intent(); 73444c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller intent.setClass(mContext, RecentApplicationsActivity.class); 73544c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK 73644c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 73744c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mContext.startActivity(intent); 73844c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller } else { 73944c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller if ((mDisabled & StatusBarManager.DISABLE_EXPAND) == 0) { 74044c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller int msg = (mRecentsPanel.getVisibility() == View.GONE) 74144c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller ? MSG_OPEN_RECENTS_PANEL 74244c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller : MSG_CLOSE_RECENTS_PANEL; 74344c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mHandler.removeMessages(msg); 74444c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller mHandler.sendEmptyMessage(msg); 74544c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller } 74644c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller } 7473eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7483eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7493eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler private class NotificationClicker implements View.OnClickListener { 7503eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler private PendingIntent mIntent; 7513eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler private String mPkg; 7523eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler private String mTag; 7533eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler private int mId; 7543eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7553eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler NotificationClicker(PendingIntent intent, String pkg, String tag, int id) { 7563eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler mIntent = intent; 7573eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler mPkg = pkg; 7583eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler mTag = tag; 7593eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler mId = id; 7603eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7613eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7623eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler public void onClick(View v) { 7633eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler try { 7643eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // The intent we are sending is for the application, which 7653eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // won't have permission to immediately start an activity after 7663eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // the user switches to home. We know it is safe to do at this 7673eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // point, so make sure new activity switches are now allowed. 7683eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler ActivityManagerNative.getDefault().resumeAppSwitches(); 7693eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } catch (RemoteException e) { 7703eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7713eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7723eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (mIntent != null) { 7733eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler int[] pos = new int[2]; 7743eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler v.getLocationOnScreen(pos); 7753eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Intent overlay = new Intent(); 7763eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler overlay.setSourceBounds( 7773eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler new Rect(pos[0], pos[1], pos[0]+v.getWidth(), pos[1]+v.getHeight())); 7783eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler try { 779f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato mIntent.send(mContext, 0, overlay); 7803eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } catch (PendingIntent.CanceledException e) { 7813eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // the stack trace isn't very helpful here. Just log the exception message. 7823eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.w(TAG, "Sending contentIntent failed: " + e); 7833eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7843eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7853eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7863eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler try { 7873eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler mBarService.onNotificationClick(mPkg, mTag, mId); 7883eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } catch (RemoteException ex) { 7893eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // system process is dead if we're here. 7903eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7913eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7923eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // close the shade if it was open 7933eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler animateCollapse(); 7943eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 7953eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // If this click was on the intruder alert, hide that instead 7963eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler// mHandler.sendEmptyMessage(MSG_HIDE_INTRUDER); 7973eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7983eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 7993eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 8003eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler StatusBarNotification removeNotificationViews(IBinder key) { 8010f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler NotificationData.Entry entry = mNotns.remove(key); 8023eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (entry == null) { 8033eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.w(TAG, "removeNotification for unknown key: " + key); 8043eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return null; 8053eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 8063eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Remove the expanded view. 8073eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler ViewGroup rowParent = (ViewGroup)entry.row.getParent(); 8083eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (rowParent != null) rowParent.removeView(entry.row); 8093eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Remove the icon. 8100f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler// ViewGroup iconParent = (ViewGroup)entry.icon.getParent(); 8110f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler// if (iconParent != null) iconParent.removeView(entry.icon); 8120f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler refreshIcons(); 8133eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 8143eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return entry.notification; 8153eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 8163eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 817b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler private class NotificationIconTouchListener implements View.OnTouchListener { 818b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler VelocityTracker mVT; 819b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 820b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler public NotificationIconTouchListener() { 821b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 822b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 823b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler public boolean onTouch(View v, MotionEvent event) { 824b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler boolean peeking = mNotificationPeekWindow.getVisibility() != View.GONE; 825b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler boolean panelShowing = mNotificationPanel.getVisibility() != View.GONE; 826b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (panelShowing) return false; 827b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 828b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler switch (event.getAction()) { 829b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MotionEvent.ACTION_DOWN: 830b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mVT = VelocityTracker.obtain(); 831b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 832b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // fall through 833b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MotionEvent.ACTION_OUTSIDE: 834b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MotionEvent.ACTION_MOVE: 835b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // peek and switch icons if necessary 836b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler int numIcons = mIconLayout.getChildCount(); 8375e759460dcb91ba96758c2ac6d354ff8563b78a4Joe Onorato int peekIndex = (int)((float)event.getX() * numIcons / mIconLayout.getWidth()); 838b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (peekIndex > numIcons - 1) peekIndex = numIcons - 1; 839b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler else if (peekIndex < 0) peekIndex = 0; 840b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 841b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (!peeking || mNotificationPeekIndex != peekIndex) { 842b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (DEBUG) Slog.d(TAG, "will peek at notification #" + peekIndex); 843b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler Message peekMsg = mHandler.obtainMessage(MSG_OPEN_NOTIFICATION_PEEK); 844b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler peekMsg.arg1 = peekIndex; 845b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 846b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mHandler.removeMessages(MSG_OPEN_NOTIFICATION_PEEK); 847b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 848b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // no delay if we're scrubbing left-right 8495e759460dcb91ba96758c2ac6d354ff8563b78a4Joe Onorato mHandler.sendMessage(peekMsg); 850b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 851b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 852b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // check for fling 853b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (mVT != null) { 854b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mVT.addMovement(event); 855b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mVT.computeCurrentVelocity(1000); 856b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler // require a little more oomph once we're already in peekaboo mode 857b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (!panelShowing && ( 858b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler (peeking && mVT.getYVelocity() < -mNotificationFlingVelocity*3) 859b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler || (mVT.getYVelocity() < -mNotificationFlingVelocity))) { 860b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mHandler.removeMessages(MSG_OPEN_NOTIFICATION_PEEK); 861b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mHandler.removeMessages(MSG_OPEN_NOTIFICATION_PANEL); 862b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mHandler.sendEmptyMessage(MSG_CLOSE_NOTIFICATION_PEEK); 863b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mHandler.sendEmptyMessage(MSG_OPEN_NOTIFICATION_PANEL); 864b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 865b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 866b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler return true; 867b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MotionEvent.ACTION_UP: 868b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler case MotionEvent.ACTION_CANCEL: 869b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mHandler.removeMessages(MSG_OPEN_NOTIFICATION_PEEK); 870b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (peeking) { 8715e759460dcb91ba96758c2ac6d354ff8563b78a4Joe Onorato mHandler.sendEmptyMessageDelayed(MSG_CLOSE_NOTIFICATION_PEEK, 5000); 872b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 873b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mVT.recycle(); 874b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mVT = null; 875b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler return true; 876b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 877b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler return false; 878b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 879b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 880b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 8813eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler StatusBarIconView addNotificationViews(IBinder key, StatusBarNotification notification) { 882dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if (DEBUG) { 883dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler Slog.d(TAG, "addNotificationViews(key=" + key + ", notification=" + notification); 884dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 8853eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Construct the icon. 886f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato final StatusBarIconView iconView = new StatusBarIconView(mContext, 8873eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.pkg + "/0x" + Integer.toHexString(notification.id)); 8883eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler iconView.setScaleType(ImageView.ScaleType.CENTER_INSIDE); 8893eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 8903eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler final StatusBarIcon ic = new StatusBarIcon(notification.pkg, 8913eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.notification.icon, 8923eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.notification.iconLevel, 8933eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler notification.notification.number); 8943eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (!iconView.set(ic)) { 8953eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler handleNotificationError(key, notification, "Couldn't attach StatusBarIcon: " + ic); 8963eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return null; 8973eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 8983eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Construct the expanded view. 8993eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler NotificationData.Entry entry = new NotificationData.Entry(key, notification, iconView); 900dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if (!inflateViews(entry, mPile)) { 9013eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler handleNotificationError(key, notification, "Couldn't expand RemoteViews for: " 9023eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler + notification); 9033eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return null; 9043eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 905b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 9063eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // Add the icon. 907dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler mNotns.add(entry); 9080f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler refreshIcons(); 9090f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler 9103eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return iconView; 9113eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 9123eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 9130f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler private void refreshIcons() { 9140f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler // XXX: need to implement a new limited linear layout class 9150f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler // to avoid removing & readding everything 916dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 917b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler final int ICON_LIMIT = 4; 918b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler final LinearLayout.LayoutParams params 919b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler = new LinearLayout.LayoutParams(mIconSize, mIconSize); 920b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 9210f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler int N = mNotns.size(); 922dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 923dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler if (DEBUG) { 924b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler Slog.d(TAG, "refreshing icons: " + N + " notifications, mIconLayout=" + mIconLayout); 925dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 926dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 927b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ArrayList<View> toShow = new ArrayList<View>(); 928b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 929b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (int i=0; i<ICON_LIMIT; i++) { 9300f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler if (i>=N) break; 931b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler toShow.add(mNotns.get(N-i-1).icon); 9320f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler } 933dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler 934b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ArrayList<View> toRemove = new ArrayList<View>(); 935b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (int i=0; i<mIconLayout.getChildCount(); i++) { 936b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler View child = mIconLayout.getChildAt(i); 937b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (!toShow.contains(child)) { 938b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler toRemove.add(child); 939b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 940b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 941b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 942b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (View remove : toRemove) { 943b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mIconLayout.removeView(remove); 944dfa08db1652585a8cf27f929371c7ca6bf18ca60Daniel Sandler } 945271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler 946b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (int i=0; i<toShow.size(); i++) { 947b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler View v = toShow.get(i); 948b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (v.getParent() == null) { 949b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mIconLayout.addView(toShow.get(i), i, params); 950b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 951b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 952b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 953b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler loadNotificationPanel(); 954271ea12dc29ad30009df785f21f6782ec29844c8Daniel Sandler refreshNotificationTrigger(); 9550f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler } 9560f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler 957b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler private void loadNotificationPanel() { 958b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler int N = mNotns.size(); 959b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 960b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ArrayList<View> toShow = new ArrayList<View>(); 961b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 962b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (int i=0; i<N; i++) { 963b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler View row = mNotns.get(N-i-1).row; 964b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler toShow.add(row); 965b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 966b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 967b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler ArrayList<View> toRemove = new ArrayList<View>(); 968b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (int i=0; i<mPile.getChildCount(); i++) { 969b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler View child = mPile.getChildAt(i); 970b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (!toShow.contains(child)) { 971b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler toRemove.add(child); 972b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 973b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 974b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 975b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (View remove : toRemove) { 976b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mPile.removeView(remove); 977b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 978b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 979b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler for (int i=0; i<toShow.size(); i++) { 980b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler View v = toShow.get(i); 981b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler if (v.getParent() == null) { 982b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler mPile.addView(toShow.get(i)); 983b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 984b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 985b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler } 986b0cc50de14dc9e2d0d224803bb523aa7f48904acDaniel Sandler 9874daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato void workAroundBadLayerDrawableOpacity(View v) { 9884daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato LayerDrawable d = (LayerDrawable)v.getBackground(); 9894daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato v.setBackgroundDrawable(null); 9904daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato d.setOpacity(PixelFormat.TRANSLUCENT); 9914daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato v.setBackgroundDrawable(d); 9924daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato } 9934daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato 9943eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler private boolean inflateViews(NotificationData.Entry entry, ViewGroup parent) { 9953eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler StatusBarNotification sbn = entry.notification; 9963eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler RemoteViews remoteViews = sbn.notification.contentView; 9973eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (remoteViews == null) { 9983eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return false; 9993eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 10003eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 10013eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // create the row view 1002f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato LayoutInflater inflater = (LayoutInflater)mContext.getSystemService( 1003f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato Context.LAYOUT_INFLATER_SERVICE); 1004755cc74e4cebdf67d21a2477512a4ac9b01e8323Joe Onorato View row = inflater.inflate(R.layout.status_bar_notification_row, parent, false); 10054daaeafd278d22ec9013d1cdaade562044ee907eJoe Onorato workAroundBadLayerDrawableOpacity(row); 10060f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler View vetoButton = row.findViewById(R.id.veto); 1007a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato if (entry.notification.isClearable()) { 1008a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato final String _pkg = sbn.pkg; 1009a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato final String _tag = sbn.tag; 1010a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato final int _id = sbn.id; 101144c66fe2cd912fcea2e9824eb421d5c8d9ffadbdJim Miller vetoButton.setOnClickListener(new View.OnClickListener() { 1012a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato public void onClick(View v) { 1013a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato try { 1014a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato mBarService.onNotificationClear(_pkg, _tag, _id); 1015a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato } catch (RemoteException ex) { 1016a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato // system process is dead if we're here. 1017a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato } 10180f0b11c8719495ce559b93366fe9cd79782d791cDaniel Sandler } 1019a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato }); 1020a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato } else { 1021a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato vetoButton.setVisibility(View.INVISIBLE); 1022a4a6503d30ed21402847dbd25849ba2dc68a1369Joe Onorato } 10233eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 1024561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato // the large icon 1025561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato ImageView largeIcon = (ImageView)row.findViewById(R.id.large_icon); 1026561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato if (sbn.notification.largeIcon != null) { 1027561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato largeIcon.setImageBitmap(sbn.notification.largeIcon); 1028561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato } else { 1029561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato largeIcon.getLayoutParams().width = 0; 1030561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato largeIcon.setVisibility(View.INVISIBLE); 1031561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato } 1032561d3858bb9409b999a19f7ba93f0b12e1db835fJoe Onorato 10333eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // bind the click event to the content area 10343eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler ViewGroup content = (ViewGroup)row.findViewById(R.id.content); 10353eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler // XXX: update to allow controls within notification views 10363eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler content.setDescendantFocusability(ViewGroup.FOCUS_BLOCK_DESCENDANTS); 10373eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler// content.setOnFocusChangeListener(mFocusChangeListener); 10383eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler PendingIntent contentIntent = sbn.notification.contentIntent; 10393eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (contentIntent != null) { 10403eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler content.setOnClickListener(new NotificationClicker(contentIntent, 10413eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler sbn.pkg, sbn.tag, sbn.id)); 1042184498ce5a8d77e1d9c45693363829daaeef9611Joe Onorato } else { 1043184498ce5a8d77e1d9c45693363829daaeef9611Joe Onorato content.setOnClickListener(null); 10443eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 10453eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 10463eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler View expanded = null; 10473eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Exception exception = null; 10483eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler try { 1049f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato expanded = remoteViews.apply(mContext, content); 10503eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 10513eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler catch (RuntimeException e) { 10523eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler exception = e; 10533eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 10543eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler if (expanded == null) { 105546439cec0eb0da4d0f853f2d8712d0c00c98475bJoe Onorato final String ident = sbn.pkg + "/0x" + Integer.toHexString(sbn.id); 10563eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler Slog.e(TAG, "couldn't inflate view for notification " + ident, exception); 10573eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return false; 10583eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } else { 10593eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler content.addView(expanded); 10603eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler row.setDrawingCacheEnabled(true); 10613eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 10623eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 10633eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler entry.row = row; 10643eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler entry.content = content; 10653eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler entry.expanded = expanded; 10663eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler 10673eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler return true; 10683eebd1ffbf4583270e6926e9c74ff088a2113e07Daniel Sandler } 1069ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler 1070b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public class ShadowController { 1071b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler boolean mShowShadows; 1072b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler Map<View, View> mShadowsForElements = new IdentityHashMap<View, View>(7); 1073b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler Map<View, View> mElementsForShadows = new IdentityHashMap<View, View>(7); 1074b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler LayoutTransition mElementTransition, mShadowTransition; 1075b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1076b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler View mTouchTarget; 1077f63b0f44eb53f535a65bd83dbc1d8b95abc501daJoe Onorato 1078b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler ShadowController(boolean showShadows) { 1079b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mShowShadows = showShadows; 1080b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mTouchTarget = null; 1081b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1082b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementTransition = new LayoutTransition(); 1083b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// AnimatorSet s = new AnimatorSet(); 1084b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// s.play(ObjectAnimator.ofInt(null, "top", 48, 0)) 1085b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// .with(ObjectAnimator.ofFloat(null, "scaleY", 0.5f, 1f)) 1086b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// .with(ObjectAnimator.ofFloat(null, "alpha", 0.5f, 1f)) 1087b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// ; 1088b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementTransition.setAnimator(LayoutTransition.APPEARING, //s); 1089b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ObjectAnimator.ofInt(null, "top", 48, 0)); 1090b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementTransition.setDuration(LayoutTransition.APPEARING, 100); 1091b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementTransition.setStartDelay(LayoutTransition.APPEARING, 0); 1092b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1093b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// s = new AnimatorSet(); 1094b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// s.play(ObjectAnimator.ofInt(null, "top", 0, 48)) 1095b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// .with(ObjectAnimator.ofFloat(null, "scaleY", 1f, 0.5f)) 1096b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// .with(ObjectAnimator.ofFloat(null, "alpha", 1f, 0.5f)) 1097b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler// ; 1098b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementTransition.setAnimator(LayoutTransition.DISAPPEARING, //s); 1099b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ObjectAnimator.ofInt(null, "top", 0, 48)); 1100b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementTransition.setDuration(LayoutTransition.DISAPPEARING, 400); 1101b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1102b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowTransition = new LayoutTransition(); 1103b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowTransition.setAnimator(LayoutTransition.APPEARING, 1104b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ObjectAnimator.ofFloat(null, "alpha", 0f, 1f)); 1105b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowTransition.setDuration(LayoutTransition.APPEARING, 200); 1106b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowTransition.setStartDelay(LayoutTransition.APPEARING, 100); 1107b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowTransition.setAnimator(LayoutTransition.DISAPPEARING, 1108b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ObjectAnimator.ofFloat(null, "alpha", 1f, 0f)); 1109b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowTransition.setDuration(LayoutTransition.DISAPPEARING, 100); 1110b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1111b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ViewGroup bar = (ViewGroup) TabletStatusBar.this.mBarContents; 1112b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler bar.setLayoutTransition(mElementTransition); 1113b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ViewGroup nav = (ViewGroup) TabletStatusBar.this.mNavigationArea; 1114b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler nav.setLayoutTransition(mElementTransition); 1115b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler ViewGroup shadowGroup = (ViewGroup) bar.findViewById(R.id.shadows); 1116b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler shadowGroup.setLayoutTransition(mShadowTransition); 1117b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler } 1118b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1119b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler public void add(View element, View shadow) { 1120b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler shadow.setOnTouchListener(makeTouchListener()); 1121b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mShadowsForElements.put(element, shadow); 1122b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mElementsForShadows.put(shadow, element); 1123f63b0f44eb53f535a65bd83dbc1d8b95abc501daJoe Onorato } 1124f63b0f44eb53f535a65bd83dbc1d8b95abc501daJoe Onorato 1125b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public boolean getShadowState() { 1126b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler return mShowShadows; 1127f63b0f44eb53f535a65bd83dbc1d8b95abc501daJoe Onorato } 1128f63b0f44eb53f535a65bd83dbc1d8b95abc501daJoe Onorato 1129b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public View.OnTouchListener makeTouchListener() { 1130b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler return new View.OnTouchListener() { 1131b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public boolean onTouch(View v, MotionEvent ev) { 1132b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler final int action = ev.getAction(); 1133b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 1134b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (DEBUG) Slog.d(TAG, "ShadowController: v=" + v + ", ev=" + ev); 1135b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 1136b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler // currently redirecting events? 1137b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (mTouchTarget == null) { 1138b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler mTouchTarget = mElementsForShadows.get(v); 1139b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1140b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 1141b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (mTouchTarget != null && mTouchTarget.getVisibility() != View.GONE) { 1142b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler boolean last = false; 1143b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler switch (action) { 1144b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler case MotionEvent.ACTION_CANCEL: 1145b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler case MotionEvent.ACTION_UP: 1146e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler mHandler.removeMessages(MSG_RESTORE_SHADOWS); 1147b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (mShowShadows) { 1148e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler mHandler.sendEmptyMessageDelayed(MSG_RESTORE_SHADOWS, 1149b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler v == mNotificationShadow ? 5000 : 500); 1150b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1151b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler last = true; 1152b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler break; 1153b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler case MotionEvent.ACTION_DOWN: 1154e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler mHandler.removeMessages(MSG_RESTORE_SHADOWS); 1155b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler setElementShadow(mTouchTarget, false); 1156b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler break; 1157b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1158b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mTouchTarget.dispatchTouchEvent(ev); 1159b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (last) mTouchTarget = null; 1160b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler return true; 1161b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1162b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 1163b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler return false; 1164b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1165b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler }; 1166b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1167b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 1168e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler public void refresh() { 1169b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler for (View element : mShadowsForElements.keySet()) { 1170b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler setElementShadow(element, mShowShadows); 1171b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler } 1172e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler } 1173e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler 1174b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public void showAllShadows() { 1175b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mShowShadows = true; 1176e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler refresh(); 1177ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler } 1178ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler 1179b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler public void hideAllShadows() { 1180b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler mShowShadows = false; 1181e03d1bcfc42188e574a8e401154c77d5714eea41Daniel Sandler refresh(); 1182b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1183b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler 1184b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler // Use View.INVISIBLE for things hidden due to shadowing, and View.GONE for things that are 1185b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler // disabled (and should not be shadowed or re-shown) 1186b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler public void setElementShadow(View button, boolean shade) { 1187b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler View shadow = mShadowsForElements.get(button); 1188b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (shadow != null) { 1189b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler if (button.getVisibility() != View.GONE) { 1190b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler shadow.setVisibility(shade ? View.VISIBLE : View.INVISIBLE); 1191b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler button.setVisibility(shade ? View.INVISIBLE : View.VISIBLE); 1192b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1193b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1194b6d3dc68977eada24515a825c43eb01df9a4edb5Daniel Sandler } 1195b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1196b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // Hide both element and shadow, using default layout animations. 1197b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler public void hideElement(View button) { 1198b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler Slog.d(TAG, "hiding: " + button); 1199b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler View shadow = mShadowsForElements.get(button); 1200b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler if (shadow != null) { 1201b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler shadow.setVisibility(View.GONE); 1202b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler } 1203b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler button.setVisibility(View.GONE); 1204b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler } 1205b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler 1206b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler // Honoring the current shadow state. 1207b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler public void showElement(View button) { 1208b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler Slog.d(TAG, "showing: " + button); 1209b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler View shadow = mShadowsForElements.get(button); 1210b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler if (shadow != null) { 1211b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler shadow.setVisibility(mShowShadows ? View.VISIBLE : View.INVISIBLE); 1212b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler } 1213b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler button.setVisibility(mShowShadows ? View.INVISIBLE : View.VISIBLE); 1214b96069936c4e6d10c119efa9943fba818b09373eDaniel Sandler } 1215ce70d91844d2e4fb987617d2924ae5b73096e5c3Daniel Sandler } 1216b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato 1217b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato public class TouchOutsideListener implements View.OnTouchListener { 1218b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato private int mMsg; 1219ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato private StatusBarPanel mPanel; 1220b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato 1221ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato public TouchOutsideListener(int msg, StatusBarPanel panel) { 1222b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mMsg = msg; 1223ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato mPanel = panel; 1224b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato } 1225b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato 1226b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato public boolean onTouch(View v, MotionEvent ev) { 1227ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato final int action = ev.getAction(); 1228ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato if (action == MotionEvent.ACTION_OUTSIDE 1229ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato || (action == MotionEvent.ACTION_DOWN 1230ddf680bff5bb9bc04ef04667644db8ade0b38c46Joe Onorato && !mPanel.isInContentArea((int)ev.getX(), (int)ev.getY()))) { 1231b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mHandler.removeMessages(mMsg); 1232b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato mHandler.sendEmptyMessage(mMsg); 1233b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato return true; 1234b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato } 1235b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato return false; 1236b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato } 1237b62ac127824e9723534a197189eca58d30f15d3dJoe Onorato } 1238091e1b8a86d34d2d51d2a5f7ae3cd903925fa5bfJoe Onorato 1239f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato public void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 1240f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato pw.print("mDisabled=0x"); 1241f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato pw.println(Integer.toHexString(mDisabled)); 1242f3c3c4fd14cb4185ec6df5a4355aab8b9f4039dcJoe Onorato } 1243808182dc874e93582da38d013a4a790d6bc08fc9Joe Onorato} 1244d39e388e6d7f19d6e8d620e449af4124efab1d0dDaniel Sandler 1245d39e388e6d7f19d6e8d620e449af4124efab1d0dDaniel Sandler 1246